如何生成我的所有实体通过T4自动化为每个实体组成两个表

yle*_*are 18 .net c# t4 linq-to-entities entity-framework

我有一个使用Entity Framework 4的数据访问层的类库项目.我的项目需要一个版本控制概念.我的数据库包含许多包含«Id»和«CreationDateTime»的表.每个表都与包含详细信息的版本表相关联.所有表格都以相同的方式构造,并以版本表的"版本"为后缀.

我通过T4自动化搜索生成所有实体(EF4模型)的方法,该自动化将统一表和TableVersion(针对指定版本)放在一个实体中.

此统一实体必须支持获取,插入,更新和删除操作.

是否可以通过修改其中一个T4模板来完成?如果是的话,怎么样?

非常感谢任何指针.

Gor*_*vic 1

可能不是您正在寻找的内容,但您可以查看这篇博客文章,其中我为日志/版本控制数据库做了类似的概念证明。我没有使用 T4(这就是为什么我认为这可能不是您正在寻找的,但您可能找不到更好的解决方案)和生成的实体,而是从具有版本控制属性的一个基本实体继承了所有实体。基本上,我通过重写 SaveChanges 方法来扩展 DbContext,并在那里设置我的版本控制属性:

foreach (var entry in this.ChangeTracker.Entries())
    {
        // Make sure that this customized save changes executes only for entities that
        // inherit from our base entity (IEntity)
        var entity = (entry.Entity as JEntity);
        if (entity == null) continue;
 
        switch (entry.State)
        {
            // In case entity is added, we need to set OriginalId AFTER it was saved to
            // database, as Id is generated by database and cannot be known in advance.
            // That is why we save reference to this object into insertedList and update
            // original id after object was saved.
            case System.Data.EntityState.Added:
                entity.UserCreated = user;
                entity.DateCreated = now;
                insertedList.Add(entity);
                break;
 
            // Deleted entity should only be marked as deleted.
            case System.Data.EntityState.Deleted:
                if (!entity.IsActive(now))
                {
                    invalidList.Add(entity);
                    continue;
                }
                entry.Reload();
                entity.DateDeleted = now;
                entity.UserDeleted = user;
                break;
 
            case System.Data.EntityState.Detached:
                break;
 
            case System.Data.EntityState.Modified:
                if (!entity.IsActive(now))
                {
                    invalidList.Add(entity);
                    continue;
                }
                entity.UserCreated = user;
                entity.DateCreated = now;
 
                JEntity newVersion = this.Set(entity.GetType()).Create(entity.GetType()) as JEntity;
                newVersion = this.Set(entity.GetType()).Add(newVersion) as JEntity;
                this.Entry(newVersion).CurrentValues.SetValues(entity);
 
                this.Entry(entity).Reload();
 
                entity.DateDeleted = newVersion.DateCreated;
                entity.UserDeleted = user;
                break;
            case System.Data.EntityState.Unchanged:
                break;
            default:
                break;
        }
    }
Run Code Online (Sandbox Code Playgroud)

文章中提供了 github 上完整源代码的链接。

该解决方案对当前和过去版本的实体使用相同的表,我计划通过尝试将实体的所有“已删除”版本放入单独的表中来改进这个概念,该表在 DbContext 上是私有的,并且所有用于传输的逻辑历史记录中的项目将在保存更改时进行。这种方式将允许公开的公共数据库集仅包含项目的当前版本,从而允许在此类上下文之上构建任何类似动态数据的通用解决方案。