Проблема с операцией UPDATE в Entity Framework 4 (чистые POCO)

У меня есть модель Entity Framework 4.0, реализованная с использованием чистых POCO (без генерации кода, без самоконтроля сущностей, просто старые объекты CLR).

Теперь вот код, который у меня есть в моем пользовательском интерфейсе для выполнения ОБНОВЛЕНИЯ:

[HttpPost]
public ActionResult UpdatePerson(Person person)
{
    repository.Attach(person);
    unitOfWork.Commit();
}

По сути, у меня есть метод действия, который принимает строго типизированный объект Person, и мне нужно ОБНОВИТЬ эту сущность.

Не выдает ошибку, но и не сохраняет изменения в БД.:(

Когда я проверяю EntityState во время "коммитов" моей единицы работы:

var entities = ObjectStateManager.GetObjectStateEntries(EntityState.Added | EntityState.Deleted | EntityState.Modified | EntityState.Unchanged);

Я вижу свою сущность с EntityState.Unchanged.

Так что это объясняет, почему это не было сохранено. Мои операции поиска, добавления, удаления работают нормально (сохраняются правильно). Но ОБНОВЛЕНИЕ, кажется, не работает.

Я обнаружил, что некоторые потоки говорят, что мне нужно вручную установить состояние объекта:

ctx.ObjectStateManager.ChangeObjectState(person, EntityState.Modified);

Это верно? Куда бы я положил эту логику? Выставить как операцию на моей единице работы?

Очевидно, что проблема заключается в том, что у меня нет отслеживания изменений, из-за использования Pure POCO (без получения EntityObject, без реализации INotifyPropertyChanging).

Но я не нашел проблемы с этим до сих пор.

Что я делаю неправильно?

1 ответ

Решение

Ну, поскольку у вас нет отслеживания изменений и т. Д., У EF должен быть способ определить, что делать с присоединенным объектом, когда SaveChanges() называется. По умолчанию EntityState не изменяется, поэтому, если вы хотите обновить, вы должны вручную установить состояние.

Другим способом было бы запросить Person с этим идентификатором, перепишите свойства с данными, которые вы выбираете из контроллера, и вызовите SaveChanges(), На самом деле это более безопасный способ, так как вы можете защитить себя от ситуации, когда Person удаляется, пока пользователь редактирует веб-форму; но это, очевидно, требует дополнительного обхода БД, что часто менее желательно.

В любом случае у меня был бы репозиторий Update() метод (более конкретный, чем Attach), что на самом деле прикрепит сущность и изменит EntityState в Modified, И у вас все еще есть относительно чистый код в вашем действии:

public ActionResult UpdatePerson(Person person)
{
    repository.Update(person);
    unitOfWork.Commit();
}
Другие вопросы по тегам