c# 操作mysql的帮助类

MySqlHelper 的静态类,其中包含了一些用于执行 MySQL 数据库操作的方法。这些方法包括执行存储过程、插入、更新、删除操作以及执行数据库事务查询操作等。

该类中的方法主要有:

  1. ExecuteNonQuery 方法:用于执行存储过程、插入、更新、删除操作,并返回受影响的行数。
  2. ExecuteScalar 方法:执行数据库事务查询操作或普通查询操作,返回结果集中位于第一行第一列的值。
  3. PrepareCommand 方法:执行数据库命令前的准备工作,设置命令对象的属性和参数。
  4. ToObject 方法:将 MySqlDataReader 转换为指定类型的对象。
  5. 其他辅助方法:用于处理参数、设置属性值、转换值等。

这些方法使用了异步编程模型 async/await,并且在执行数据库操作后进行了相应的资源释放,以确保数据库连接得到正确关闭。

复制代码
using MySql.Data.MySqlClient;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Reflection;
using System.Threading.Tasks;

namespace MSEBP.Kernel.DataCommon.DBHelper
{
    /// <summary>
    /// MySql数据库操作类
    /// </summary>
    public static class MySqlHelper
    {
        private static string _connectionString = MSEApplication.GetConfigValue("ConnectionStrings:ReadConn");

        /// <summary>
        /// 用于执行存储过程、插入、更新、删除
        /// </summary>
        /// <param name="cmdType"></param>
        /// <param name="cmdText"></param>
        /// <param name="cmdParms"></param>
        /// <returns></returns>
        public static async Task<int> ExecuteNonQuery(CommandType cmdType, string cmdText, object cmdParms)
        {
            using (MySqlConnection conn = new MySqlConnection(_connectionString))
            {
                using (MySqlCommand cmd = conn.CreateCommand())
                {
                    try
                    {
                        PrepareCommand(cmd, conn, null, cmdType, cmdText, cmdParms);
                        int result = cmd.ExecuteNonQuery();
                        cmd.Parameters.Clear();
                        return await Task.FromResult(result);
                    }
                    catch (Exception ex)
                    {
                        throw ex;
                    }
                    finally
                    {
                        if (conn.State == ConnectionState.Open)
                        {
                            conn.Close();
                        }
                    }
                }
            }
        }

        /// <summary>
        /// 执行数据库事务查询操作,返回结果集中位于第一行第一列的Object类型的值
        /// </summary>
        /// <param name="trans">一个已存在的数据库事务对象</param>
        /// <param name="cmdType">命令类型</param>
        /// <param name="cmdText">MySql存储过程名称或PL/SQL命令</param>
        /// <param name="cmdParms">命令参数集合</param>
        /// <returns>当前事务查询操作返回的结果集中位于第一行第一列的Object类型的值</returns>
        public static async Task<T> ExecuteScalar<T>(MySqlTransaction trans, CommandType cmdType, string cmdText, object cmdParms)
        {
            MySqlConnection conn;
            if (trans != null)
            {
                conn = trans.Connection;
                if (conn == null)
                    throw new ArgumentException("当前事务所在的数据库连接不存在");
            }
            else
            {
                conn = new MySqlConnection(_connectionString);
            }
            using (MySqlCommand cmd = conn.CreateCommand())
            {
                try
                {
                    object result = null;
                    PrepareCommand(cmd, conn, trans, cmdType, cmdText, cmdParms);
                    result = cmd.ExecuteScalar();
                    cmd.Parameters.Clear();
                    return await Task.FromResult(ConvertTo<T>(result));
                }
                catch (Exception ex)
                {
                    throw ex;
                }
                finally
                {
                    if (trans == null)
                    {
                        if (conn.State == ConnectionState.Open)
                        {
                            conn.Close();
                        }
                    }
                }
            }
        }

