title: asp.net vb website loop through database rows
body: <p>I am working on my first website and need help with a loop. I have a database table containing food items named Menu with 8 categories (such as Burgers, Appetizers). I also have a menu page on website with 8 different pics to display items from each category. I need to loop through rows of database. What is happening is it's only looping through columns and repeating first line over and over. I'm aware I need a loop but for some reason cannot get that right. </p>
  
  <p>This is code behind:</p>
  
  <pre><code>Partial Class Burger
      Inherits System.Web.UI.Page
  
      'String Used to build the necessary markup and product information
      Dim str As String = ""
      'Var used to interact with SQL database
      Dim db As New Interaction
  
      'Adds the necessary markup for each menu item, using its productName
      Protected Sub printMenuBlock(ByVal productName As String)
          'Set up variable storing the product
          Dim product As Product
          'Pull the product in from our database using the productName
          product = db.ReadProduct(productName)
          'Add necessary markup to str variable, with products information within
          str += "&lt;div class='storeItem'&gt;"
          ' str += "    &lt;img alt='Item Picture' class='itemPicture' src='" + product.ImagePath.Substring(3).Replace("\", "/") + "' /&gt;"
          ' str += "    &lt;div class='itemInfo'&gt;"
          str += "        &lt;h1 class='itemName'&gt;"
          str += "            " + product.Name + "&lt;/h1&gt;"
          str += "        &lt;h3 class='itemDescription'&gt;"
          str += "            " + product.Description + "&lt;/h3&gt;"
          str += "        &lt;p class='itemPrice'&gt;"
          str += "            " + product.Price.ToString("c") + "&lt;/p&gt;"
          str += "        "
          str += "        &lt;/div&gt;"
          str += "    &lt;/div&gt;"
      End Sub
  
      'Uses
      Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
          Dim productNames As New List(Of String)
          'Pull the product names using the database
          productNames = db.getProductNames
          'Loop through all product names
          For Each name As String In productNames
  
              'Add necessary markup and product info to str variable
              printMenuBlock(name)
          Next
          'Print the str variable in our menuPlace div
          menuPlace.InnerHtml = str
      End Sub
  End Class
  </code></pre>
  
  <p>This is functions from interaction class:</p>
  
  <pre><code>Private Sub GetProduct(ByVal CatIn As String)
      ' SQL String
      Dim strSelect As String
      strSelect = "SELECT * "
      strSelect &amp;= " FROM Menu "
      ' strSelect &amp;= " WHERE (ProductCat = 'Burgers')"
      ' Set up the connection to the datebase
      cmdSelect.Connection = conIn.Connect
      ' Add the SQL string to the connection
      cmdSelect.CommandText = strSelect
      ' Add the parameters to the connection
      cmdSelect.Parameters.Add("@CatIn", SqlDbType.NVarChar).Value = CatIn
  End Sub
  
  'Executes the SQL statement to find a Product by ProductId
  Public Function ReadProduct(ByVal CatIn As String) As Product
      ' Product object initalized to nothing
      Dim prod As Product = Nothing
      Try
          Call GetProduct(CatIn)
          Dim dbr As SqlDataReader
          Dim strCat As String
          Dim strName As String
          Dim strDesc As String
          Dim decPrice As Decimal
          Dim strPath As String
  
          ' Execute the created SQL command from GetProduct and set to the SqlDataReader object
          dbr = cmdSelect.ExecuteReader
          dbr.Read()
          ' Check if there are any returned values
          If dbr.HasRows Then
  
              ' Assign the value in column two to strName
              strCat = dbr.GetString(1)
  
              ' Assign the value in column two to strName
              strName = dbr.GetString(2)
              ' Assign the value in column three to strDesc
              strDesc = dbr.GetString(3)
              ' Assing the value in column four to intPrice
              decPrice = ToDecimal(dbr.GetValue(4))
              'Assign the value in column five to strPath
              'strPath = dbr.GetString(3)
              ' Create the new Product object from the returned values
              prod = New Product(strName, strDesc, decPrice, strCat, strPath)
          End If
          ' Clear the SQL parameters and close the connection
          cmdSelect.Parameters.Clear()
          dbr.Close()
      Catch ex As SqlException
          Dim strOut As String
          strOut = ex.Message
          Console.WriteLine(strOut)
      End Try
      ' Return the Product object
      Return prod
  End Function
  'Returns a list of Product Names
  Public Function getProductNames() As List(Of String)
      Dim list As New List(Of String)
  
      Dim sql As String = "SELECT  ProductName FROM Menu " +
     "WHERE (ProductCat) = 'Burgers'"
      '"DISTINCT 'ProductName'"
      cmdSelect.CommandText = sql
      cmdSelect.Connection = conIn.Connect
      Dim dbr As SqlDataReader
  
      dbr = cmdSelect.ExecuteReader
  
  
  
  
      If dbr.HasRows Then
          Do While dbr.Read()
              list.Add(dbr.GetString(0))
          Loop
      End If
  
  
  
  
  
      dbr.Close()
      Return list
  End Function
  </code></pre>
  
  <p>There is obviously a Product Class but don't think that is necessary to show on here. 
  Also, ignore the string path, that will be for images later. Thanks for any help. I'm pretty sure instead of do while I need a for each somewhere but just can't get her done. Thanks in advance. </p>
  
  <p>Products Class:</p>
  
  <pre><code>Public Class Product
  
      Private pName As String
      Private pDescription As String
      Private pPrice As Integer
      Private pPath As String
      Private pCat As String
  
      'Constructor, uses database to populate properties based on productName
      Public Sub New(ByVal productName As String)
          Dim data As New Interaction
          Dim work As Product
          work = data.ReadProduct(productName)
          pCat = work.Cat
          pName = work.Name
          pDescription = work.Description
          pPrice = work.Price
  
      End Sub
  
      'Constructor, populates properties from passed in values
      Public Sub New(ByVal NameIn As String,
                     ByVal DescriptionIn As String, ByVal PriceIn As Integer, ByVal CatIn As String, ByVal ImagePathIn As String)
  
          pName = NameIn
          pDescription = DescriptionIn
          pPrice = PriceIn
          pPath = ImagePathIn
          pCat = CatIn
      End Sub
  
  
      'Stores name of product
      Public ReadOnly Property Name() As String
          Get
              Return pName
          End Get
      End Property
      'Stores a description of the product
      Public ReadOnly Property Description() As String
          Get
              Return pDescription
          End Get
      End Property
      'Stores the price of the product
      Public ReadOnly Property Price() As Integer
          Get
              Return pPrice
          End Get
      End Property
      'Stores the path to the image associated with this product
      Public ReadOnly Property ImagePath() As String
          Get
              Return pPath
          End Get
      End Property
  
      'Stores name of product
      Public ReadOnly Property Cat() As String
          Get
              Return pCat
          End Get
      End Property
  
  End Class
  </code></pre>