问题描述
我几乎完成了旨在使用 EF6 部分同步数据库的技术代码。但我仍然不适应某些场景。
我所有的痛苦都源于我需要首先对 DBContext
包括关系建立一个良好的描述。而且我很难获得(我称之为)实体之间关系的完整描述。
通过完整的描述,我的意思是:
- 两端的类型
- 两端的导航属性(如果存在)
- 两端的关系多样性
为此,我使用了 MetadataWorkspace。例如,在一对多关系的情况下,如果我从描述“多”实体表的 EntityType 获取 NavigationProperty,我就可以获得此描述。但是,从描述“一个”实体表的 EntityType 中,我无法找到例如反向导航属性。当两个实体中都没有定义导航属性时会出现另一个问题:我的代码两次返回属性名称。
为了更清楚,这里有一段代码。我遍历上下文中描述的每个 DBset,然后遍历 EntityType 中描述表的每个导航属性(最后我操作 TestResult List 以创建有用的字典 <Type,TableRelationshipDescription>
)。
ObjectContext objContext = ((IObjectContextAdapter)context).ObjectContext;
MetadataWorkspace workspace = objContext.MetadataWorkspace;
var dbSetList = typeof(SandBoxDbContext).GetProperties().Where(p => p.PropertyType.Name.Contains("DbSet")).ToList();
foreach (PropertyInfo p in dbSetList)
{
Type sourceTableType = p.PropertyType.GetGenericArguments().First();
EntityType table = GetTableEntityType(sourceTableType,workspace);
typesVSOneRelationshipNavPropertyDict.Add(key: sourceTableType,value: new List<TableRelationshipDescription>());
foreach (NavigationProperty np in table.NavigationProperties)
{
string sourceNavPropName = np.Name;
var endMemberEntityType = np.ToEndMember.GetEntityType();
var typestring = sourceTableType.Namespace + "." + endMemberEntityType.Name + "," + endMemberEntityType.NamespaceName;
Type targetTableType = Type.GetType(typestring);
string targetNavPropName = GetPropertyNameForNavigationProperty(np);
if (np.ToEndMember.RelationshipMultiplicity != RelationshipMultiplicity.Many)
{
var tableRelationshipDescription = new TableRelationshipDescription()
{
FromTableType = sourceTableType,FromNavigationProperty = sourceNavPropName,FromMultiplicity = np.ToEndMember.RelationshipMultiplicity,ToTableType = targetTableType,ToNavigationProperty = targetNavPropName,ToMultiplicity = np.FromEndMember.RelationshipMultiplicity
};
TestResult.Add(tableRelationshipDescription);
// Trick to have a proper desc of the relationship from "one" side
if (tableRelationshipDescription.ToMultiplicity == RelationshipMultiplicity.Many)
{
TestResult.Add(tableRelationshipDescription.GetReverseDescription());
}
}
}
}
和:
private string GetPropertyNameForNavigationProperty(NavigationProperty navigationProperty)
{
var ForeignKeyName = navigationProperty.RelationshipType.Name.Split('_');
var propertyName = ForeignKeyName[ForeignKeyName.Length - 1];
return propertyName;
}
简而言之...我需要帮助
编辑: 我不再需要它了,因为我找到了在同步过程中保持实体连接的方法:-)。
之所以需要完整的描述,是因为当一个实体的ID在其他表中用作外键时,我必须断开(可为空的)关系。保持实体附加使 EF6 有机会自行管理此场景。
最终,我只需要部分关系描述(来自仅定义外键的表)即可在同步期间添加、更新或断开相关实体。
如果其他程序员对它的答案感兴趣,我是否应该保留这个主题?
亚历克斯
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)