проблема удаления структуры объекта (с wpf) - PullRequest
2 голосов
/ 22 февраля 2011

У меня следующая проблема.У меня типичный сценарий мастер / деталь UI.Я установил основной объект (CommissionPlan) как DataContext.Затем я привязываю сетку к CommissionPlanItems (это коллекция дочерних элементов)

Все отлично работает с дополнениями / обновлениями.Когда я пытаюсь удалить существующую строку - я получаю следующую ошибку EF: Отношение не может быть изменено, потому что одно или несколько свойств внешнего ключа не обнуляются.Когда в отношение вносится изменение, для соответствующего свойства внешнего ключа устанавливается нулевое значение.Если внешний ключ не поддерживает нулевые значения, необходимо определить новое отношение, свойству внешнего ключа должно быть присвоено другое ненулевое значение или несвязанный объект должен быть удален.

Iнашел кучу рецептов о том, как справиться с этим.Но я не уверен, как это сделать в моем случае, так как удаление происходит автоматически, через удаление строки из сетки.Что я должен изменить в этом случае?

Ответы [ 4 ]

2 голосов
/ 22 февраля 2011

Проблема заключается в том, что сетка WPF удаляет только элемент из коллекции CommissionPlan.CommissionPlanItems.В общем случае это не означает, что элемент будет удален в базе данных.Будут удалены только отношения между элементами, а для CommisionPlanItem's CommissionPlanId будет установлено значение null.Если это не допустимо, вы получите свое исключение.

Решение состоит в том, чтобы удалить удаленный элемент в ObjectContext или изменить вашу модель сущности, чтобы поддерживать идентифицирующие отношения (я думаю, что это возможно только в EntityРамки 4).

1 голос
/ 22 февраля 2011

Вот что я в итоге сделал, чтобы "очистить".Я отмечу это как ответ, но я буду признателен, если кто-нибудь даст мне лучший способ сделать это.По сути, я проверяю ObjectStateManager на наличие измененных сущностей (есть ли лучший способ увидеть их?), А затем, если я вижу, что это изменение подразумевает установку родителя на «ноль» - я знаю, что эта сущность была «отделена» от моего графика, и я идувперед и удали его.

modified = context.ObjectStateManager.GetObjectStateEntries(EntityState.Modified);
                if (modified != null && modified.Count() > 0)
                {
                    foreach (ObjectStateEntry ose in modified)
                    {
                        if (
                            (ose.Entity.GetType() == typeof(CommissionPlanCustomer) && ((CommissionPlanCustomer)ose.Entity).CommissionPlan == null)
                            ||
                            (ose.Entity.GetType() == typeof(CommissionPlanItemEligibleUser) && ((CommissionPlanItemEligibleUser)ose.Entity).CommissionPlanItem == null)
                            ||
                            (ose.Entity.GetType() == typeof(CommissionPlanItem) && ((CommissionPlanItem)ose.Entity).CommissionPlan == null)
                           )
                        {
                            context.DeleteObject(ose.Entity);
                        }
                    }
                }
0 голосов
/ 29 июня 2011

Вы также можете подключить событие AssociationChanged, чтобы определить, когда DataGrid удалил отношение EF.В случае, если вы вызываете DeleteObject для вашей сущности.Полное объяснение предоставлено Джули Лерман в этой статье под названием Перетаскивание привязки данных с помощью Entity Framework и WPF .Ее сопровождающее видео довольно хорошо объясняет эту технику (продвиньте видео до отметки 25 минут).

0 голосов
/ 11 марта 2011

Вот еще одно предложение: вы можете изменить модель объекта, чтобы поддерживать идентифицирующее отношение, не изменяя структуру базы данных.Затем откройте файл edmx в редакторе XML и добавьте ссылочное поле в ключевые поля.В этом случае это будет выглядеть примерно так:

<edmx:StorageModels>
<Schema ...>
  ...
  <EntityType Name="CommissionPlanItems">
    <Key>
       <PropertyRef Name="CommissionPlanItemsId" />
       <PropertyRef Name="CommissionPlanId" /> <!-- This line added -->
    </Key>
  ...
  </Schema>
</edmx:StorageModels>
<edmx:ConceptualModels>
  <Schema ...>
      ...
     <EntityType Name="CommissionPlanItems">
        <Key>
          <PropertyRef Name="CommissionPlanItemsId" />
          <PropertyRef Name="CommissionPlanId" /> <!-- This line added -->
        </Key>
      ...
  </Schema>
</edmx:ConceptualModels>

Я попробовал это и теперь могу использовать сетку данных для вставки, удаления и обновления элементов сведений.Возможно, потребуется дальнейшее тестирование.Если вы запустите «Обновить модель из базы данных», вам, вероятно, придется снова редактировать файл edmx.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...