When combo box data selected, fill out textbox with data from Database - vb.net

I am working on an application and I have a question, I have a Combo box that is bound to a table in my databse, when data is selected in the combo box I would like 'textbox 1' and 'textbox2' to be automatically filled out with data from the table, is this possible? so say for instance when I select 'Richard' on the combo box, 'Richards' 'Address1' and 'Postcode' are filled out in text boxes. I have a sample code that does this but it only seems to work with Int32, see insterted below.
Public Class Form1
Private Sub cmdGetByIdentifier_Click(sender As Object, e As EventArgs) Handles cmdGetByIdentifier.Click
If Not String.IsNullOrWhiteSpace(txtIdentifier1.Text) Then
Dim Identifier As Int32 = 0
If Int32.TryParse(txtIdentifier1.Text, Identifier) Then
txtCompanyName1.Text = GetCustomerNameByIdentifier(Identifier)
Else
MessageBox.Show("'" & txtIdentifier1.Text & "' is not a valid integer.")
End If
Else
MessageBox.Show("Must enter an identifier to get a company name.")
End If
End Sub
Private Sub cmdGetCustomer_Click(sender As Object, e As EventArgs) Handles cmdGetCustomer.Click
If Not String.IsNullOrWhiteSpace(txtIdentifier2.Text) Then
Dim Identifier As Int32 = 0
If Int32.TryParse(txtIdentifier2.Text, Identifier) Then
Dim Cust As Customer = GetCustomer(Identifier)
txtCompanyName2.Text = Cust.Name
txtContactName2.Text = Cust.ContactName
Else
MessageBox.Show("'" & txtIdentifier1.Text & "' is not a valid integer.")
End If
Else
MessageBox.Show("Must enter an identifier to get a company name.")
End If
End Sub
End Class
Module DatabaseOperations
Public Function GetCustomerNameByIdentifier(ByVal Identifier As Int32) As String
Dim CompanyName As String = ""
Dim Builder As New OleDb.OleDbConnectionStringBuilder With {.Provider = "Microsoft.ACE.OLEDB.12.0", .DataSource = IO.Path.Combine(Application.StartupPath, "Database1.accdb")}
Using cn As New OleDb.OleDbConnection With {.ConnectionString = Builder.ConnectionString}
Using cmd As New OleDb.OleDbCommand With {.Connection = cn}
cmd.CommandText = "SELECT CompanyName FROM Customer WHERE Identifier =#P1"
Dim NameParameter As New OleDb.OleDbParameter With {.DbType = DbType.Int32, .ParameterName = "P1", .Value = Identifier}
cmd.Parameters.Add(NameParameter)
cn.Open()
CompanyName = CStr(cmd.ExecuteScalar)
End Using
End Using
Return CompanyName
End Function
Public Function GetCustomer(ByVal Identifier As Int32) As Customer
Dim Customer As New Customer
Dim CompanyName As String = ""
Dim Builder As New OleDb.OleDbConnectionStringBuilder With {.Provider = "Microsoft.ACE.OLEDB.12.0", .DataSource = IO.Path.Combine(Application.StartupPath, "Database1.accdb")}
Using cn As New OleDb.OleDbConnection With {.ConnectionString = Builder.ConnectionString}
Using cmd As New OleDb.OleDbCommand With {.Connection = cn}
cmd.CommandText = "SELECT Identifier, CompanyName,ContactName FROM Customer WHERE Identifier =#P1"
Dim NameParameter As New OleDb.OleDbParameter With {.DbType = DbType.Int32, .ParameterName = "P1", .Value = Identifier}
cmd.Parameters.Add(NameParameter)
cn.Open()
Dim Reader As OleDb.OleDbDataReader = cmd.ExecuteReader
If Reader.HasRows Then
Reader.Read()
Customer.Identifier = Identifier
Customer.Name = Reader.GetString(1)
Customer.ContactName = Reader.GetString(2)
End If
End Using
End Using
Return Customer
End Function
End Module
Public Class Customer
Public Property Identifier As Int32
Public Property Name As String
Public Property ContactName As String
Public Sub New()
End Sub
End Class

