写出易调试的SQL(修订版)

2017-01-06 19:40:05来源:cnblogs.com作者:蒋奎人点击

1.前言

上篇 写出易调试的SQL , 带来了一些讨论, 暴露了不能重用执行计划和sql注入问题, 十分感谢园友们的建议 .

经过调整后 ,将原来的SQLHelper 抓SQL 用做调试环境用, 发布环境还是走Dapper的参数化查询, 保持原有优势.

见如下代码.

2. 在开发调试阶段 抓最终SQL

 将Dapper 查询Query 和执行Execute 进行了再包装, 插入了 抓最终sql 的代码

 public class DapperTaller    {        /// <summary>        /// dapper 执行查询 sql        /// </summary>        /// <typeparam name="T"></typeparam>        /// <param name="sql"></param>        /// <param name="param"></param>        /// <returns></returns>        public static IEnumerable<T> Query<T>(string sql, object param)        {            IEnumerable<T> result = null;            using (var con = DBHelper.GetConnection())            {                result = con.Query<T>(sql, param);            }            //开发环境代码            if (GlobalVariable.env.IsDevelopment()) //IsDevelopment 方法为Asp.NET Core 自带的 是否为开发环境的判断方法            {                //最终SQL                var debugSql = GetDebugSQL(sql, param);                Debug.WriteLine(debugSql);            }            return result;        }        /// <summary>        /// dapper 执行 增加, 删除 ,修改 sql        /// </summary>        /// <param name="sql"></param>        /// <param name="param"></param>        /// <returns></returns>        public static int Execute(string sql, object param)        {            int result;            using (var con = DBHelper.GetConnection())            {                result = con.Execute(sql, param);            }            //开发环境代码            if (GlobalVariable.env.IsDevelopment()) //IsDevelopment 方法为Asp.NET Core 自带的 是否为开发环境的判断方法            {                //最终SQL                var debugSql = GetDebugSQL(sql, param);                Debug.WriteLine(debugSql);            }            //生产环境代码            if (GlobalVariable.env.IsProduction())            {                //根据需要将最终SQL 记录到日志            }            return result;        }        public static string GetDebugSQL(string sql, object param)        {            var sqlHelper = new SqlHelper();            foreach (var item in param.GetType().GetProperties())            {                var name = item.Name;                var value = item.GetValue(param);                sqlHelper.Param.Add(name, value);            }            sqlHelper.ReplaceParam(ref sql);            return sql;        }    }    public class DBHelper    {        public static IDbConnection GetConnection()        {            return SQLServerHelper.GetConnection();        }    }

调用代码:

 public IEnumerable<Ptype> GetPtypeDetail()        {            var sql = @" SELECT     *  FROM dbo.CoacherStudentMoney a INNER JOIN dbo.BaseData b ON a.CourseTypeId=b.Id WHERE  StudentUserId=@StudentUserId AND Amount=@Amount AND IsPay=@IsPay AND CreateDate=@CreateDate ";            var param = new            {                StudentUserId = "001",                CreateDate = DateTime.Now,                Amount = 3,                IsPay = true            };            IEnumerable<Ptype> plist = new List<Ptype>();            plist = DapperTaller.Query<Ptype>(sql, param);            return plist;        }

 

最上面代码的此处为最终SQL 抓取

          //开发环境代码            if (GlobalVariable.env.IsDevelopment())            {                //最终SQL                var debugSql = GetDebugSQL(sql, param);                Debug.WriteLine(debugSql);            }    

并且会在VS 的输出窗口输出

进一步方便了调试.

 

3.最后

现在最终SQL 的抓取发生在 调试开发阶段 .

发布代码后, 将不会进行最终SQL的抓取. 并且走的还是Dapper 原有参数化查询的方式, 依旧拥有执行计划重用, 防SQL注入的优势.

 

注:

完整可执行代码见: https://pan.baidu.com/s/1jI4YcQi    

本文代码是 AnuoApc.Data 项目下的 -> Dapper目录下的 ->  DapperTaller.cs 文件, 可从这里开始看

 

作者: 蒋奎

博客: http://www.cnblogs.com/anuo/

欢迎转载,请在明显位置给出出处及链接

最新文章

123

最新摄影

微信扫一扫

第七城市微信公众平台