配置文件升级+修改(重要更新!)
This commit is contained in:
parent
a548d8f3f2
commit
d111c8c2c0
13
U8Server/AutoMapperProfile/AutoMapperProfile.cs
Normal file
13
U8Server/AutoMapperProfile/AutoMapperProfile.cs
Normal file
@ -0,0 +1,13 @@
|
||||
using AutoMapper;
|
||||
|
||||
namespace ZR.Admin.WebApi.AutoMapperProfile
|
||||
{
|
||||
public class AutoMapperProfile : Profile
|
||||
{
|
||||
public AutoMapperProfile()
|
||||
{
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
211
U8Server/Controllers/BaseController.cs
Normal file
211
U8Server/Controllers/BaseController.cs
Normal file
@ -0,0 +1,211 @@
|
||||
using Infrastructure;
|
||||
using Infrastructure.Extensions;
|
||||
using Infrastructure.Model;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using MiniExcelLibs;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
using System.Web;
|
||||
using Io = System.IO;
|
||||
|
||||
namespace WebApi.Controllers
|
||||
{
|
||||
public class BaseController : ControllerBase
|
||||
{
|
||||
public static string TIME_FORMAT_FULL = "yyyy-MM-dd HH:mm:ss";
|
||||
|
||||
/// <summary>
|
||||
/// 返回成功封装
|
||||
/// </summary>
|
||||
/// <param name="data"></param>
|
||||
/// <param name="timeFormatStr"></param>
|
||||
/// <returns></returns>
|
||||
protected IActionResult SUCCESS(object data, string timeFormatStr = "yyyy-MM-dd HH:mm:ss")
|
||||
{
|
||||
string jsonStr = GetJsonStr(GetApiResult(data != null ? ResultCode.SUCCESS : ResultCode.NO_DATA, data), timeFormatStr);
|
||||
return Content(jsonStr, "application/json");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// json输出带时间格式的
|
||||
/// </summary>
|
||||
/// <param name="apiResult"></param>
|
||||
/// <returns></returns>
|
||||
protected IActionResult ToResponse(ApiResult apiResult)
|
||||
{
|
||||
string jsonStr = GetJsonStr(apiResult, TIME_FORMAT_FULL);
|
||||
|
||||
return Content(jsonStr, "application/json");
|
||||
}
|
||||
|
||||
protected IActionResult ToResponse(long rows, string timeFormatStr = "yyyy-MM-dd HH:mm:ss")
|
||||
{
|
||||
string jsonStr = GetJsonStr(ToJson(rows), timeFormatStr);
|
||||
|
||||
return Content(jsonStr, "application/json");
|
||||
}
|
||||
|
||||
protected IActionResult ToResponse(ResultCode resultCode, string msg = "")
|
||||
{
|
||||
return ToResponse(new ApiResult((int)resultCode, msg));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 导出Excel
|
||||
/// </summary>
|
||||
/// <param name="path">完整文件路径</param>
|
||||
/// <param name="fileName">带扩展文件名</param>
|
||||
/// <returns></returns>
|
||||
protected IActionResult ExportExcel(string path, string fileName)
|
||||
{
|
||||
//var webHostEnvironment = App.WebHostEnvironment;
|
||||
if (!Path.Exists(path))
|
||||
{
|
||||
throw new CustomException(fileName + "文件不存在");
|
||||
}
|
||||
var stream = Io.File.OpenRead(path); //创建文件流
|
||||
|
||||
Response.Headers.Add("Access-Control-Expose-Headers", "Content-Disposition");
|
||||
return File(stream, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", HttpUtility.UrlEncode(fileName));
|
||||
// return File(stream, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",fileName);
|
||||
}
|
||||
|
||||
#region 方法
|
||||
|
||||
/// <summary>
|
||||
/// 响应返回结果
|
||||
/// </summary>
|
||||
/// <param name="rows">受影响行数</param>
|
||||
/// <param name="data"></param>
|
||||
/// <returns></returns>
|
||||
protected ApiResult ToJson(long rows, object? data = null)
|
||||
{
|
||||
return rows > 0 ? ApiResult.Success("success", data) : GetApiResult(ResultCode.FAIL);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 全局Code使用
|
||||
/// </summary>
|
||||
/// <param name="resultCode"></param>
|
||||
/// <param name="data"></param>
|
||||
/// <returns></returns>
|
||||
protected ApiResult GetApiResult(ResultCode resultCode, object? data = null)
|
||||
{
|
||||
var msg = resultCode.GetDescription();
|
||||
|
||||
return new ApiResult((int)resultCode, msg, data);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="apiResult"></param>
|
||||
/// <param name="timeFormatStr"></param>
|
||||
/// <returns></returns>
|
||||
private static string GetJsonStr(ApiResult apiResult, string timeFormatStr)
|
||||
{
|
||||
if (string.IsNullOrEmpty(timeFormatStr))
|
||||
{
|
||||
timeFormatStr = TIME_FORMAT_FULL;
|
||||
}
|
||||
var serializerSettings = new JsonSerializerSettings
|
||||
{
|
||||
// 设置为驼峰命名
|
||||
ContractResolver = new CamelCasePropertyNamesContractResolver(),
|
||||
DateFormatString = timeFormatStr
|
||||
};
|
||||
|
||||
return JsonConvert.SerializeObject(apiResult, Formatting.Indented, serializerSettings);
|
||||
}
|
||||
#endregion
|
||||
|
||||
/// <summary>
|
||||
/// 导出Excel
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="list"></param>
|
||||
/// <param name="sheetName"></param>
|
||||
/// <param name="fileName"></param>
|
||||
protected string ExportExcel<T>(List<T> list, string sheetName, string fileName)
|
||||
{
|
||||
return ExportExcelMini(list, sheetName, fileName).Item1;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="list"></param>
|
||||
/// <param name="sheetName"></param>
|
||||
/// <param name="fileName"></param>
|
||||
/// <returns></returns>
|
||||
protected (string, string) ExportExcelMini<T>(List<T> list, string sheetName, string fileName)
|
||||
{
|
||||
IWebHostEnvironment webHostEnvironment = (IWebHostEnvironment)App.ServiceProvider.GetService(typeof(IWebHostEnvironment));
|
||||
string sFileName = $"{fileName}{DateTime.Now:MM-dd-HHmmss}.xlsx";
|
||||
string fullPath = Path.Combine(webHostEnvironment.WebRootPath, "export", sFileName);
|
||||
|
||||
Directory.CreateDirectory(Path.GetDirectoryName(fullPath));
|
||||
|
||||
MiniExcel.SaveAs(fullPath, list, sheetName: sheetName);
|
||||
return (sFileName, fullPath);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 导出多个工作表(Sheet)
|
||||
/// </summary>
|
||||
/// <param name="sheets"></param>
|
||||
/// <param name="fileName"></param>
|
||||
/// <returns></returns>
|
||||
protected (string, string) ExportExcelMini(Dictionary<string, object> sheets, string fileName)
|
||||
{
|
||||
IWebHostEnvironment webHostEnvironment = (IWebHostEnvironment)App.ServiceProvider.GetService(typeof(IWebHostEnvironment));
|
||||
string sFileName = $"{fileName}{DateTime.Now:MM-dd-HHmmss}.xlsx";
|
||||
string fullPath = Path.Combine(webHostEnvironment.WebRootPath, "export", sFileName);
|
||||
|
||||
Directory.CreateDirectory(Path.GetDirectoryName(fullPath));
|
||||
|
||||
MiniExcel.SaveAs(fullPath, sheets);
|
||||
return (sFileName, fullPath);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 下载导入模板
|
||||
/// </summary>
|
||||
/// <typeparam name="T">数据类型</typeparam>
|
||||
/// <param name="list">空数据类型集合</param>
|
||||
/// <param name="fileName">下载文件名</param>
|
||||
/// <returns></returns>
|
||||
protected (string, string) DownloadImportTemplate<T>(List<T> list, string fileName)
|
||||
{
|
||||
IWebHostEnvironment webHostEnvironment = App.WebHostEnvironment;
|
||||
string sFileName = $"{fileName}.xlsx";
|
||||
string fullPath = Path.Combine(webHostEnvironment.WebRootPath, "ImportTemplate", sFileName);
|
||||
|
||||
//不存在模板创建模板
|
||||
if (!Directory.Exists(fullPath))
|
||||
{
|
||||
Directory.CreateDirectory(Path.GetDirectoryName(fullPath));
|
||||
MiniExcel.SaveAs(fullPath, list, overwriteFile: true);
|
||||
}
|
||||
return (sFileName, fullPath);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 下载指定文件模板
|
||||
/// </summary>
|
||||
/// <param name="fileName">下载文件名</param>
|
||||
/// <returns></returns>
|
||||
protected (string, string) DownloadImportTemplate(string fileName)
|
||||
{
|
||||
IWebHostEnvironment webHostEnvironment = (IWebHostEnvironment)App.ServiceProvider.GetService(typeof(IWebHostEnvironment));
|
||||
string sFileName = $"{fileName}.xlsx";
|
||||
string fullPath = Path.Combine(webHostEnvironment.WebRootPath, "ImportTemplate", sFileName);
|
||||
|
||||
return (sFileName, fullPath);
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
243
U8Server/Controllers/WMentryWarehousing_productController.cs
Normal file
243
U8Server/Controllers/WMentryWarehousing_productController.cs
Normal file
@ -0,0 +1,243 @@
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using ZR.Admin.WebApi.Extensions;
|
||||
using ZR.Model.MES.wms;
|
||||
using ZR.Model.MES.wms.Dto;
|
||||
using ZR.Service.mes.wms.IService;
|
||||
|
||||
namespace WebApi.Controllers.mes.wms
|
||||
{
|
||||
/// <summary>
|
||||
/// 入库模块
|
||||
/// </summary>
|
||||
[Route("/mes/wm/entrywarehouse")]
|
||||
public class WMentryWarehousing_productController : BaseController
|
||||
{
|
||||
|
||||
private readonly IWMentryWarehousing_productService wm_entryWarehousing_productService;
|
||||
public WMentryWarehousing_productController(IWMentryWarehousing_productService wm_entryWarehousing_productService)
|
||||
{
|
||||
this.wm_entryWarehousing_productService = wm_entryWarehousing_productService;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 1. 判断是否为库位码
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
[HttpGet("is_production_location")]
|
||||
[Log(Title = "判断是否为库位码")]
|
||||
public IActionResult IsProductionLocation(string production_location_code = "")
|
||||
{
|
||||
if (string.IsNullOrEmpty(production_location_code))
|
||||
{
|
||||
return ToResponse(new ApiResult(200, "传入为空", false));
|
||||
|
||||
}
|
||||
// 查询 wm_info 表,根据库位码,查询在表中是否存在,true false
|
||||
bool state = this.wm_entryWarehousing_productService.IsProductionLoacation(production_location_code);
|
||||
|
||||
return ToResponse(new ApiResult(200, "success", state));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 2. 判断是否为成品库箱子码
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
[HttpGet("is_production_package")]
|
||||
[Log(Title = "判断是否为成品库箱子码")]
|
||||
public IActionResult IsProductionPackage(string package_code = "")
|
||||
{
|
||||
if (string.IsNullOrEmpty(package_code))
|
||||
{
|
||||
return ToResponse(new ApiResult(200, "传入为空", false));
|
||||
|
||||
}
|
||||
int state = this.wm_entryWarehousing_productService.isProductionPackage(package_code);
|
||||
string msg = null;
|
||||
if (state == 0)
|
||||
msg = "外箱标签码不存在";
|
||||
else if (state == 1)
|
||||
msg = "success";
|
||||
|
||||
else if (state == 2)
|
||||
msg = "误扫码,不是外箱标签码";
|
||||
|
||||
|
||||
return ToResponse(new ApiResult(200, msg, state));
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 3.判断是否为满箱
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
[HttpGet("is_full_package")]
|
||||
[Log(Title = "判断是否为满箱")]
|
||||
public IActionResult IsFullPackage(string package_code = "")
|
||||
{
|
||||
|
||||
if (string.IsNullOrEmpty(package_code))
|
||||
{
|
||||
return ToResponse(new ApiResult(200, "传入为空", false));
|
||||
|
||||
}
|
||||
bool state = this.wm_entryWarehousing_productService.isFullPackage(package_code);
|
||||
string msg = null;
|
||||
if (state)
|
||||
{
|
||||
msg = "满箱";
|
||||
}
|
||||
else
|
||||
{
|
||||
msg = "零头箱";
|
||||
}
|
||||
|
||||
return ToResponse(new ApiResult(200, msg, state));
|
||||
}
|
||||
/// <summary>
|
||||
/// 4.入库
|
||||
/// </summary>
|
||||
/// <param name="wmgoodsDto"></param>
|
||||
/// <returns></returns>
|
||||
[HttpPost("into_product_warehouse")]
|
||||
[Log(Title = "入库")]
|
||||
public IActionResult IntoProductwarehouse([FromBody] WmgoodsDto wmgoodsDto)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (wmgoodsDto == null)
|
||||
{
|
||||
return ToResponse(new ApiResult(200, "传入参数为空", false));
|
||||
}
|
||||
string msg = "";
|
||||
|
||||
string createName = HttpContext.GetName();
|
||||
int num = this.wm_entryWarehousing_productService.IntoProductwarehouse(wmgoodsDto, createName);
|
||||
if (num == 0)
|
||||
{
|
||||
msg = "入库数为0!";
|
||||
|
||||
|
||||
}
|
||||
else if (num >= 1)
|
||||
{
|
||||
msg = "成功入库" + num + "箱";
|
||||
|
||||
|
||||
}
|
||||
return ToResponse(new ApiResult(200, msg, num));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
return ToResponse(new ApiResult(500, e.Message, e.Message));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 获取库位已经存在箱子
|
||||
/// </summary>
|
||||
/// <param name="locationcode"></param>
|
||||
/// <returns></returns>
|
||||
[HttpGet("packagelist")]
|
||||
[Log(Title = "获取库位已经存在箱子")]
|
||||
public IActionResult Getpackagelist(string locationcode)
|
||||
{
|
||||
if (string.IsNullOrEmpty(locationcode))
|
||||
{
|
||||
return ToResponse(new ApiResult(200, "传入为空", false));
|
||||
}
|
||||
string msg = null;
|
||||
|
||||
List<WmGoodsNowProduction> productionList = this.wm_entryWarehousing_productService.Getpackagelist(locationcode);
|
||||
|
||||
return ToResponse(new ApiResult(200, msg, productionList));
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 解析外标签码
|
||||
/// </summary>
|
||||
/// <param name="code"></param>
|
||||
/// <returns></returns>
|
||||
[HttpGet("resolution_package")]
|
||||
public IActionResult ResolutionPackage(string code = "")
|
||||
{
|
||||
try
|
||||
{
|
||||
if (string.IsNullOrEmpty(code))
|
||||
{
|
||||
|
||||
return ToResponse(new ApiResult(200, "传入为空", false));
|
||||
}
|
||||
ResultionPackageCodeDto data = this.wm_entryWarehousing_productService.ResolutionPackage(code);
|
||||
if (data == null)
|
||||
{
|
||||
return ToResponse(new ApiResult(500, "外标签解析异常", data));
|
||||
}
|
||||
return ToResponse(new ApiResult(200, "success", data));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return ToResponse(new ApiResult(500, ex.Message, "外标签解析异常"));
|
||||
}
|
||||
;
|
||||
|
||||
}
|
||||
/// <summary>
|
||||
/// 7 判断箱子是否存在成品库仓库里
|
||||
/// </summary>
|
||||
/// <param name="PatchCode"></param>
|
||||
/// <returns></returns>
|
||||
[HttpGet("is_existed_warehouse")]
|
||||
public IActionResult IsExistedWarehouse(string originalCode = "")
|
||||
{
|
||||
if (string.IsNullOrEmpty(originalCode))
|
||||
{
|
||||
|
||||
return ToResponse(new ApiResult(200, "传入为空", false));
|
||||
}
|
||||
string msg = null;
|
||||
bool data = this.wm_entryWarehousing_productService.IsExistedWarehouse(originalCode);
|
||||
if (data)
|
||||
{
|
||||
msg = "存在";
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
msg = "不存在";
|
||||
}
|
||||
|
||||
return ToResponse(new ApiResult(200, msg, data));
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// all.判断标签扫描结果是否可入库(综合结果判断)
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
[HttpGet("checkWarehousing")]
|
||||
[Log(Title = "判断标签扫描结果是否可入库")]
|
||||
public IActionResult CheckWarehousing(string production_packcode = "", string location = "",
|
||||
bool isStrict = false)
|
||||
{
|
||||
string msg = this.wm_entryWarehousing_productService.checkWarehousing(production_packcode, location, isStrict);
|
||||
if ("ok".Equals(msg))
|
||||
{
|
||||
// 可入库
|
||||
return ToResponse(new ApiResult(200, msg, true));
|
||||
}
|
||||
else
|
||||
{
|
||||
// 不可入库
|
||||
return ToResponse(new ApiResult(200, msg, false));
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
24
U8Server/Controllers/v1/V1U8AuthController.cs
Normal file
24
U8Server/Controllers/v1/V1U8AuthController.cs
Normal file
@ -0,0 +1,24 @@
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using U8Server.Util;
|
||||
using WebApi.Controllers;
|
||||
namespace U8Server.Controllers.v1
|
||||
{
|
||||
[ApiController]
|
||||
[Route("/v1/u8/auth")]
|
||||
public class V1U8AuthController : BaseController
|
||||
{
|
||||
private readonly ILogger<V1U8AuthController> _logger;
|
||||
|
||||
public V1U8AuthController(ILogger<V1U8AuthController> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
[HttpGet(Name = "getMd5")]
|
||||
[Log(Title = "»ñÈ¡md5ÃØÔ¿")]
|
||||
public string GetMd5()
|
||||
{
|
||||
return GetSign.GetBy16Md5();
|
||||
}
|
||||
}
|
||||
}
|
||||
24
U8Server/Controllers/v1/V1U8WarehouseController.cs
Normal file
24
U8Server/Controllers/v1/V1U8WarehouseController.cs
Normal file
@ -0,0 +1,24 @@
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using U8Server.Util;
|
||||
using WebApi.Controllers;
|
||||
namespace U8Server.Controllers.v1
|
||||
{
|
||||
[ApiController]
|
||||
[Route("/v1/u8/warehouse")]
|
||||
public class V1U8WarehouseController : BaseController
|
||||
{
|
||||
private readonly ILogger<V1U8WarehouseController> _logger;
|
||||
|
||||
public V1U8WarehouseController(ILogger<V1U8WarehouseController> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
[HttpGet(Name = "getMd52")]
|
||||
[Log(Title = "»ñÈ¡md5ÃØÔ¿")]
|
||||
public string GetMd5()
|
||||
{
|
||||
return GetSign.GetBy16Md5();
|
||||
}
|
||||
}
|
||||
}
|
||||
68
U8Server/Extensions/AppServiceExtensions.cs
Normal file
68
U8Server/Extensions/AppServiceExtensions.cs
Normal file
@ -0,0 +1,68 @@
|
||||
using System.Reflection;
|
||||
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
/// <summary>
|
||||
/// App服务注册
|
||||
/// </summary>
|
||||
public static class AppServiceExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// 注册引用程序域中所有有AppService标记的类的服务
|
||||
/// </summary>
|
||||
/// <param name="services"></param>
|
||||
public static void AddAppService(this IServiceCollection services)
|
||||
{
|
||||
var cls = AppSettings.Get<string[]>("InjectClass");
|
||||
if (cls == null || cls.Length <= 0)
|
||||
{
|
||||
throw new Exception("请更新appsettings类");
|
||||
}
|
||||
foreach (var item in cls)
|
||||
{
|
||||
Register(services, item);
|
||||
}
|
||||
}
|
||||
|
||||
private static void Register(IServiceCollection services, string item)
|
||||
{
|
||||
Assembly assembly = Assembly.Load(item);
|
||||
foreach (var type in assembly.GetTypes())
|
||||
{
|
||||
var serviceAttribute = type.GetCustomAttribute<AppServiceAttribute>();
|
||||
|
||||
if (serviceAttribute != null)
|
||||
{
|
||||
var serviceType = serviceAttribute.ServiceType;
|
||||
//情况1 适用于依赖抽象编程,注意这里只获取第一个
|
||||
if (serviceType == null && serviceAttribute.InterfaceServiceType)
|
||||
{
|
||||
serviceType = type.GetInterfaces().FirstOrDefault();
|
||||
}
|
||||
//情况2 不常见特殊情况下才会指定ServiceType,写起来麻烦
|
||||
if (serviceType == null)
|
||||
{
|
||||
serviceType = type;
|
||||
}
|
||||
|
||||
switch (serviceAttribute.ServiceLifetime)
|
||||
{
|
||||
case LifeTime.Singleton:
|
||||
services.AddSingleton(serviceType, type);
|
||||
break;
|
||||
case LifeTime.Scoped:
|
||||
services.AddScoped(serviceType, type);
|
||||
break;
|
||||
case LifeTime.Transient:
|
||||
services.AddTransient(serviceType, type);
|
||||
break;
|
||||
default:
|
||||
services.AddTransient(serviceType, type);
|
||||
break;
|
||||
}
|
||||
//System.Console.WriteLine($"注册:{serviceType}");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
27
U8Server/Extensions/CorsExtension.cs
Normal file
27
U8Server/Extensions/CorsExtension.cs
Normal file
@ -0,0 +1,27 @@
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
public static class CorsExtension
|
||||
{
|
||||
/// <summary>
|
||||
/// 跨域配置
|
||||
/// </summary>
|
||||
/// <param name="services"></param>
|
||||
/// <param name="configuration"></param>
|
||||
public static void AddCors(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
var corsUrls = configuration.GetSection("corsUrls").Get<string[]>();
|
||||
|
||||
//配置跨域
|
||||
services.AddCors(c =>
|
||||
{
|
||||
c.AddPolicy("Policy", policy =>
|
||||
{
|
||||
policy.WithOrigins(corsUrls ?? Array.Empty<string>())
|
||||
.AllowAnyHeader()//允许任意头
|
||||
.AllowCredentials()//允许cookie
|
||||
.AllowAnyMethod();//允许任意方法
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
120
U8Server/Extensions/DataPermi.cs
Normal file
120
U8Server/Extensions/DataPermi.cs
Normal file
@ -0,0 +1,120 @@
|
||||
using SqlSugar;
|
||||
using SqlSugar.IOC;
|
||||
using ZR.Admin.WebApi.Framework;
|
||||
using ZR.Model.System;
|
||||
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
public enum DataPermiEnum
|
||||
{
|
||||
None = 0,
|
||||
/// <summary>
|
||||
/// 全部数据权限
|
||||
/// </summary>
|
||||
All = 1,
|
||||
/// <summary>
|
||||
/// 仅本人数据权限
|
||||
/// </summary>
|
||||
SELF = 5,
|
||||
/// <summary>
|
||||
/// 部门数据权限
|
||||
/// </summary>
|
||||
DEPT = 3,
|
||||
/// <summary>
|
||||
/// 自定数据权限
|
||||
/// </summary>
|
||||
CUSTOM = 2,
|
||||
/// <summary>
|
||||
/// 部门及以下数据权限
|
||||
/// </summary>
|
||||
DEPT_CHILD = 4
|
||||
}
|
||||
/// <summary>
|
||||
/// 数据权限
|
||||
/// </summary>
|
||||
public class DataPermi
|
||||
{
|
||||
/// <summary>
|
||||
/// 数据过滤
|
||||
/// </summary>
|
||||
/// <param name="configId">多库id</param>
|
||||
public static void FilterData(int configId)
|
||||
{
|
||||
//获取当前用户的信息
|
||||
var user = JwtUtil.GetLoginUser(App.HttpContext);
|
||||
if (user == null) return;
|
||||
//管理员不过滤
|
||||
if (user.RoleIds.Any(f => f.Equals(GlobalConstant.AdminRole))) return;
|
||||
var db = DbScoped.SugarScope.GetConnectionScope(configId);
|
||||
var expUser = Expressionable.Create<SysUser>();
|
||||
var expRole = Expressionable.Create<SysRole>();
|
||||
var expLoginlog = Expressionable.Create<SysLogininfor>();
|
||||
|
||||
foreach (var role in user.Roles.OrderBy(f => f.DataScope))
|
||||
{
|
||||
var dataScope = (DataPermiEnum)role.DataScope;
|
||||
if (DataPermiEnum.All.Equals(dataScope))//所有权限
|
||||
{
|
||||
break;
|
||||
}
|
||||
else if (DataPermiEnum.CUSTOM.Equals(dataScope))//自定数据权限
|
||||
{
|
||||
//" OR {}.dept_id IN ( SELECT dept_id FROM sys_role_dept WHERE role_id = {} ) ", deptAlias, role.getRoleId()));
|
||||
|
||||
expUser.Or(it => SqlFunc.Subqueryable<SysRoleDept>().Where(f => f.DeptId == it.DeptId && f.RoleId == role.RoleId).Any());
|
||||
}
|
||||
else if (DataPermiEnum.DEPT.Equals(dataScope))//本部门数据
|
||||
{
|
||||
expUser.Or(it => it.DeptId == user.DeptId);
|
||||
}
|
||||
else if (DataPermiEnum.DEPT_CHILD.Equals(dataScope))//本部门及以下数据
|
||||
{
|
||||
//SQl OR {}.dept_id IN ( SELECT dept_id FROM sys_dept WHERE dept_id = {} or find_in_set( {} , ancestors ) )
|
||||
var allChildDepts = db.Queryable<SysDept>().ToChildList(it => it.ParentId, user.DeptId);
|
||||
|
||||
expUser.Or(it => allChildDepts.Select(f => f.DeptId).ToList().Contains(it.DeptId));
|
||||
}
|
||||
else if (DataPermiEnum.SELF.Equals(dataScope))//仅本人数据
|
||||
{
|
||||
expUser.Or(it => it.UserId == user.UserId);
|
||||
expRole.Or(it => user.RoleIds.Contains(it.RoleKey));
|
||||
expLoginlog.And(it => it.UserName == user.UserName);
|
||||
}
|
||||
}
|
||||
|
||||
db.QueryFilter.AddTableFilter(expUser.ToExpression());
|
||||
db.QueryFilter.AddTableFilter(expRole.ToExpression());
|
||||
db.QueryFilter.AddTableFilter(expLoginlog.ToExpression());
|
||||
}
|
||||
|
||||
public static void FilterData1(int configId)
|
||||
{
|
||||
//获取当前用户的信息
|
||||
var user = JwtUtil.GetLoginUser(App.HttpContext);
|
||||
if (user == null) return;
|
||||
var db = DbScoped.SugarScope.GetConnectionScope(configId);
|
||||
|
||||
foreach (var role in user.Roles.OrderBy(f => f.DataScope))
|
||||
{
|
||||
var dataScope = (DataPermiEnum)role.DataScope;
|
||||
if (DataPermiEnum.All.Equals(dataScope))//所有权限
|
||||
{
|
||||
break;
|
||||
}
|
||||
else if (DataPermiEnum.CUSTOM.Equals(dataScope))//自定数据权限
|
||||
{
|
||||
}
|
||||
else if (DataPermiEnum.DEPT.Equals(dataScope))//本部门数据
|
||||
{
|
||||
}
|
||||
else if (DataPermiEnum.DEPT_CHILD.Equals(dataScope))//本部门及以下数据
|
||||
{
|
||||
|
||||
}
|
||||
else if (DataPermiEnum.SELF.Equals(dataScope))//仅本人数据
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
208
U8Server/Extensions/DbExtension.cs
Normal file
208
U8Server/Extensions/DbExtension.cs
Normal file
@ -0,0 +1,208 @@
|
||||
using Infrastructure.Extensions;
|
||||
using SqlSugar;
|
||||
using SqlSugar.IOC;
|
||||
using ZR.Model;
|
||||
using ZR.Model.System;
|
||||
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
/// <summary>
|
||||
/// sqlsugar 数据处理
|
||||
/// </summary>
|
||||
public static class DbExtension
|
||||
{
|
||||
private static NLog.Logger logger = NLog.LogManager.GetCurrentClassLogger();
|
||||
|
||||
/// <summary>
|
||||
/// 初始化db
|
||||
/// </summary>
|
||||
/// <param name="services"></param>
|
||||
/// <param name="Configuration"></param>
|
||||
/// <param name="environment"></param>
|
||||
public static void AddDb(this IServiceCollection services, IConfiguration Configuration, IWebHostEnvironment environment)
|
||||
{
|
||||
List<DbConfigs> dbConfigs = Configuration.GetSection("DbConfigs").Get<List<DbConfigs>>();
|
||||
|
||||
var iocList = new List<IocConfig>();
|
||||
foreach (var item in dbConfigs)
|
||||
{
|
||||
iocList.Add(new IocConfig()
|
||||
{
|
||||
ConfigId = item.ConfigId,
|
||||
ConnectionString = item.Conn,
|
||||
DbType = (IocDbType)item.DbType,
|
||||
IsAutoCloseConnection = item.IsAutoCloseConnection
|
||||
});
|
||||
}
|
||||
SugarIocServices.AddSqlSugar(iocList);
|
||||
ICacheService cache = new SqlSugarCache();
|
||||
SugarIocServices.ConfigurationSugar(db =>
|
||||
{
|
||||
var u = App.User;
|
||||
if (u != null)
|
||||
{
|
||||
DataPermi.FilterData(0);
|
||||
//ConfigId = 1的数据权限过滤
|
||||
//DataPermi.FilterData1(1);
|
||||
}
|
||||
|
||||
iocList.ForEach(iocConfig =>
|
||||
{
|
||||
SetSugarAop(db, iocConfig, cache);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 数据库Aop设置
|
||||
/// </summary>
|
||||
/// <param name="db"></param>
|
||||
/// <param name="iocConfig"></param>
|
||||
/// <param name="cache"></param>
|
||||
private static void SetSugarAop(SqlSugarClient db, IocConfig iocConfig, ICacheService cache)
|
||||
{
|
||||
var config = db.GetConnectionScope(iocConfig.ConfigId).CurrentConnectionConfig;
|
||||
var showDbLog = AppSettings.Get<bool>("ShowDbLog");
|
||||
string configId = config.ConfigId;
|
||||
db.GetConnectionScope(configId).Aop.OnLogExecuting = (sql, pars) =>
|
||||
{
|
||||
if (showDbLog)
|
||||
{
|
||||
string log = $"【db{configId} SQL语句】{UtilMethods.GetSqlString(config.DbType, sql, pars)}\n";
|
||||
if (sql.TrimStart().StartsWith("SELECT", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
logger.Info(log);
|
||||
}
|
||||
else if (sql.StartsWith("UPDATE", StringComparison.OrdinalIgnoreCase) || sql.StartsWith("INSERT", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
logger.Warn(log);
|
||||
}
|
||||
else if (sql.StartsWith("DELETE", StringComparison.OrdinalIgnoreCase) || sql.StartsWith("TRUNCATE", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
logger.Error(log);
|
||||
}
|
||||
else
|
||||
{
|
||||
log = $"【db{configId} SQL语句】dbo.{sql} {string.Join(", ", pars.Select(x => x.ParameterName + " = " + GetParsValue(x)))};\n";
|
||||
logger.Info(log);
|
||||
}
|
||||
}
|
||||
};
|
||||
db.GetConnectionScope(configId).Aop.OnError = (ex) =>
|
||||
{
|
||||
//var pars = db.Utilities.SerializeObject(((SugarParameter[])ex.Parametres).ToDictionary(it => it.ParameterName, it => it.Value));
|
||||
|
||||
string sql = "【错误SQL】" + UtilMethods.GetSqlString(config.DbType, ex.Sql, (SugarParameter[])ex.Parametres) + "\r\n";
|
||||
logger.Error(ex, $"{sql}\r\n{ex.Message}\r\n{ex.StackTrace}");
|
||||
};
|
||||
db.GetConnectionScope(configId).Aop.DataExecuting = (oldValue, entiyInfo) =>
|
||||
{
|
||||
};
|
||||
//差异日志功能
|
||||
db.GetConnectionScope(configId).Aop.OnDiffLogEvent = it =>
|
||||
{
|
||||
//操作前记录 包含: 字段描述 列名 值 表名 表描述
|
||||
var editBeforeData = it.BeforeData;//插入Before为null,之前还没进库
|
||||
//操作后记录 包含: 字段描述 列名 值 表名 表描述
|
||||
var editAfterData = it.AfterData;
|
||||
var sql = it.Sql;
|
||||
var parameter = it.Parameters;
|
||||
var data = it.BusinessData;//这边会显示你传进来的对象
|
||||
var time = it.Time;
|
||||
var diffType = it.DiffType;//enum insert 、update and delete
|
||||
|
||||
if (diffType == DiffType.delete)
|
||||
{
|
||||
string name = App.UserName;
|
||||
|
||||
foreach (var item in editBeforeData)
|
||||
{
|
||||
var pars = db.Utilities.SerializeObject(item.Columns.ToDictionary(it => it.ColumnName, it => it.Value));
|
||||
|
||||
SqlDiffLog log = new()
|
||||
{
|
||||
BeforeData = pars,
|
||||
BusinessData = data?.ToString(),
|
||||
DiffType = diffType.ToString(),
|
||||
Sql = sql,
|
||||
TableName = item.TableName,
|
||||
UserName = name,
|
||||
AddTime = DateTime.Now,
|
||||
ConfigId = configId
|
||||
};
|
||||
//logger.WithProperty("title", data).Info(pars);
|
||||
db.GetConnectionScope(0).Insertable(log).ExecuteReturnSnowflakeId();
|
||||
}
|
||||
}
|
||||
};
|
||||
db.GetConnectionScope(configId).CurrentConnectionConfig.MoreSettings = new ConnMoreSettings()
|
||||
{
|
||||
IsAutoRemoveDataCache = true
|
||||
};
|
||||
db.GetConnectionScope(configId).CurrentConnectionConfig.ConfigureExternalServices = new ConfigureExternalServices()
|
||||
{
|
||||
DataInfoCacheService = cache,
|
||||
EntityService = (c, p) =>
|
||||
{
|
||||
if (p.IsPrimarykey == true)//主键不能为null
|
||||
{
|
||||
p.IsNullable = false;
|
||||
}
|
||||
else if (p.ExtendedAttribute?.ToString() == ProteryConstant.NOTNULL.ToString())
|
||||
{
|
||||
p.IsNullable = false;
|
||||
}
|
||||
else//则否默认为null
|
||||
{
|
||||
p.IsNullable = true;
|
||||
}
|
||||
|
||||
if (config.DbType == DbType.PostgreSQL)
|
||||
{
|
||||
if (c.Name == nameof(SysMenu.IsCache) || c.Name == nameof(SysMenu.IsFrame))
|
||||
{
|
||||
p.DataType = "char(1)";
|
||||
}
|
||||
}
|
||||
#region 兼容Oracle
|
||||
if (config.DbType == DbType.Oracle)
|
||||
{
|
||||
if (p.IsIdentity == true)
|
||||
{
|
||||
if (p.EntityName == nameof(SysUser))
|
||||
{
|
||||
p.OracleSequenceName = "SEQ_SYS_USER_USERID";
|
||||
}
|
||||
else if (p.EntityName == nameof(SysRole))
|
||||
{
|
||||
p.OracleSequenceName = "SEQ_SYS_ROLE_ROLEID";
|
||||
}
|
||||
else if (p.EntityName == nameof(SysDept))
|
||||
{
|
||||
p.OracleSequenceName = "SEQ_SYS_DEPT_DEPTID";
|
||||
}
|
||||
else if (p.EntityName == nameof(SysMenu))
|
||||
{
|
||||
p.OracleSequenceName = "SEQ_SYS_MENU_MENUID";
|
||||
}
|
||||
else
|
||||
{
|
||||
p.OracleSequenceName = "SEQ_ID";
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private static object GetParsValue(SugarParameter x)
|
||||
{
|
||||
if (x.DbType == System.Data.DbType.String || x.DbType == System.Data.DbType.DateTime || x.DbType == System.Data.DbType.String)
|
||||
{
|
||||
return "'" + x.Value + "'";
|
||||
}
|
||||
return x.Value;
|
||||
}
|
||||
}
|
||||
}
|
||||
46
U8Server/Extensions/EntityExtension.cs
Normal file
46
U8Server/Extensions/EntityExtension.cs
Normal file
@ -0,0 +1,46 @@
|
||||
|
||||
using System.Reflection;
|
||||
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
public static class EntityExtension
|
||||
{
|
||||
public static TSource ToCreate<TSource>(this TSource source, HttpContext? context = null)
|
||||
{
|
||||
var types = source?.GetType();
|
||||
if (types == null) return source;
|
||||
BindingFlags flag = BindingFlags.Public | BindingFlags.IgnoreCase | BindingFlags.Instance;
|
||||
|
||||
types.GetProperty("CreateTime", flag)?.SetValue(source, DateTime.Now, null);
|
||||
types.GetProperty("CreatedTime", flag)?.SetValue(source, DateTime.Now, null);
|
||||
types.GetProperty("AddTime", flag)?.SetValue(source, DateTime.Now, null);
|
||||
if(context != null)
|
||||
{
|
||||
types.GetProperty("CreateBy", flag)?.SetValue(source, context.GetName(), null);
|
||||
types.GetProperty("Create_by", flag)?.SetValue(source, context.GetName(), null);
|
||||
types.GetProperty("CreatedBy", flag)?.SetValue(source, context.GetName(), null);
|
||||
types.GetProperty("UserId", flag)?.SetValue(source, context.GetUId(), null);
|
||||
}
|
||||
return source;
|
||||
}
|
||||
|
||||
public static TSource ToUpdate<TSource>(this TSource source, HttpContext? context = null)
|
||||
{
|
||||
var types = source?.GetType();
|
||||
if (types == null) return source;
|
||||
BindingFlags flag = BindingFlags.Public | BindingFlags.IgnoreCase | BindingFlags.Instance;
|
||||
|
||||
types.GetProperty("UpdateTime", flag)?.SetValue(source, DateTime.Now, null);
|
||||
types.GetProperty("Update_time", flag)?.SetValue(source, DateTime.Now, null);
|
||||
types.GetProperty("UpdatedTime", flag)?.SetValue(source, DateTime.Now, null);
|
||||
if(context != null)
|
||||
{
|
||||
types.GetProperty("UpdateBy", flag)?.SetValue(source, context.GetName(), null);
|
||||
types.GetProperty("Update_by", flag)?.SetValue(source, context.GetName(), null);
|
||||
types.GetProperty("UpdatedBy", flag)?.SetValue(source, context.GetName(), null);
|
||||
}
|
||||
return source;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
225
U8Server/Extensions/HttpContextExtension.cs
Normal file
225
U8Server/Extensions/HttpContextExtension.cs
Normal file
@ -0,0 +1,225 @@
|
||||
using Infrastructure.Extensions;
|
||||
using System.Security.Claims;
|
||||
using System.Text;
|
||||
using System.Text.RegularExpressions;
|
||||
using UAParser;
|
||||
using ZR.Model.System;
|
||||
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
/// <summary>
|
||||
/// HttpContext扩展类
|
||||
/// </summary>
|
||||
public static partial class HttpContextExtension
|
||||
{
|
||||
/// <summary>
|
||||
/// 是否是ajax请求
|
||||
/// </summary>
|
||||
/// <param name="request"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsAjaxRequest(this HttpRequest request)
|
||||
{
|
||||
if (request == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(request));
|
||||
}
|
||||
|
||||
//return request.Headers.ContainsKey("X-Requested-With") &&
|
||||
// request.Headers["X-Requested-With"].Equals("XMLHttpRequest");
|
||||
|
||||
return request.Headers["X-Requested-With"] == "XMLHttpRequest" || request.Headers != null && request.Headers["X-Requested-With"] == "XMLHttpRequest";
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取客户端IP
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static string GetClientUserIp(this HttpContext context)
|
||||
{
|
||||
if (context == null) return "";
|
||||
var result = context.Request.Headers["X-Forwarded-For"].FirstOrDefault();
|
||||
if (string.IsNullOrEmpty(result))
|
||||
{
|
||||
result = context.Connection.RemoteIpAddress?.ToString();
|
||||
}
|
||||
if (string.IsNullOrEmpty(result))
|
||||
throw new Exception("获取IP失败");
|
||||
|
||||
if (result.Contains("::1"))
|
||||
result = "127.0.0.1";
|
||||
|
||||
result = result.Replace("::ffff:", "127.0.0.1");
|
||||
result = result.Split(':')?.FirstOrDefault() ?? "127.0.0.1";
|
||||
result = IsIP(result) ? result : "127.0.0.1";
|
||||
return result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 判断是否IP
|
||||
/// </summary>
|
||||
/// <param name="ip"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsIP(string ip)
|
||||
{
|
||||
return Regex.IsMatch(ip, @"^((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)$");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取登录用户id
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static long GetUId(this HttpContext context)
|
||||
{
|
||||
var uid = context.User.FindFirstValue(ClaimTypes.PrimarySid);
|
||||
return !string.IsNullOrEmpty(uid) ? long.Parse(uid) : 0;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取登录用户名
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static string? GetName(this HttpContext context)
|
||||
{
|
||||
var uid = context.User?.Identity?.Name;
|
||||
|
||||
return uid;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 判断是否是管理员
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsAdmin(this HttpContext context)
|
||||
{
|
||||
List<string> roles = new();
|
||||
roles.Add($"{GlobalConstant.AdminRole}");
|
||||
roles.Add("杨琳磊");
|
||||
var userName = context.GetName();
|
||||
return roles.Contains(userName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// ClaimsIdentity
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static IEnumerable<ClaimsIdentity>? GetClaims(this HttpContext context)
|
||||
{
|
||||
return context.User?.Identities;
|
||||
}
|
||||
//public static int GetRole(this HttpContext context)
|
||||
//{
|
||||
// var roleid = context.User.FindFirstValue(ClaimTypes.Role) ?? "0";
|
||||
|
||||
// return int.Parse(roleid);
|
||||
//}
|
||||
|
||||
public static string GetUserAgent(this HttpContext context)
|
||||
{
|
||||
return context.Request.Headers["User-Agent"];
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取请求令牌
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static string GetToken(this HttpContext context)
|
||||
{
|
||||
return context.Request.Headers["Authorization"];
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取浏览器信息
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static ClientInfo GetClientInfo(this HttpContext context)
|
||||
{
|
||||
var str = context.GetUserAgent();
|
||||
var uaParser = Parser.GetDefault();
|
||||
ClientInfo c = uaParser.Parse(str);
|
||||
|
||||
return c;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取请求Url
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static string? GetRequestUrl(this HttpContext context)
|
||||
{
|
||||
return context != null ? context.Request.Path.Value : "";
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取请求参数
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static string GetQueryString(this HttpContext context)
|
||||
{
|
||||
return context != null ? context.Request.QueryString.Value : "";
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 获取body请求参数
|
||||
/// </summary>
|
||||
/// <param name="context"></param>
|
||||
/// <returns></returns>
|
||||
public static string GetBody(this HttpContext context)
|
||||
{
|
||||
context.Request.EnableBuffering();
|
||||
//context.Request.Body.Seek(0, SeekOrigin.Begin);
|
||||
//using var reader = new StreamReader(context.Request.Body, Encoding.UTF8);
|
||||
////需要使用异步方式才能获取
|
||||
//return reader.ReadToEndAsync().Result;
|
||||
string body = string.Empty;
|
||||
var buffer = new MemoryStream();
|
||||
context.Request.Body.Seek(0, SeekOrigin.Begin);
|
||||
context.Request.Body.CopyToAsync(buffer);
|
||||
buffer.Position = 0;
|
||||
try
|
||||
{
|
||||
using StreamReader streamReader = new(buffer, Encoding.UTF8);
|
||||
body = streamReader.ReadToEndAsync().Result;
|
||||
}
|
||||
finally
|
||||
{
|
||||
buffer?.Dispose();
|
||||
}
|
||||
return body;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 设置请求参数
|
||||
/// </summary>
|
||||
/// <param name="operLog"></param>
|
||||
/// <param name="context"></param>
|
||||
public static void GetRequestValue(this HttpContext context, SysOperLog operLog)
|
||||
{
|
||||
string reqMethod = operLog.RequestMethod;
|
||||
string param = string.Empty;
|
||||
|
||||
if (HttpMethods.IsPost(reqMethod) || HttpMethods.IsPut(reqMethod) || HttpMethods.IsDelete(reqMethod))
|
||||
{
|
||||
param = context.GetBody();
|
||||
param = PwdRep().Replace(param, "***");
|
||||
}
|
||||
if (param.IsEmpty())
|
||||
{
|
||||
param = context.GetQueryString();
|
||||
}
|
||||
operLog.OperParam = param;
|
||||
}
|
||||
|
||||
[GeneratedRegex("(?<=\"password\":\")[^\",]*")]
|
||||
private static partial Regex PwdRep();
|
||||
}
|
||||
|
||||
}
|
||||
64
U8Server/Extensions/SqlSugarCache.cs
Normal file
64
U8Server/Extensions/SqlSugarCache.cs
Normal file
@ -0,0 +1,64 @@
|
||||
namespace ZR.Admin.WebApi.Extensions
|
||||
{
|
||||
public class SqlSugarCache : SqlSugar.ICacheService
|
||||
{
|
||||
public void Add<V>(string key, V value)
|
||||
{
|
||||
//RedisServer.Cache.Set(key, value, 3600 + RedisHelper.RandomExpired(5, 30));
|
||||
CacheHelper.SetCache(key, value);
|
||||
}
|
||||
|
||||
public void Add<V>(string key, V value, int cacheDurationInSeconds)
|
||||
{
|
||||
//RedisServer.Cache.Set(key, value, cacheDurationInSeconds);
|
||||
CacheHelper.SetCaches(key, value, cacheDurationInSeconds);
|
||||
}
|
||||
|
||||
public bool ContainsKey<V>(string key)
|
||||
{
|
||||
//return RedisServer.Cache.Exists(key);
|
||||
return CacheHelper.Exists(key);
|
||||
}
|
||||
|
||||
public V Get<V>(string key)
|
||||
{
|
||||
//return RedisServer.Cache.Get<V>(key);
|
||||
return (V)CacheHelper.Get(key);
|
||||
}
|
||||
|
||||
public IEnumerable<string> GetAllKey<V>()
|
||||
{
|
||||
//return RedisServer.Cache.Keys("*");
|
||||
return CacheHelper.GetCacheKeys();
|
||||
}
|
||||
|
||||
public V GetOrCreate<V>(string cacheKey, Func<V> create, int cacheDurationInSeconds = int.MaxValue)
|
||||
{
|
||||
if (ContainsKey<V>(cacheKey))
|
||||
{
|
||||
var result = Get<V>(cacheKey);
|
||||
if (result == null)
|
||||
{
|
||||
return create();
|
||||
}
|
||||
else
|
||||
{
|
||||
return result;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
var restul = create();
|
||||
|
||||
Add(cacheKey, restul, cacheDurationInSeconds);
|
||||
return restul;
|
||||
}
|
||||
}
|
||||
|
||||
public void Remove<V>(string key)
|
||||
{
|
||||
//RedisServer.Cache.Del(key);
|
||||
CacheHelper.Remove(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
170
U8Server/Framework/JwtUtil.cs
Normal file
170
U8Server/Framework/JwtUtil.cs
Normal file
@ -0,0 +1,170 @@
|
||||
using Infrastructure.Extensions;
|
||||
using Microsoft.IdentityModel.Tokens;
|
||||
using Newtonsoft.Json;
|
||||
using System.IdentityModel.Tokens.Jwt;
|
||||
using System.Security.Claims;
|
||||
using System.Text;
|
||||
using ZR.Admin.WebApi.Extensions;
|
||||
using ZR.Model.System.Dto;
|
||||
using ZR.Service.System;
|
||||
|
||||
namespace ZR.Admin.WebApi.Framework
|
||||
{
|
||||
/// <summary>
|
||||
/// 2020-11-20
|
||||
/// </summary>
|
||||
public class JwtUtil
|
||||
{
|
||||
/// <summary>
|
||||
/// 获取用户身份信息
|
||||
/// </summary>
|
||||
/// <param name="httpContext"></param>
|
||||
/// <returns></returns>
|
||||
public static LoginUser GetLoginUser(HttpContext httpContext)
|
||||
{
|
||||
string token = httpContext.GetToken();
|
||||
|
||||
if (!string.IsNullOrEmpty(token))
|
||||
{
|
||||
return ValidateJwtToken(ParseToken(token));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 生成token
|
||||
/// </summary>
|
||||
/// <param name="claims"></param>
|
||||
/// <param name="jwtSettings"></param>
|
||||
/// <returns></returns>
|
||||
public static string GenerateJwtToken(List<Claim> claims, JwtSettings jwtSettings)
|
||||
{
|
||||
var authTime = DateTime.Now;
|
||||
var expiresAt = authTime.AddMinutes(jwtSettings.Expire);
|
||||
var tokenHandler = new JwtSecurityTokenHandler();
|
||||
var key = Encoding.ASCII.GetBytes(jwtSettings.SecretKey);
|
||||
claims.Add(new Claim("Audience", jwtSettings.Audience));
|
||||
claims.Add(new Claim("Issuer", jwtSettings.Issuer));
|
||||
|
||||
var tokenDescriptor = new SecurityTokenDescriptor
|
||||
{
|
||||
Subject = new ClaimsIdentity(claims),
|
||||
Issuer = jwtSettings.Issuer,
|
||||
Audience = jwtSettings.Audience,
|
||||
IssuedAt = authTime,//token生成时间
|
||||
Expires = expiresAt,
|
||||
//NotBefore = authTime,
|
||||
TokenType = "Bearer",
|
||||
//对称秘钥,签名证书
|
||||
SigningCredentials = new SigningCredentials(new SymmetricSecurityKey(key), SecurityAlgorithms.HmacSha256Signature)
|
||||
};
|
||||
var token = tokenHandler.CreateToken(tokenDescriptor);
|
||||
return tokenHandler.WriteToken(token);
|
||||
}
|
||||
/// <summary>
|
||||
/// 检查客户端和服务器的Token是否一样
|
||||
/// </summary>
|
||||
/// <returns></returns>
|
||||
public static TokenValidationParameters ValidParameters()
|
||||
{
|
||||
JwtSettings jwtSettings = new();
|
||||
AppSettings.Bind("JwtSettings", jwtSettings);
|
||||
|
||||
if (jwtSettings == null || jwtSettings.SecretKey.IsEmpty())
|
||||
{
|
||||
throw new Exception("JwtSettings获取失败");
|
||||
}
|
||||
var key = Encoding.ASCII.GetBytes(jwtSettings.SecretKey);
|
||||
|
||||
var tokenDescriptor = new TokenValidationParameters
|
||||
{
|
||||
ValidateIssuerSigningKey = true,
|
||||
ValidateIssuer = true,
|
||||
ValidateAudience = true,
|
||||
ValidIssuer = jwtSettings.Issuer,
|
||||
ValidAudience = jwtSettings.Audience,
|
||||
IssuerSigningKey = new SymmetricSecurityKey(key),
|
||||
ValidateLifetime = true,//是否验证Token有效期,使用当前时间与Token的Claims中的NotBefore和Expires对比
|
||||
ClockSkew = TimeSpan.FromSeconds(30)
|
||||
//RequireExpirationTime = true,//过期时间
|
||||
};
|
||||
return tokenDescriptor;
|
||||
}
|
||||
/// <summary>
|
||||
/// 从令牌中获取数据声明
|
||||
/// </summary>
|
||||
/// <param name="token">令牌</param>
|
||||
/// <returns></returns>
|
||||
public static IEnumerable<Claim>? ParseToken(string token)
|
||||
{
|
||||
var tokenHandler = new JwtSecurityTokenHandler();
|
||||
var validateParameter = ValidParameters();
|
||||
token = token.Replace("Bearer ", "");
|
||||
try
|
||||
{
|
||||
tokenHandler.ValidateToken(token, validateParameter, out SecurityToken validatedToken);
|
||||
|
||||
var jwtToken = tokenHandler.ReadJwtToken(token);
|
||||
return jwtToken.Claims;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine(ex.Message);
|
||||
// return null if validation fails
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// jwt token校验 合法用户和其权限
|
||||
/// </summary>
|
||||
/// <param name="jwtToken"></param>
|
||||
/// <returns></returns>
|
||||
public static LoginUser? ValidateJwtToken(IEnumerable<Claim> jwtToken)
|
||||
{
|
||||
try
|
||||
{
|
||||
LoginUser loginUser = null;
|
||||
//todo: ClaimTypes.UserData ??? 从何而来
|
||||
var userData = jwtToken.FirstOrDefault(x => x.Type == ClaimTypes.UserData)?.Value;
|
||||
if (userData != null)
|
||||
{
|
||||
loginUser = JsonConvert.DeserializeObject<LoginUser>(userData);
|
||||
//todo 从缓存拿到权限,如果拿不到权限说明非法用户
|
||||
var permissions = CacheService.GetUserPerms(GlobalConstant.UserPermKEY + loginUser?.UserId);
|
||||
|
||||
if (loginUser?.UserName == GlobalConstant.AdminRole)
|
||||
{
|
||||
permissions = new List<string>() { GlobalConstant.AdminPerm };
|
||||
}
|
||||
if (permissions == null) return null;
|
||||
loginUser.Permissions = permissions;
|
||||
}
|
||||
return loginUser;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine(ex.Message);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///组装Claims
|
||||
/// </summary>
|
||||
/// <param name="user"></param>
|
||||
/// <returns></returns>
|
||||
public static List<Claim> AddClaims(LoginUser user)
|
||||
{
|
||||
var claims = new List<Claim>()
|
||||
{
|
||||
new Claim(ClaimTypes.PrimarySid, user.UserId.ToString()),
|
||||
new Claim(ClaimTypes.Name, user.UserName),
|
||||
new Claim(ClaimTypes.UserData, JsonConvert.SerializeObject(user))
|
||||
};
|
||||
|
||||
return claims;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
7
U8Server/GlobalUsing.cs
Normal file
7
U8Server/GlobalUsing.cs
Normal file
@ -0,0 +1,7 @@
|
||||
global using Infrastructure;
|
||||
global using Infrastructure.Attribute;
|
||||
global using Infrastructure.Enums;
|
||||
global using Infrastructure.Model;
|
||||
global using Mapster;
|
||||
global using Microsoft.AspNetCore.Authorization;
|
||||
global using ZR.Common;
|
||||
137
U8Server/Middleware/GlobalExceptionMiddleware.cs
Normal file
137
U8Server/Middleware/GlobalExceptionMiddleware.cs
Normal file
@ -0,0 +1,137 @@
|
||||
using IPTools.Core;
|
||||
using Microsoft.AspNetCore.Http.Features;
|
||||
using NLog;
|
||||
using System.Text.Encodings.Web;
|
||||
using System.Text.Json;
|
||||
using ZR.Admin.WebApi.Extensions;
|
||||
using ZR.Model.System;
|
||||
using ZR.Service.System.IService;
|
||||
|
||||
namespace ZR.Admin.WebApi.Middleware
|
||||
{
|
||||
/// <summary>
|
||||
/// 全局异常处理中间件
|
||||
/// 调用 app.UseMiddlewareGlobalExceptionMiddleware>();
|
||||
/// </summary>
|
||||
public class GlobalExceptionMiddleware
|
||||
{
|
||||
private readonly RequestDelegate next;
|
||||
private readonly ISysOperLogService SysOperLogService;
|
||||
|
||||
static readonly Logger Logger = LogManager.GetCurrentClassLogger();
|
||||
|
||||
public GlobalExceptionMiddleware(RequestDelegate next, ISysOperLogService sysOperLog)
|
||||
{
|
||||
this.next = next;
|
||||
this.SysOperLogService = sysOperLog;
|
||||
}
|
||||
|
||||
public async Task Invoke(HttpContext context)
|
||||
{
|
||||
try
|
||||
{
|
||||
await next(context);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
await HandleExceptionAsync(context, ex);
|
||||
}
|
||||
}
|
||||
|
||||
private async Task HandleExceptionAsync(HttpContext context, Exception ex)
|
||||
{
|
||||
NLog.LogLevel logLevel = NLog.LogLevel.Info;
|
||||
int code = (int)ResultCode.GLOBAL_ERROR;
|
||||
string msg;
|
||||
string error = string.Empty;
|
||||
//自定义异常
|
||||
if (ex is CustomException customException)
|
||||
{
|
||||
code = customException.Code;
|
||||
msg = customException.Message;
|
||||
error = customException.LogMsg;
|
||||
}
|
||||
else if (ex is ArgumentException)//参数异常
|
||||
{
|
||||
code = (int)ResultCode.PARAM_ERROR;
|
||||
msg = ex.Message;
|
||||
}
|
||||
else
|
||||
{
|
||||
msg = "服务器好像出了点问题,请联系系统管理员...";
|
||||
error = $"{ex.Message}";
|
||||
logLevel = NLog.LogLevel.Error;
|
||||
context.Response.StatusCode = 500;
|
||||
}
|
||||
var options = new JsonSerializerOptions
|
||||
{
|
||||
Encoder = JavaScriptEncoder.UnsafeRelaxedJsonEscaping,
|
||||
PropertyNamingPolicy = JsonNamingPolicy.CamelCase,
|
||||
WriteIndented = true
|
||||
};
|
||||
|
||||
ApiResult apiResult = new(code, msg);
|
||||
string responseResult = JsonSerializer.Serialize(apiResult, options).ToLower();
|
||||
string ip = HttpContextExtension.GetClientUserIp(context);
|
||||
var ip_info = IpTool.Search(ip);
|
||||
|
||||
SysOperLog sysOperLog = new()
|
||||
{
|
||||
Status = 1,
|
||||
OperIp = ip,
|
||||
OperUrl = HttpContextExtension.GetRequestUrl(context),
|
||||
RequestMethod = context.Request.Method,
|
||||
JsonResult = responseResult,
|
||||
ErrorMsg = string.IsNullOrEmpty(error) ? msg : error,
|
||||
OperName = HttpContextExtension.GetName(context),
|
||||
OperLocation = ip_info.Province + " " + ip_info.City,
|
||||
OperTime = DateTime.Now
|
||||
};
|
||||
HttpContextExtension.GetRequestValue(context, sysOperLog);
|
||||
var endpoint = GetEndpoint(context);
|
||||
if (endpoint != null)
|
||||
{
|
||||
var logAttribute = endpoint.Metadata.GetMetadata<LogAttribute>();
|
||||
if (logAttribute != null)
|
||||
{
|
||||
sysOperLog.BusinessType = (int)logAttribute.BusinessType;
|
||||
sysOperLog.Title = logAttribute?.Title;
|
||||
sysOperLog.OperParam = logAttribute.IsSaveRequestData ? sysOperLog.OperParam : "";
|
||||
sysOperLog.JsonResult = logAttribute.IsSaveResponseData ? sysOperLog.JsonResult : "";
|
||||
}
|
||||
}
|
||||
LogEventInfo ei = new(logLevel, "GlobalExceptionMiddleware", error)
|
||||
{
|
||||
Exception = ex,
|
||||
Message = error
|
||||
};
|
||||
ei.Properties["status"] = 1;//走正常返回都是通过走GlobalExceptionFilter不通过
|
||||
ei.Properties["jsonResult"] = responseResult;
|
||||
ei.Properties["requestParam"] = sysOperLog.OperParam;
|
||||
ei.Properties["user"] = sysOperLog.OperName;
|
||||
|
||||
Logger.Log(ei);
|
||||
context.Response.ContentType = "text/json;charset=utf-8";
|
||||
await context.Response.WriteAsync(responseResult, System.Text.Encoding.UTF8);
|
||||
|
||||
string errorMsg = $"> 操作人:{sysOperLog.OperName}" +
|
||||
$"\n> 操作地区:{sysOperLog.OperIp}({sysOperLog.OperLocation})" +
|
||||
$"\n> 操作模块:{sysOperLog.Title}" +
|
||||
$"\n> 操作地址:{sysOperLog.OperUrl}" +
|
||||
$"\n> 错误信息:{msg}\n\n> {error}";
|
||||
|
||||
WxNoticeHelper.SendMsg("系统出错", errorMsg, "", WxNoticeHelper.MsgType.markdown);
|
||||
SysOperLogService.InsertOperlog(sysOperLog);
|
||||
}
|
||||
|
||||
public static Endpoint GetEndpoint(HttpContext context)
|
||||
{
|
||||
if (context == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(context));
|
||||
}
|
||||
|
||||
return context.Features.Get<IEndpointFeature>()?.Endpoint;
|
||||
}
|
||||
}
|
||||
}
|
||||
30
U8Server/Program.cs
Normal file
30
U8Server/Program.cs
Normal file
@ -0,0 +1,30 @@
|
||||
using Nacos.AspNetCore.V2;
|
||||
|
||||
var builder = WebApplication.CreateBuilder(args);
|
||||
|
||||
// Add services to the container.
|
||||
//ÅäÖÃÖÐÐÄ
|
||||
builder.Configuration.AddNacosV2Configuration(builder.Configuration.GetSection("NacosConfig"));
|
||||
//·þÎñ×¢²á
|
||||
builder.Services.AddNacosAspNet(builder.Configuration);
|
||||
|
||||
|
||||
builder.Services.AddControllers();
|
||||
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
|
||||
builder.Services.AddEndpointsApiExplorer();
|
||||
builder.Services.AddSwaggerGen();
|
||||
|
||||
var app = builder.Build();
|
||||
|
||||
// Configure the HTTP request pipeline.
|
||||
if (app.Environment.IsDevelopment())
|
||||
{
|
||||
app.UseSwagger();
|
||||
app.UseSwaggerUI();
|
||||
}
|
||||
|
||||
app.UseAuthorization();
|
||||
|
||||
app.MapControllers();
|
||||
|
||||
app.Run();
|
||||
31
U8Server/Properties/launchSettings.json
Normal file
31
U8Server/Properties/launchSettings.json
Normal file
@ -0,0 +1,31 @@
|
||||
{
|
||||
"$schema": "https://json.schemastore.org/launchsettings.json",
|
||||
"iisSettings": {
|
||||
"windowsAuthentication": false,
|
||||
"anonymousAuthentication": true,
|
||||
"iisExpress": {
|
||||
"applicationUrl": "http://localhost:62659",
|
||||
"sslPort": 0
|
||||
}
|
||||
},
|
||||
"profiles": {
|
||||
"http": {
|
||||
"commandName": "Project",
|
||||
"dotnetRunMessages": true,
|
||||
"launchBrowser": true,
|
||||
"launchUrl": "swagger",
|
||||
"applicationUrl": "http://localhost:5222",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
}
|
||||
},
|
||||
"IIS Express": {
|
||||
"commandName": "IISExpress",
|
||||
"launchBrowser": true,
|
||||
"launchUrl": "swagger",
|
||||
"environmentVariables": {
|
||||
"ASPNETCORE_ENVIRONMENT": "Development"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
28
U8Server/U8Server.csproj
Normal file
28
U8Server/U8Server.csproj
Normal file
@ -0,0 +1,28 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<Nullable>enable</Nullable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="AspNetCoreRateLimit" Version="5.0.0" />
|
||||
<PackageReference Include="IPTools.China" Version="1.6.0" />
|
||||
<PackageReference Include="Mapster" Version="7.3.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="7.0.19" />
|
||||
<PackageReference Include="nacos-sdk-csharp" Version="1.3.10" />
|
||||
<PackageReference Include="nacos-sdk-csharp.AspNetCore" Version="1.3.10" />
|
||||
<PackageReference Include="nacos-sdk-csharp.Extensions.Configuration" Version="1.3.10" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
|
||||
<PackageReference Include="NPOI" Version="2.7.0" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
|
||||
<PackageReference Include="UAParser" Version="3.1.47" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\Infrastructure\Infrastructure.csproj" />
|
||||
<ProjectReference Include="..\ZR.Service\ZR.Service.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
19
U8Server/Util/GetSign.cs
Normal file
19
U8Server/Util/GetSign.cs
Normal file
@ -0,0 +1,19 @@
|
||||
using System.Globalization;
|
||||
using U8Server.Extensions;
|
||||
|
||||
namespace U8Server.Util
|
||||
{
|
||||
public class GetSign
|
||||
{
|
||||
public static string GetBy16Md5()
|
||||
{
|
||||
string appId = "gN9yId!!lfwaRoi3";
|
||||
string appSecret = "xr35$IQAutBRX1UYhgOUY#CqChI#Y3b$";
|
||||
string timestamp = DateTime.Now.ToString("yyyyMMddHHmmss", CultureInfo.InvariantCulture);
|
||||
string key = $"{appSecret}{appId}{timestamp}{appSecret}";
|
||||
string sign = key.ToMD5Encrypt(uppercase: false, is16bit: true)
|
||||
?? throw new InvalidOperationException("MD5加密失败");
|
||||
return sign;
|
||||
}
|
||||
}
|
||||
}
|
||||
110
U8Server/Util/MD5Encryption.cs
Normal file
110
U8Server/Util/MD5Encryption.cs
Normal file
@ -0,0 +1,110 @@
|
||||
using System.Security.Cryptography;
|
||||
using System.Text;
|
||||
|
||||
namespace U8Server.Util
|
||||
{
|
||||
//
|
||||
// 摘要:
|
||||
// MD5 加密
|
||||
public static class MD5Encryption
|
||||
{
|
||||
//
|
||||
// 摘要:
|
||||
// MD5 比较
|
||||
//
|
||||
// 参数:
|
||||
// text:
|
||||
// 加密文本
|
||||
//
|
||||
// hash:
|
||||
// MD5 字符串
|
||||
//
|
||||
// uppercase:
|
||||
// 是否输出大写加密,默认 false
|
||||
//
|
||||
// is16:
|
||||
// 是否输出 16 位
|
||||
//
|
||||
// 返回结果:
|
||||
// bool
|
||||
public static bool Compare(string text, string hash, bool uppercase = false, bool is16 = false)
|
||||
{
|
||||
return Compare(Encoding.UTF8.GetBytes(text), hash, uppercase, is16);
|
||||
}
|
||||
|
||||
//
|
||||
// 摘要:
|
||||
// MD5 加密
|
||||
//
|
||||
// 参数:
|
||||
// text:
|
||||
// 加密文本
|
||||
//
|
||||
// uppercase:
|
||||
// 是否输出大写加密,默认 false
|
||||
//
|
||||
// is16:
|
||||
// 是否输出 16 位
|
||||
public static string Encrypt(string text, bool uppercase = false, bool is16 = false)
|
||||
{
|
||||
return Encrypt(Encoding.UTF8.GetBytes(text), uppercase, is16);
|
||||
}
|
||||
|
||||
//
|
||||
// 摘要:
|
||||
// MD5 加密
|
||||
//
|
||||
// 参数:
|
||||
// bytes:
|
||||
// 字节数组
|
||||
//
|
||||
// uppercase:
|
||||
// 是否输出大写加密,默认 false
|
||||
//
|
||||
// is16:
|
||||
// 是否输出 16 位
|
||||
public static string Encrypt(byte[] bytes, bool uppercase = false, bool is16 = false)
|
||||
{
|
||||
byte[] array = MD5.HashData(bytes);
|
||||
StringBuilder stringBuilder = new StringBuilder();
|
||||
for (int i = 0; i < array.Length; i++)
|
||||
{
|
||||
stringBuilder.Append(array[i].ToString("x2"));
|
||||
}
|
||||
|
||||
string text = stringBuilder.ToString();
|
||||
string text2 = ((!is16) ? text : text.Substring(8, 16));
|
||||
if (uppercase)
|
||||
{
|
||||
return text2.ToUpper();
|
||||
}
|
||||
|
||||
return text2;
|
||||
}
|
||||
|
||||
//
|
||||
// 摘要:
|
||||
// MD5 比较
|
||||
//
|
||||
// 参数:
|
||||
// bytes:
|
||||
// 字节数组
|
||||
//
|
||||
// hash:
|
||||
// MD5 字符串
|
||||
//
|
||||
// uppercase:
|
||||
// 是否输出大写加密,默认 false
|
||||
//
|
||||
// is16:
|
||||
// 是否输出 16 位
|
||||
//
|
||||
// 返回结果:
|
||||
// bool
|
||||
public static bool Compare(byte[] bytes, string hash, bool uppercase = false, bool is16 = false)
|
||||
{
|
||||
string value = Encrypt(bytes, uppercase, is16);
|
||||
return hash.Equals(value, StringComparison.OrdinalIgnoreCase);
|
||||
}
|
||||
}
|
||||
}
|
||||
20
U8Server/Util/StringExtensions.cs
Normal file
20
U8Server/Util/StringExtensions.cs
Normal file
@ -0,0 +1,20 @@
|
||||
using U8Server.Util;
|
||||
|
||||
namespace U8Server.Extensions
|
||||
{
|
||||
public static class StringExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// 对字符串进行 MD5 加密(扩展方法)
|
||||
/// </summary>
|
||||
/// <param name="input">待加密的字符串</param>
|
||||
/// <param name="uppercase">是否返回大写形式</param>
|
||||
/// <param name="is16bit">是否返回 16 位 MD5(默认 32 位)</param>
|
||||
/// <returns>加密后的字符串</returns>
|
||||
public static string ToMD5Encrypt(this string input, bool uppercase = false, bool is16bit = false)
|
||||
{
|
||||
// 直接调用现有的 MD5Encryption.Encrypt 方法
|
||||
return MD5Encryption.Encrypt(input, uppercase, is16bit);
|
||||
}
|
||||
}
|
||||
}
|
||||
8
U8Server/appsettings.Development.json
Normal file
8
U8Server/appsettings.Development.json
Normal file
@ -0,0 +1,8 @@
|
||||
{
|
||||
"Logging": {
|
||||
"LogLevel": {
|
||||
"Default": "Information",
|
||||
"Microsoft.AspNetCore": "Warning"
|
||||
}
|
||||
}
|
||||
}
|
||||
21
U8Server/appsettings.json
Normal file
21
U8Server/appsettings.json
Normal file
@ -0,0 +1,21 @@
|
||||
{
|
||||
"Logging": {
|
||||
"LogLevel": {
|
||||
"Default": "Information",
|
||||
"Microsoft.AspNetCore": "Warning"
|
||||
}
|
||||
},
|
||||
"NacosConfig": {
|
||||
"Listeners": [
|
||||
{
|
||||
"Optional": false,
|
||||
"DataId": "U8ServerConfig",
|
||||
"Group": "DEFAULT_GROUP"
|
||||
}
|
||||
],
|
||||
// 服务注册必填参数
|
||||
"ServerAddresses": [ "http://127.0.0.1:8848" ], // Nacos 服务器地址
|
||||
"Namespace": ""// 命名空间(默认 public)
|
||||
},
|
||||
"AllowedHosts": "*"
|
||||
}
|
||||
@ -3,6 +3,7 @@ using Microsoft.AspNetCore.Authentication.JwtBearer;
|
||||
using Microsoft.AspNetCore.DataProtection;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.IdentityModel.Tokens;
|
||||
using Nacos.AspNetCore.V2;
|
||||
using System.Text.Json.Serialization;
|
||||
using ZR.Admin.WebApi.AutoMapperProfile;
|
||||
using ZR.Admin.WebApi.Extensions;
|
||||
@ -14,9 +15,12 @@ using ZR.Common.Cache;
|
||||
using ZR.Common.MqttHelper;
|
||||
|
||||
var builder = WebApplication.CreateBuilder(args);
|
||||
|
||||
// Add services to the container.
|
||||
builder.Services.AddControllers();
|
||||
//配置中心
|
||||
//builder.Configuration.AddNacosV2Configuration(builder.Configuration.GetSection("NacosConfig"));
|
||||
//服务注册
|
||||
//builder.Services.AddNacosAspNet(builder.Configuration);
|
||||
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
|
||||
builder.Services.AddEndpointsApiExplorer();
|
||||
builder.Services.AddSwaggerGen();
|
||||
|
||||
@ -36,6 +36,9 @@
|
||||
<PackageReference Include="AspNetCoreRateLimit" Version="5.0.0" />
|
||||
<PackageReference Include="Lazy.Captcha.Core" Version="2.0.3" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="7.0.7" />
|
||||
<PackageReference Include="nacos-sdk-csharp" Version="1.3.10" />
|
||||
<PackageReference Include="nacos-sdk-csharp.AspNetCore" Version="1.3.10" />
|
||||
<PackageReference Include="nacos-sdk-csharp.Extensions.Configuration" Version="1.3.10" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
|
||||
<PackageReference Include="NPOI" Version="2.7.0" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
|
||||
|
||||
@ -16,5 +16,17 @@
|
||||
"QualityOfServiceLevel": "AtLeastOnce"
|
||||
}
|
||||
]
|
||||
},
|
||||
"NacosConfig": {
|
||||
"Listeners": [
|
||||
{
|
||||
"Optional": false,
|
||||
"DataId": "MesServerConfig",
|
||||
"Group": "DEFAULT_GROUP"
|
||||
}
|
||||
],
|
||||
// 服务注册必填参数
|
||||
"ServerAddresses": [ "http://127.0.0.1:8848" ], // Nacos 服务器地址
|
||||
"Namespace": "" // 命名空间(默认 public)
|
||||
}
|
||||
}
|
||||
@ -19,6 +19,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ZR.Repository", "ZR.Reposit
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "ZR.CodeGenerator", "ZR.CodeGenerator\ZR.CodeGenerator.csproj", "{B353DE0B-12C6-4C15-909A-DB68F71D5AE9}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "U8Server", "U8Server\U8Server.csproj", "{B1F5C2C3-8E09-4140-A573-C19FD2E33ADE}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
@ -57,6 +59,10 @@ Global
|
||||
{B353DE0B-12C6-4C15-909A-DB68F71D5AE9}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{B353DE0B-12C6-4C15-909A-DB68F71D5AE9}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{B353DE0B-12C6-4C15-909A-DB68F71D5AE9}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{B1F5C2C3-8E09-4140-A573-C19FD2E33ADE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{B1F5C2C3-8E09-4140-A573-C19FD2E33ADE}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{B1F5C2C3-8E09-4140-A573-C19FD2E33ADE}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{B1F5C2C3-8E09-4140-A573-C19FD2E33ADE}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user