如何让持久化计算列在EF代码第一?(How to make persisted computed c

2019-07-18 03:02发布

我如何获得类似于数据库中的持久化计算列此列?

我目前的尝试(它加载所有CompCol行与种子空):

    public class Call
    {
        public Call()
        {
        }

        [Key]
        public int Id { get; set; }

        [DatabaseGenerated(DatabaseGeneratedOption.Computed)]
        public string CompCol
        {
            get
            {
                return "ABC-" + Convert.ToString(Id).PadLeft(5, '0');
            }
            protected set {}
        }
}

Answer 1:

我找到的解决方案是:

  1. 确保自动迁移关闭。 这是为了让VS会生成一个脚本(流利API代码)为我们进一步定制,而不是仅仅运行它。 所以在配置类:

     public Configuration() { AutomaticMigrationsEnabled = false; } 
  2. 该字段添加到类,并将其设置为计算像这样,二传手是私有的,因为我们显然不能写入计算字段:

     [DatabaseGenerated(DatabaseGeneratedOption.Computed)] public string BreakdownNo { get; private set; } 
  3. 然后做一个add-migration [xyz-name]在Package Manager控制台来生成迁移代码,将与定名称的迁移文件夹下出现。

  4. 内而外的代码迁移评论Up()和添加自定义的SQL就像这样:

     public override void Up() { //AddColumn("dbo.Calls", "BreakdownNo", c => c.String()); Sql("ALTER TABLE dbo.Calls ADD BreakdownNo AS ('BD'+RIGHT('00000'+ CAST(Id AS VARCHAR), 6))"); } 
  5. 做一个update-database中的PM,它应该适当加计算列。

还注意到 :如果你得到的公式错误,那么你将不得不做一个还原回迁移update-database -targetMigration: [name of migration to go back to]然后做另一个add-migration name并修改您的公式有,整理关与更新数据库。 有可能是一个更好的办法,但这是我发现和使用。

我没找到不过的方式,使该领域仍然存在呢。



Answer 2:

为什么不叫这样的SQL:

public class demo
{
    void demoMethod()
    {
        Model1 model = new Model1();//Model1 : DbContext
        model.Database.ExecuteSqlCommand("alter table Results drop column Total; alter table Results add Total AS (Arabic + English + Math + Science)");
    }
}


Answer 3:

我跑进使用公认的答案提出的方法有些麻烦。 我提供的是为我工作的替代解决方案。

我遇到运行此查询时失败:

oDb.LogEntries.Where(Function(LogEntry) LogEntry.LogTime = dDate).SingleOrDefault

错误信息:

在“LogEntry”的“MinutesOffline”属性不能被设置为“System.Int32”值。 您必须将此属性设置为类型的非空值“System.Single”。

正如我们所看到的,EF 6.2想写一个价值的财产。 这是否是由于内部EF试图写入到Private Set ,我不知道。 它似乎像它。 但最终的结果是最重要的:语句失败。

相反,列设置为的DatabaseGeneratedOption.Computed ,最后我干脆忽略它: Builder.Entity(Of LogEntry).Ignore(Function(LogEntry) LogEntry.MinutesOffline)

这使我能够建立一个只读属性:

Public ReadOnly Property MinutesOffline As Single
  Get
    Return IIf(Me.Scale < 1, 5, 0)
  End Get
End Property

它也有,我们不必注释掉产生迁移任何线的好处。

我们仍然必须自定义Sql()的调用Up()

ALTER TABLE [LogEntries] ADD [MinutesOffline] AS (IIF([Scale] < 1, 5, 0)) PERSISTED

...和PERSISTED关键字不会在这里工作。 这将成为一个持久化计算列。

因人而异



文章来源: How to make persisted computed column in EF code first?