突发奇想,想把业务修改的所有字段原始值和修改后的值,做一个记录,然后发现使用EF可以非常简单的实现这个功能

覆盖父类中的 SaveShanges() 方法

        public new int SaveChanges()
{
//是否记录EF变更日志
bool efLogFlag = true;
if (efLogFlag)
{
WriteEFDataLog();
} return base.SaveChanges();
}

获取到EF 数据库上下文中所有的变更条目

因为是测试Demo所以之记录了 Update 操作日志

        /// <summary>
/// EF变更日志
/// </summary>
private void WriteEFDataLog()
{
//获取到EF变更条目
var list = this.ChangeTracker.Entries();
foreach (var item in list)
{
//对应的表名
string tableName = ""; #region 获取表名
Type type = item.Entity.GetType();
Type patientMngAttrType = typeof(TableAttribute);
TableAttribute attribute = null;
if (type.IsDefined(patientMngAttrType, true))
{
attribute = type.GetCustomAttributes(patientMngAttrType, true).FirstOrDefault() as TableAttribute;
if (attribute != null)
{
tableName = attribute.Name;
}
} if (string.IsNullOrEmpty(tableName))
{
tableName = type.Name;
}
#endregion switch (item.State)
{
case EntityState.Detached: break;
case EntityState.Unchanged: break;
case EntityState.Deleted: break;
case EntityState.Modified:
WriteEFUpdateLog(item, tableName);
break;
case EntityState.Added: break;
}
}
}

然后获取到修改字段的原始值,和当前值,组装成自己想要的格式,保存到自定义的地方。

        /// <summary>
/// 记录EF修改操作日志
/// </summary>
/// <param name="entry"></param>
/// <param name="tableName"></param>
private void WriteEFUpdateLog(EntityEntry entry, string tableName)
{
var propertyList = entry.CurrentValues.Properties.Where(i => entry.Property(i.Name).IsModified); PropertyEntry keyEntity = entry.Property("KeyId");
foreach (var prop in propertyList)
{
PropertyEntry entity = entry.Property(prop.Name);
string log = $"用户:{ userName },对表:{ tableName } 进行了修改,原始值:{ entity.OriginalValue },当前值:{ entity.CurrentValue }, 唯一标识:{ keyEntity.CurrentValue }";
WriteLog(log, EntityState.Modified);
}
}

因为是Demo的原因就直接记录到了txt里面

        private void WriteLog(string log, EntityState state)
{
string logPath = AppContext.BaseDirectory + "EFLog.txt";
FileStreamHelper.AppendAllLineText(logPath, $"{ state }: 创建时间:{ DateTime.Now } 日志内容: { log }");
}
    public class FileStreamHelper
{
/// <summary>
/// 向文件的末尾添加文本内容
/// </summary>
/// <param name="path"></param>
/// <param name="textContent"></param>
public static void AppendAllText(string path, string textContent)
{
File.AppendAllText(path, textContent);
} /// <summary>
/// 另起一行在把文本内容追加到后面
/// </summary>
/// <param name="path"></param>
/// <param name="textContent"></param>
public static void AppendAllLineText(string path, string textContent)
{
File.AppendAllText(path, $" \t\n{ textContent }");
}
}

输出:

Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:124e388b-1efb-4a62-b894-0c9aa86524d5
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:00bc43f8-f8ed-48f0-ba38-bc7121d8b87e
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:94f1986b-2f05-464b-a671-17de4b6a3547
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:cf5c2152-3bc7-411f-97e1-6ed6883b77fd
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:a9e58f1d-5ac0-411b-88fd-2636241e810c
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:2446c584-8008-4f82-9b1f-b873f6ffad7e
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:457767ff-6979-4a61-a53b-1dcbae837c59
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:fca224d6-35f6-4d31-9284-41e783ea91ba
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:256e72ee-2bdd-4ebd-a4a1-c70da4c85a23
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:3,当前值:4, 唯一标识:27706c42-ccbd-440c-a0ce-e83dfc1ed988
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:2,当前值:3, 唯一标识:a1f2fcca-9cd8-43fa-964e-0786706fae6b
Modified: 创建时间:2020/6/18 12:59:22 日志内容: 用户:乔安生,对表:Users 进行了修改,原始值:2,当前值:3, 唯一标识:bae8b72e-b5c1-4e7b-98bd-731a9c6d1ab0