1.Refer Below Link To Fetch Data from Sql server
2.Create a Function Which Will Return your Data with ID as parameter
Dataadapter with dataset - sql sever

Not 100% sure about using Access but in theory what you would do is have a customer object
You would have a SQL Stored Procedure
Select * from Customers where id=#ID
...
Then a class
Public Class Customer
public property ID as Integer
Public property Name as string
public Property Surname as string
....
End Class
In your code where you access the data you would have something like
Public Function GetCustomerDetailsByID (byval CustomerID as Integer) As Customer ' Or whatever you want to return it as
Dim myCust as New Customer
' Code to access SQL
' Call your SQL procedure called GetCustByID(CustID)
With myCust
.Name = valueFromYourProcedure
End With
End Function
In your client app, you would then call the above, then assign the values to your controls i.e.
Dim SingleCustomer as Customer = GetCustomerDetailsByID(1) ' i.e. value form your dropdown
txtBoxName.Text = SingleCustomer.Name
Thats a very rough example and isnt fully complete but should give you some idea of how to go about this. Theres a lot of ways to do the above and everyone has their own way so you may need to do some extra research to be comfortable with it.
Hope this helps

Related

Issues on loop for retrieve the dynamic sql parameter values from dynamic textboxes

all. I am a new VB.NET beginner. I am facing the issue of how to pass the dynamic SQL parameter values from the dynamic textboxes to search the data. I had added control of dynamic textboxes and labels and would like to search the data on the database table based on the dynamic textboxes value inputted from the user. Currently, I can only able to search the data from 1 dynamic textbox value only.
I want all the values from the dynamic textboxes that the user had been entered can be retrieved, and search the data based on the SQL parameter variable name and value entered by the user.
Can someone give me some solutions on how to solve this problem? I had stuck on this problem for a few days. Thank you for all the help!
What I had tried:
Private Sub FilterData()
Dim count As Integer = 0
'filterdata for radiobutton
Try
For Each TextBox As TextBox In grp2.Controls.OfType(Of TextBox)()
For Each Label As Label In grp2.Controls.OfType(Of Label)()
Using connection As New SqlConnection("connectionString")
'user key in the SQL statement
sql = TextBox1.Text
Dim sql2 As String
sql2 = sql
Dim sp1 As String() = sql.Split(New String() {"where"}, StringSplitOptions.None)
sql = sp1(0) & " where " & Label.Text & " = #parameter or " & Label.Text & " =#parameter"
If (TextBox.Text <> "") Then
count += 1
For j As Integer = 0 To count - 1
Using cmd As New SqlCommand(sql, connection)
cmd.Parameters.AddWithValue("#parameter", TextBox.Text)
'cmd.Parameters.Add("#parameter", SqlDbType.NVarChar, 20).Value = TextBox.Text
connection.Open()
Dim dt As New DataTable()
Dim reader As SqlDataReader
reader = cmd.ExecuteReader()
dt.Load(reader)
DataGridView1.DataSource = dt
End Using
Next
Else
GetData()
End If
'cmd.Dispose()
connection.Close()
End Using
Next
Next
Catch ex As Exception
'MsgBox(ex.Message)
End Try
End Sub
Firstly, if you have a 1:1 correspondence between Labels and TextBoxes then you should not be using two nested For Each loops, because that is going to pair up each and every Label with each and every TextBox. What you should be doing is creating arrays and then using a single For loop to access the pairs of controls:
Dim labels = grp2.Controls.OfType(Of Label)().ToArray()
Dim textBoxes = grp2.Controls.OfType(Of TextBox)().ToArray()
For i = 0 To labels.getUpperBound(0)
Dim label = labels(i)
Dim textBox = textBoxes(i)
'...
Next
As for build the SQL and adding the parameters, I would tend to do it something like this:
Dim labels = grp2.Controls.OfType(Of Label)().ToArray()
Dim textBoxes = grp2.Controls.OfType(Of TextBox)().ToArray()
Dim criteria As New List(Of String)
Dim command As New SqlCommand
For i = 0 To labels.getUpperBound(0)
Dim label = labels(i)
Dim textBox = textBoxes(i)
Dim parameterName = "#" & label.Text.Replace(" ", "_")
criteria.Add($"[{label.Text}] = {parameterName}")
command.Parameters.AddWithValue(parameterName, textBox.Text)
Next
Dim sql = "SELECT * FROM MyTable"
If criteria.Any() Then
sql &= " WHERE " & String.Join(" OR ", criteria)
End If
command.CommandText = sql
I think that you should begin to separate UI and data logic here is an example of implementation:
First you have a table in database:
CREATE TABLE Customer (
Id INT IDENTITY (1, 1) PRIMARY KEY,
FirstName VARCHAR (255) NOT NULL,
LastName VARCHAR (255) NOT NULL,
Phone VARCHAR (25),
Email VARCHAR (255) NOT NULL,
Street VARCHAR (255),
City VARCHAR (50),
State VARCHAR (25),
ZipCode VARCHAR (5)
);
Then you create the underlying entity in VB. Net:
Public Class Customer
Public Property Id As Integer
Public Property FirstName As String
Public Property LastName As String
Public Property Phone As String
Public Property Email As String
Public Property Street As String
Public Property City As String
Public Property State As String
Public Property ZipCode As String
End Class
Data loader
Now you need a data access component that loads records to a list of this above entity here a nice implementation:
Imports System.Data.SqlClient
Public Class CustomerDataAccess
Public Property ConStr As String
Public Sub New(ByVal constr As String)
constr = constr
End Sub
Public Function GetCustomersByCriterias(constraints As Object) As List(Of Customer)
Dim query As String = "SELECT Id, FirstName, LastName, Phone, Email, Street, City, State, ZipCode
FROM [dbo].[Customer] "
Dim result = New List(Of Customer)()
Using con = New SqlConnection(ConStr)
Using cmd = con.CreateCommand()
cmd.CommandType = CommandType.Text
cmd.CommandText = query
'' here the magic to add dynamic criteria coming from constraints
cmd.ApplyConstraints(Of Customer)(constraints)
con.Open()
LoadCustomerData(cmd, result)
End Using
End Using
Return result
End Function
Private Sub LoadCustomerData(ByVal cmd As SqlCommand, ByVal result As List(Of Customer))
Using rdr = cmd.ExecuteReader()
Dim idIdx As Integer = rdr.GetOrdinal("Id")
Dim firstNameIdx As Integer = rdr.GetOrdinal("FirstName")
Dim lastNameIdx As Integer = rdr.GetOrdinal("LastName")
Dim phoneIdx As Integer = rdr.GetOrdinal("Phone")
Dim emailIdx As Integer = rdr.GetOrdinal("Email")
Dim streetIdx As Integer = rdr.GetOrdinal("Street")
Dim cityIdx As Integer = rdr.GetOrdinal("City")
Dim stateIdx As Integer = rdr.GetOrdinal("State")
Dim zipCodeIdx As Integer = rdr.GetOrdinal("ZipCode")
While rdr.Read()
Dim item = New Customer()
item.Id = rdr.GetValueOrDefault(Of Integer)(idIdx)
item.FirstName = rdr.GetValueOrDefault(Of String)(firstNameIdx)
item.LastName = rdr.GetValueOrDefault(Of String)(lastNameIdx)
item.Phone = rdr.GetValueOrDefault(Of String)(phoneIdx)
item.Email = rdr.GetValueOrDefault(Of String)(emailIdx)
item.Street = rdr.GetValueOrDefault(Of String)(streetIdx)
item.City = rdr.GetValueOrDefault(Of String)(cityIdx)
item.State = rdr.GetValueOrDefault(Of String)(stateIdx)
item.ZipCode = rdr.GetValueOrDefault(Of String)(zipCodeIdx)
result.Add(item)
End While
End Using
End Sub
End Class
Extensions methods
Below are extensions methods referenced above that do the magic you are looking for:
DataReader extensions to make it easy to read values from SalDataReader with Dbnull exfeptional case and casting
Module DataReaderExtenions
<Extension()>
Function GetValueOrDefault(Of T)(row As IDataRecord, fieldName As String) As T
Dim ordinal = row.GetOrdinal(fieldName)
Return row.GetValueOrDefault(Of T)(ordinal)
End Function
<Extension()>
Function GetValueOrDefault(Of T)(row As IDataRecord, ordinal As Integer) As T
Return (If(row.IsDBNull(ordinal), Nothing, row.GetValue(ordinal)))
End Function
<Extension()>
Function GetValueOrDefaultSqlite(Of T)(row As IDataRecord, fieldName As String) As T
Dim ordinal = row.GetOrdinal(fieldName)
Return row.GetValueOrDefault(Of T)(ordinal)
End Function
<Extension()>
Function GetValueOrDefaultSqlite(Of T)(row As IDataRecord, ordinal As Integer) As T
Return (If(row.IsDBNull(ordinal), Nothing, Convert.ChangeType(row.GetValue(ordinal), GetType(T))))
End Function
End Module
Command extensions that lets you extract criteria from an anonymous object values:
Imports System.Reflection
Imports System.Runtime.CompilerServices
Module CommandExtensions
<Extension()>
Function AddParameter(command As IDbCommand, name As String, value As Object) As IDataParameter
If command Is Nothing Then Throw New ArgumentNullException("command")
If name Is Nothing Then Throw New ArgumentNullException("name")
Dim p = command.CreateParameter()
p.ParameterName = name
p.Value = If(value, DBNull.Value)
command.Parameters.Add(p)
Return p
End Function
<Extension()>
Function ToDictionary(data As Object) As Dictionary(Of String, Object)
If TypeOf data Is String OrElse data.[GetType]().IsPrimitive Then Return New Dictionary(Of String, Object)()
Return (From [property] In data.[GetType]().GetProperties(BindingFlags.[Public] Or BindingFlags.Instance)
Where [property].CanRead
Select [property]).ToDictionary(Function([property]) [property].Name, Function([property]) [property].GetValue(data, Nothing))
End Function
<Extension()>
Sub ApplyConstraints(Of TEntity)(cmd As IDbCommand, constraints As Object)
If constraints Is Nothing Then Return
Dim dictionary = constraints.ToDictionary()
Dim whereClause = " WHERE "
For Each kvp In dictionary
Dim columnName = kvp.Key
Dim propertyName = kvp.Key
Dim prefix = "#"c
Dim value = kvp.Value
whereClause += $"{columnName} **like** {prefix}{propertyName} AND "
cmd.AddParameter(propertyName, value)
Next
If String.IsNullOrEmpty(whereClause) Then Return
cmd.CommandText += whereClause.Remove(whereClause.Length - 5, 5)
End Sub
End Module
Example:
After coded all these stuff now you can do the following:
Dim DataGridView1 As DataGridView = New DataGridView()
Dim ConStr As String = ConfigurationManager.ConnectionStrings("MyApp").ConnectionString
Dim dal As CustomerDataAccess = New CustomerDataAccess(ConStr)
Dim criterias = New With {.FirstName = "%James%", .LastName = "%Nadin%"}
DataGridView1.DataSource = dal.GetCustomersByCriterias(criterias)
Despite all this code you are still need to bind your textbox (after naming them correctly) to a SearchEntity and use this entity to provide criterias
I hope this material can help you tackle your issue and incite you to improve your architecture & dev skills

