多对多关系对孩子的一个表中插入空FK记录

问题描述:

我有一个模型,这种结构多对多关系对孩子的一个表中插入空FK记录

1 -TABLEA

2 - MODEL

3 -TABLEB

定义: Table MODEL与TABLEA具有一对多的关系 Table MODEL与TABLEB具有一对多的关系 TABLEA与TABLEB具有多对多的关系

每个这些表中的一个具有这种模型定义:

With modelBuilder.Entity(Of TABLEA)() 
     .Property(Function(t) t.dbTableAID). 
      HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity) 
     .HasKey(Function(t) t.dbTableAID) 
     .Property(Function(t) t.Name). 
      HasColumnName("TableName") 
     .ToTable("TI") 

每个类型被定义为这样的:

Public Class Model 

Public Sub New() 
    Me.TableAs = New HashSet(Of TableA)() 
    Me.TableBs = New HashSet(Of TableB)() 
End Sub 

Public Property model_id as integer 

Public Overridable Property TableAs() As ICollection(Of TableA) 
Public Overridable Property TableBs() As ICollection(Of TableB) 

Public Sub LoadModel(Query) 

     For Each objTableA In Query.cbsSrcCubes 
     Dim objDb As TableA = New TableA() 
     Me.TableAs.Add(objDbSrcCube.CastCubeToDB(objDb)) 
    Next 

     For Each objTableB In Query.cbsSrcCubes 
     Dim objDb As TableB = New TableB() 
     Me.TableBs.Add(objDbSrcCube.CastCubeToDB(objDb)) 
    Next 
End Sub 

End Class 


Public Class TableA 

Public Sub New() 
    Me.TableBs = New HashSet(Of TableB)() 
End Sub 

Public Property TableA_id as integer 

Public Overridable Property Model() As Model 
Public Overridable Property TableBs() As ICollection(Of TableB) 

End Class 

Public Class TableB 

Public Sub New() 
    Me.TableAs = New HashSet(Of TableA)() 
End Sub 

Public Property TableB_id as integer 

Public Overridable Property Model() As Model 
Public Overridable Property TableAs() As ICollection(Of TableA) 

Public Sub LoadTableA(Query) 
     For Each objTableA In Query.TableACol 
     Dim objDb As TableA = New TableA() 
     Me.TableAs.Add(objDb) 
    Next 
End Sub 


End Class 

这是上下文的定义

Public Class QDModelContext 
Inherits DbContext 

Public Property Models() As DbSet(Of Model) 
Public Property TableAs() As DbSet(Of TableA) 
Public Property TableBs() As DbSet(Of TableB) 

Protected Overrides Sub OnModelCreating(ByVal modelBuilder As DbModelBuilder) 
    modelBuilder.Conventions.Remove(Of PluralizingTableNameConvention)() 

    'Specific Features of the MODEL Objects 
    With modelBuilder.Entity(Of Model)() 
     .Property(Function(t) t.model_id). 
      HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity) 
     .HasKey(Function(t) t.model_id) 
     .Property(Function(t) t.Name). 
      HasColumnName("ModelName") 
    End With 

    With modelBuilder.Entity(Of TableA)() 
     .Property(Function(t) t.tablea_id). 
      HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity) 
     .HasKey(Function(t) t.tablea_id) 
     .Property(Function(t) t.Name). 
      HasColumnName("TableAName") 

     modelBuilder.Entity(Of TableA)(). 
      HasMany(Function(t) t.TableBs). 
      WithMany(Function(t) t.TableAs). 
     Map(Sub(m) 
       m.ToTable("TableA-TableB") 
       m.MapLeftKey("tablea_id") 
       m.MapRightKey("tableb-id") 
      End Sub) 
    End With 

    With modelBuilder.Entity(Of TableB)() 
     .Property(Function(t) t.tableb_id). 
      HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity) 
     .HasKey(Function(t) t.tableb_id) 
     .Property(Function(t) t.Name). 
      HasColumnName("TableBName") 
    End With 

End Class 

保存从主机调用的例程:

Public Function PersistModel(CurrentModel As Model) 
     Try 
      Using context As New QDModelContext() 
       Dim ModelObj As Model = New Model() 
       context.Models.Add(ModelObj) 
       context.SaveChanges() 
      End Using 
     Catch ex As Exception 
      buildError("Couldn't Persist Model.", ex.Source & ": " & Err.Description, ex) 
     End Try 
    End Function 

我曾尝试正确定义FK关系,都遇到过这样以下错误:

 modelBuilder.Entity(Of TableB)(). 
      HasRequired(Function(t) t.Model). 
      WithMany(Function(t) t.TableBs). 
     Map(Sub(m) 
       m.MapKey("ModelID_FK") 
      End Sub) 

它工作正常...但只要我添加了多对多的关系它说这是不可能将一些对象从TableA映射到Model。

,所以如果我设置为可选:

 modelBuilder.Entity(Of TableB)(). 
      HasOPTIONAL(Function(t) t.Model). 
      WithMany(Function(t) t.TableBs). 
     Map(Sub(m) 
       m.MapKey("ModelID_FK") 
      End Sub) 

它工作得很好,它创建的连接表表A-表B,但它增加了表B中的几个行重复与ModelID_FK空值...我认为是那些关系表A-表B B值的表B. 奇怪不存在...

我不知道是否有加载顺序或实体之间的一些周期或为了做到......

任何帮助将不胜感激。谢谢!!!

我认为这是关系到许多人的装载许多

每个表的问题,B有一个标识列,它是关键。 当我加载表A我加载B项目的集合。 和表B被加载。

当我将更改另存为HasOptional时,所有表A项都映射到多对多T ableA-TableB表中并且表B具有所有表B项和存在于连接表中的所有B项,但是具有NULL外键模型的关键。

所以映射到多方的一方不会发生。

所以我认为在A中加载Ta​​bleB项目的时机存在问题。 当我保存更改时,Join表上的表B项目不被识别为存在,因此没有被映射到现有的......这就是为什么EF在表B中创建这些新条目以将它们映射到某些东西的原因。

如果我改变从模型中的外键表B到HasRequired我得到以下错误:

Entities in 'Context.TableB' participate in the 'TableB_Model' relationship. 0 related 'TableB_Model_Target' were found. 1 'TableB_Model_Target' is expected."} 

我越来越近,但现在还没有。 任何帮助,将不胜感激!

+0

我很确定问题是在加载多对多记录和更改时未保存EF不知道表B的哪些元素是我添加的,因此它会创建新记录。我如何告诉EF表A中表B的类型与表B的记录有关的那些元素? – DataAnalyst1

+0

这两个表有一个关于密钥的自发ID,所以它在更改保存时生成我想 – DataAnalyst1