实体框架:将多个表映射为一个实体 - 插入问题

问题描述:

今天我有一个实体框架问题。我有两个表:项目和Projects_Rights实体框架:将多个表映射为一个实体 - 插入问题

alt text http://www.zaczek.net/EF-*.jpg

  • 项目包含了一些项目...
  • Project_Rights包含对每个标识(=用户)对每个项目的访问权限。该表由触发器/函数计算。

这些映射表放入一个实体是没有挑战:

class Project 
{ 
    int ID; 
    double AufwandGes; 
    DateTime CreatedOn; 
    ... 
    int CurrentIdentity__Implementation__; 
    int CurrentAccessRights__Implementation__; 
} 

<EntitySetMapping Name="Projekt"> 
    <EntityTypeMapping TypeName="IsTypeOf(Model.Projekt)"> 
    <MappingFragment StoreEntitySet="Projekt"> 
     <ScalarProperty Name="ID" ColumnName="ID" /> 
     <ScalarProperty Name="AufwandGes" ColumnName="AufwandGes" /> 
     <ScalarProperty Name="ChangedOn" ColumnName="ChangedOn" /> 
     <ScalarProperty Name="CreatedOn" ColumnName="CreatedOn" /> 
     <ScalarProperty Name="Kundenname" ColumnName="Kundenname" /> 
     <ScalarProperty Name="Name" ColumnName="Name" /> 
    </MappingFragment> 
    <MappingFragment StoreEntitySet="Projekt_Rights"> 
     <ScalarProperty Name="ID" ColumnName="ID" /> 
     <ScalarProperty Name="CurrentIdentity__Implementation__" ColumnName="Identity" /> 
     <ScalarProperty Name="CurrentAccessRights__Implementation__" ColumnName="Right" /> 
    </MappingFragment> 
    </EntityTypeMapping> 
</EntitySetMapping> 

选择项目之一:

var prjList = ctx.GetQuery<Project>() 
    // This condition is added automatically by a custom Linq Provider 
    .Where(p => p.CurrentIdentity__Implementation__ == Thread.CurrentPrincipal.Identity.ID); 

我从更新想出如何防止实体框架CurrentIdentity__Implementation __(= Identity)& CurrentAccessRights__Implementation __(= Right)。这是通过设置StoreGeneratedPattern =“Computed”在SSDL中完成的。

<EntityType Name="Projekte_Rights"> 
    <Key> 
     <PropertyRef Name="ID" /> 
    </Key> 
    <Property Name="ID" Type="int" Nullable="false" /> 
    <Property Name="Identity" Type="int" Nullable="false" StoreGeneratedPattern="Computed" /> 
    <Property Name="Right" Type="int" Nullable="false" StoreGeneratedPattern="Computed" /> 
    </EntityType> 

我已经声明级联在我的SQL Server和SSDL删除。很棒!

我的问题是:如何防止实体框架从插入记录到Project_Rights表中?添加记录是通过触发器/函数完成的。

感谢您指点我正确的方向!

编辑:

我找到了另一种方式。感谢Alex帮助我离开这条道路。

我创建了一个查看

create view Projekte_with_Rights as 
select tbl.*, r.[Identity], r.[Right] 
from Projekte tbl 
inner join Projekte_Rights r on tbl.ID = r.id 

这种观点是可更新的。为了能够删除行我实现了这个触发:

create trigger Projekte_with_Rights_DeleteTrigger 
ON Projekte_with_Rights 
INSTEAD OF DELETE AS 
BEGIN 
    DELETE FROM Projekte WHERE ID in (SELECT ID FROM deleted) 
END 

现在我可以映射这个观点在实体框架“表”。 [身份]和[权利]被映射为计算列。

另一个触发器现在负责填写正确的身份和权利。在这里,我有另一个问题。如果我在Projekte_Rights表中插入多于一行的信息,EF声称一个实体返回多个行。但这是另一个故事,超出了这个问题的范围。

如果您想要更精细地控制插入&更新,您需要使用StoredProcedures进行插入/更新/删除操作。

不幸的是,更新/插入/删除的范围是实体,无法获得更精细的配置Sproc(对于一个表)和标准T-SQL(对于其他表)。

这意味着如果您需要重写Projekt_Rights表的控制权,您还必须为Projekt表执行该控制。

查看更多this sample

注意:如果你需要这样做插入,不幸的是你必须做更新和删除。

希望这有助于

亚历

+0

+1:我害怕听到这个消息。谢谢你帮助我离开这个方向。我将尝试使用可更新视图的解决方案。 – Arthur 2010-01-13 09:15:56