You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

159 lines
6.5 KiB
C#

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using EntrustSettle.Common;
using EntrustSettle.Common.Caches;
using EntrustSettle.Common.DB;
using EntrustSettle.Common.DB.Aop;
using EntrustSettle.Model;
using Microsoft.Extensions.DependencyInjection;
using SqlSugar;
using System;
using System.Linq;
using System.Text.RegularExpressions;
using Yitter.IdGenerator;
namespace EntrustSettle.Extensions
{
/// <summary>
/// SqlSugar 启动服务
/// </summary>
public static class SqlsugarSetup
{
public static void AddSqlsugarSetup(this IServiceCollection services)
{
if (services == null) throw new ArgumentNullException(nameof(services));
// 使用自定义的雪花Id算法程序启动时执行一次就行
StaticConfig.CustomSnowFlakeFunc = YitIdHelper.NextId;
// 默认添加主数据库连接
if (!AppSettings.app("MainDB").IsNullOrEmpty())
{
DBConst.MainDbConfigId = AppSettings.app("MainDB");
}
BaseDBConfig.MutiConnectionString.allDbs.ForEach(m =>
{
var config = new ConnectionConfig()
{
ConfigId = m.ConnId.ObjToString().ToLower(),
ConnectionString = m.Connection,
DbType = (DbType)m.DbType,
IsAutoCloseConnection = true,
// Check out more information: https://github.com/anjoy8/EntrustSettle/issues/122
//IsShardSameThread = false,
MoreSettings = new ConnMoreSettings()
{
//IsWithNoLockQuery = true,
IsAutoRemoveDataCache = true,
SqlServerCodeFirstNvarchar = true,
},
// 从库
SlaveConnectionConfigs = m.Slaves?.Where(s => s.HitRate > 0).Select(s => new SlaveConnectionConfig
{
ConnectionString = s.Connection,
HitRate = s.HitRate
}).ToList(),
// 自定义特性
ConfigureExternalServices = new ConfigureExternalServices()
{
DataInfoCacheService = new SqlSugarCacheService(),
EntityService = (property, column) =>
{
if (column.IsPrimarykey && property.PropertyType == typeof(int))
{
column.IsIdentity = true;
}
// 为long?/Datetime?等可为Null的类型以及String统一设置IsNullable=true
if (column.IsPrimarykey == false &&
(column.PropertyInfo.PropertyType == typeof(string) || Nullable.GetUnderlyingType(column.PropertyInfo.PropertyType) != null))
{
column.IsNullable = true;
}
}
},
InitKeyType = InitKeyType.Attribute
};
if (DBConst.LogDbConfigId.ToLower().Equals(m.ConnId.ToLower()))
{
BaseDBConfig.LogConfig = config;
}
else
{
if (string.Equals(config.ConfigId, DBConst.MainDbConfigId,
StringComparison.CurrentCultureIgnoreCase))
{
BaseDBConfig.MainConfig = config;
}
else if (m.ConnId.ToLower().StartsWith(DBConst.MainDbConfigId.ToLower()))
{
//复用连接
BaseDBConfig.ReuseConfigs.Add(config);
}
BaseDBConfig.ValidConfig.Add(config);
}
BaseDBConfig.AllConfigs.Add(config);
});
if (AppSettings.app("AppSettings", "LogToDb").ObjToBool() && BaseDBConfig.LogConfig is null)
{
throw new ApplicationException("未配置Log库连接");
}
// SqlSugarScope是线程安全可使用单例注入
// 参考https://www.donet5.com/Home/Doc?typeId=1181
services.AddSingleton<ISqlSugarClient>(o =>
{
return new SqlSugarScope(BaseDBConfig.AllConfigs, db =>
{
BaseDBConfig.ValidConfig.ForEach(config =>
{
var dbProvider = db.GetConnectionScope((string)config.ConfigId);
// 打印SQL语句
dbProvider.Aop.OnLogExecuting = (s, parameters) =>
{
SqlSugarAop.OnLogExecuting(sql: s,
param: parameters,
path: App.HttpContext?.Request?.Path,
user: App.User?.Name?.ObjToString(),
traceId: App.HttpContext?.TraceIdentifier);
};
// 数据初始化
dbProvider.Aop.DataExecuting = SqlSugarAop.DataExecuting;
// 配置实体假删除过滤器
RepositorySetting.SetDeletedEntityFilter(dbProvider);
// 这里不需要用到租户
// RepositorySetting.SetTenantEntityFilter(dbProvider);
});
//故障转移,检查主库链接自动切换备用连接
SqlSugarReuse.AutoChangeAvailableConnect(db);
});
});
}
private static string ExtractTableName(string sql)
{
// 匹配 SQL 语句中的表名的正则表达式
//string regexPattern = @"\s*(?:UPDATE|DELETE\s+FROM|SELECT\s+\*\s+FROM)\s+(\w+)";
string regexPattern = @"(?i)(?:FROM|UPDATE|DELETE\s+FROM)\s+`(.+?)`";
Regex regex = new Regex(regexPattern, RegexOptions.IgnoreCase);
Match match = regex.Match(sql);
if (match.Success)
{
// 提取匹配到的表名
return match.Groups[1].Value;
}
else
{
// 如果没有匹配到表名,则返回空字符串或者抛出异常等处理
return string.Empty;
}
}
}
}