简体   繁体   中英

SQLDataAdapter.Update() not Updating when RowState = Modified

I am trying to set up a program that, when a user updates an item description, will update the database upon the save of the form. I have set up everything I have found that is required and yet the adapter never updates. It selects and inserts great but never update. Code as follows:

  internal void UpdateDB(DataTable Items)
    {
      using ( var ItemsAdapter = new SqlDataAdapter("select * from dbo.Items", Properties.Settings.Default.ConnectionString) )
      using ( var ItemsCB = new SqlCommandBuilder(ItemsAdapter) )
      {
        ItemsAdapter.UpdateCommand = ItemsCB.GetUpdateCommand(true);
        ItemsAdapter.InsertCommand = ItemsCB.GetInsertCommand(true);
        ItemsAdapter.DeleteCommand = ItemsCB.GetDeleteCommand(true);

        ItemsAdapter.AcceptChangesDuringUpdate = true;
        foreach ( DataRow Row in Items.AsEnumerable() )
        {
          if ( !_Items.TableContains("Item", Row["Item"]) )
          { Row.AcceptChanges(); Row.SetAdded(); }
          else if ( _Items.TableContains("Item", Row["Item"]) )
          { Row.AcceptChanges(); Row.SetModified(); }
        }
        ItemsAdapter.Update(Items);

        _LoadAll();
      }
    }

The .TableContains() extension is a home brew extension I built to check against the table to see if a value exists. It is running perfect and sets rows where the PK exists already to modified and rows where the PK does not exist to Added.

public static bool TableContains(this DataTable DT, string ColumnName, object ItemtoCheck)
{
  return DT.AsEnumerable()
           .Select(r => r.Field<string>(ColumnName))
           .ToList()
           .FindIndex(x => x.Equals(ItemtoCheck.ToString(), StringComparison.OrdinalIgnoreCase)) != -1;
}

The _LoadAll(); method is just a method to reload all the DataTables after the changes have been made to the database.

I figured out what I was doing wrong. I was using a table that had a null reference as its original row value and when the SQLDataAdapter.Update() ran it was looking for a row with a null value which did not exist and therefore was ignored. To fix this I changed my "Item" table logic as follows:

    ItemsAdapter.AcceptChangesDuringUpdate = true;
    foreach ( DataRow Row in Items.AsEnumerable() )
    {
      if ( !_Items.TableContains("Item", Row["Item"]) )
      { ItemsTable.Rows.Add(Row); }
      else if ( _Items.TableContains("Item", Row["Item"]) )
      {
        ItemsTable.AsEnumerable()
                  .Join(Items.AsEnumerable(), r1 => r1.ItemArray[0], r2 => r2.ItemArray[0], (r1, r2) => new { r1, r2 })
                  .ToList()
                  .ForEach(i => i.r1.SetField(1, i.r2.ItemArray[1]));
      }
    }
    ItemsAdapter.Update(ItemsTable);

This change set the new table passed to the update method to update my internal DataTable that had the database values in it to the new update and then used that to update the database and it worked properly.

Hope this may help anyone who may end up with the same issue I had.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM