4

I'm really scratching my head with this. I'm trying to use the Dynamics CRM SDK to update an account record. No matter what I try, it's failing. Here goes.

Account sampleAccount = CrmAccount.GetAccountsBySubmissionCode(crmService, "ERZZUP").Single<Account>();
sampleAccount.Name = "AMC Edited";
crmService.Update(sampleAccount);

Gives the error: EntityState must be set to null, Created (for Create message) or Changed (for Update message)

XrmServiceContext ctx = new XrmServiceContext(crmService);
Account sampleAccount = CrmAccount.GetAccountsBySubmissionCode(crmService, "ERZZUP").Single<Account>();
sampleAccount.Name = "AMC Edited";
ctx.UpdateObject(sampleAccount);
ctx.SaveChanges();

Gives the error: The context is not currently tracking the 'account' entity.

XrmServiceContext ctx = new XrmServiceContext(crmService);
Account sampleAccount = CrmAccount.GetAccountsBySubmissionCode(crmService, "ERZZUP").Single<Account>();
sampleAccount.Name = "AMC Edited";
ctx.Attach(sampleAccount);
ctx.UpdateObject(sampleAccount);
ctx.SaveChanges();

Gives the error: The 'account' entity is already attached to a context.

For reference, 1. The Account object is created by the SDK Early Bound Code Generation Tool 2. crmService is the IOrganizationService connection object 3. GetAccounts ... performs a LINQ query and return an IEnumerable

Please help. Thanks, Chris.

Chris Felstead
  • 1,170
  • 1
  • 9
  • 19

1 Answers1

4

Refer to http://msdn.microsoft.com/en-us/library/gg695783.aspx, particularly the "Multiple Data Contexts" part. It seems you're using multiple contexts to track the entities. The CrmAccount.GetAccountsBySubmissionCode method just hides this from you.

Make sure within the CrmAccount.GetAccountsBySubmissionCode method to dispose of the context/service before returning the IEnumerable<Account>, or make sure you use the same context/service to Update.

Thijs Kuipers
  • 475
  • 5
  • 8
  • You're right about there being a context in the GetAccounts.... method. However, I am now calling Dispose() on the context prior to returning the IEnumerable and I'm still getting the error. – Chris Felstead Apr 18 '12 at 19:38
  • Ok. Been playing more and moving the LINQ fixes it. I'm going to restructure my method to pass in an existing context for use. Thanks for your pointer, it's really helped. – Chris Felstead Apr 18 '12 at 19:48
  • 2
    A more robust way of disposing the context is to use a `using(var context = new XrmServiceContext()) { //code }` block. Declare the IEnumerable before the using block, assign the result in the using block and return the result afterwards. – Thijs Kuipers Apr 18 '12 at 19:53
  • Another way would be to make the `CrmAccount.GetAccountsBySubmissionCode` static and give it the context/service as an argument. That way you're absolutely sure the context is the same. – Thijs Kuipers Apr 18 '12 at 19:56