升级.NET6后使用Pomelo.EntityFrameworkCore.MySql访问byte属性报错如何解决
问题根因
该报错核心原因是 Pomelo.EntityFrameworkCore.MySql 驱动默认会将 MySQL 中tinyint(1)类型的字段映射为 C# 的bool类型,你当前实体类使用byte类型和驱动默认映射规则不匹配,因此触发类型不支持异常。
错误原文:System.InvalidOperationException: The property 'SqlClass.Disabled' is of type 'byte' which is not supported by the current database provider. Either change the property CLR type, or ignore the property using the '[NotMapped]' attribute or by using 'EntityTypeBuilder.Ignore' in 'OnModelCreating'.
解决方案
可根据业务场景选择以下任意一种方案处理:
方案1:修改实体类类型为bool(适用二元状态场景)
如果Disabled字段本身仅用来表示「启用/禁用」的二元逻辑,直接将实体类属性改为bool类型即可,无需额外调整映射规则:
// 实体类属性调整,删除无用的MaxLength注解 [Required] public bool Disabled { get; set; }
对应Fluent配置简化:
entity.Property(e => e.Disabled) .IsRequired() .HasColumnName("disabled") .HasColumnType("tinyint(1)");
方案2:关闭全局tinyint(1)转bool规则(适用需存储多值byte场景)
如果业务需要用byte存储0~255范围内的多值,可在注册DbContext时关闭驱动默认的tinyint(1)转bool规则:
builder.Services.AddDbContext<你的DbContext类名>(options => options.UseMySql("你的数据库连接串", new MySqlServerVersion(new Version(8, 0, 30)), mysqlOpt => { // 关闭tinyint(1)默认映射为bool的规则 mysqlOpt.TreatTinyAsBoolean = false; }));
修改后驱动会将所有tinyint类型字段默认映射为byte,和你的实体类属性类型匹配。
方案3:单独为当前字段配置类型转换(不想修改全局规则场景)
如果仅需要适配这一个字段的类型,不需要修改全局映射规则,直接开启你之前注释的转换配置即可:
entity.Property(e => e.Disabled) // 开启byte类型转换 .HasConversion<byte>() .IsRequired() .HasColumnName("disabled") .HasColumnType("tinyint(1)");
注意:无论选哪种方案,都可以删除实体类和Fluent配置中没用的HasMaxLength(255)配置,该配置仅对字符串类型生效,对数值类型无意义
内容的提问来源于stack exchange,提问作者WingmanColt