Defining Variables that are accessible page wide

Good morning guys,
I am working on vb.net. The aim is to make a CodeFile run some sql queries and then return the values to the webpage as an sqldatasource query parameter on page load.
I have the following vb code
Partial Class Consult
Inherits Page
Public totalCount As Integer = "0"
'*******Here i declare the variable***************
Public Property PatNo() As String
Get
Return ViewState("PatNo")
End Get
Set(ByVal value As String)
ViewState("PatNo") = value
End Set
End Property
Public PatNam As String = "abc"
Public ConID As String = "abc"
Public TreatType As String = "abc"
Public HPC As Char = "abc"
Public LvTyp As RadioButtonList
Protected Sub Page_Load(ByVal sender As Object, ByVal e As EventArgs) Handles Me.Load
Me.PatNo = Request.QueryString("pNo")
Session("PatientNo") = PatNo
Dim ConsultationID As String = Request.QueryString("consultID")
ConID = ConsultationID
Response.Write(PatNo)
Dim constr As String = ConfigurationManager.ConnectionStrings("DefaultConnection").ConnectionString
Using con As New SqlConnection(constr)
'**********BELOW LINE CAUSES ERROR**************
Dim query As String = "SELECT * FROM hPatients WHERE pNO=#PatNo"
query += "SELECT * FROM hPatients WHERE pNO='001/000034824'"
Using cmd As New SqlCommand(query)
cmd.Parameters.Add("#PatNo", SqlDbType.NVarChar).Value = PatNo
Using sda As New SqlDataAdapter()
cmd.Connection = con
sda.SelectCommand = cmd
Using ds As New DataSet()
sda.Fill(ds)
gvPatientInfo.DataSource = ds.Tables(0)
'Return ds.Tables(0).Rows(0).Item(2)
'Response.Write(ds.Tables(0).Rows(0).Item(2))
gvPatientInfo.DataBind()
gvClientInfo.DataSource = ds.Tables(1)
gvClientInfo.DataBind()
End Using
End Using
End Using
End Using
If Not Me.IsPostBack Then
'Dim di As DataInfo = Me.GetInfo()
'Populating a DataTable from database.
Dim dt As DataTable = Me.GetData()
'Response.Write(ConID + " " + PatNo)
'Building an HTML string.
Dim html As New StringBuilder()
'Table start.
html.Append("<table border = '1' class = 'table'>")
'Building the Header row.
html.Append("<tr>")
For Each column As DataColumn In dt.Columns
html.Append("<th>")
html.Append(column.ColumnName)
html.Append("</th>")
Next
html.Append("</tr>")
'Building the Data rows.
For Each row As DataRow In dt.Rows
html.Append("<tr>")
For Each column As DataColumn In dt.Columns
html.Append("<td>")
html.Append(row(column.ColumnName))
html.Append("</td>")
Next
html.Append("</tr>")
Next
'Table end.
html.Append("</table>")
'Append the HTML string to Placeholder.
PlaceHolder1.Controls.Add(New Literal() With { _
.Text = html.ToString() _
})
End If
End Sub
The error i get is
Must declare the scalar variable "#PatNo".
The error occurs in the first step of getting the variable to execute the query in the page_load function.
The second step would be to get the result of the query and use on the webpage.
Somebody, Anybody, Please HELP!!!.
I think the problem is with this line:
cmd.Parameters.Add("PatNo", SqlDbType.NVarChar).Value = PatNo
Change the name from "PatNo" to "#PatNo" and it should work.

