Results 1 to 4 of 4

Thread: Update Database from DataGridView

  1. #1

    Thread Starter
    Hyperactive Member Jonny1409's Avatar
    Join Date
    Mar 2005
    Posts
    308

    Update Database from DataGridView

    Hello,

    I wonder if someone can help me please?

    I currently have a form which is reading Names from a DB into a DatagridView.
    Once a user selects one of the names, another DataGridView is populated with entries belonging to the chosen name. (Each Name can have 0-5 entries)

    I then want to make changes to the data in this 2nd DataGridView and update this to the DB.

    It all should be straightforward, but it's not working so I'm assuming I'm doing it wrong. (I have done very little with ADO etc so I'm more than likely missing something)

    Anyway - my code to populate the 2nd DataGridView is here:

    Code:
    Private Sub PopulateDataGridView(GUID)
            Dim DataAdapter As New SqlDataAdapter("SELECT FIELD_A FROM TABLE_A WHERE GUID = '" & GUID & "'", connectionString)
            Dim DataSet As New DataSet
            Dim commandBuilder As New SqlCommandBuilder(DataAdapter)
    
            Try
                DataAdapter.Fill(DataSet, "ds")
                dgv1.DataSource = DataSet.Tables("ds")
    			
            Catch ex As Exception
                MessageBox.Show(ex.Message)
            End Try
    End Sub
    As you can see, when this sub is called, the person's GUID is passed in and the dataset is filled with the relevant rows.
    This works fine and populates the DataGridView fine with 0-5 rows.

    Assuming I amend one of the rows in the DataGridView or Add / Remove a row, I would like to just press my 'Update' button which would then write the new entries back to the DB.

    This is the part I'm having trouble with.
    How would I do this?

    Thank you in advance.

  2. #2
    Super Moderator jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    111,222

    Re: Update Database from DataGridView

    Would it be practical to retrieve all the child data upfront, at the same time as you retrieve the parent data? It would simply things somewhat because you can simply let the data-binding filter the data automatically so you don't have to do anything when the user selects a parent record?

    If that's not practical then you can still do the binding once and once only and then simply fill an existing DataTable when the selection changes. It should be just three lines of code: clear the current data, set the parameter value and retrieve the new data.
    Why is my data not saved to my database? | MSDN Data Walkthroughs
    VBForums Database Development FAQ
    My CodeBank Submissions: VB | C#
    My Blog: Data Among Multiple Forms (3 parts)
    Beginner Tutorials: VB | C# | SQL

  3. #3

    Thread Starter
    Hyperactive Member Jonny1409's Avatar
    Join Date
    Mar 2005
    Posts
    308

    Re: Update Database from DataGridView

    Hi jmcilhinney, it wouldn't unfortunately because each person's child data is different.

    So the table would have something like the following:

    Name - Role
    Joe - 1
    Joe - 2
    Joe - 3
    Jim - 1
    Bob - 1
    Paul - 2
    Paul - 3
    Peter - 0
    Peter - 1

    This said, how would I go about setting up the binding as per your 2nd paragraph?

  4. #4
    Super Moderator jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    111,222

    Re: Update Database from DataGridView

    The fact that each parent's child data is different is not a problem and in fact is to be expected. As I said, you can set up the binding so that the filtering occurs automatically. That way, you just bind the child table to the child grid and then its contents is filtered such that you only see those records that are related to the selected parent. If you want to see how that's done, follow the CodeBank link in my signature below and check out my thread on Master/Detail Data-binding.

    The issue to consider is how much child data there is in total. If you want to do it the way I have in that CodeBank thread then you have to retrieve all the child data in a single batch upfront. If there's a lot then that will slow the initial loading of the form. If only a small subset of that data will be used then it's also wasteful. In that case, it's worth retrieving only the child data that you need as you need it. Even then though, you should still use a filter on the child data so that you can keep the data you have already retrieved and use it again later if required. Here's an example of what you might do:
    vb.net Code:
    1. Imports System.Data.SqlClient
    2.  
    3. Public Class Form1
    4.  
    5.     Private data As New DataSet
    6.     Private connection As New SqlConnection("connection string here")
    7.     Private parentAdapter As New SqlDataAdapter("SELECT * FROM Parent", connection)
    8.     Private childAdapter As New SqlDataAdapter("SELECT * FROM Child WHERE ParentGuid = @ParentGuid", connection)
    9.     Private parentBuilder As New SqlCommandBuilder(Me.parentAdapter)
    10.     Private childBuilder As New SqlCommandBuilder(Me.childAdapter)
    11.  
    12.     Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    13.         Me.childAdapter.SelectCommand.Parameters.Add("@ParentGuid", SqlDbType.UniqueIdentifier).Value = DBNull.Value
    14.  
    15.         Me.connection.Open()
    16.  
    17.         'Get the parent data.
    18.         Me.parentAdapter.Fill(Me.data, "Parent")
    19.  
    20.         'Build the child schema but this will retrieve no data because the parameter is NULL.
    21.         Me.childAdapter.Fill(Me.data, "Child")
    22.  
    23.         Me.connection.Close()
    24.  
    25.         Me.childBindingSource.DataSource = Me.data.Tables("Child")
    26.         Me.childDataGridView.DataSource = Me.childBindingSource
    27.  
    28.         Me.parentBindingSource.DataSource = Me.data.Tables("Parent")
    29.         Me.parentDataGridView.DataSource = Me.parentBindingSource
    30.     End Sub
    31.  
    32.     Private Sub parentBindingSource_CurrentChanged(sender As Object, e As EventArgs) Handles parentBindingSource.CurrentChanged
    33.         'A new parent row has been selected.
    34.         Dim parentRow = DirectCast(Me.parentBindingSource.Current, DataRowView)
    35.         Dim parentGuid = DirectCast(parentRow("Guid"), Guid)
    36.  
    37.         Dim filter = String.Format("ParentGuid = '{0}'", parentGuid)
    38.         Dim childCount = CInt(Me.data.Tables("Child").Compute("COUNT(ParentGuid)", filter))
    39.  
    40.         If childCount = 0 Then
    41.             'The child data has not yet been retrieved for the current parent.
    42.             Me.childAdapter.SelectCommand.Parameters("@ParentGuid").Value = parentGuid
    43.             Me.childAdapter.Fill(Me.data, "Child")
    44.         End If
    45.  
    46.         'Filter the child data to exclude all but that for the current parent.
    47.         Me.childBindingSource.Filter = filter
    48.     End Sub
    49.  
    50. End Class
    That code is untested so it may not be perfect but hopefully it clearly illustrates the principles.
    Why is my data not saved to my database? | MSDN Data Walkthroughs
    VBForums Database Development FAQ
    My CodeBank Submissions: VB | C#
    My Blog: Data Among Multiple Forms (3 parts)
    Beginner Tutorials: VB | C# | SQL

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width