突发奇想,想把业务修改的所有字段原始值和修改后的值,做一个记录,然后发现使用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. 【LeetCode】215. Kth Largest Element in an Array 解题报告(Python & C++)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 方法一:移除最大值 方法二:排序 方法三:大顶堆 方 ...

  2. 从头造轮子:python3 asyncio 之 run(2)

    前言 书接上文,本文造第二个轮子,也是asyncio包里面非常常用的一个函数run 一.知识准备 ● 相对于run_until_complete,改动并不大,就是将入口函数重新封装了一下,基础知识主要 ...

  3. HPU积分赛 2019.8.18

    A题 给出n个数,问这n个数能不能分成奇数个连续的长度为奇数并且首尾均为奇数的序列 Codeforces849A 题解传送门 代码 1 #include <bits/stdc++.h> 2 ...

  4. ELK集中化日志解决方案——看这一篇全搞定

    一.前言 在软件发开技术管理里有两个永恒经典的问题,适合我们初到一家软件企业或一家公司的科技团队,来判断自己该从哪里入手帮助整个团队提升科技水平和产能.问题一是"在我们团队里,只涉及一行代码 ...

  5. electron使用动态配置文件及持久化存储

    1.如何在打包之后,把动态配置文件比如[config.json]放在根目录,不被打包到asar文件中 //解决思路,electron可以拷贝静态资源,比如你把config.json放在项目的根目录下, ...

  6. 使用 JavaScript 的 HTML 页面混合、JavaScript 文件引用和 HTML 代码嵌入 3 种方式在 HTML 页面上打印出“点击我进入到百度首页”的超链接

    查看本章节 查看作业目录 需求说明: 使用 JavaScript 的 HTML 页面混合.JavaScript 文件引用和 HTML 代码嵌入 3 种方式在 HTML 页面上打印出"点击我进 ...

  7. MySQL创建数据库 easyShopping,包括area表、goods表、customer表、orders表、ordersdetall表、test表

    MySQL创建数据库 easyShopping,包括area表.goods表.customer表.orders表.ordersdetall表.test表 商品表表结构: 字段名 说 明 类 型 长 度 ...

  8. js 简单版发布留言 案例

    <!DOCTYPE html>   <html lang="en">   <head>       <meta charset=" ...

  9. python+requests传两种参数体

    在JMeter请求参数中,我们了解到,在做接口测试时,发送请求的参数有两种格式,一种是Parameters,一种是JSON.怎么区分请看 https://www.cnblogs.com/testlea ...

  10. mysql 的 if 和 SQL server 的 iif

    在sql语句中,mysql 使用 if 而SQL server 使用iif 如 mysql : SELECT IF(1<2,'yes ','no'); sql server: SELECT II ...