ibms-dome/Repository/BaseRepository/Implement/BaseRepository.cs

893 lines
30 KiB
C#
Raw Normal View History

2022-10-14 16:08:54 +08:00
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Dapper;
using Repository.Helper;
using Repository.Models;
using Repository.BaseRepository.Interface;
using System.Reflection;
using System.Data;
using System.Text;
using System.Data.SqlClient;
using MySql.Data.MySqlClient;
using Repository.Services.Implement;
namespace Repository.BaseRepository.Implement
{
public class BaseRepository : IBaseRepository
{
protected readonly IDatabaseHelper _databaseHelper;
protected string UseDB;
protected IDbConnection con;
private BackgroundService backgroundService;
//排除要加入至派送的資料表
private List<string> exclude_data_delivery = new List<string>()
{
"background_service_message_notification_task",
"background_service_message_notification_task_log",
"background_service_plan",
"background_service_task",
"background_service_task_log",
"device_import_temp",
"device_import_ckeck_temp",
"operation_back_log",
"operation_log",
"task_detail",
"api_earthquake",
"api_rain",
"api_sync",
"api_typhoon",
"api_weateher",
"archive_electric_meter_day",
"archive_electric_meter_hour",
"archive_electric_meter_month",
"archive_electric_meter_week"
};
public BaseRepository(IDatabaseHelper databaseHelper)
{
this._databaseHelper = databaseHelper;
}
public IDbConnection GetDbConnection()
{
IDbConnection conn;
if (UseDB == "MSSQL")
{
conn = new SqlConnection(this._databaseHelper.GetMSSqlConnectionString());
}
else
{
conn = new MySqlConnection(this._databaseHelper.GetMySqlConnectionString());
}
return conn;
}
public string InsertGenerateString(List<string> properties, string table_name)
{
var insertQuery = new StringBuilder($"INSERT INTO {table_name} ");
insertQuery.Append("(");
properties.ForEach(prop => { insertQuery.Append($"{table_name}.{prop.Replace("@", "")},"); });
insertQuery
.Remove(insertQuery.Length - 1, 1)
.Append(") VALUES (");
properties.ForEach(prop => { insertQuery.Append($"{prop},"); });
insertQuery
.Remove(insertQuery.Length - 1, 1)
.Append(");");
return insertQuery.ToString();
}
public string UpdateGenerateString(List<string> properties, string table_name, string sWhere)
{
var updateQuery = new StringBuilder($"UPDATE {table_name} SET ");
properties.ForEach(property =>
{
if (property.Contains("@"))
{
updateQuery.Append($"{property.Replace("@", "")}={property},");
}
});
updateQuery.Remove(updateQuery.Length - 1, 1); //remove last comma
updateQuery.Append($" WHERE {sWhere}");
return updateQuery.ToString();
}
#region GetAll
/// <summary>
/// 取得所有資料(根據條件以及排序)
/// </summary>
/// <typeparam name="A"></typeparam>
/// <param name="tableName"></param>
/// <param name="sWhere"></param>
/// <param name="param">Ex: new { status = 1}</param>
/// <returns></returns>
public virtual async Task<List<A>> GetAllAsync<A>(string tableName, string sWhere, object param = null, string sOrderBy = "")
{
List<A> result;
using (IDbConnection conn = GetDbConnection())
{
try
{
var sql = $"SELECT * FROM {tableName}";
if (!string.IsNullOrEmpty(sWhere))
{
sql += $" WHERE {sWhere}";
}
if (!string.IsNullOrEmpty(sOrderBy))
{
sql += $" ORDER BY {sOrderBy}";
}
result = (await conn.QueryAsync<A>(sql, param)).ToList();
}
catch (Exception exception)
{
throw exception;
}
return result;
}
}
/// <summary>
/// 根據SQL語句抓取整包資料
/// </summary>
/// <typeparam name="A"></typeparam>
/// <param name="sqlString"></param>
/// <returns></returns>
public virtual async Task<List<A>> GetAllAsync<A>(string sqlString, object param = null)
{
List<A> result;
using (IDbConnection conn = GetDbConnection())
{
try
{
var sql = sqlString;
result = (await conn.QueryAsync<A>(sql, param)).ToList();
}
catch (Exception exception)
{
throw exception;
}
return result;
}
}
/// <summary>
/// 取得多筆資料的某個欄位變成列表
/// </summary>
/// <param name="guid">流水號</param>
/// <param name="table_name">資料表名稱</param>
/// <param name="idName">指定欄位名稱的流水號</param>
/// <param name="selCol">選擇陣列資料庫欄位名稱</param>
/// <returns></returns>
public virtual async Task<List<object>> GetAllWithCustomDBNameAndTableAsync(string guid, string table_name, string idName, string selCol)
{
List<object> result;
using (IDbConnection conn = GetDbConnection())
{
try
{
var sql = $"SELECT {selCol} FROM {table_name} WHERE {idName} = @Guid";
result = (await conn.QueryAsync<object>(sql, new { Guid = guid })).ToList();
}
catch (Exception exception)
{
throw exception;
}
return result;
}
}
#endregion GetAll
#region GetOne
/// <summary>
/// 取得單一筆資料(排序)
/// </summary>
/// <typeparam name="A"></typeparam>
/// <param name="tableName"></param>
/// <param name="sWhere"></param>
/// <param name="param">參數值</param>
/// <param name="sOrderBy"></param>
/// <returns></returns>
public virtual async Task<A> GetOneAsync<A>(string tableName, string sWhere, object param = null, string sOrderBy = "")
{
A result;
using (IDbConnection conn = GetDbConnection())
{
try
{
var sql = $"SELECT * FROM {tableName}";
if (!string.IsNullOrEmpty(sWhere))
{
sql += $" WHERE {sWhere}";
}
if (!string.IsNullOrEmpty(sOrderBy))
{
sql += $" ORDER BY {sOrderBy}";
}
result = await conn.QueryFirstOrDefaultAsync<A>(sql, param);
}
catch (Exception exception)
{
throw exception;
}
return result;
}
}
/// <summary>
/// 取得單一筆資料某一欄位(排序)
/// </summary>
/// <param name="tableName"></param>
/// <param name="sWhere"></param>
/// <param name="selCol">填放欄位</param>
/// <param name="param">參數值</param>
/// <param name="sOrderBy"></param>
/// <returns></returns>
public virtual async Task<object> GetOneAsync(string tableName, string sWhere, string selCol, object param = null, string sOrderBy = "")
{
object result;
using (IDbConnection conn = GetDbConnection())
{
try
{
var sql = $"SELECT {selCol} FROM {tableName}";
if (!string.IsNullOrEmpty(sWhere))
{
sql += $" WHERE {sWhere}";
}
if (!string.IsNullOrEmpty(sOrderBy))
{
sql += $" ORDER BY {sOrderBy}";
}
result = await conn.QueryFirstOrDefaultAsync<object>(sql, param);
}
catch (Exception exception)
{
throw exception;
}
return result;
}
}
/// <summary>
/// 取得單一筆資料(根據自訂SQL, 自訂參數)
/// </summary>
/// <param name="sqlString"></param>
/// <param name="param"></param>
/// <returns></returns>
public virtual async Task<A> GetOneAsync<A>(string sqlString, object param = null)
{
A result;
using (IDbConnection conn = GetDbConnection())
{
try
{
var sql = sqlString;
result = await conn.QueryFirstOrDefaultAsync<A>(sql, param);
}
catch (Exception exception)
{
throw exception;
}
return result;
}
}
#endregion GetOne
#region DeleteOne ()
/// <summary>
/// 透過guid軟刪除單一筆資料
/// UPDATE {tableName} SET deleted = 1 WHERE {idName} = @Guid
/// </summary>
/// <param name="guid"></param>
/// <returns></returns>
public virtual async Task DeleteOne(string guid, string tableName, string idName)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
var sql = $"UPDATE {tableName} SET deleted = 1 WHERE {idName} = @Guid";
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(tableName))
{
Dictionary<string, object> dict = new Dictionary<string, object>()
{
{ idName, guid},
{ "@deleted", 1},
};
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", tableName, "delete", dict, null, guid);
}
await conn.ExecuteAsync(sql, new { Guid = guid }, trans);
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
/// <summary>
/// 透過guid、db_name、table_name刪除指定的資料庫之資料表的一筆資料
/// </summary>
/// <param name="guid"></param>
/// <param name="db_name"></param>
/// <param name="table_name"></param>
/// <returns></returns>
public virtual async Task DeleteOneByGuidWithCustomDBNameAndTable(string guid, string db_name, string table_name, string idName)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
var sql = $"UPDATE {db_name}.{table_name} SET Deleted = 1 WHERE {idName} = @Guid";
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(table_name))
{
Dictionary<string, object> dict = new Dictionary<string, object>()
{
{ idName, guid},
{ "@deleted", 1},
};
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", $"{db_name}.{table_name}", "delete", dict, null, guid);
}
await conn.ExecuteAsync(sql, new { Guid = guid }, trans);
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
#endregion DeleteOne ()
#region PurgeOne ()
/// <summary>
/// 根據Where條件進行刪除
/// </summary>
/// <param name="table_name"></param>
/// <param name="sWhere"></param>
/// <returns></returns>
public virtual async Task PurgeOneByGuidWithCustomDBNameAndTable(string table_name, string sWhere)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
var sql = $"DELETE FROM {table_name} WHERE {sWhere}";
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(table_name))
{
Dictionary<string, object> dict = new Dictionary<string, object>();
//判斷是否有and的情況
var swhere_splits_and = sWhere.Split("and");
foreach (var sWhere_and in swhere_splits_and)
{
var swhere_split = sWhere_and.Split('=');
if (swhere_split.Length > 0)
{
dict.Add(swhere_split[0].Trim(), swhere_split[1].Replace("'", "").Trim());
}
}
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", table_name, "purge", dict);
}
await conn.ExecuteAsync(sql, null, trans);
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
/// <summary>
/// 指定單一欄位,實際刪除單一筆資料
/// </summary>
/// <param name="guid"></param>
/// <param name="table_name"></param>
/// <param name="idName"></param>
/// <returns></returns>
public virtual async Task PurgeOneAsync(string guid, string table_name, string idName)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
var sql = $"DELETE FROM {table_name} WHERE {idName} = @Guid";
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(table_name))
{
Dictionary<string, object> dict = new Dictionary<string, object>()
{
{ idName, guid},
};
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", table_name, "purge", dict, null, guid);
}
await conn.ExecuteAsync(sql, new { Guid = guid }, trans);
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
#endregion PurgeOne ()
#region AddMuti
/// <summary>
/// 新增Table多筆資料
/// </summary>
/// <param name="dict"></param>
/// <param name="Table_name"></param>
/// <returns></returns>
public async Task AddMutiByCustomTable(List<Dictionary<string, object>> dict, string Table_name)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
List<string> properties = dict[0].Keys.ToList();
string sql = InsertGenerateString(properties, Table_name);
await conn.ExecuteAsync(sql, dict, trans);
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(Table_name))
{
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", Table_name, "insert_list", dict);
}
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
#endregion AddMuti
#region AddOne
/// <summary>
/// 新增table一筆資料
/// </summary>
/// <param name="dict">新增資料庫名稱以及值</param>
/// <param name="Table_name">資料表名稱</param>
/// <returns></returns>
public async Task AddOneByCustomTable(Dictionary<string, object> dict, string Table_name)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
List<string> properties = dict.Keys.ToList();
string sql = InsertGenerateString(properties, Table_name);
await conn.ExecuteAsync(sql, dict, trans);
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(Table_name))
{
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", Table_name, "insert", dict);
}
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
#endregion AddOne
#region UpdateOne
/// <summary>
/// 更新Table一筆資料
/// </summary>
/// <param name="dict">更新資料庫名稱以及值</param>
/// <param name="Table_name">資料表名稱</param>
/// <param name="sWhere">Where條件</param>
/// <returns></returns>
public async Task UpdateOneByCustomTable(Dictionary<string, object> dict, string Table_name, string sWhere)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
List<string> properties = dict.Keys.ToList();
string sql = UpdateGenerateString(properties, Table_name, sWhere);
await conn.ExecuteAsync(sql, dict, trans);
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(Table_name))
{
//判斷是否有and的情況
var swhere_splits_and = sWhere.Split("and");
foreach(var sWhere_and in swhere_splits_and)
{
var swhere_split = sWhere_and.Split('=');
if (swhere_split.Length > 0)
{
dict.Add(swhere_split[0].Trim(), swhere_split[1].Replace("'", "").Trim());
}
}
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", Table_name, "update", dict);
}
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
#endregion UpdateOne
#region UpdateList
/// <summary>
/// 更新Table多筆筆資料
/// </summary>
/// <param name="dict">更新資料庫名稱以及值</param>
/// <param name="Table_name">資料表名稱</param>
/// <param name="sWhere">Where條件</param>
/// <returns></returns>
public async Task UpdateListByCustomTable(List<Dictionary<string, object>> dicts, string Table_name, string sWhere)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
List<string> properties = dicts.First().Keys.ToList();
string sql = UpdateGenerateString(properties, Table_name, sWhere);
await conn.ExecuteAsync(sql, dicts, trans);
if (UseDB == "MSSQL" && !exclude_data_delivery.Contains(Table_name))
{
backgroundService = new BackgroundService(conn, trans);
await backgroundService.AddTask("", "", Table_name, "update_list", dicts);
}
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
}
#endregion UpdateList
/// <summary>
/// 取資料庫當前流水號
/// </summary>
/// <param name="Table_name"></param>
/// <param name="where"></param>
/// <returns></returns>
public async Task<string> GetCurrentSerialNumber(string Table_name, string where = "")
{
string Num;
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
try
{
var sql = @$"SELECT SerialNumber FROM {Table_name}";
if (!string.IsNullOrEmpty(where))
{
sql += $" WHERE {where}";
}
sql += " ORDER BY SerialNumber DESC";
Num = await conn.QueryFirstOrDefaultAsync<string>(sql);
}
catch (Exception exception)
{
throw exception;
}
finally
{
conn.Close();
}
}
return Num;
}
/// <summary>
/// 取資料表當前優先序
/// <para>SELECT Priority FROM {Table_name} WHERE {where} ORDER BY Priority DESC</para>
/// </summary>
/// <param name="Table_name"></param>
/// <param name="where"></param>
/// <returns></returns>
public async Task<int> GetCurrentPriority(string Table_name, string where = "")
{
int Num = 0;
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
try
{
var sql = @$"SELECT Priority FROM {Table_name}";
if (!string.IsNullOrEmpty(where))
{
sql += $" WHERE {where}";
}
sql += " ORDER BY Priority DESC";
Num = await conn.QueryFirstOrDefaultAsync<int>(sql);
}
catch (Exception exception)
{
throw exception;
}
finally
{
conn.Close();
}
}
return Num;
}
/// <summary>
/// 透過id來搜尋此筆資料是否存在
/// </summary>
/// <param name="id">id值</param>
/// <param name="Table_name">table名稱</param>
/// <param name="id_name">id名稱</param>
/// <returns></returns>
public async Task<Boolean> HasExistsWithGuid(string guid, string Table_name, string id_name)
{
using (IDbConnection conn = GetDbConnection())
{
Boolean hasExists = false;
conn.Open();
try
{
var sql = $"SELECT * FROM {Table_name} WHERE {id_name} = @Guid";
var result = await conn.QueryFirstOrDefaultAsync<string>(sql, new { Guid = guid });
if (result != null)
{
hasExists = true;
}
}
catch (Exception exception)
{
throw exception;
}
finally
{
conn.Close();
}
return hasExists;
}
}
/// <summary>
/// 根據SQL條件搜尋此筆資料是否存在
/// </summary>
/// <param name="sql"></param>
/// <returns></returns>
public async Task<Boolean> HasExistsWithParam(string sql, object param = null)
{
using (IDbConnection conn = GetDbConnection())
{
Boolean hasExists = false;
conn.Open();
try
{
var result = await conn.QueryFirstOrDefaultAsync<object>(sql, param);
if (result != null)
{
hasExists = true;
}
}
catch (Exception exception)
{
throw exception;
}
finally
{
conn.Close();
}
return hasExists;
}
}
/// <summary>
/// 直接執行SQL語句
/// </summary>
/// <param name="sql"></param>
/// <param name="param"></param>
/// <returns></returns>
public async Task ExecuteSql(string sql, object param = null)
{
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
try
{
var result = await conn.ExecuteAsync(sql, param);
}
catch (Exception exception)
{
throw exception;
}
finally
{
conn.Close();
}
}
}
#region AddOneReturnId
/// <summary>
/// 新增table一筆資料
/// </summary>
/// <param name="dict">新增資料庫名稱以及值</param>
/// <param name="Table_name">資料表名稱</param>
/// <returns></returns>
public async Task<int> AddOneByCustomTableReturnId(Dictionary<string, object> dict, string Table_name, bool returnId = true)
{
var id = 0;
using (IDbConnection conn = GetDbConnection())
{
conn.Open();
using (var trans = conn.BeginTransaction())
{
try
{
List<string> properties = dict.Keys.ToList();
string sql = InsertGenerateString(properties, Table_name);
if (returnId)
{
sql += " SELECT LAST_INSERT_ID()";
2022-10-14 16:08:54 +08:00
}
id = await conn.QueryFirstOrDefaultAsync<int>(sql, dict, trans);
//await conn.ExecuteAsync(sql, dict, trans);
trans.Commit();
}
catch (Exception exception)
{
trans.Rollback();
throw exception;
}
finally
{
conn.Close();
}
}
}
return id;
}
#endregion AddOneReturnId
}
}