7

我有這樣的代碼在Windows服務針對.NET 4.5使用數據庫,第一實體框架層:當我更新父項時,爲什麼實體框架會插入子項?

var existingState = DataProcessor.GetProcessState(workerId); 

existingState.ProcessStatusTypeId = (int)status; 
existingState.PercentProgress = percentProgress; 
existingState.ProgressLog = log; 

DataProcessor.UpdateProcessState(existingState); 

而這種代碼在數據處理類在同一個解決方案:

public ProcessState GetProcessState(int id) 
{ 
    using (var context = new TaskManagerEntities()) 
    { 
     var processes = (from p in context.ProcessStates.Include("ProcessType").Include("ProcessStatusType") 
         where p.IsActive && p.ProcessStateId == id 
         select p); 

     return processes.FirstOrDefault(); 
    } 
} 

public ProcessState UpdateProcessState(ProcessState processState) 
{ 
    using (var context = new TaskManagerEntities()) 
    { 
     context.ProcessStates.Add(processState); 
     context.Entry(processState).State = System.Data.EntityState.Modified; 
     context.SaveChanges(); 
    } 

    return processState; 
} 

ProcessState是另外兩個類ProcessStatusType和ProcessType的父類。當我在Windows服務中運行該代碼時,它將檢索記錄,更新實體並將其保存。儘管在上面的代碼中永遠不會使用ProcessType子類,但在執行ProcessState實體保存時,EF會在ProcessType表上執行插入操作並在其中創建新記錄。然後它更改ProcessStatus實體中的FK,將其指向新的子節點並將其保存到數據庫。

它確實不是在ProcessStatusType表中執行此操作,該表使用基本上相同的FK父子關係進行設置。

我現在有一個數據庫完全相同的ProcessType條目,我不需要,我不知道這是爲什麼發生。我覺得我犯了一些我看不見的明顯錯誤,因爲這是我的第一個EF項目。我允許上下文在呼叫之間過期但維護同一實體的問題是否存在?

+1

檢查以確保您正在加載的ProcessType對象具有其表的主鍵的屬性並且它已正確填充。例如,如果'ProcessType.Id = 0',EF會認爲它是一個新對象,並插入它 – 2013-02-15 21:15:53

+0

我剛剛檢查過,它確實如此。主鍵存在且正在進行中,並且在新數據庫記錄出現時被設置爲主鍵。 – RedBrogdon 2013-02-15 21:22:56

回答

5

使用Add將所有元素的狀態設置爲Added,這會導致子元素被插入。當您爲此元素指定EntityState.Modified時,不插入父元素。

嘗試在UpdateProcessState中使用以下內容,而不是使用Add。

context.ProcessStates.Attach(processState); 
context.Entry(processState).State = EntityState.Modified; 
context.SaveChanges(); 

附加將設置所有元素不變和通過的狀態確定爲修改父元素要表示只有這個元件應該被更新。

另一個說明。您應該使用強類型的Include(x => x.ProcessType)而不是Include("ProcessType")

+0

感謝您的幫助。附加/添加問題導致了問題。我做了這個改變,現在一切正常。關於強類型的包含語句,那些仍然可以在EF5中使用的語句?我的編譯器在他們拋出一個錯誤,我看到這個帖子:http://stackoverflow.com/questions/4544756/using-include-in-entity-framework-4-with-lambda-expressions這似乎表明他們是棄用。 – RedBrogdon 2013-02-15 21:54:00

+1

是的,支持強類型的Include,http://msdn.microsoft.com/en-us/library/gg671236(VS.103).aspx。嘗試添加一個使用System.Data.Entity,使編譯器停止抱怨。 – Martin4ndersen 2013-02-15 21:59:07

+0

他們在那裏。再次感謝。有趣的是,Intellisense會建議將「使用」語句用於未引用但可用的引用程序集方法,但是如果它們是已經存在於命名空間中的東西的多態性,則不會。 – RedBrogdon 2013-02-15 22:06:12

相關問題