Failed to convert parameter value from a List`1 to a String

I am getting the error message:
"Failed to convert parameter value from a List`1 to a String"
and I am not sure how to correct the issue. It happens when I attempt to save a cleaningList to a Cleaner object in a database.
I am very new to visual basic and appreciate any feedback to help make this program work.
Public Class FrmMain
Dim currentRoom As String
Dim lastId As Integer
Dim cleaners As New BindingList(Of Cleaner)
'new instance of cleaner and storing it in a reference variable
Dim currentCleaner As New Cleaner()
'-------------Functions----------------
Private Function connectWithDb() As SqlConnection
'create a connection string
Dim connectionString As String = "Server=(LocalDB)\MSSQLLocalDB;Integrated Security=true;AttachDbFileName=C:\Users\Julia\Desktop\JklimeckFinalProject\JklimeckFinalProject\cleanerLists.mdf;"
'create connection object and tell it how to connect using connectionString
Dim dbConnection As New SqlConnection(connectionString)
'open the connection
dbConnection.Open()
'return the connection
Return dbConnection
End Function
'function to change the list to a string seperated by commas
Public Function changeToString() As String
'turn the list of strings into a single string for the database
'trim the leading white space so it won't show up when the list is
'converted back later
currentCleaner.CleaningList = LTrim(String.Join(",", currentCleaner.ItemList.ToArray()))
Return currentCleaner.CleaningList
End Function
'public function to get index of items that are selected
Public Function GetAllItems(index As Integer) As CheckState
End Function
'function to generate a cleaning list
Public Function getCleanList() As List(Of String)
'if statement to display tasks in lbxTasks
Dim indexChecked As Integer
'variable to hold the tasks that are listed depending on the room
'selected ' for current cleaner
Dim itemList As New List(Of String)
'determine the room and create the list of tasks depending on the checked boxes
If currentRoom = "Living Room" Then
itemList.AddRange(currentCleaner.LivRoomTasks)
ElseIf currentRoom = "Kitchen" Then
itemList.AddRange(currentCleaner.KitchenTasks)
ElseIf currentRoom = "Bathroom" Then
itemList.AddRange(currentCleaner.BathroomTasks)
ElseIf currentRoom = "Bedroom" Then
itemList.AddRange(currentCleaner.BedroomTasks)
ElseIf currentRoom = "Dining Room" Then
itemList.AddRange(currentCleaner.DinRoomTasks)
ElseIf currentRoom = "Office" Then
itemList.AddRange(currentCleaner.OfficeTasks)
ElseIf currentRoom = "Laundry Room" Then
itemList.AddRange(currentCleaner.LauRoomTasks)
ElseIf currentRoom = "General" Then
itemList.AddRange(currentCleaner.GeneralTasks)
End If
For Each indexChecked In cbxRoomItems.CheckedIndices
lbxTasks.Items.Add(itemList.Item(indexChecked).ToString)
Next
Return itemList
End Function
'function to seperated the string version of the list
Public Function changeToList() As List(Of String)
'change the comma separated sting back to a list by spliting it at the commas
lbxTasks.Items.AddRange(currentCleaner.CleaningList.Split(New Char() {","c}))
Return currentCleaner.ItemList
End Function
Private Sub FrmMain_Load(sender As Object, e As EventArgs) Handles Me.Load
'when the application loads, show list of cleaners and display by name
lbxNames.DataSource = cleaners
lbxNames.DisplayMember = "Name"
Dim dbConnection As SqlConnection = connectWithDb()
'string of sql
Dim sqlString As String = "SELECT * FROM Cleaner"
'command object pass in what to run and the object
Dim selectCommand As New SqlCommand(sqlString, dbConnection)
'place in a try catch block to keep exceptions from crashing application
Try
'variable to hold the sqlDataReader object
Dim reader As SqlDataReader = selectCommand.ExecuteReader()
If reader.HasRows Then
'read is boolean
While reader.Read
'call the sub
populateCleaners(reader)
End While
End If
reader.Close()
'determine the highest ID number in the database
'and store it in a class level variable so we can access it
'where ever it is needed
Dim identSql As String = "SELECT IDENT_CURRENT('Cleaner') as lastID"
Dim identCom As New SqlCommand(identSql, dbConnection)
Dim identReader As SqlDataReader = identCom.ExecuteReader
If identReader.HasRows Then
identReader.Read()
lastId = CInt(identReader.Item("lastId"))
End If
Catch ex As Exception
End Try
'close and dispose the connection to the db
dbConnection.Close()
dbConnection.Dispose()
End Sub
'Sub to populate the database with a new character
Private Sub populateCleaners(reader As SqlDataReader)
Dim dbCleaner As New Cleaner()
changeToString()
'get info from reader and store into new object
dbCleaner.Id = CInt(reader.Item("Id"))
dbCleaner.Name = reader.Item("Name").ToString
dbCleaner.CleaningList = reader.Item("CleaningList").ToString
'add to binding list
cleaners.Add(dbCleaner)
End Sub
'----------------Butttons------------------
'add to list button
Private Sub btnClean_Click(sender As Object, e As EventArgs) Handles btnClean.Click
'label to show the correct list is being displayed
lblCurrentCleaner.Text = currentCleaner.Name
getCleanList()
End Sub
'save cleaning list
Private Sub btnSave_Click(sender As Object, e As EventArgs) Handles btnSave.Click
Dim newCleaner As New Cleaner()
'referencing object and assigning it to the Name property for the new cleaner
newCleaner.Name = txtName.Text
'exception if the user does not enter a name
Try
newCleaner.Name = txtName.Text
Catch ex As Exception
MessageBox.Show("a cleaner has no name")
End Try
For ctr = 0 To lbxTasks.Items.Count - 1
newCleaner.ItemList.Add(lbxTasks.Items(ctr).ToString)
'change this list to a string
changeToString()
Next
newCleaner.CleaningList = changeToString()
lbxTasks.Items.Clear()
cleaners.Add(newCleaner)
currentCleaner = newCleaner
'update a cleaning list if the Id is already in the database, or create a new object
Dim dbConnection As SqlConnection = connectWithDb()
Dim sqlString As String
If currentCleaner.Id > 0 Then
sqlString = "UPDATE Cleaner SET Name = #name, CleaningList = #cleaningList WHERE Id = #id"
Else
sqlString = "INSERT INTO Cleaner (Name, CleaningList) VALUES(#name, #cleaningList)"
'increment the last Id and save that id number to the new entry in the db
lastId += 1
currentCleaner.Id = lastId
End If
Dim com As New SqlCommand(sqlString, dbConnection)
'set the values of current cleaner in the database
com.Parameters.Add("#id", SqlDbType.Int).Value = currentCleaner.Id
com.Parameters.Add("#name", SqlDbType.VarChar).Value = currentCleaner.Name
com.Parameters.Add("#cleaningList", SqlDbType.NVarChar).Value = currentCleaner.ItemList
Try
Dim result = com.ExecuteNonQuery()
MessageBox.Show(result.ToString)
Catch ex As Exception
MessageBox.Show(ex.Message)
End Try
End Sub
I have a Cleaner class that stores the public properties.
In the program the user clicks on different buttons that populate a checklistbox with different items found in that room, by selecting the items and clicking btnClean it populates a listbox with a list of tasks associated with the items the user selected. My problem seems to be centered around that list; it is stored in a list(of String), but I made a function to turn that list into a single string separated by commas so it can be stored in a database and another function to separated that list so it can be displayed back in the listbox when the user's name is selected.
I am not sure where it is I am going wrong.
The exception is being thrown in:
'save cleaning list
Private Sub btnSave_Click(sender As Object, e As EventArgs) Handles btnSave.Click
Dim newCleaner As New Cleaner()
'referencing object and assigning it to the Name property for the new cleaner
newCleaner.Name = txtName.Text
'exception if the user does not enter a name
Try
newCleaner.Name = txtName.Text
Catch ex As Exception
MessageBox.Show("a cleaner has no name")
End Try
For ctr = 0 To lbxTasks.Items.Count - 1
newCleaner.ItemList.Add(lbxTasks.Items(ctr).ToString)
'change this list to a string
changeToString()
Next
lbxTasks.Items.Clear()
cleaners.Add(newCleaner)
currentCleaner = newCleaner
'update a cleaning list if the Id is already in the database, or create a new object
Dim dbConnection As SqlConnection = connectWithDb()
Dim sqlString As String
If currentCleaner.Id > 0 Then
sqlString = "UPDATE Cleaner SET Name = #name, CleaningList = #cleaningList WHERE Id = #id"
Else
sqlString = "INSERT INTO Cleaner (Name, CleaningList) VALUES(#name, #cleaningList)"
'increment the last Id and save that id number to the new entry in the db
lastId += 1
currentCleaner.Id = lastId
End If
Dim com As New SqlCommand(sqlString, dbConnection)
com.Parameters.Add("#name", SqlDbType.VarChar).Value = currentCleaner.Name
com.Parameters.Add("#cleaningList", SqlDbType.NVarChar).Value = currentCleaner.ItemList
Try
Dim result = com.ExecuteNonQuery()
MessageBox.Show(result.ToString)
Catch ex As Exception
MessageBox.Show(ex.Message)
End Try
End Sub
Again thank you for any suggestions/help!

