312 lines
11 KiB
C#
312 lines
11 KiB
C#
using Dlhis.Basic.Organization.Request;
|
|
using Dlhis.Basic.Organization.Response;
|
|
using Dlhis.Entity.Basic.Entity;
|
|
using Dlhis.Entity.Basic.Enums;
|
|
using Dlhis.Entity.Device.Entities;
|
|
using Kurisu.AspNetCore.Cache;
|
|
using Kurisu.AspNetCore.CustomClass;
|
|
using Kurisu.AspNetCore.DataAccess.SqlSugar.Services;
|
|
using Kurisu.AspNetCore.Utils.Extensions;
|
|
using Mapster;
|
|
using SqlSugar;
|
|
|
|
namespace Dlhis.Basic.Organization.Services.Implements;
|
|
|
|
public class GainfoOutsourceService : IGainfoOutsourceService
|
|
{
|
|
private readonly IDbContext _dbContext;
|
|
private readonly RedisCache _redisCache;
|
|
private readonly IGainfoService _gainfoService;
|
|
private readonly IFactorySettingService _factorySettingService;
|
|
private readonly ILogger<GainfoOutsourceService> _logger;
|
|
|
|
public GainfoOutsourceService(IDbContext dbContext,
|
|
RedisCache redisCache,
|
|
IGainfoService gainfoService,
|
|
IFactorySettingService factorySettingService,
|
|
ILogger<GainfoOutsourceService> logger)
|
|
{
|
|
_dbContext = dbContext;
|
|
_redisCache = redisCache;
|
|
_gainfoService = gainfoService;
|
|
_factorySettingService = factorySettingService;
|
|
_logger = logger;
|
|
}
|
|
|
|
public async Task SaveAsync(GainfoOutsourceRequest request)
|
|
{
|
|
await CheckDuplicate(request);
|
|
var sapCodeExists = await _dbContext.Queryable<GainfoEntity>()
|
|
.Where(x => x.Code == request.ExternalInfo.SapCode)
|
|
.AnyAsync();
|
|
sapCodeExists.ThrowIfFalse("对接人不存在");
|
|
var isOutsource = await _dbContext.Queryable<OutsourceEntity>()
|
|
.Where(x => x.Code == request.ExternalInfo.SapCode)
|
|
.AnyAsync();
|
|
isOutsource.ThrowIfTrue("对接人不可为外包人员");
|
|
|
|
if (!request.Id.HasValue)
|
|
{
|
|
if (!await _dbContext.Queryable<GainfoEntity>().Where(x => x.IdNo == request.IdNo).AnyAsync())
|
|
{
|
|
var entity = request.Adapt<GainfoEntity>();
|
|
entity.No = Guid.NewGuid().ToString();
|
|
entity.Type = GainfoUserTypeEnumType.Outsource;
|
|
entity.Code = request.Code.IsPresent()
|
|
? request.Code
|
|
: await GetOutSourceCodeAsync();
|
|
|
|
await _dbContext.InsertAsync(entity);
|
|
|
|
if (!await _dbContext.Queryable<OutsourceEntity>().Where(x => x.Code == entity.Code).AnyAsync())
|
|
{
|
|
await _dbContext.InsertAsync(new OutsourceEntity
|
|
{
|
|
Code = entity.Code,
|
|
Supplier = request.ExternalInfo.Supplier,
|
|
SapCode = request.ExternalInfo.SapCode,
|
|
SapPhone = request.ExternalInfo.SapPhone
|
|
});
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
var entity = await _dbContext.Queryable<GainfoEntity>().FirstAsync(x => x.Id == request.Id);
|
|
entity.ThrowIfNull("档案数据不存在");
|
|
|
|
var outsource = await _dbContext.Queryable<OutsourceEntity>().FirstAsync(x => x.Code == entity.Code);
|
|
(outsource == null).ThrowIfTrue("不可编辑非外包人员档案数据");
|
|
|
|
var idNo = entity.IdNo;
|
|
var phone = entity.Phone;
|
|
request.Adapt(entity);
|
|
entity.IdNo = idNo;
|
|
entity.Phone = phone;
|
|
|
|
outsource!.Code = entity.Code;
|
|
request.ExternalInfo.Adapt(outsource);
|
|
|
|
await _dbContext.UpdateAsync(entity);
|
|
await _dbContext.UpdateAsync(outsource);
|
|
}
|
|
}
|
|
|
|
|
|
public async Task<GainfoOutSourceExternalInfoResponse> GetExternalInfoAsync(string userNo)
|
|
{
|
|
try
|
|
{
|
|
var data = await _dbContext.Queryable<OutsourceEntity>()
|
|
.LeftJoin<GainfoEntity>((a, b) => a.Code == b.Code)
|
|
.LeftJoin<GainfoEntity>((a, b, c) => a.SapCode == c.Code)
|
|
.Where((a, b, c) => b.No == userNo)
|
|
.Select((a, b, c) => new GainfoOutSourceExternalInfoResponse
|
|
{
|
|
UserCode = b.Code,
|
|
Supplier = a.Supplier,
|
|
SapCode = a.SapCode,
|
|
SapPhone = a.SapPhone,
|
|
SapName = c.Name,
|
|
EntryDate = b.EntryDate,
|
|
ResignationDate = b.ResignationDate,
|
|
Factory = b.Factory
|
|
})
|
|
.SingleAsync();
|
|
|
|
data.IsWhiteListInAutoResign = await _dbContext.Queryable<OutsourceWhiteListEntity>()
|
|
.Where(x => x.UserCode == data.UserCode)
|
|
.AnyAsync();
|
|
|
|
return data;
|
|
}
|
|
catch (Exception)
|
|
{
|
|
return null;
|
|
}
|
|
}
|
|
|
|
|
|
public async Task AutoResignAsync()
|
|
{
|
|
var outsources = await _dbContext.Queryable<GainfoEntity>()
|
|
.Where(x => x.Type == GainfoUserTypeEnumType.Outsource)
|
|
.Where(x => SqlFunc.Subqueryable<OutsourceWhiteListEntity>()
|
|
.Where(p => p.UserCode == x.Code)
|
|
.Where(p => p.IsDeleted == false)
|
|
.NotAny()
|
|
)//不存在白名单中
|
|
.Select(x => new { x.Id, x.Code, x.Factory, x.CreateTime })
|
|
.ToListAsync();
|
|
|
|
var settings = await _factorySettingService.GetListAsync(false);
|
|
|
|
var holidaies = await _dbContext
|
|
.Queryable<HolidayEntity>()
|
|
.Select(x => new
|
|
{
|
|
x.Type,
|
|
x.Start,
|
|
x.End
|
|
})
|
|
.ToListAsync();
|
|
|
|
|
|
var weekends = new List<DayOfWeek>() { DayOfWeek.Saturday, DayOfWeek.Sunday };
|
|
foreach (var grp in outsources.GroupBy(x => x.Factory))
|
|
{
|
|
var setting = settings.First(x => x.Factory == grp.Key);
|
|
if (setting.NoRecordAutoResignOutsourceDays == 0)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
foreach (var outsource in grp)
|
|
{
|
|
//获取最近一次通行记录的时间,如果没有则取创建时间
|
|
DateTime raiseDateTime = await _dbContext.Queryable<DeviceUploadLogEntity>()
|
|
.Where(x => x.UserUniqueNo == outsource.Code)
|
|
.Where(x => x.TenantId == grp.Key) //本厂区的
|
|
.Select(x => SqlFunc.IsNull(SqlFunc.AggregateMax(x.RaiseDateTime), outsource.CreateTime))
|
|
.SingleAsync();
|
|
|
|
var checkDates = GetDaysUntilToday(raiseDateTime);
|
|
var days = checkDates.Count;
|
|
foreach (var date in checkDates)
|
|
{
|
|
//date.DayOfWeek
|
|
foreach (var holiday in holidaies)
|
|
{
|
|
var isPresent = date >= holiday.Start && date <= holiday.Start;
|
|
if (isPresent)
|
|
{
|
|
if (holiday.Type == HolidayEnumType.Rest)
|
|
{
|
|
days--;
|
|
}
|
|
}
|
|
}
|
|
if (weekends.Contains(date.DayOfWeek))
|
|
{
|
|
days--;
|
|
}
|
|
}
|
|
if (days >= setting.NoRecordAutoResignOutsourceDays)
|
|
{
|
|
try
|
|
{
|
|
await _gainfoService.ResignAsync(new GainfoResignRequest
|
|
{
|
|
Id = outsource.Id,
|
|
Reason = $"{setting.NoRecordAutoResignOutsourceDays}天无通行记录",
|
|
Date = DateTime.Now
|
|
});
|
|
}
|
|
catch (Exception e)
|
|
{
|
|
_logger.LogError(e, "自动离职外包异常:{msg}", e.Message);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
public List<DateOnly> GetDaysUntilToday(DateTime begin)
|
|
{
|
|
var start = DateOnly.FromDateTime(begin.Date);
|
|
var today = DateOnly.FromDateTime(DateTime.Today);
|
|
if (start > today) return new List<DateOnly>();
|
|
|
|
var days = new List<DateOnly>();
|
|
for (var d = start; d < today; d = d.AddDays(1))
|
|
{
|
|
days.Add(d);
|
|
}
|
|
|
|
return days;
|
|
}
|
|
|
|
//********************************************************************** help methods ***********************************************************************************
|
|
|
|
private async Task<string> GetOutSourceCodeAsync()
|
|
{
|
|
await using var handler = await _redisCache.LockAsync("gainfo:outsource:code-generate", expiry: TimeSpan.FromSeconds(3), retryInterval: TimeSpan.FromSeconds(1), retryCount: 3);
|
|
handler.Acquired.ThrowIfFalse("生成虚拟工号失败");
|
|
|
|
// var value = await _dbContext.Queryable<BasicTypeEntity>().Where(x => x.Type == "gainfoExternalMaxNum").Select(x => x.Code).SingleAsync();
|
|
// if (value.IsEmpty())
|
|
// {
|
|
// code = 1;
|
|
// await _dbContext.InsertAsync(new BasicTypeEntity
|
|
// {
|
|
// Type = "gainfoExternalMaxNum",
|
|
// Code = "1",
|
|
// Display = "外部人员序号",
|
|
// DisplayEn = "外部人员序号",
|
|
// Sequence = 1
|
|
// });
|
|
// }
|
|
// else
|
|
// {
|
|
// code = int.Parse(value) + 1;
|
|
// }
|
|
//
|
|
// return "EXT" + code.ToString().PadLeft(6, '0');
|
|
|
|
|
|
int code;
|
|
var entity = await _dbContext.Queryable<OutsourceEntity>().Where(x => x.Code.StartsWith("LS")).OrderBy(x => x.Id, OrderByType.Desc).FirstAsync();
|
|
if (entity == null)
|
|
{
|
|
code = 1;
|
|
}
|
|
else
|
|
{
|
|
code = int.Parse(entity.Code.Replace("LS", "").TrimStart('0')) + 1;
|
|
}
|
|
|
|
return "LS" + code.ToString().PadLeft(6, '0');
|
|
}
|
|
|
|
/// <summary>
|
|
/// 检查证件号重复
|
|
/// </summary>
|
|
/// <param name="request"></param>
|
|
private async Task CheckDuplicate(GainfoOutsourceRequest request)
|
|
{
|
|
var gainfo = await _dbContext.Queryable<GainfoEntity>()
|
|
.WhereIF(request.Id.HasValue, x => x.Id != request.Id)
|
|
.Where(x => x.IdNo == request.IdNo).SingleAsync();
|
|
|
|
if (gainfo != null)
|
|
{
|
|
var msg = string.Empty;
|
|
var outsource = await _dbContext.Queryable<OutsourceEntity>().Where(x => x.Code == request.Code).SingleAsync();
|
|
if (outsource != null)
|
|
{
|
|
msg = $",对接人工号为{outsource.SapCode}";
|
|
}
|
|
|
|
gainfo.ThrowIfNotNull($"证件号{request.IdNo}重复,厂区为{gainfo.Factory}" + msg);
|
|
}
|
|
|
|
if (request.Code.IsPresent())
|
|
{
|
|
gainfo = await _dbContext.Queryable<GainfoEntity>()
|
|
.WhereIF(request.Id.HasValue, x => x.Id != request.Id)
|
|
.Where(x => x.Code == request.Code).SingleAsync();
|
|
|
|
if (gainfo != null)
|
|
{
|
|
var msg = string.Empty;
|
|
var outsource = await _dbContext.Queryable<OutsourceEntity>().Where(x => x.Code == request.Code).SingleAsync();
|
|
if (outsource != null)
|
|
{
|
|
msg = $",对接人工号为{outsource.SapCode}";
|
|
}
|
|
|
|
gainfo.ThrowIfNotNull($"工号{request.Code}重复,厂区为{gainfo.Factory}" + msg);
|
|
}
|
|
}
|
|
}
|
|
} |