这是我参与8月更文挑战的第27天,活动详情查看:8月更文挑战
- 📢欢迎点赞 :👍 收藏 ⭐留言 📝 如有错误敬请指正,赐人玫瑰,手留余香!
- 📢本文作者:由webmote 原创,首发于 【掘金】
- 📢作者格言: 生活在于折腾,当你不折腾生活时,生活就开始折腾你,让我们一起加油!💪💪💪
1.来自RowVersion的映射困惑
Sqlserve里的RowVersion类型的字段通常被用作乐观锁并发写,而我们平常使用的时候基本把它映射为byte[]即可,无需为它赋值。
但有时候由于业务需要,可能需要读取它,做些业务动作,我们该怎么映射它呢,能直接映射为long或ulong吗?
答案很客观,直接映射为其他类型,直接提示不能把byte[]映射为其他类型。
Stackoverflow有个伙计说,自己读到byte[],然后解析为ulong,哦哦哦,非常麻烦的了。
2. EF 值转换
其实EF提供了值转换功能,可以完成各种类型的读、写转换。
转换器允许在读取或写入数据库时转换属性值。 此转换可以从一个值转换为同一类型的另一个值,并且你不需要处理null这种情况,因为null数据不会调用该转换器。
3. 配置转换器
值转换在 DbContext.OnModelCreating中进行配置。
protected override void OnModelCreating(ModelBuilder modelBuilder) {
modelBuilder
.Entity<Rider>()
.Property(e => e.Mount)
.HasConversion(
v => v.ToString(),
v => (EquineBeast)Enum.Parse(typeof(EquineBeast), v)
);
}
HasConversion 提供2个Func来完成clr类型到db 类型的转换,以及db类型到clr类型的转换。
EF内置了非常多的常用转换,以至于你几乎不用在重写这些转换。
例如:
modelBuilder .Entity<Rider>() .Property(e => e.Mount) .HasConversion<string>();
当然更简单的是直接使用属性标签Column
public class Rider2 {
public int Id { get; set; }
[Column(TypeName = "nvarchar(24)")]
public EquineBeast Mount { get; set; }
}
或
modelBuilder .Entity<Rider2>()
.Property(e => e.Mount)
.HasColumnType("nvarchar(24)");
内置的转换有很多:
- .HasConversion()
- .HasConversion()
- .HasConversion() ...
4. RowVersion的转换
SQL Server使用 8[字节二进制列][支持乐观 rowversion / timestamp 并发], 它们始终使用 8 字节数组从数据库中读取和写入。
但是,字节数组是可变的引用类型,这使得它们有点难以处理。
值转换器允许将其映射为 long等类型。
例如,假设 Blog 实体具有 ulong 并发令牌:
public class Blog
{
public int Id { get; set; }
public string Name { get; set; }
public ulong Version { get; set; }
}
可以使用值转换器将SQL rowversion 服务器列:
modelBuilder.Entity<Blog>()
.Property(e => e.Version)
.IsRowVersion()
.HasConversion<byte[]>();
5.加密属性值
值转换器也可用于在将属性值发送到数据库之前对其进行加密,然后在读取时解密它们。
例如,使用字符串反转替代实际加密算法:
modelBuilder.Entity<User>().Property(e => e.Password).HasConversion(
v => new string(v.Reverse().ToArray()),
v => new string(v.Reverse().ToArray()));
6. 小结
有了值转换后,在操作数据库内的特殊类型时,方便了很多,这里不单单方便了RowVersion类型,注入json格式字符串、日期等特殊类型,均可以从值转换中受益。
例行小结,理性看待!
结的是啥啊,结的是我想你点赞而不可得的寂寞。😳😳😳
👓都看到这了,还在乎点个赞吗?
👓都点赞了,还在乎一个收藏吗?
👓都收藏了,还在乎一个评论吗?