You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用EFCore.BulkExtensions的BulkInsertOrUpdate正确维护时间字段

解决EFCore.BulkExtensions批量维护CreationTime和LatestUpdate字段的问题

问题分析

你当前的代码里,预先给LatestUpdate赋值为DateTime.Now,再用PropertiesToExcludeOnCompare排除它的比较逻辑,导致只要是更新操作,不管其他业务字段有没有变化,都会把预先设置的当前时间写入LatestUpdate,这不符合“仅其他字段变更时才更新”的需求。

正确实现方案

方案一:数据库层面维护(推荐,性能更优)

直接通过数据库默认值和触发器实现,不需要在代码里做额外配置:

  1. CreationTime配置:
    • 数据库表中CreationTime字段设置默认值为GETDATE()
    • 实体类中标记该字段为[DatabaseGenerated(DatabaseGeneratedOption.Identity)],确保仅插入时生成值,更新时不修改
  2. LatestUpdate配置:
    • 数据库表中LatestUpdate字段设置默认值为GETDATE()
    • 创建UPDATE触发器,当记录的业务字段发生变更时,自动将LatestUpdate更新为当前时间:
      CREATE TRIGGER TR_YourTable_UpdateLatestUpdate
      ON YourTable
      AFTER UPDATE
      AS
      BEGIN
          IF UPDATE(业务字段1) OR UPDATE(业务字段2) -- 替换为实际需要监控的业务字段
          BEGIN
              UPDATE t
              SET t.LatestUpdate = GETDATE()
              FROM YourTable t
              INNER JOIN inserted i ON t.Id = i.Id
          END
      END
      
  3. 代码中只需保留PropertiesToExcludeOnUpdate排除CreationTime即可:
    BulkInsertOrUpdate(Entities, new BulkConfig()
    {
        PropertiesToExcludeOnUpdate = new List<string>()
        {
            nameof(BaseEntity.CreationTime)
        }
    });
    

方案二:纯代码层面配置

如果不想依赖数据库触发器,可以通过EFCore.BulkExtensions的扩展配置实现:

  1. CreationTime配置:和方案一一致,确保仅插入时生成值
  2. LatestUpdate配置:
    • 不要预先给LatestUpdate赋值
    • 通过PropertiesToIncludeOnCompare指定用来判断是否需要更新的业务字段(排除CreationTime和LatestUpdate)
    • 通过UpdateSqlExpression指定更新时动态设置LatestUpdate为当前时间
      示例代码:
    BulkInsertOrUpdate(Entities, new BulkConfig()
    {
        // 仅比较业务字段,判断是否需要更新
        PropertiesToIncludeOnCompare = new List<string>()
        {
            nameof(BaseEntity.Name), // 替换为实际业务字段
            nameof(BaseEntity.Age)
            // 其他业务字段...
        },
        PropertiesToExcludeOnUpdate = new List<string>()
        {
            nameof(BaseEntity.CreationTime)
        },
        // 更新时自动设置LatestUpdate为当前时间(SQL Server语法)
        UpdateSqlExpression = "LatestUpdate = GETDATE()"
    });
    

原理说明

  • PropertiesToIncludeOnCompare会指定哪些字段用来对比判断记录是否需要更新,只有这些字段发生变化时,才会触发更新操作
  • UpdateSqlExpression会在更新操作执行时,动态执行指定的SQL语句设置LatestUpdate,避免预先赋值导致的无意义更新

内容的提问来源于stack exchange,提问作者GIovanni

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 15:32:45