实体框架/ dbMigration - 不需要的小数舍入

时间:2018-04-17 19:09:38

标签: c# entity-framework-6 dbmigrator

我正在开发一个新的Code-First Entity Framework(使用dbMigration)解决方案,而且我遇到了一些我无法通过的障碍。

即使我修改了生成的Migration文件,将十进制字段的精度/比例设置为18和9,当我运行update-database来构建数据库并调用我编写的方法来播种数据时,它会舍入数据到2位小数而不是我预期的9位。在我试图播种的示例数据中,我正在尝试将Price属性设置为0.4277,但它在数据库中显示为0.420000000

我一直在寻找解决这个问题的方法,包括为OnModelCreating创建一个覆盖(在我的上下文类中),以强制那里的精度/比例。但是当我有这个时(参见下面代码中注释掉的行),虽然数据库迁移仍然按计划完成(包括按预期创建DECIMAL(18,9)),但现在Seed调用不运行

我希望我只是缺少一些小东西(很容易修复)。但有人可以提出我可以尝试的建议吗?

以下是相关代码(包括最初生成的迁移代码):

public class Product
{
    public int ID { get; set; }
    public decimal Price { get; set; }
}

internal sealed class Configuration : DbMigrationsConfiguration<ConfiguratorContext>
{
    public Configuration()
    {
        AutomaticMigrationsEnabled = true;
    }

    protected override void Seed(ConfiguratorContext context)
    {
        //  This method will be called after migrating to the latest version.

        //  You can use the DbSet<T>.AddOrUpdate() helper extension method 
        //  to avoid creating duplicate seed data.
        SeedData.Initialize();        
    }
}

public partial class Initial : DbMigration
{
    public override void Up()
    {
        CreateTable(
            "dbo.Products",
            c => new
            {
                ID = c.Int(nullable: false, identity: true),
                Price = c.Decimal(nullable: false, precision: 18, scale: 9)
                })
            .PrimaryKey(t => t.ID);
    }   

    public override void Down()
    {
        DropTable("dbo.Products");
    }       
}   

public class ConfiguratorContext : DbContext
{
    public ConfiguratorContext() : base("name=ConfiguratorConnectionString")
    {
        Database.SetInitializer<ConfiguratorContext>(new CreateDatabaseIfNotExists<ConfiguratorContext>());
    }

    public DbSet<Product> Products { get; set; }

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        //modelBuilder.Entity<Product>().Property(a => a.Price).HasPrecision(18, 9);
    }
}

public class SeedData
{
    public static void Initialize()
    {
        using (var context = new ConfiguratorContext())
        {
            if (context.Products.Any())
            {
                return;   // DB has been seeded
            }

            context.Products.Add(new Product
            {
                Price = Convert.ToDecimal(0.4277),
            });

            context.SaveChanges();
        }
    }
}   

我错过了什么?

谢谢!

2 个答案:

答案 0 :(得分:1)

我认为您的迁移未执行,默认情况下使用decimal(18, 2)创建数据库。

您可以尝试使用以下初始化程序,但它不会为您的

创建数据库
Database.SetInitializer<ConfiguratorContext>(new MigrateDatabaseToLatestVersion<ConfiguratorContext, Configuration>());

您评论过的行modelBuilder.Entity<Product>().Property(a => a.Price).HasPrecision(18, 9);恰到好处地完成了工作。

如果可以的话,我建议远离自动迁移,并通过Update-Database更新数据库,以便在数据库架构更改时获得一致且可预测的结果。

答案 1 :(得分:0)

  • 首先,取消注释OnModelCreating方法的主体。这将确保数据库中价格列的精确度。
  • 在种子方法中设置如下值: Price = 0.4277m
  • Price = Convert.ToDecimal(0.4277),个实例