        /// <summary>
        /// 执行数据库查询操作,返回结果集中位于第一行第一列的Object类型的值
        /// </summary>
        /// <param name="cmdType">Command类型</param>
        /// <param name="cmdText">MySql存储过程名称或PL/SQL命令</param>
        /// <param name="cmdParms">命令参数集合</param>
        /// <returns>当前查询操作返回的结果集中位于第一行第一列的Object类型的值</returns>
        public static async Task<T> ExecuteScalar<T>(CommandType cmdType, string cmdText, object cmdParms)
        {
            using (MySqlConnection conn = new MySqlConnection(_connectionString))
            {
                using (MySqlCommand cmd = conn.CreateCommand())
                {
                    try
                    {
                        object result = null;
                        PrepareCommand(cmd, conn, null, cmdType, cmdText, cmdParms);
                        result = cmd.ExecuteScalar();
                        cmd.Parameters.Clear();
                        return await Task.FromResult(ConvertTo<T>(result));
                    }
                    catch (Exception ex)
                    {
                        throw ex;
                    }
                    finally
                    {
                        if (conn.State == ConnectionState.Open)
                        {
                            conn.Close();
                        }
                    }
                }
            }
        }



        /// <summary>
        /// 执行数据库命令前的准备工作
        /// </summary>
        /// <param name="cmd">Command对象</param>
        /// <param name="conn">数据库连接对象</param>
        /// <param name="trans">事务对象</param>
        /// <param name="cmdType">Command类型</param>
        /// <param name="cmdText">MySql存储过程名称或PL/SQL命令</param>
        /// <param name="cmdParms">命令参数集合</param>
        private static void PrepareCommand(MySqlCommand cmd, MySqlConnection conn, MySqlTransaction trans, CommandType cmdType, string cmdText, object cmdParms)
        {
            if (conn?.State != ConnectionState.Open)
                conn.Open();

            cmd.Connection = conn;
            cmd.CommandText = cmdText;

            if (trans != null)
                cmd.Transaction = trans;

            cmd.CommandType = cmdType;
            cmd.CommandTimeout = 60 * 2;

            if (cmdParms != null)
            {
                if (cmdParms is IDictionary<string, object> dict)
                {
                    foreach (var item in dict)
                    {
                        cmd.Parameters.AddWithValue($"@{item.Key}", item.Value ?? DBNull.Value);
                    }
                }
                else
                {
                    PropertyInfo[] properties = cmdParms.GetType().GetProperties();
                    foreach (PropertyInfo property in properties)
                    {
                        object value = property.GetValue(cmdParms);
                        cmd.Parameters.AddWithValue($"@{property.Name}", value ?? DBNull.Value);
                    }
                }
            }
        }





        /// <summary>
        /// 
        /// </summary>
        /// <param name="cmdParms"></param>
        /// <returns></returns>
        private static IEnumerable<MySqlParameter> GetParameters(object cmdParms)
        {
            if (cmdParms is null)
                yield break;

            if (cmdParms is IDictionary<string, object> dict)
            {
                foreach (var item in dict)
                {
                    yield return new MySqlParameter($"@{item.Key}", item.Value ?? DBNull.Value);
                }
            }
            else
            {
                var properties = cmdParms.GetType().GetProperties();
                foreach (var property in properties)
                {
                    var value = property.GetValue(cmdParms);
                    yield return new MySqlParameter($"@{property.Name}", value ?? DBNull.Value);
                }
            }
        }

        /// <summary>
        ///  reader转成类型数据
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="reader"></param>
        /// <returns></returns>
        public static T ToObject<T>(this MySqlDataReader reader)
        {
            if (!reader.HasRows)
                return default(T);

            Type type = typeof(T);
            if (type.IsPrimitive || type == typeof(string) || type == typeof(decimal) || type == typeof(DateTime) || type == typeof(Guid) || type.IsEnum || type.IsArray)
            {
                reader.Read(); // 移动到第一行
                object value = reader.GetValue(0);
                return value == DBNull.Value ? default(T) : ConvertTo<T>(value);
            }

            int columnCount = reader.FieldCount;
            var properties = type.GetProperties().Where(p => p.CanWrite);
            T obj = (T)Activator.CreateInstance(type);
            if (reader.Read()) // 读取第一行数据
            {
                foreach (var property in properties)
                {
                    int columnIndex = Enumerable.Range(0, columnCount)
                        .FirstOrDefault(i => string.Compare(reader.GetName(i), property.Name,
                        StringComparison.OrdinalIgnoreCase) == 0);
                    if (columnIndex >= 0)
                    {
                        object value = reader.IsDBNull(columnIndex) ? null : reader.GetValue(columnIndex);
                        if (value != DBNull.Value)
                        {
                            if (property.PropertyType.IsEnum)
                            {
                                value = Enum.Parse(property.PropertyType, value.ToString());
                            }
                            else
                            {
                                value = ConvertValue(value, property.PropertyType);
                            }
                            SetProperty(property, value, obj);
                        }
                    }
                }
            }
            reader.Dispose();
            reader.Close();
            return obj;
        }