How to Combine Multiple VB Functions / SQL Lookups into one vb.net function

I have two functions that check the same table, one right after the other. This setup seems inefficient. Is there a way to combine these?
getCustomerName(customerID)
getCustomerEmail(customerID)
'GET CUSTOMER NAME
Public Shared function getCustomerName(myArg) as String
Dim objConnection As New SqlConnection(System.Configuration.ConfigurationSettings.AppSettings("connectionString"))
Dim finalCustomerName as string
objConnection.Open()
Dim objCommand As New SqlCommand("SELECT customerName FROM customers WHERE customerID = '" + MyArg + "'", objConnection)
Dim objDataReader as SqlDataReader = objCommand.ExecuteReader(CommandBehavior.CloseConnection)
While objDataReader.Read()
finalCustomerName = objDataReader("customerName")
End While
objConnection.Close()
Return finalCustomerName
End function
'GET CUSTOMER EMAIL
Public Shared function getCustomerEmail(myArg) as String
Dim objConnection As New SqlConnection(System.Configuration.ConfigurationSettings.AppSettings("connectionString"))
Dim finalCustomerEmail as string
objConnection.Open()
Dim objCommand As New SqlCommand("SELECT customerEmail FROM customers WHERE customerID = '" + MyArg + "'", objConnection)
Dim objDataReader as SqlDataReader = objCommand.ExecuteReader(CommandBehavior.CloseConnection)
While objDataReader.Read()
finalCustomerEmail = objDataReader("customerEmail")
End While
objConnection.Close()
Return finalCustomerEmail
End function
Try this
New Customer class (you can add more properties that are related to customer and return them from function below):
Public Class Customer
Public Property CustomerName() As String
Get
Return m_CustomerName
End Get
Set
m_CustomerName = Value
End Set
End Property
Private m_CustomerName As String
Public Property CustomerEmail() As String
Get
Return m_CustomerEmail
End Get
Set
m_CustomerEmail = Value
End Set
End Property
Private m_CustomerEmail As String
End Class
And your function should be
// your function to get customer details
Public function getCustomer(myArg) as Customer
Dim custobj as New Customer()
Dim objCommand As New SqlCommand("SELECT customerEmail,CustomerName FROM customers WHERE customerID = #custid", objConnection)
objCommand.Parameters.AddWithValue("#custid",myArg) //use parameters to avoid sql injections
Dim objDataReader as SqlDataReader = objCommand.ExecuteReader(CommandBehavior.CloseConnection)
While objDataReader.Read()
custobj.CustomerName = objDataReader("customerName")
custobj.CustomerEmail = objDataReader("customerEmail")
End While
objDataReader.Close()
objConnection.Close()
Return custObj
End function

