Attaching an entity of type failed because another entity of the same type already has the same primary key value.

20,864

Solution 1

Synthesizing the answer objectively: The object you are trying to update don't came from the base, this is the reason of the error. The object came from the post of the View.

The solution is to retrieve the object from base, this will make Entity Framework know and manage the object in the context. Then you will have to get each value that has changed from View and consist in the object controlled by the Entity.

// POST: /SubnetSettings/Edit1/5   
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit1([Bind(Include = "Id,Name,fDialUp,fPulse,fUseExternalGSMModem,fGsmDialUp,bUploadMethodId")] SubnetSettings subnetsettings)
{
    if (ModelState.IsValid)
        {
            //Retrieve from base by id
            SubnetSettings objFromBase = templateDb2.GetById(subnetsettings.Id);

            //This will put all attributes of subnetsettings in objFromBase
            FunctionConsist(objFromBase, subnetsettings)

            templateDb2.Save(objFromBase);   
            //templateDb2.Save(subnetsettings);   

            return RedirectToAction("Index");
        }
    return View(subnetsettings);
}

Solution 2

To remove the error I used AutoMapper to copy the view model object into the base object, before Updating.

Category categoryFromBase = Repository.GetById(categoryFromViewModel.Id);
Mapper.CreateMap<Category, Category>();

Mapper.Map<Category, Category>(categoryFromViewModel, categoryFromBase);
Repository.Save(categoryFromBase);   
Share:
20,864
Admin
Author by

Admin

Updated on April 20, 2020

Comments

  • Admin
    Admin about 4 years

    Let me quickly describe my problem.

    I have 5 databases for 5 customers and each has the same table called SubnetSettings.

    I already created a dropdownlist to select a customer and will shows up the SubnetSetting table which belong to selected customer and allow me to create, edit and delete.

    I can create, delete without problem but when I want to edit the data it brings the error:

    Server Error in '/TMS' Application.

    Attaching an entity of type 'CFS.Domain.Entities.SubnetSettings' failed because another entity of the same type already has the same primary key value. This can happen when using the 'Attach' method or setting the state of an entity to 'Unchanged' or 'Modified' if any entities in the graph have conflicting key values. This may be because some entities are new and have not yet received database-generated key values. In this case use the 'Add' method or the 'Added' entity state to track the graph and then set the state of non-new entities to 'Unchanged' or 'Modified' as appropriate.

    Here is my Edit in my Controller

        // GET: /SubnetSettings/Edit1/5   
        public ActionResult Edit1(short? id)  
        {
            if (id == null)
            {
                return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
            }
            SubnetSettings subnetsettings = detailView.SubnetSettings.SingleOrDefault(t => t.Id == id); 
            if (subnetsettings == null)
            {
                return HttpNotFound();
            } 
            return View(subnetsettings);
        }
    
    
        // POST: /SubnetSettings/Edit1/5   
        [HttpPost]
        [ValidateAntiForgeryToken]
        public ActionResult Edit1([Bind(Include = "Id,Name,fDialUp,fPulse,fUseExternalGSMModem,fGsmDialUp,bUploadMethodId")] SubnetSettings subnetsettings)
        {
            if (ModelState.IsValid)
                {
                    templateDb2.Save(subnetsettings);   
                    return RedirectToAction("Index");
                }
            return View(subnetsettings);
        }
    

    Here is the Save method in the EF

         public SubnetSettings Save(SubnetSettings subnetsettings) {
    
         if (subnetsettings.Id == 0){                        
             context.SubnetSettings.Add(subnetsettings);
         }
         else {
    
             context.SubnetSettings.Attach(subnetsettings);               
             context.Entry(subnetsettings).State = EntityState.Modified; 
         }
            context.SaveChanges();
            return subnetsettings;
        }
    

    I know it's hard to understand other people's code. So any recommend or suggestion is very thankful.

  • Junior Mayhé
    Junior Mayhé over 9 years
    to avoid that annoying message I had to load the record from database in order to use context.Entry(obj).State = EntityState.Modified;
  • Displee
    Displee about 6 years
    Thanks for the clarification. I bounded my ItemsSource to an entity framework model in XAML. I then requested the ItemsSource variable (which is an ObservableCollection) and tried to update that. It resulted in the error above. Then I tried to set the ItemsSource by code: ItemsSource = database_context.model.Local and it solved my problem.
  • wha7ever
    wha7ever about 6 years
    Once I read this "The object you are trying to update don't came from the base, this is the reason of the error. The object came from the post of the View." it all became clear to me. Problem solved. Thank you.