Why A and B in a many-to-many relationship, when inserting record to A table, a new record will be added in B table as well?
There are two model classes, Customer
and Course
. One customer can choose many courses. Also, one course can be chosen by many customers.
The problem I met is that when I create a customer with some courses he selected (for example course1
and course2
), course1
and course2
are already in the Courses
table, but it will automatically insert course1
and course2
again which is not what I want.
Customer class:
public class Customer
{
public int Id { get; set; }
[MaxLength(20)]
public string City { get; set; }
[Range(16,58)]
public int Age { get; set; }
public Gender Gender { get; set; }
[MaxLength(20)]
public string Name { get; set; }
public IList<Course> CoursesEnrolled { get; set; }
}
Course class:
public class Course
{
public int Id { get; set; }
[MaxLength(50)]
[Required]
public string Name { get; set; }
}
CustomerController
, Save
method:
[HttpPost]
public ActionResult Save( Customer customer
{
if (customer.Id == 0)
{
Customer customerInDb = new Customer()
{
Name = customer.Name ,
City = customer.City ,
Age = customer.Age ,
Gender = customer.Gender ,
CoursesEnrolled = customer.CoursesEnrolled
};
_context.Customers.Add(customerInDb);
}
else
{
var customerInDb = _context.Customers.SingleOrDefault(c => c.Id == customer.Id);
if (customerInDb == null)
{
return HttpNotFound();
}
customerInDb.Name = customer.Name;
customerInDb.Age = customer.Age;
customerInDb.City = customer.City;
customerInDb.Gender = customer.Gender;
customerInDb.CoursesEnrolled = customer.CoursesEnrolled;
}
try
{
_context.SaveChanges();
}
catch (System.Data.Entity.Validation.DbEntityValidationException dbEx)
{
Exception raise = dbEx;
foreach (var validationErrors in dbEx.EntityValidationErrors)
{
foreach (var validationError in validationErrors.ValidationErrors)
{
string message = string.Format("{0}:{1}",
validationErrors.Entry.Entity.ToString(),
validationError.ErrorMessage);
raise = new InvalidOperationException(message, raise);
}
}
throw raise;
}
return RedirectToAction("Index" , "Customer");
}
Four courses exist in the Courses
table:
When I create a customer with some courses selected, Customer
saves successfully, and CustomersCourses
also added the data.
But in the Courses
table, the selecting courses that the customer enrolled also are added to the courses table.
The data in the red triangle is not we want.
Any help or suggestions would be appreciated, thanks!
I think you use new instances of Courses (with the same ID as that of the persisted record in the database) every time a new Customer instance is created. EF tracks them as a newly added objects and inserts them to db as new records on save changes. There are a couple of options:
Load Courses from the context and add them to the CoursesEnrolled collection of the customer instance, which lets EF know that the entity is already persisted in the database.
Explcitly mark the CoursesEnrolled as Unchanged/Detached so that EF would skip it.
foreach (var course in customerInDb.CoursesEnrolled) { _context.Entry(course).State = System.Data.Entity.EntityState.Unchanged; }
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.