Vul*_*ary 16 c# code-first entity-framework-4 ef-code-first
我有一个简单的问题,但我自己无法找到答案.
我正在使用EF4 CTP-5 Code First Model和手工生成的POCO.它正在处理生成的SQL中的字符串比较
WHERE N'Value' = Object.Property
Run Code Online (Sandbox Code Playgroud)
我知道我可以使用以下方法覆盖此功能:
[Column(TypeName = "varchar")]
public string Property {get;set;}
Run Code Online (Sandbox Code Playgroud)
这解决了该单个事件的问题并正确生成SQL为:
WHERE 'Value' = Object.Property
Run Code Online (Sandbox Code Playgroud)
但是,我正在处理一个非常大的域模型并遍历每个字符串字段并设置TypeName ="varchar"将非常非常繁琐.我想指定EF应该在整个板上看到字符串为varchar,因为这是该数据库中的标准,nvarchar是例外情况.
想要纠正这个问题的推理是查询执行效率.varchar和nvarchar之间的比较在SQL Server 2k5中非常低效,其中varchar到varchar比较几乎立即执行.
在EF 4.1之前,您可以使用约定并将以下约定添加到ModelBuilder:
using System;
using System.Data.Entity.ModelConfiguration.Configuration.Properties.Primitive;
using System.Data.Entity.ModelConfiguration.Conventions.Configuration;
using System.Reflection;
public class MakeAllStringsNonUnicode :
IConfigurationConvention<PropertyInfo, StringPropertyConfiguration>
{
public void Apply(PropertyInfo propertyInfo,
Func<StringPropertyConfiguration> configuration)
{
configuration().IsUnicode = false;
}
}
Run Code Online (Sandbox Code Playgroud)
(摘自http://blogs.msdn.com/b/adonet/archive/2011/01/10/ef-feature-ctp5-pluggable-conventions.aspx)
更新:4.1版本的可插入约定已被删除.查看我的博客以寻找替代方法)
对于任何希望在 EF Core(v3 及更高版本)中执行此操作的人来说,实现此目的的快速方法是通过属性ModelBuilder.Model
;它可以轻松访问模型中的所有实体和属性。
“简单”的实现如下:
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
// Apply configurations via regular modelBuilder code-first calls
// ...
// ...
// Override the configurations to force Unicode to false
var entities = modelBuilder.Model.GetEntityTypes();
foreach (var entity in entities)
{
foreach (var property in entity.GetProperties())
{
property.SetIsUnicode(false);
}
}
}
Run Code Online (Sandbox Code Playgroud)
EF Core 很高兴地忽略SetIsUnicode
对非字符串属性的调用,因此您甚至不必检查属性类型(但如果这让您感觉更好的话,您可以轻松检查:)
对于那些喜欢更明确一点的人来说,在调用中添加一个 where 子句GetProperties()
就可以解决问题:
...
var stringProperties = entity.GetProperties()
.Where(e=> e.ClrType == typeof(string));
foreach (var property in stringProperties)
{
property.SetIsUnicode(false);
}
...
Run Code Online (Sandbox Code Playgroud)
您现在可以使用 EF Core 6 的预约定模型配置来执行此类开箱即用的全局映射
下面显示了如何使用此新功能实现此目的的示例:
configurationBuilder
.DefaultTypeMapping<string>()
.IsUnicode(false);
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
9982 次 |
最近记录: |