I’m new to Entify Framework so this is probably a very basic question. In a WinForms application I have a data entry page that works fine until I add a listbox and try to update the database with the selections that have been made.
On the form the user selects a file to upload and specifies one or more departments that can access the file. Here’s how I thought it would work:
using (var ctx = new FCEntities())
{
var batch = new Batch() { Description = txtDescription.Text, Filename = filename, Departments = (System.Data.Objects.DataClasses.EntityCollection<Department>)lstDepartments.SelectedItems };
ctx.AddToBatches(batch);
ctx.SaveChanges();
}
But when this didn’t work I did some research and learned that I can’t cast the SelectedItems to EntityCollection so I decided to copy the items from the original collection into a new collection and then use the new collection as follows:
using (var ctx = new FCEntities())
{
var departments = new System.Data.Objects.DataClasses.EntityCollection<Department>();
foreach (var department in lstDepartments.SelectedItems)
{
departments.Add((Department)department);
}
var batch = new Batch() {Description = txtDescription.Text, Filename = filename, Departments=departments };
ctx.AddToBatches(batch);
ctx.SaveChanges();
}
This didn’t work either and gave this error on the departments.Add line:
“An object that is attached to an ObjectContext cannot be added to an
EntityCollection or EntityReference that is not associated with a
source object.”
I don’t understand because it doesn’t appear to me that the department object is attached to the ObjectContext? I’m obviously missing something fundamental, so any advice and/or links to examples of how others do this would be appreciated.
I wanted to leave an answer to this in case someone else runs into this someday. The comments left by Wiktor were helpful in getting me in the right direction. I decided I had a lack of fundamental understanding so I did some reading on MSDN and was able to resolve my issue.
The datamodel behind this existed of three tables: Batches, Departments, and Batches_Departments which allowed for a many to many relationship between Batches and Departments.
The problem with my original code/logic, in a nutshell, was that the Department objects in the ListBox were associated with a different context than the one I was using in my Save method. EF didn’t like this for obvious reasons (at least now they are obvious), so in the save method I used the ID from the selected Departments to get a reference to the same Department in the current context. I could then add this Department to the newly created batch.
Here’s what the code now looks like:
Hopefully this helps someone else who is dealing with the same issue.