        /// <summary>
        /// 设置值
        /// </summary>
        /// <param name="property"></param>
        /// <param name="value"></param>
        /// <param name="obj"></param>
        private static void SetProperty(PropertyInfo property, object value, object obj)
        {
            if (value == null) return;

            if (property.PropertyType == typeof(Guid))
            {
                value = Guid.Parse(value.ToString());
            }
            else if (property.PropertyType.IsGenericType && property.PropertyType.GetGenericTypeDefinition() == typeof(Nullable<>))
            {
                Type underlyingType = Nullable.GetUnderlyingType(property.PropertyType);
                value = Convert.ChangeType(value, underlyingType);
            }
            else
            {
                value = Convert.ChangeType(value, property.PropertyType);
            }

            property.SetValue(obj, value, null);
        }

        /// <summary>
        /// 转换值
        /// </summary>
        /// <param name="value"></param>
        /// <param name="type"></param>
        /// <returns></returns>
        private static object ConvertValue(object value, Type type)
        {
            if (type == typeof(Guid))
            {
                return Guid.Parse(value.ToString());
            }
            if (type.IsGenericType && type.GetGenericTypeDefinition() == typeof(Nullable<>))
            {
                Type underlyingType = Nullable.GetUnderlyingType(type);
                if (value == null)
                {
                    return null;
                }
                else
                {
                    return Convert.ChangeType(value, underlyingType);
                }
            }
            return Convert.ChangeType(value, type);
        }

        /// <summary>
        /// 单值数据类型转换
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="value"></param>
        /// <returns></returns>
        private static T ConvertTo<T>(object value)
        {
            if (value == null || value == DBNull.Value)
            {
                return default(T);
            }
            Type targetType = typeof(T);
            if (targetType == typeof(Guid))
            {
                return (T)(object)Guid.Parse(value.ToString());
            }
            if (targetType.IsGenericType && targetType.GetGenericTypeDefinition() == typeof(Nullable<>))
            {
                targetType = Nullable.GetUnderlyingType(targetType);
            }
            return (T)Convert.ChangeType(value, targetType);
        }

    }
}
相关推荐
csbysj202027 分钟前
如何使用 XML Schema
开发语言
R6bandito_33 分钟前
STM32中printf的重定向详解
开发语言·经验分享·stm32·单片机·嵌入式硬件·mcu
earthzhang202140 分钟前
【1007】计算(a+b)×c的值
c语言·开发语言·数据结构·算法·青少年编程
杨枝甘露小码1 小时前
Python学习之基础篇
开发语言·python
武文斌771 小时前
项目学习总结:LVGL图形参数动态变化、开发板的GDB调试、sqlite3移植、MQTT协议、心跳包
linux·开发语言·网络·arm开发·数据库·嵌入式硬件·学习
爱吃喵的鲤鱼1 小时前
仿mudou——Connection模块(连接管理)
linux·运维·服务器·开发语言·网络·c++
beyond谚语1 小时前
C#学习小笔记(完整版)—— Patience
c#
爱吃小胖橘2 小时前
Unity网络开发--超文本传输协议Http(1)
开发语言·网络·网络协议·http·c#·游戏引擎
郝学胜-神的一滴2 小时前
使用Linux的read和write系统函数操作文件
linux·服务器·开发语言·数据库·c++·程序人生·软件工程
小火柴1232 小时前
利用R语言绘制直方图
开发语言·r语言