zhuangpei-mesbackend/DOAN.Service/MES/process/ProcessmodelProjectService.cs

576 lines
26 KiB
C#
Raw Normal View History

2025-11-03 16:57:55 +08:00
using DOAN.Model;
using DOAN.Model.Business;
2025-11-04 20:56:03 +08:00
using DOAN.Model.Dto;
using DOAN.Model.MES.process;
2025-11-03 16:57:55 +08:00
using DOAN.Repository;
using DOAN.Service.Business.IBusinessService;
2025-11-04 20:56:03 +08:00
using Infrastructure.Attribute;
using Infrastructure.Extensions;
using Microsoft.AspNetCore.Http;
using NPOI.SS.UserModel;
using NPOI.XSSF.UserModel;
using SqlSugar;
using System;
2025-11-03 16:57:55 +08:00
using System.Linq;
namespace DOAN.Service.Business
{
/// <summary>
/// 产品项目表Service业务层处理
/// </summary>
[AppService(ServiceType = typeof(IProcessmodelProjectService), ServiceLifetime = LifeTime.Transient)]
public class ProcessmodelProjectService : BaseService<ProcessmodelProject>, IProcessmodelProjectService
{
2025-11-04 20:56:03 +08:00
// 静态变量,标记是否已执行过删除旧数据
private static bool _hasDeletedOldData = false;
2025-11-03 16:57:55 +08:00
/// <summary>
/// 查询产品项目表列表
/// </summary>
/// <param name="parm"></param>
/// <returns></returns>
public PagedInfo<ProcessmodelProjectDto> GetList(ProcessmodelProjectQueryDto parm)
{
2025-11-04 20:56:03 +08:00
var predicate = Expressionable.Create<ProcessmodelProject>()
.AndIF(!string.IsNullOrEmpty(parm.ProjectCode), p => parm.ProjectCode.Contains(p.ProjectCode))
.AndIF(!string.IsNullOrEmpty(parm.ProjectName), p => parm.ProjectName.Contains(p.ProjectName));
2025-11-03 16:57:55 +08:00
var response = Queryable()
.Where(predicate.ToExpression())
.ToPage<ProcessmodelProject, ProcessmodelProjectDto>(parm);
return response;
}
/// <summary>
/// 获取详情
/// </summary>
/// <param name="Id"></param>
/// <returns></returns>
2025-11-04 20:56:03 +08:00
public ProcessmodelProject GetInfo(long Id)
2025-11-03 16:57:55 +08:00
{
var response = Queryable()
.Where(x => x.Id == Id)
.First();
return response;
}
/// <summary>
/// 添加产品项目表
/// </summary>
/// <param name="model"></param>
/// <returns></returns>
public ProcessmodelProject AddProcessmodelProject(ProcessmodelProject model)
{
return Context.Insertable(model).ExecuteReturnEntity();
}
/// <summary>
/// 修改产品项目表
/// </summary>
/// <param name="model"></param>
/// <returns></returns>
public int UpdateProcessmodelProject(ProcessmodelProject model)
{
//var response = Update(w => w.Id == model.Id, it => new ProcessmodelProject()
//{
// ProjectCode = model.ProjectCode,
// ProjectName = model.ProjectName,
// ProductCode = model.ProductCode,
// ProductName = model.ProductName,
// CreatedBy = model.CreatedBy,
// CreatedTime = model.CreatedTime,
// UpdatedBy = model.UpdatedBy,
// UpdatedTime = model.UpdatedTime,
//});
//return response;
return Update(model, true);
}
2025-11-04 20:56:03 +08:00
/// <summary>
/// 新增导入Excel
/// </summary>
/// <param name="formFile"></param>
/// <param name="username"></param>
/// <returns></returns>
public int AddImportExcel(IFormFile formFile, string username)
{
_hasDeletedOldData = false;
int insertCount = 0;
using (var stream = formFile.OpenReadStream())
{
try
{
List<ProcessmodelProject> projectList = new List<ProcessmodelProject>();
List<ProcessmodelRouting> routingList = new List<ProcessmodelRouting>();
List<ProcessmodelProcess> processList = new List<ProcessmodelProcess>();
List<ProcessmodelWorkStep> stepList = new List<ProcessmodelWorkStep>();
IWorkbook workbook = new XSSFWorkbook(stream);
ISheet sheet = workbook.GetSheet("Sheet1");
// 从第二行开始读取
for (int i = 1; i <= sheet.LastRowNum; i++)
{
IRow row = sheet.GetRow(i);
if (row == null) continue;
// 读取基础数据
string projectCode = GetCellStringValue(row.GetCell(0)); // A列项目号
string projectName = GetCellStringValue(row.GetCell(1)); // B列项目名称
string productCode = GetCellStringValue(row.GetCell(2)); // C列零件号
string productName = GetCellStringValue(row.GetCell(3)); // D列零件名称
string routingCode = GetCellStringValue(row.GetCell(4)); // E列工艺路线号
string routingName = GetCellStringValue(row.GetCell(5)); // F列工艺路线名称
string processCode = GetCellStringValue(row.GetCell(6)); // G列工序号
string processName = GetCellStringValue(row.GetCell(7)); // H列工序名称
string stepCode = GetCellStringValue(row.GetCell(8)); // I列工步号
string stepName = GetCellStringValue(row.GetCell(9)); // J列工步名称
// 跳过空行
if (string.IsNullOrEmpty(projectCode) && string.IsNullOrEmpty(productCode) &&
string.IsNullOrEmpty(routingCode) && string.IsNullOrEmpty(stepCode))
continue;
// 检查是否已存在相同的项目
if (!projectList.Any(p => p.ProjectCode == projectCode))
{
var project = new ProcessmodelProject
{
ProjectCode = projectCode,
ProjectName = projectName,
ProductCode = productCode,
ProductName = productName,
CreatedBy = username,
CreatedTime = DateTime.Now,
};
projectList.Add(project);
}
// 检查是否已存在相同的工艺路线
if (!routingList.Any(r => r.RoutingCode == routingCode))
{
var routing = new ProcessmodelRouting
{
RoutingCode = routingCode,
RoutingName = routingName,
ProductCode = productCode,
Description = $"{productName}的工艺路线",
Version = "1.0",
CreateTime = DateTime.Now,
IsActive = "1"
};
routingList.Add(routing);
}
// 检查是否已存在相同的工序
if (!processList.Any(p => p.ProcessCode == processCode))
{
var process = new ProcessmodelProcess
{
ProcessCode = processCode,
ProcessName = processName,
RoutingCode = routingCode,
//PorcessSeq = processSeq,
WorkCenter = "", // 可根据需要设置默认值
StandardTime = 0, // 可根据需要设置默认值
Description = $"{processName}工序",
CreateTime = DateTime.Now,
IsActive = "1"
};
processList.Add(process);
}
// 处理工步和唯一键K列到O列
for (int col = 10; col <= 14; col++) // K列到O列
{
string uniqueValue = GetCellStringValue(row.GetCell(col));
if (!string.IsNullOrEmpty(uniqueValue))
{
if (!stepList.Any(p => p.StepCode == stepCode))
{
var workStep = new ProcessmodelWorkStep
{
StepCode = stepCode,
StepName = stepName,
ProcessCode = processCode,
Description = $"{stepName}工步",
IsActive = "1",
UniqueValue = uniqueValue,
CreateTime = DateTime.Now,
CreateBy = username,
Remark = $"导入自项目:{projectCode}, 产品:{productCode}"
};
stepList.Add(workStep);
}
}
}
}
Context.Ado.BeginTran();
try
{
// 批量插入数据(按依赖顺序)
// 1. 先插入项目表
if (projectList.Count != 0)
{
Context.Insertable(projectList).ExecuteCommand();
insertCount += projectList.Count;
}
// 2. 插入工艺路线表
if (routingList.Count != 0)
{
Context.Insertable(routingList).ExecuteCommand();
insertCount += routingList.Count;
}
// 3. 插入工序表
if (processList.Count != 0)
{
Context.Insertable(processList).ExecuteCommand();
insertCount += processList.Count;
}
// 4. 最后插入工步表
if (stepList.Count != 0)
{
Context.Insertable(stepList).ExecuteCommand();
insertCount += stepList.Count;
}
Context.Ado.CommitTran(); // 成功提交
}
catch
{
Context.Ado.RollbackTran(); // 失败回滚
throw;
}
return insertCount;
}
catch (Exception ex)
{
// 建议记录日志,而不是直接抛出
// Log.Error(ex, "导入Excel失败");
throw; // 不要 throw ex直接 throw 保留堆栈
}
}
}
/// <summary>
/// 覆盖导入Excel
/// </summary>
/// <param name="formFile"></param>
/// <param name="username"></param>
/// <returns></returns>
public int CoverImportExcel(IFormFile formFile, string username)
{
_hasDeletedOldData = false;
int insertCount = 0;
using (var stream = formFile.OpenReadStream())
{
try
{
List<ProcessmodelProject> projectList = new List<ProcessmodelProject>();
List<ProcessmodelRouting> routingList = new List<ProcessmodelRouting>();
List<ProcessmodelProcess> processList = new List<ProcessmodelProcess>();
List<ProcessmodelWorkStep> stepList = new List<ProcessmodelWorkStep>();
IWorkbook workbook = new XSSFWorkbook(stream);
ISheet sheet = workbook.GetSheet("Sheet1");
// 从第二行开始读取
for (int i = 1; i <= sheet.LastRowNum; i++)
{
IRow row = sheet.GetRow(i);
if (row == null) continue;
// 读取基础数据
string projectCode = GetCellStringValue(row.GetCell(0)); // A列项目号
string projectName = GetCellStringValue(row.GetCell(1)); // B列项目名称
string productCode = GetCellStringValue(row.GetCell(2)); // C列零件号
string productName = GetCellStringValue(row.GetCell(3)); // D列零件名称
string routingCode = GetCellStringValue(row.GetCell(4)); // E列工艺路线号
string routingName = GetCellStringValue(row.GetCell(5)); // F列工艺路线名称
string processCode = GetCellStringValue(row.GetCell(6)); // G列工序号
string processName = GetCellStringValue(row.GetCell(7)); // H列工序名称
string stepCode = GetCellStringValue(row.GetCell(8)); // I列工步号
string stepName = GetCellStringValue(row.GetCell(9)); // J列工步名称
// 跳过空行
if (string.IsNullOrEmpty(projectCode) && string.IsNullOrEmpty(productCode) &&
string.IsNullOrEmpty(routingCode) && string.IsNullOrEmpty(stepCode))
continue;
// 检查是否已存在相同的项目
if (!projectList.Any(p => p.ProjectCode == projectCode))
{
var project = new ProcessmodelProject
{
ProjectCode = projectCode,
ProjectName = projectName,
ProductCode = productCode,
ProductName = productName,
CreatedBy = username,
CreatedTime = DateTime.Now,
};
projectList.Add(project);
}
// 检查是否已存在相同的工艺路线
if (!routingList.Any(r => r.RoutingCode == routingCode))
{
var routing = new ProcessmodelRouting
{
RoutingCode = routingCode,
RoutingName = routingName,
ProductCode = productCode,
Description = $"{productName}的工艺路线",
Version = "1.0",
CreateTime = DateTime.Now,
IsActive = "1"
};
routingList.Add(routing);
}
// 检查是否已存在相同的工序
if (!processList.Any(p => p.ProcessCode == processCode))
{
var process = new ProcessmodelProcess
{
ProcessCode = processCode,
ProcessName = processName,
RoutingCode = routingCode,
//PorcessSeq = processSeq,
WorkCenter = "", // 可根据需要设置默认值
StandardTime = 0, // 可根据需要设置默认值
Description = $"{processName}工序",
CreateTime = DateTime.Now,
IsActive = "1"
};
processList.Add(process);
}
// 处理工步和唯一键K列到O列
for (int col = 10; col <= 14; col++) // K列到O列
{
string uniqueValue = GetCellStringValue(row.GetCell(col));
if (!string.IsNullOrEmpty(uniqueValue))
{
var workStep = new ProcessmodelWorkStep
{
StepCode = stepCode,
StepName = stepName,
ProcessCode = processCode,
Description = $"{stepName}工步",
IsActive = "1",
UniqueValue = uniqueValue,
CreateTime = DateTime.Now,
CreateBy = username,
Remark = $"导入自项目:{projectCode}, 产品:{productCode}"
};
stepList.Add(workStep);
}
}
}
Context.Ado.BeginTran();
// 开启事务:使用 SqlSugar 的 UsingTran 方法(自动管理事务生命周期)
try
{
// 1. 删除旧数据(子表→父表,避免外键约束)
Context.Deleteable<ProcessmodelWorkStep>().ExecuteCommand();
Context.Deleteable<ProcessmodelProcess>().ExecuteCommand();
Context.Deleteable<ProcessmodelRouting>().ExecuteCommand();
Context.Deleteable<ProcessmodelProject>().ExecuteCommand();
// 2. 插入新数据(父表→子表,保证外键关联有效)
if (projectList != null && projectList.Count != 0)
{
Context.Insertable(projectList).ExecuteCommand();
insertCount += projectList.Count;
}
if (routingList != null && routingList.Count != 0)
{
Context.Insertable(routingList).ExecuteCommand();
insertCount += routingList.Count;
}
if (processList != null && processList.Count != 0)
{
Context.Insertable(processList).ExecuteCommand();
insertCount += processList.Count;
}
if (stepList != null && stepList.Count != 0)
{
Context.Insertable(stepList).ExecuteCommand();
insertCount += stepList.Count;
}
Context.Ado.CommitTran(); // 成功提交
}
catch
{
Context.Ado.RollbackTran(); // 失败回滚
throw;
}
return insertCount;
}
catch (Exception ex)
{
// 记录日志
throw new Exception($"导入Excel失败: {ex.Message}", ex);
}
}
}
/// <summary>
/// 导出
/// </summary>
/// <returns></returns>
public (byte[] fileBytes, string fileName) ExportProjectExcel()
{
// 创建工作簿
IWorkbook workbook = new XSSFWorkbook();
ISheet sheet = workbook.CreateSheet("Sheet1");
// 创建表头行
IRow headerRow = sheet.CreateRow(0);
headerRow.CreateCell(0).SetCellValue("项目号");
headerRow.CreateCell(1).SetCellValue("项目名称");
headerRow.CreateCell(2).SetCellValue("零件号");
headerRow.CreateCell(3).SetCellValue("零件名称");
headerRow.CreateCell(4).SetCellValue("工艺路线号");
headerRow.CreateCell(5).SetCellValue("工艺路线名称");
headerRow.CreateCell(6).SetCellValue("工序号");
headerRow.CreateCell(7).SetCellValue("工序名称");
headerRow.CreateCell(8).SetCellValue("工步号");
headerRow.CreateCell(9).SetCellValue("工步名称");
headerRow.CreateCell(10).SetCellValue("唯一键");
headerRow.CreateCell(11).SetCellValue("唯一键");
headerRow.CreateCell(12).SetCellValue("唯一键");
headerRow.CreateCell(13).SetCellValue("唯一键");
headerRow.CreateCell(14).SetCellValue("唯一键");
headerRow.CreateCell(15).SetCellValue("唯一键");
// 查询数据库获取数据
var projects = Context.Queryable<ProcessmodelProject>().ToList();
var routings = Context.Queryable<ProcessmodelRouting>().ToList();
var processes = Context.Queryable<ProcessmodelProcess>().ToList();
var workSteps = Context.Queryable<ProcessmodelWorkStep>().ToList();
// 构建导出数据
var exportData = new List<dynamic>();
// 遍历工步表,然后关联其他表
foreach (var step in workSteps)
{
// 找到对应的工序
var process = processes.FirstOrDefault(p => p.ProcessCode == step.ProcessCode);
if (process == null) continue;
// 找到对应的工艺路线
var routing = routings.FirstOrDefault(r => r.RoutingCode == process.RoutingCode);
if (routing == null) continue;
// 找到对应的项目
var project = projects.FirstOrDefault(p => p.ProductCode == routing.ProductCode);
if (project == null) continue;
exportData.Add(new
{
Project = project,
Routing = routing,
Process = process,
Step = step
});
}
// 按工步代码和工序代码分组,因为同一工序下的工步代码可能相同,但不同工序的工步代码可能相同
var groupedData = exportData
.GroupBy(x => new { x.Step.StepCode, x.Process.ProcessCode })
.Select(g => new
{
Project = g.First().Project,
Routing = g.First().Routing,
Process = g.First().Process,
StepCode = g.Key.StepCode,
StepName = g.First().Step.StepName,
UniqueValues = g.Select(x => x.Step.UniqueValue).Distinct().ToList()
})
.ToList();
int rowIndex = 1;
foreach (var item in groupedData)
{
IRow dataRow = sheet.CreateRow(rowIndex++);
// 填充基础数据
dataRow.CreateCell(0).SetCellValue(item.Project.ProjectCode ?? "");
dataRow.CreateCell(1).SetCellValue(item.Project.ProjectName ?? "");
dataRow.CreateCell(2).SetCellValue(item.Project.ProductCode ?? "");
dataRow.CreateCell(3).SetCellValue(item.Project.ProductName ?? "");
dataRow.CreateCell(4).SetCellValue(item.Routing.RoutingCode ?? "");
dataRow.CreateCell(5).SetCellValue(item.Routing.RoutingName ?? "");
dataRow.CreateCell(6).SetCellValue(item.Process.ProcessCode ?? "");
dataRow.CreateCell(7).SetCellValue(item.Process.ProcessName ?? "");
dataRow.CreateCell(8).SetCellValue(item.StepCode ?? "");
dataRow.CreateCell(9).SetCellValue(item.StepName ?? "");
// 处理统一编号数据
for (int col = 10; col <= 15; col++)
{
if (col - 10 < item.UniqueValues.Count)
{
dataRow.CreateCell(col).SetCellValue(item.UniqueValues[col - 10] ?? "");
}
else
{
dataRow.CreateCell(col).SetCellValue("");
}
}
}
// 自动调整列宽
for (int i = 0; i < 16; i++)
{
sheet.AutoSizeColumn(i);
}
// 将工作簿写入内存流
using (MemoryStream ms = new MemoryStream())
{
workbook.Write(ms);
return (ms.ToArray(), "产品项目模板_导出.xlsx");
}
}
// 辅助方法:获取单元格字符串值
private string GetCellStringValue(ICell cell)
{
if (cell == null) return string.Empty;
switch (cell.CellType)
{
case CellType.String:
return cell.StringCellValue?.Trim();
case CellType.Numeric:
return cell.NumericCellValue.ToString();
case CellType.Boolean:
return cell.BooleanCellValue.ToString();
case CellType.Formula:
try
{
return cell.StringCellValue?.Trim();
}
catch
{
return cell.NumericCellValue.ToString();
}
default:
return string.Empty;
}
}
2025-11-03 16:57:55 +08:00
}
}