在EntityFrameworkCore中记录EF修改日志,保存,修改字段的原始值,当前值,表名等信息的更多相关文章

  1. MVC4数据访问EF查询linq语句的时候报错找不到表名问题

    一天做项目的时候遇到这样的问题,MVC4用EF访问数据查询用linq语句的时候报错找不到表名:报错如下图: 研究了几种情况,最后还是没有找到正真的问题所在,不过可能是和路由解析问题有关,暂时还没有进行 ...

  2. Netty中消除开始的日志消息修改日志级别

    我是使用logback作为日志打印,之前使用slf4j,日志打印不出,就干脆换掉了. 1.首先引入依赖 <dependency> <groupId>ch.qos.logback ...

  3. 在MySQL数据库的表中可以给某个整数类型的字段赋字符串类型的值

  4. Python中内置的日志模块logging用法详解

    logging模块简介 Python的logging模块提供了通用的日志系统,可以方便第三方模块或者是应用使用.这个模块提供不同的日志级别,并可以采用不同的方式记录日志,比如文件,HTTP GET/P ...

  5. 探索ASP.Net Core 3.0系列六:ASP.NET Core 3.0新特性启动信息中的结构化日志

    前言:在本文中,我将聊聊在ASP.NET Core 3.0中细小的变化——启动时记录消息的方式进行小的更改. 现在,ASP.NET Core不再将消息直接记录到控制台,而是正确使用了logging 基 ...

  6. mysql表名忽略大小写问题记录

    问题描述:一开发同事在linux下调一个程序老是报错说找不到表,但是登陆mysql,show tables查看明明是已经创建了这张表的!!如下: mysql> show tables; +--- ...

  7. mysql添加用户、修改权限,修改登录权限ip

    1.添加用户 1.1 登录MYSQL: @>mysql -u root -p @>密码 1.2 创建用户: 格式:grant select on 数据库.* to 用户名@登录主机 ide ...

  8. DateTimeField如何自动设置为当前时间并且能被修改 ——django日期时间字段的使用

    参考于:https://www.cnblogs.com/huchong/p/7895263.html 创建django的model时,有DateTimeField.DateField和TimeFiel ...

  9. django:DateTimeField如何自动设置为当前时间并且能被修改 ——django日期时间字段的使用

    创建django的model时,有DateTimeField.DateField和TimeField三种类型可以用来创建日期字段,其值分别对应着datetime().date().time()三中对象 ...

随机推荐

  1. 阿克曼函数推导过程(m<=3)

    阿克曼函数(Ackermann)是非原始递归函数的例子.它需要两个自然数作为输入值,输出一个自然数.它的输出值增长速度非常快,仅是对于(4,3)的输出已大得不能准确计算. \[A(m, n)=\lef ...

  2. 全网连夜修复的Log4j漏洞,如何做到一行代码都不改?

    GitHub 21.5k Star 的Java工程师成神之路,不来了解一下吗! GitHub 21.5k Star 的Java工程师成神之路,真的不来了解一下吗! Apache Log4j2 远程代码 ...

  3. MADE: Masked Autoencoder for Distribution Estimation

    目录 概 主要内容 代码 Germain M., Gregor K., Murray I. and Larochelle H. MADE: Masked Autoencoder for Distrib ...

  4. Learning a Similarity Metric Discriminatively, with Application to Face Verification

    目录 概 主要内容 genuine 和 impostor 文1 文2 Chopra S, Hadsell R, Lecun Y, et al. Learning a similarity metric ...

  5. 以简御繁介绍IOC

    1.IOC的理论背景 大家开发理念,一直都是奔着架构稳定.低耦合性.而IOC初衷,就是为了解决模块依赖问题,理解<六大设计原则(SOLID)> 如图所示,在我们开发中,业务的实现,就是靠着 ...

  6. 【jvm】02-手写自己的类加载器

    [jvm]02-手写自己的类加载器 欢迎关注b站账号/公众号[六边形战士夏宁],一个要把各项指标拉满的男人.该文章已在github目录收录. 屏幕前的大帅比和大漂亮如果有帮助到你的话请顺手点个赞.加个 ...

  7. Zookeeper集群安装(开启kerberos)

    安装规划 zookeeper集群模式,安装到如下三台机器 10.43.159.237 zdh-237 10.43.159.238 zdh-238 10.43.159.239 zdh-239 Kerbe ...

  8. Jenkins安装、配置与说明

    Jenkins是一个开源的.提供友好操作界面的持续集成(CI)工具,主要用于持续.自动的构建/测试软件项目.监控外部任务的运行. 这么解释很抽象,举个例子,我们开发完一个功能,我们要将项目发布打包好, ...

  9. Linux_无法解析域名

    现象如下:ping baidu.com不通,但是ping 114.114.114.114能通 产生的问题:无法使用 wget下载包 解决方法:增加DNS配置. 注:配置的域名解析地址必须能Ping通.

  10. 服务性能监控之Micrometer详解

    Micrometer 为基于 JVM 的应用程序的性能监测数据收集提供了一个通用的 API,支持多种度量指标类型,这些指标可以用于观察.警报以及对应用程序当前状态做出响应. 通过添加如下依赖可以将 M ...