Updating Existing Entities

By Martin Schaeferle | September 19, 2012

Querying data is a useful benefit of using Entity Framework, but you'll often need to create, modify, and delete entity data as well. As with most of its features, Entity Framework provides rich support for changing data and has lots of options. This article discusses updating existing entities. When you query the model and retrieve one or more entities then modify them, you can simply call SaveChanges to persist the changes.

The following code retrieves all customers with the first name Ann and selects the first one, then writes the entity's current state to the console window. Then the code changes a couple of property values, and again writes the state. Then it calls SaveChanges and writes the state yet again, then confirms that it updated the entity.

private static void UpdateOneEntity(AWLTEntities context) { var customer = context.Customers .Where(c => c.FirstName == "Ann").First();
 Console.WriteLine("State initially: {0}", customer.EntityState);
 customer.FirstName = "Anne"; customer.ModifiedDate = DateTime.Now;
 Console.WriteLine("State after changes: {0}", customer.EntityState);
 Console.WriteLine("State after saving: {0}", customer.EntityState);
 Console.WriteLine("Entity Updated: {0}, {1} {2}", customer.CompanyName, customer.FirstName, customer.LastName); }

Figure 1 shows the results in the console window. Notice that immediately after materializing the Customer object, its state is Unchanged. This is as you'd expect, since no entity data has changed. After making changes but before saving them, the state is Modified. And after saving the changes, the state is once again Unchanged, because the context updated the entity's original values to the new values to reflect the values now stored in the database.



Figure 1. The results of changing a single entity.

If you run SQL Profiler and examine the UPDATE statement that Entity Framework generated to persist the changes, you'll find the following statement. Notice that Entity Framework is passing only the two updated fields, not the entire set of entity data. The context keeps track of which properties changed, so is able to create more efficient SQL for the operation.

exec sp_executesql N'update [SalesLT].[Customer] set [FirstName] = @0, [ModifiedDate] = @1 where ([CustomerID] = @2) ',N'@0 nvarchar(50),@1 datetime2(7),@2 int',@0=N'Anne',@1='2011-09-11 18:16:57.8320312',@2=472

An interesting experiment is to update the FirstName property to Ann instead of Anne; in other words to set the value of the property to its current value. Change the code for that statement to the following and comment out the line that updates the ModifiedDate property. Then run the application again. And again. And once more. Notice that each time you get the same Unchanged/Modified/Unchanged states that you saw in Figure 1. Entity Framework sees that you assign a value to the property and changes the state to Modified without comparing the new value to the old one.

customer.FirstName = "Ann";

If you use SQL Profiler to look at the SQL statement generated with this new version of the code, you'll find that it is the following statement every time. The UPDATE statement sets the FirstName field to 'Ann' even though that is already its value.

exec sp_executesql N'update [SalesLT].[Customer] set [FirstName] = @0 where ([CustomerID] = @1) ',N'@0 nvarchar(50),@1 int',@0=N'Ann',@1=694

You can also update related data using the navigation properties of each entity, as long as those related objects are materialized in the query. Usually the easiest way to do that is to use the Include method for the related entities to make sure their data is available in memory for modification.

Martin Schaeferle

Martin Schaeferle has taught IT professionals nationwide to develop applications using Visual Basic, Microsoft SQL Server, ASP, and XML. He has been a featured speaker at Microsoft Tech-Ed and the Microsoft NCD Channel Summit, and he specializes in developing Visual Basic database applications, COM-based components, and ASP-based Web sites. In addition to writing and presenting technical training content, Martin is also LearnNowOnline's vice president of technology.

This blog entry was originally posted September 19, 2012 by Martin Schaeferle