0

EFを更新して保存するObjectDataSourceWhich Callsビジネスレイヤーメソッドがあります。私はこの奇妙な問題を抱えています。以下は ODS マークアップです。

<asp:ObjectDataSource ID="odsDeviceForm" runat="server"  ypeName="Spectre.BLL..DeviceManager"
  DataObjectTypeName="Model.Device" SelectMethod="GetById" 
  InsertMethod="Insert" oninserting="OnItemInserting" UpdateMethod="UpdateEx" 
  oninserted="OnItemInserted" onupdated="OnItemUpdated" 
  onupdating="OnItemUpdating" onobjectcreated="OnOdsObjectCreated" 
  onselected="OnOdsItemSelected"  ConflictDetection="CompareAllValues" OldValuesParameterFormatString="orig{0}"   >
  <SelectParameters>
    <asp:SessionParameter Name="primaryKey" SessionField="SelectedDeviceId" Type="Int32" />
  </SelectParameters>

以下は BLL と repositoryCode: BLL:

public void UpdateEx(T entity, T origentity)
{
  try
  {
    repository.Update(origentity, entity);
    repository.Save();
  }
  catch (Exception)
  {
    throw;
  }
}

リポジトリ:

public void Update(T orig, T newEntity)
{
  myContext.Entry<T>(newEntity).CurrentValues.SetValues(newEntity);

}

このコードを実行すると、例外が発生します。

エンティティがコンテキストに存在しないため、タイプ 'Device' のエンティティに対してメンバー 'CurrentValues' を呼び出すことはできません。エンティティをコンテキストに追加するには、DbSet の Add メソッドまたは Attach メソッドを呼び出します。

しかし、dbset.attach を実行すると、エンティティが既に存在するという例外が発生します。

どうすればよいかわかりません。循環問題のように思えます。私はこれで髪を引っ張って半分ハゲになりました。助けてください。

4

1 に答える 1

0

コンテキストに既に読み込まれているデバイス クラスのナビゲーション プロパティの新しいインスタンスを作成した可能性があります。例えば

device.Foo = new Foo { Id = 1 };
context.Devices.Attach(device);

Fooコンテキストには、 のインスタンスがすでにある可能性がありますId=1。したがって、アタッチDeviceすると、アタッチも試行Fooされますが、コンテキストによって既に追跡されている一致するインスタンスがあるため失敗します。

可能であれば、スカラー プロパティのみを設定してみてください。

device.FooId = 1;
context.Devices.Attach(device);

Fooインスタンスがロードされているかどうかを判断するには

var foo = context.ObjectStateManager
  .GetObjectStateEntries(EntityState.Added | EtityState.Modified | EntityState.Unchanged)
  .Select(s => s.Entity).OfType<Foo>().SingleOrDefault(f => f.Id == device.FooId);

if (foo != null)
{
   // foo is loaded
}

または、コンテキストがナビゲーション プロパティをロードしたかどうかを確認し、ロードされている場合はそのインスタンスを使用します。

于 2012-01-21T00:28:09.467 に答える