add a value to a dropdownlist populated from database in vb.net

this is my code -
SqlCmd = New SqlCommand("sp_load_names", SqlCnn)
SqlCmd.CommandType = CommandType.StoredProcedure
SqlDR = SqlCmd.ExecuteReader()
While SqlDR.Read
ads_list.Items.Add(New ListItem(SqlDR(1) & ""))
End While
SqlDR.Close()
this shall populate the dropdownlist data, but in the value i need it to pick up the "ID" field from the stored proc.
the stored proc sends two parameters, ID and Name. so i populate name, but how do i populate the id in value like this -
Mark
Sam
Dennis
i hope im not confusing anyone
One of the ListItem constructor overloads sets both the text and value properties:
New ListItem("Text", "Value")
You should be able to access both columns in the SQL data reader using SqlDR(1) and SqlDR(2).
ListItems are objects, so you can create your own simple ListItem class to contain both the ID and Display Value
Class MyListItem
Public ID As Integer
Public Text As String
Public Sub New(iID As Integer, sText As String)
Me.ID = iID
Me.Text = sText
End Sub
Public Overrides Function ToString() As String
Return Me.Text
End Sub
End Class
...
Dim oItem As MyListItem
While SqlDR.Read
oItem = new MyListItem(SqlDR(0),SqlDR(1))
ads_list.Items.Add(oItem)
End While
...
oItem = CType(ads_list.SelectedItem,MyListItem)
SqlCmd = New SqlCommand("sp_load_names", SqlCnn)
SqlCmd.CommandType = CommandType.StoredProcedure
SqlDR = SqlCmd.ExecuteReader()
While SqlDR.Read
ads_list.Items.Add(SqlDR(1).ToString)
End While
SqlDR.Close()