Learn.Archives/Learn.Archives.API/Controllers/AdminController.cs

196 lines
7.9 KiB
C#

using Azure.Core;
using Learn.Archives.API.Controllers.Dto;
using Learn.Archives.API.Expand;
using Learn.Archives.Core.Common;
using Learn.Archives.Core.Model;
using Learn.Archives.Core.Model.Dto;
using Learn.Archives.Core.Model.Enum;
using Mapster;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using MiniExcelLibs;
using System.Diagnostics;
using System.Security.Claims;
using System.Text.RegularExpressions;
using UserCenter.Model.Common;
namespace Learn.Archives.API.Controllers
{
public class AdminController : BackController<Admin>
{
readonly Repository<Admin> baseService;
readonly Repository<MenuRelation> menuRelationDB;
readonly Repository<Menu> menuDB;
readonly Repository<AdminRole> roleDB;
readonly LiveUserInfo userInfo;
readonly IHttpContextAccessor accessor;
public AdminController(Repository<Admin> baseService, Repository<MenuRelation> menuRelationDB, Repository<Menu> menuDB, IHttpContextAccessor accessor, Repository<AdminRole> roleDB, LiveUserInfo userInfo = null) : base(baseService)
{
this.baseService = baseService;
this.menuRelationDB = menuRelationDB;
this.menuDB = menuDB;
this.accessor = accessor;
this.roleDB = roleDB;
this.userInfo = userInfo;
}
/// <summary>
/// 管理员登录
/// </summary>
/// <param name="model"></param>
/// <returns></returns>
[HttpPost, AllowAnonymous]
[HttpLogEnable]
public async Task<object> Login([FromBody] AdminLoginReq model)
{
if (string.IsNullOrWhiteSpace(model.Account))
Oh.Error("登录失败,用户名不能为空");
if (string.IsNullOrWhiteSpace(model.Password))
Oh.Error("登录失败,密码不能为空");
var admin = await baseService.GetFirstAsync(x => x.Account == model.Account);
if (admin == null)
Oh.Error("登录失败,用户不存在!");
if (!admin!.Enable)
Oh.Error("登录失败,用户已锁定!");
if (admin.Password != model.Password.GetMD5())
Oh.Error("登录失败,密码错误");
// 获取租户信息
var buttonRole = admin.RoleId == 1
? ["*:*:*"]
: await menuRelationDB.AsQueryable()
.LeftJoin<Menu>((mr, m) => mr.MenuId == m.Id)
.Where((mr, m) => mr.RoleId == admin.RoleId && m.IsButton)
.Select((mr, m) => m.Auths)
.ToArrayAsync();
//获取
return new
{
//按钮权限
Permissions = buttonRole,
//用户名
UserName = admin.Name,
NickName = admin.Name,
AccessToken = JwtHelper.GetToken(AppCommon.Config.AuthKey,
[
new Claim(ClaimEnum.UserCenterRole,"1"),//让所有用户都有用户中心操作权限
new Claim(ClaimEnum.Role,admin.RoleId.ToString()),
new Claim(ClaimEnum.UserId,admin.Id.ToString()),
new Claim(ClaimEnum.UserId,admin.Id.ToString()),
new Claim(ClaimEnum.Scope,"档案系统"),
new Claim(ClaimEnum.Id, admin.Id.ToString()),
new Claim(ClaimEnum.Name, admin.Name),
])
};
}
public override async Task<bool> Edit([FromBody] Admin model)
{
//创建用户时 密码加密
if (model.Id == 0)
model.Password = model.Password.GetMD5();
if (string.IsNullOrEmpty(model.Account) || model.Account.Length < 2 ||
string.IsNullOrEmpty(model.Phone) || model.Phone.Length < 11 ||
string.IsNullOrEmpty(model.Name) || model.Phone.Length < 2)
{
Oh.ModelError("账号/手机号/名称 不合法");
}
if (await baseService.IsAnyAsync(s => s.Account == model.Account && s.Id != model.Id))
Oh.ModelError($"账号 {model.Account} 已被使用!");
return await base.Edit(model);
}
/// <summary>
/// 下载导入模板
/// </summary>
/// <returns></returns>
[HttpGet, ResultIgnore, AllowAnonymous]
public IActionResult DwImportTemplate()
{
var resultList = new List<AdminImport>() { new AdminImport()
{
Account = "登录账号[建议使用手机号]",
Name = "必填:用户名称",
Phone = "联系方式",
Role = "必填:与系统的角色名称匹配\r\n普通成员 管理员",
Password = "必填: 登录密码",
} };
return File(resultList.ExportExcel(), "application/ms-excel",
$"导入管理员模板{DateTime.Now.ToString("MMddHHmm")}.xlsx");
}
/// <summary>
/// 导入用户信息
/// </summary>
/// <returns></returns>
[HttpPost, ResultIgnore]
[HttpLogEnable]
public async Task<IActionResult> Import(IFormFile? file)
{
if(!userInfo.IsSa)
Oh.ModelError("只允许管理员使用本功能!");
var fl = file != null ? file : accessor.HttpContext?.Request.Form.Files[0];
if (fl == null) Oh.ModelError("传入无效的数据");
if (!Path.GetExtension(fl.FileName).Equals(".xlsx", StringComparison.OrdinalIgnoreCase))
Oh.ModelError("请选择导入文件为.xlsx的后缀名!");
//分析excel
IEnumerable<AdminImportError> dataList;
using var stream = new MemoryStream();
{
await fl.CopyToAsync(stream);
dataList = stream.Query<AdminImportError>()
.Where(s => !string.IsNullOrEmpty(s.Account));
}
if (dataList == null || dataList.Count() == 0)
Oh.ModelError("导入失败:无有效数据");
//处理数据
var accountArr = await baseService.AsQueryable()
.Select(s => s.Account ).Distinct()
.ToArrayAsync();
var accountH = accountArr.ToHashSet();
var roleDic = await roleDB.AsQueryable()
.ToDictionaryAsync(s => s.Name, s => s.Id);
var errorExcelInfo = new List<AdminImportError>();
var insertInfo = new List<Admin>();
foreach (var imp in dataList)
{
imp.Account = imp.Account.Trim();
imp.Phone = imp.Phone.Trim();
imp.Name = imp.Name.Trim();
imp.Role = imp.Role.Trim();
if (accountH.Contains(imp.Account))
{
imp.Error = $"导入失败:账号已被使用!";
errorExcelInfo.Add(imp);
continue;
}
else if (!roleDic.ContainsKey(imp.Role))
{
imp.Error = $"导入失败:无效的 角色名称!";
errorExcelInfo.Add(imp);
continue;
}
var admin = imp.Adapt<Admin>();
admin.Enable = true;
admin.RoleId = (long)roleDic[imp.Role];
admin.Password = imp.Password.Trim().GetMD5();
insertInfo.Add(admin);
//excel内预计新增的账号也计入重复
accountH.Add(admin.Account);
}
if (errorExcelInfo.Count != 0)
return File(errorExcelInfo.ExportExcel(), "application/ms-excel"
, $"错误管理员信息{DateTime.Now.ToString("MMddHHmm")}.xlsx");
//写入数据库
await baseService.InsertRangeAsync(insertInfo);
return Ok();
}
}
}