私が取り組んでいるプロジェクトでは、データベースから「ユーザー」を削除する必要があります。この「ユーザー」には、外部キーを参照する2つのテーブルがあります。ハード削除するとき、「ユーザー」への外部キーを持つテーブルAとテーブルBからすべてのレコードを削除してから、その「ユーザー」レコードを削除しようとしています。これはすべてリポジトリ内でオブジェクトファクトリを使用して行われます。
コードは次のとおりです。
public void RemoveUserByUserId(int userId)
{
var user = m_context.User.GetByKey(userId);
ObjectFactory.Inject(m_context);
UserTokenRepository.RemoveUserTokensByUserId(userId);
UserMappingRepository.RemoveUserMappingsByUserId(userId);
m_context.User.DeleteOnSubmit(user);
m_context.SubmitChanges();
ObjectFactory.ResetDefaults();
}
public static void RemoveUserTokensByUserId(int userId)
{
var dataContext = ObjectFactory.GetInstance<DataContext>();
var userTokens = dataContext.UserToken.ByUserId(userId);
dataContext.UserToken.DeleteAllOnSubmit(userTokens.AsEnumerable());
}
public static void RemoveUserMappingsByUserId(int userId)
{
var dataContext = ObjectFactory.GetInstance<DataContext>();
var userMappings= dataContext.UserMapping.ByUserId(userId);
dataContext.UserMapping.DeleteAllOnSubmit(userMappings.AsEnumerable());
}
各テーブルに1つのレコードがある場合、それは正常に機能します。テーブルに複数ある場合、これはUserTokenとUserMappingsでのみ発生する可能性があり、次のエラーが発生します。
System.ArgumentException was unhandled by user code
Message=An item with the same key has already been added.
Source=mscorlib
StackTrace:
at System.ThrowHelper.ThrowArgumentException(ExceptionResource resource)
at System.Collections.Generic.Dictionary`2.Insert(TKey key, TValue value, Boolean add)
at System.Data.Linq.ChangeProcessor.EdgeMap.Add(MetaAssociation assoc, TrackedObject from, TrackedObject to)
at System.Data.Linq.ChangeProcessor.BuildEdgeMaps()
at System.Data.Linq.ChangeProcessor.SubmitChanges(ConflictMode failureMode)
at System.Data.Linq.DataContext.SubmitChanges(ConflictMode failureMode)
at XXXX.XXXX.XXXX.XXXXDataContext.SubmitChanges(ConflictMode failureMode) in XXXX:line 519
at System.Data.Linq.DataContext.SubmitChanges()
at XXXX.UserRepository.RemoveUserByUserId(Int32 userId) in XXXX:line 146
at XXXX(Int32 profileUserId) in XXXX:line 948
at XXXX(Int32 profileUserId) in XXXX:line 165
at SyncInvokeUnregisterUserForActivationFailed(Object , Object[] , Object[] )
at System.ServiceModel.Dispatcher.SyncMethodInvoker.Invoke(Object instance, Object[] inputs, Object[]& outputs)
at System.ServiceModel.Dispatcher.DispatchOperationRuntime.InvokeBegin(MessageRpc& rpc)
プライバシー上の理由からXXXXを入力する必要がありました。私がこれを読んだのは、LINQはSQLの変更の準備を保存していて、それを辞書に入れているということでした。どういうわけか、2つのキーは同じであり、変更が発生する前にエラーが発生します。
どんな助けでも大歓迎です。