using MongoDB.Driver;
using VitalService.Entities;
using VitalService.Request;
using VitalService.Common;
using WingServerCommon.Mapper;
using WingInterfaceLibrary.Interface.DBVitalInterface;
using WingInterfaceLibrary.Request.DBVitalRequest;
using WingInterfaceLibrary.DTO.Vital;
using WingInterfaceLibrary.Request;
using WingInterfaceLibrary.Enum.VitalEnum;
using WingServerCommon.Log;
namespace VitalService.Service
{
///
/// 合约记录数据服务
///
public partial class VitalDatabaseService : IVitalContractRecordDBService
{
private FindOptions listProjection = new FindOptions
{
Projection = Builders.Projection
.Exclude(f => f.ContractedFileUrl)
.Exclude(f => f.Photos)
};
///
/// 创建合约记录数据
///
/// 创建请求
///
public async Task CreateContractRecordAsync(CreateContractRecordDBRequest request)
{
AddDoctorCode(request.OperationDoctor);
if (string.IsNullOrWhiteSpace(request.ContractRecordNo))
{
request.ContractRecordNo = NumberGenerator.GenerateNumber();
}
var entity = request.MappingTo();
var info = await SetRequestCreatedFrom(entity, request.OperationDoctor);
if (info.team != null)
{
entity.ContractedTeam = info.team.Code;
if (string.IsNullOrWhiteSpace(entity.ContractedDoctor) && !string.IsNullOrWhiteSpace(info.team.Principal))
{
entity.ContractedDoctor = info.team.Principal;
}
}
var contactRecordCode = await _contractRecordDBRepository.InsertOneAsync(entity);
await UpdatePatientContactStateAsync(entity.ContractedPatient);
return contactRecordCode;
}
private async Task UpdatePatientContactStateAsync(string cardNo)
{
try
{
var contractRecordFilter = Builders.Filter.Where(x => x.IsDelete == false && x.ContractedPatient == cardNo);
var contractRecordList = await _contractRecordDBRepository.FindAllAsync(contractRecordFilter);
if (contractRecordList?.Any() ?? false)
{
var contractEntity = contractRecordList.OrderByDescending(x => x.CreateTime).FirstOrDefault();
var patientFilter = Builders.Filter.Eq(p => p.Code, cardNo);
var patientEntity = await _patientDBRepository.FindOneAsync(patientFilter);
if (patientEntity != null)
{
var patientUpdates = Builders.Update.Set(f => f.ContractState, contractEntity.ContractState);
if (contractEntity.ContractState == ContractStateEnum.Signed)
{
patientUpdates = patientUpdates.Set(f => f.ServiceStartDate, contractEntity.ServiceStartDate)
.Set(f => f.ServiceEndDate, contractEntity.ServiceEndDate);
}
await _patientDBRepository.UpdateOneAsync(patientFilter, patientUpdates, false);
}
}
}
catch (Exception ex)
{
Logger.WriteLineWarn($"ContractRecordDBService UpdatePatientContactStateAsync error, ex:{ex}");
}
}
///
/// 根据编码获取合约记录数据
///
/// 获取请求
///
public async Task GetContractRecordDetailAsync(GetContractRecordDBRequest request)
{
var filter = Builders.Filter.Eq(x => x.Code, request.Code);
filter = await AddPermissionFilter(filter, request.OperationDoctor);
var result = await _contractRecordDBRepository.FindOneAsync(filter);
return await ConvertToDTO(result, request.OperationDoctor);
}
///
/// 根据关键字段获取合约记录数据
///
/// 获取请求
///
public async Task GetContractRecordDetailByKeyAsync(GetContractRecordByKeyDBRequest request)
{
var filter = Builders.Filter.Eq(request.Key, request.Value);
filter = await AddPermissionFilter(filter, request.OperationDoctor);
var result = await _contractRecordDBRepository.FindOneAsync(filter);
return await ConvertToDTO(result, request.OperationDoctor);
}
///
/// 获取合约记录数据分页
///
/// 分页请求
///
public async Task> GetContractRecordPageAsync(DBPageRequest request)
{
var filter = await _contractRecordDBRepository.GetPageFilter(request);
filter = await AddPermissionFilter(filter, request.OperationDoctor);
var pageFilter = new DBPageRequest
{
PageIndex = request.PageIndex,
PageSize = request.PageSize,
Filter = filter,
Sort = Builders.Sort.Descending(x => x.CreateTime)
};
var result = await _contractRecordDBRepository.GetPages(pageFilter, listProjection);
return await ConvertToDTOPage(result, request.OperationDoctor);
}
///
/// 删除合约记录数据
///
/// 删除请求
///
public async Task RemoveContractRecordAsync(RemoveContractRecordDBRequest request)
{
AddDoctorCode(request.OperationDoctor);
return await _contractRecordDBRepository.DeleteOneAsync("Code", request.Code);
}
///
/// 删除多个合约记录数据
///
/// 删除请求
///
public async Task RemoveContractRecordListAsync(RemoveContractRecordListDBRequest request)
{
AddDoctorCode(request.OperationDoctor);
var filter = new List<(string key, string val)>();
foreach (var code in request.Codes)
{
filter.Add(("Code", code));
}
return await _contractRecordDBRepository.DeleteAllAsync(filter);
}
///
/// 获取合约记录数据列表
///
/// 列表请求
///
public async Task> GetContractRecordListAsync(GetContractRecordListDBRequest request)
{
var filter = Builders.Filter.In(f => f.Code, request.Codes);
filter = await AddPermissionFilter(filter, request.OperationDoctor);
var result = await _contractRecordDBRepository.FindAllAsync(filter, listProjection);
return await ConvertToDTOList(result, request.OperationDoctor);
}
///
/// 根据关键字段获取合约记录数据列表
///
/// 列表请求
///
public async Task> GetContractRecordListByKeyAsync(GetContractRecordListByKeyDBRequest request)
{
var filter = Builders.Filter.Eq(request.Key, request.Value);
filter = await AddPermissionFilter(filter, request.OperationDoctor);
var result = await _contractRecordDBRepository.FindAllAsync(filter, listProjection);
return await ConvertToDTOList(result, request.OperationDoctor);
}
///
/// 查询医生最近签约记录
///
/// 获取请求
///
public async Task GetDoctorContractRecordDBAsync(GetDoctorContractRecordDBRequest request)
{
var createdDoctor = request.CreatedDoctor;
var filter = Builders.Filter.Where(x => x.CreatedDoctor == createdDoctor && (x.ContractState == ContractStateEnum.Signed || x.ContractState == ContractStateEnum.Expired || x.ContractState == ContractStateEnum.Cancelled));
var entities = await _contractRecordDBRepository.FindAllAsync(filter);
var entity = entities?.OrderByDescending(x => x.CreateTime)?.FirstOrDefault();
return await ConvertToDTO(entity, request.OperationDoctor);
}
///
/// 查询续签关联的签约记录
///
/// 获取请求
///
public async Task> GetRenewalContractDBAsync(GetRenewalContractDBRequest request)
{
var renewalContractCode = request.RenewalContractCode;
var filter = Builders.Filter.Where(x => x.RenewalContractCode == renewalContractCode);
var entities = await _contractRecordDBRepository.FindAllAsync(filter);
if (entities?.Any() ?? false)
{
return await ConvertToDTOList(entities, request.OperationDoctor);
}
return null;
}
///
/// 更新合约记录数据
///
/// 更新请求
///
public async Task UpdateContractRecordAsync(UpdateContractRecordDBRequest request)
{
AddDoctorCode(request.OperationDoctor);
var filter = Builders.Filter.Eq(f => f.Code, request.Code);
var updates = new List>();
if (request.ContractRecordNo != "-1")
{
updates.Add(Builders.Update.Set(f => f.ContractRecordNo, request.ContractRecordNo));
}
if (request.ContractState != null)
{
updates.Add(Builders.Update.Set(f => f.ContractState, request.ContractState));
}
if (request.ContractIsValid != null)
{
updates.Add(Builders.Update.Set(f => f.ContractIsValid, request.ContractIsValid));
}
if (request.ContractedDoctor != "-1")
{
updates.Add(Builders.Update.Set(f => f.ContractIsValid, request.ContractIsValid));
}
if (request.ContractedPatient != "-1")
{
updates.Add(Builders.Update.Set(f => f.ContractedPatient, request.ContractedPatient));
}
if (request.ContractedFileUrl != "-1")
{
updates.Add(Builders.Update.Set(f => f.ContractedFileUrl, request.ContractedFileUrl));
}
if (request.ContractedFileUrl != "-1")
{
updates.Add(Builders.Update.Set(f => f.ContractedFileUrl, request.ContractedFileUrl));
}
if (request.ContractedTime != null)
{
updates.Add(Builders.Update.Set(f => f.ContractedTime, request.ContractedTime));
}
if (request.AuditState != null)
{
updates.Add(Builders.Update.Set(f => f.AuditState, request.AuditState));
}
if (request.ServicePacks != null)
{
updates.Add(Builders.Update.Set(f => f.ServicePacks, request.ServicePacks));
}
if (request.ServiceStartDate != null)
{
updates.Add(Builders.Update.Set(f => f.ServiceStartDate, request.ServiceStartDate));
}
if (request.ServiceEndDate != null)
{
updates.Add(Builders.Update.Set(f => f.ServiceEndDate, request.ServiceEndDate));
}
if (request.Photos != null)
{
updates.Add(Builders.Update.Set(f => f.Photos, request.Photos));
}
if (request.Notes != "-1")
{
updates.Add(Builders.Update.Set(f => f.Notes, request.Notes));
}
var update = Builders.Update.Combine(updates);
var result = await _contractRecordDBRepository.UpdateOneAsync(filter, update) > 0;
if (request.ContractState != null && result)
{
var contractFilter = Builders.Filter.Eq(x => x.Code, request.Code);
var contractEntity = await _contractRecordDBRepository.FindOneAsync(contractFilter);
if (contractEntity != null && !string.IsNullOrWhiteSpace(contractEntity.ContractedPatient))
{
await UpdatePatientContactStateAsync(contractEntity.ContractedPatient);
}
}
return result;
}
private async Task ConvertToDTO(ContractRecordEntity entity, string operationDoctor)
{
if (entity == null) return null;
var record = entity?.MappingTo();
if (!string.IsNullOrWhiteSpace(entity.ContractedDoctor))
{
var filter = Builders.Filter.Eq(f => f.Code, entity.ContractedDoctor);
var userInfo = await _userDBRepository.FindOneAsync(filter);
record.ContractedDoctorCode = userInfo?.Code;
record.ContractedDoctor = !string.IsNullOrWhiteSpace(userInfo?.RealName) ? userInfo?.RealName : userInfo?.UserName;
if (!string.IsNullOrWhiteSpace(userInfo?.OrganizationCode))
{
var filterOrg = Builders.Filter.Eq(f => f.Code, userInfo.OrganizationCode);
var orgInfo = await _organizationDBRepository.FindOneAsync(filterOrg);
record.OrganizationName = orgInfo?.OrganizationName;
}
}
if (!string.IsNullOrWhiteSpace(entity.ContractedTeam))
{
var filter = Builders.Filter.Eq(f => f.Code, entity.ContractedTeam);
var teamInfo = await _teamDBRepository.FindOneAsync(filter);
record.ContractedTeam = teamInfo?.TeamName;
record.ContractedTeamCode = teamInfo?.Code;
record.SupervisingPhysician = teamInfo?.Principal;
}
if (entity.ServicePacks != null && entity.ServicePacks.Count > 0)
{
var packRequest = new GetServicePackListDBRequest { Codes = entity.ServicePacks.ToList(), OperationDoctor = operationDoctor };
record.ServicePacks = await GetServicePackListAsync(packRequest);
}
if (!string.IsNullOrWhiteSpace(entity.ContractedPatient))
{
var filter = Builders.Filter.Eq(f => f.Code, entity.ContractedPatient);
var patientInfo = await _patientDBRepository.FindOneAsync(filter);
var dto = await ConvertToDTO(patientInfo);
if (dto != null)
{
record.PatientName = dto.PatientName;
record.Birthday = dto.Birthday;
record.CardNo = dto.CardNo;
record.PatientGender = dto.PatientGender;
record.PatientAddress = dto.PatientAddress;
record.Nationality = dto.Nationality;
record.Phone = dto.Phone;
if (dto.CrowdLabels != null && dto.CrowdLabels.Count > 0)
{
record.CrowdLabels = dto.CrowdLabels;
record.LabelNames = dto.LabelNames;
}
else
{
record.CrowdLabels = new List();
}
}
}
return record;
}
private async Task> ConvertToDTOList(List entitys, string operationDoctor)
{
var userCodes = entitys.Select(f => f.ContractedDoctor).Distinct();
var filterUsers = Builders.Filter.In(f => f.Code, userCodes);
var usersInfo = await _userDBRepository.FindAllAsync(filterUsers);
var orgCodes = usersInfo.Select(u => u.OrganizationCode).Distinct();
var filterOrgs = Builders.Filter.In(f => f.Code, orgCodes);
var orgsInfo = await _organizationDBRepository.FindAllAsync(filterOrgs);
var teamCodes = entitys.Select(f => f.ContractedTeam).Distinct();
var filterTeams = Builders.Filter.In(f => f.Code, teamCodes);
var teamsInfo = await _teamDBRepository.FindAllAsync(filterTeams);
var packsCodes = entitys.SelectMany(f => f.ServicePacks ?? new List()).Distinct();
var filterPacks = new GetServicePackListDBRequest { Codes = packsCodes.ToList(), OperationDoctor = operationDoctor };
var packsInfo = await GetServicePackListAsync(filterPacks);
var patientCodes = entitys.Select(f => f.ContractedPatient).Distinct();
var filterPatients = Builders.Filter.In(f => f.Code, patientCodes);
var patientsInfo = await _patientDBRepository.FindAllAsync(filterPatients);
var filterLabel = Builders.Filter.In(f => f.LabelTypeKey, new List { "RQFL", "CJJB", "TSZG" });
var labels = await _labelDBRepository.FindAllAsync(filterLabel);
var resultList = new List();
foreach (var entity in entitys)
{
if (entity == null)
{
continue;
}
var record = entity.MappingTo();
record.ContractedFileUrl = " ";
record.Photos = new List();
if (!string.IsNullOrWhiteSpace(entity.ContractedDoctor))
{
var userInfo = usersInfo.FirstOrDefault(w => w.Code == entity.ContractedDoctor);
record.ContractedDoctor = userInfo?.Code;
record.ContractedDoctor = !string.IsNullOrWhiteSpace(userInfo?.RealName) ? userInfo?.RealName : userInfo?.UserName;
if (!string.IsNullOrWhiteSpace(userInfo.OrganizationCode))
{
var orgInfo = orgsInfo.FirstOrDefault(w => w.Code == userInfo.OrganizationCode);
record.OrganizationName = orgInfo?.OrganizationName;
}
}
if (!string.IsNullOrWhiteSpace(entity.ContractedTeam))
{
var teamInfo = teamsInfo.FirstOrDefault(w => w.Code == entity.ContractedTeam);
record.ContractedTeam = teamInfo?.TeamName;
record.ContractedTeamCode = teamInfo?.Code;
record.SupervisingPhysician = teamInfo?.Principal;
}
if (entity.ServicePacks != null && entity.ServicePacks.Count > 0)
{
var packInfo = packsInfo.Where(w => entity.ServicePacks != null && entity.ServicePacks.Count > 0 && entity.ServicePacks.Contains(w.Code)).ToList();
record.ServicePacks = packInfo;
}
if (!string.IsNullOrWhiteSpace(entity.ContractedPatient))
{
var patientInfo = patientsInfo.FirstOrDefault(w => w.Code == entity.ContractedPatient);
if (patientInfo != null)
{
var dto = await ConvertToDTO(patientInfo);
if (dto != null)
{
record.PatientName = dto.PatientName;
record.Birthday = dto.Birthday;
record.CardNo = dto.CardNo;
record.PatientGender = dto.PatientGender;
record.PatientAddress = dto.PatientAddress;
record.Nationality = dto.Nationality;
record.Phone = dto.Phone;
record.CrowdLabels = dto.CrowdLabels;
record.LabelNames = dto.LabelNames;
}
}
}
resultList.Add(record);
}
return resultList;
}
private async Task> ConvertToDTOPage(PageCollection entitys, string operationDoctor)
{
var resultPage = new PageCollection
{
DataCount = entitys.DataCount,
CurrentPage = entitys.CurrentPage,
PageSize = entitys.PageSize,
PageData = await ConvertToDTOList(entitys.PageData, operationDoctor)
};
return resultPage;
}
public async Task GetPatientLastContractRecordAsync(GetPatientLastContractRecordDBRequest request)
{
var filter = Builders.Filter.Where(f => f.ContractedPatient == request.PatientCode);
filter = await AddPermissionFilter(filter, request.OperationDoctor);
var result = await _contractRecordDBRepository.FindOneAsync(filter, new FindOptions { Sort = Builders.Sort.Descending(f => f.CreateTime).Descending(f => f.ContractState) });
return await ConvertToDTO(result, request.OperationDoctor);
}
///
/// 更新签约记录状态
///
/// update request
///
public async Task UpdateContractRecordStateAsync(UpdateContractRecordStateDBRequest request)
{
AddDoctorCode(request.OperationDoctor);
var filter = Builders.Filter.Eq(f => f.Code, request.Code);
var updates = new List>();
if (request.ContractState != null)
{
updates.Add(Builders.Update.Set(f => f.ContractState, request.ContractState));
}
if (!string.IsNullOrWhiteSpace(request.Reason))
{
updates.Add(Builders.Update.Set(f => f.Reason, request.Reason));
}
var update = Builders.Update.Combine(updates);
var result = await _contractRecordDBRepository.UpdateOneAsync(filter, update) > 0;
if (result)
{
var contractFilter = Builders.Filter.Eq(x => x.Code, request.Code);
var contractEntity = await _contractRecordDBRepository.FindOneAsync(contractFilter);
if (contractEntity != null && !string.IsNullOrWhiteSpace(contractEntity.ContractedPatient))
{
await UpdatePatientContactStateAsync(contractEntity.ContractedPatient);
}
}
return result;
}
}
}