VB.NET WinForms中如何刷新DbContext数据?
Hey Pascal, let's walk through how to nail both of these requirements—fetching fresh database data when selecting a new row in your DataGridView, and refining your entity update workflow. Here's a step-by-step breakdown tailored to your scenario:
The key here is to avoid relying on the cached entity bound to the grid, and instead pull the latest state directly from the database using a new DbContext. Here's how to implement it:
Hook up the SelectionChanged event for your DataGridView. You can do this either in the designer or in your form's constructor:
public YourForm() { InitializeComponent(); dataGridView1.SelectionChanged += DataGridView1_SelectionChanged; }Implement the event handler to fetch fresh data:
private void DataGridView1_SelectionChanged(object sender, EventArgs e) { // Exit if no row is selected if (dataGridView1.SelectedRows.Count == 0) return; // Get the bound entity from the selected row (replace YourEntity with your actual entity type) var selectedCachedEntity = dataGridView1.SelectedRows[0].DataBoundItem as YourEntity; if (selectedCachedEntity == null) return; // Use a new DbContext to avoid cached data using (var freshContext = new YourDbContext()) { // Fetch the latest version using the entity's primary key var freshEntity = freshContext.YourEntities.Find(selectedCachedEntity.Id); if (freshEntity != null) { // Populate your detail UI controls with the fresh data txtEntityName.Text = freshEntity.Name; txtEntityDescription.Text = freshEntity.Description; // ... map other properties to your form controls } } }Why a new DbContext? Because the original context used to populate the grid might have cached the entity—using a fresh one ensures you get the most recent data from the database, including changes made by other users or processes.
You're already on the right track with creating a new DbContext and using the selected row's bound item. Let's polish this to ensure updates work reliably:
private void btnSaveChanges_Click(object sender, EventArgs e) { if (dataGridView1.SelectedRows.Count == 0) return; var selectedCachedEntity = dataGridView1.SelectedRows[0].DataBoundItem as YourEntity; if (selectedCachedEntity == null) return; using (var updateContext = new YourDbContext()) { // Fetch the entity from the database first (critical for EF to track changes) var entityToUpdate = updateContext.YourEntities.Find(selectedCachedEntity.Id); if (entityToUpdate != null) { // Apply changes from your form controls to the fetched entity entityToUpdate.Name = txtEntityName.Text; entityToUpdate.Description = txtEntityDescription.Text; entityToUpdate.LastUpdated = DateTime.Now; // ... update all relevant properties // Save changes to the database updateContext.SaveChanges(); // Refresh the DataGridView to show the updated state RefreshDataGridView(); } } } // Helper method to reload the DataGridView with fresh data private void RefreshDataGridView() { using (var context = new YourDbContext()) { dataGridView1.DataSource = context.YourEntities.ToList(); // Optional: Re-select the updated row after refresh var updatedRow = dataGridView1.Rows.Cast<DataGridViewRow>() .FirstOrDefault(r => (r.DataBoundItem as YourEntity)?.Id == selectedEntityId); if (updatedRow != null) updatedRow.Selected = true; } }
Key Notes for the Update Workflow:
- Always fetch the entity from the update DbContext first—EF needs to track the entity to detect changes and save them correctly. Don't modify the cached entity from the grid directly.
- After saving, refresh the DataGridView to ensure all users see the latest data.
- If your entity doesn't have a simple primary key (to use
Find), useFirstOrDefaultwith a unique identifier instead:var entityToUpdate = updateContext.YourEntities .FirstOrDefault(x => x.UniqueIdentifier == selectedCachedEntity.UniqueIdentifier);
内容的提问来源于stack exchange,提问作者Pascal

