使用EF Core Scaffold时如何将SQL Server Date映射为DateOnly而非DateTime?
解决Scaffold-DbContext中SQL Server date列映射为datetime的问题
以下是几种可落地的解决办法:
方法1:全局/实体级手动配置类型映射
在生成的DbContext类的OnModelCreating方法中,针对特定实体或全局统一修正列类型映射:
protected override void OnModelCreating(ModelBuilder modelBuilder) { // 单个实体列配置 modelBuilder.Entity<YourTargetEntity>() .Property(e => e.YourDateColumn) .HasColumnType("date"); // 全局批量配置所有date列 foreach (var entityType in modelBuilder.Model.GetEntityTypes()) { foreach (var property in entityType.GetProperties()) { var dbColumn = property.GetColumnType(); if (dbColumn != null && dbColumn.Equals("date", StringComparison.OrdinalIgnoreCase)) { property.SetColumnType("date"); // 若使用EF Core 6+,可直接映射为DateOnly类型 // property.SetType(typeof(DateOnly)); } } } }
方法2:生成后手动修改实体类注解
执行scaffold-dbcontext时添加--data-annotations参数,生成带数据注解的实体类后,手动修改对应列的注解:
生成的默认代码:
[Column(TypeName = "datetime")] public DateTime YourDateColumn { get; set; }
修改为:
[Column(TypeName = "date")] public DateTime YourDateColumn { get; set; } // 或EF Core 6+推荐的DateOnly类型 // [Column(TypeName = "date")] // public DateOnly YourDateColumn { get; set; }
方法3:自定义反向工程规则(EF Core 5+)
创建自定义脚手架模型工厂,自动将SQL Server的date列映射为指定类型:
public class CustomScaffoldingConfig : IDesignTimeServices { public void ConfigureDesignTimeServices(IServiceCollection services) { services.AddSingleton<IScaffoldingModelFactory, CustomModelFactory>(); } } public class CustomModelFactory : RelationalScaffoldingModelFactory { public CustomModelFactory(IScaffoldingModelFactoryDependencies dependencies) : base(dependencies) { } protected override TypeMappingInfo GetTypeMappingInfo(RelationalDatabaseModel dbModel, Column column) { var baseInfo = base.GetTypeMappingInfo(dbModel, column); if (column.TypeName.Equals("date", StringComparison.OrdinalIgnoreCase)) { // 映射为DateOnly类型(EF Core 6+支持) return new TypeMappingInfo(typeof(DateOnly)) { StoreTypeName = column.TypeName }; } return baseInfo; } }
执行scaffold-dbcontext命令时,确保该配置类所在程序集被加载,即可自动完成正确映射。
内容的提问来源于stack exchange,提问作者jonrexh
相关产品推荐
相关产品推荐

