新增生产-前缫看台排班,并导入机组车台与看台排班数据
功能: - 后端新增 KtpbCtgs / KtpbDcgs / KtpbZbzs 三张表、KtpbService 与 api/prod/ktpb 接口 (车头工、挡车工、值班长分页查询与维护,挡车工按车间+班次+机组整组替换保存) - 挡车数按 F9 口径自动重算:接壤车台各计 0.5,保存时服务端重新计算并校验车台范围 - 前端新增 /prod/qianxian/ktpb 看台排班页(三页签 + 车间/班次/机组过滤 + 批量编辑弹窗) - 新增通用职工选择弹窗 EmployeeSelect(单选/多选,按部门过滤) - 生产-前缫菜单下新增「看台排班」,权限 prod:ktpb:list 数据导入: - 重新生成 biz_prod_qs_jzct.json,新增 ktpb_ctg / ktpb_dcg / ktpb_zbz 三个内嵌资源 - F9 部门 Id 经 DeptData 映射到本系统部门;职工按原始雪花 Id 关联 - 剔除软删除/脏数据:机组车台 24 条、车头工 33 条、挡车工 202 条(34 组)、值班长 7 条 - 导入幂等:机组车台按车间+机组 upsert,排班按业务唯一键去重,已维护的组不覆盖 其他:同步工作进度-12 文档与开发数据库快照
This commit is contained in:
@@ -0,0 +1,169 @@
|
||||
using F9WebAiTest.Application.Common;
|
||||
using F9WebAiTest.Application.Dtos.Prod;
|
||||
using F9WebAiTest.Application.Services.Prod;
|
||||
using F9WebAiTest.Domain.Common;
|
||||
using F9WebAiTest.Domain.Enums.SYS.Employees;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
|
||||
namespace F9WebAiTest.Api.Controllers.Prod;
|
||||
|
||||
/// <summary>看台排班(生产-前缫):车头工 / 挡车工 / 值班长</summary>
|
||||
[ApiController]
|
||||
[Route("api/prod/ktpb")]
|
||||
[Authorize]
|
||||
public class KtpbController : ControllerBase
|
||||
{
|
||||
private readonly IKtpbService _svc;
|
||||
public KtpbController(IKtpbService svc) => _svc = svc;
|
||||
|
||||
// ---------- 下拉 ----------
|
||||
|
||||
/// <summary>车间下拉(职责类型=前缫)</summary>
|
||||
[HttpGet("qianxian-deps")]
|
||||
public async Task<IActionResult> GetQianxianDeps()
|
||||
=> Ok(ApiResult<List<ChejianbanciDepOptionDto>>.Ok(await _svc.GetQianxianDepsAsync()));
|
||||
|
||||
/// <summary>机组下拉(含车台范围,来源于机组车台)</summary>
|
||||
[HttpGet("jizu-options")]
|
||||
public async Task<IActionResult> GetJizuOptions([FromQuery] long depId)
|
||||
=> Ok(ApiResult<List<KtpbJizuOptionDto>>.Ok(await _svc.GetJizuOptionsAsync(depId)));
|
||||
|
||||
// ---------- 车头工 ----------
|
||||
|
||||
[HttpGet("ctg")]
|
||||
public async Task<IActionResult> GetCtgPaged([FromQuery] long depId = 0, [FromQuery] Prod_Banci_Enum? banci = null,
|
||||
[FromQuery] int? jizu = null, [FromQuery] string like = "", [FromQuery] int pageIndex = 1,
|
||||
[FromQuery] int pageSize = 20)
|
||||
=> Ok(ApiResult<PageResult<KtpbctgReadDto_View>>.Ok(
|
||||
await _svc.GetCtgPagedAsync(depId, banci, jizu, like ?? string.Empty, pageIndex, pageSize)));
|
||||
|
||||
[HttpGet("ctg/{id}")]
|
||||
public async Task<IActionResult> GetCtgById(long id)
|
||||
{
|
||||
try { return Ok(ApiResult<KtpbctgReadDto_View>.Ok(await _svc.GetCtgByIdAsync(id))); }
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpPost("ctg")]
|
||||
public async Task<IActionResult> CreateCtg([FromBody] KtpbctgReadDto_View dto)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.CreateCtgAsync(dto);
|
||||
return Ok(ApiResult<object>.Ok(null, "新增成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpPut("ctg/{id}")]
|
||||
public async Task<IActionResult> UpdateCtg(long id, [FromBody] KtpbctgReadDto_View dto)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.UpdateCtgAsync(id, dto);
|
||||
return Ok(ApiResult<object>.Ok(null, "修改成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpDelete("ctg/{id}")]
|
||||
public async Task<IActionResult> DeleteCtg(long id)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.DeleteCtgAsync(id);
|
||||
return Ok(ApiResult<object>.Ok(null, "删除成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
// ---------- 挡车工 ----------
|
||||
|
||||
[HttpGet("dcg")]
|
||||
public async Task<IActionResult> GetDcgPaged([FromQuery] long depId = 0, [FromQuery] Prod_Banci_Enum? banci = null,
|
||||
[FromQuery] int? jizu = null, [FromQuery] string like = "", [FromQuery] int pageIndex = 1,
|
||||
[FromQuery] int pageSize = 20)
|
||||
=> Ok(ApiResult<PageResult<KtpbdcgReadDto_View>>.Ok(
|
||||
await _svc.GetDcgPagedAsync(depId, banci, jizu, like ?? string.Empty, pageIndex, pageSize)));
|
||||
|
||||
/// <summary>某「车间+班次+机组」下的整组排班(批量编辑弹窗)</summary>
|
||||
[HttpGet("dcg/group")]
|
||||
public async Task<IActionResult> GetDcgGroup([FromQuery] long depId, [FromQuery] Prod_Banci_Enum banci,
|
||||
[FromQuery] int jizu)
|
||||
{
|
||||
try { return Ok(ApiResult<List<KtpbdcgReadDto_View>>.Ok(await _svc.GetDcgGroupAsync(depId, banci, jizu))); }
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
/// <summary>整组替换保存(传空集合表示清空该组)</summary>
|
||||
[HttpPost("dcg/batch")]
|
||||
public async Task<IActionResult> SaveDcgBatch([FromBody] KtpbdcgBatchDto dto)
|
||||
{
|
||||
try
|
||||
{
|
||||
var count = await _svc.SaveDcgBatchAsync(dto);
|
||||
return Ok(ApiResult<object>.Ok(count, count > 0 ? $"已保存 {count} 条排班" : "已清空该组排班"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpDelete("dcg/{id}")]
|
||||
public async Task<IActionResult> DeleteDcg(long id)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.DeleteDcgAsync(id);
|
||||
return Ok(ApiResult<object>.Ok(null, "删除成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
// ---------- 值班长 ----------
|
||||
|
||||
[HttpGet("zbz")]
|
||||
public async Task<IActionResult> GetZbzPaged([FromQuery] long depId = 0, [FromQuery] Prod_Banci_Enum? banci = null,
|
||||
[FromQuery] string like = "", [FromQuery] int pageIndex = 1, [FromQuery] int pageSize = 20)
|
||||
=> Ok(ApiResult<PageResult<KtpbzbzReadDto_View>>.Ok(
|
||||
await _svc.GetZbzPagedAsync(depId, banci, like ?? string.Empty, pageIndex, pageSize)));
|
||||
|
||||
[HttpGet("zbz/{id}")]
|
||||
public async Task<IActionResult> GetZbzById(long id)
|
||||
{
|
||||
try { return Ok(ApiResult<KtpbzbzReadDto_View>.Ok(await _svc.GetZbzByIdAsync(id))); }
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpPost("zbz")]
|
||||
public async Task<IActionResult> CreateZbz([FromBody] KtpbzbzReadDto_View dto)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.CreateZbzAsync(dto);
|
||||
return Ok(ApiResult<object>.Ok(null, "新增成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpPut("zbz/{id}")]
|
||||
public async Task<IActionResult> UpdateZbz(long id, [FromBody] KtpbzbzReadDto_View dto)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.UpdateZbzAsync(id, dto);
|
||||
return Ok(ApiResult<object>.Ok(null, "修改成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
|
||||
[HttpDelete("zbz/{id}")]
|
||||
public async Task<IActionResult> DeleteZbz(long id)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _svc.DeleteZbzAsync(id);
|
||||
return Ok(ApiResult<object>.Ok(null, "删除成功"));
|
||||
}
|
||||
catch (ServiceException ex) { return StatusCode(ex.Code, ApiResult<object>.Fail(ex.Message, ex.Code)); }
|
||||
}
|
||||
}
|
||||
Binary file not shown.
@@ -27,6 +27,7 @@ public static class DependencyInjection
|
||||
services.AddScoped<IXdjyService, XdjyService>();
|
||||
services.AddScoped<IHbjyService, HbjyService>();
|
||||
services.AddScoped<IChejianBanciService, ChejianBanciService>();
|
||||
services.AddScoped<IKtpbService, KtpbService>();
|
||||
services.AddScoped<INotificationService, NotificationService>();
|
||||
services.AddScoped<IReportService, ReportService>();
|
||||
|
||||
|
||||
@@ -0,0 +1,70 @@
|
||||
using F9WebAiTest.Domain.Enums.SYS.Employees;
|
||||
|
||||
namespace F9WebAiTest.Application.Dtos.Prod;
|
||||
|
||||
// ==================== 车头工看台排班 ====================
|
||||
|
||||
/// <summary>车头工看台排班(列表/编辑)</summary>
|
||||
public class KtpbctgReadDto_View
|
||||
{
|
||||
public long Id { get; set; }
|
||||
public long DepId { get; set; }
|
||||
public string DeptName { get; set; } = "";
|
||||
public Prod_Banci_Enum Banci { get; set; }
|
||||
public string BanciName { get; set; } = "";
|
||||
public int Jizu { get; set; }
|
||||
public long Ygid1 { get; set; }
|
||||
public string Ygid1Name { get; set; } = "";
|
||||
public long Ygid2 { get; set; }
|
||||
public string Ygid2Name { get; set; } = "";
|
||||
}
|
||||
|
||||
// ==================== 挡车工看台排班 ====================
|
||||
|
||||
/// <summary>挡车工看台排班(列表/编辑)</summary>
|
||||
public class KtpbdcgReadDto_View
|
||||
{
|
||||
public long Id { get; set; }
|
||||
public long DepId { get; set; }
|
||||
public string DeptName { get; set; } = "";
|
||||
public Prod_Banci_Enum Banci { get; set; }
|
||||
public string BanciName { get; set; } = "";
|
||||
public int Jizu { get; set; }
|
||||
public int ChetaiStart { get; set; }
|
||||
public int ChetaiEnd { get; set; }
|
||||
public long YgId { get; set; }
|
||||
public string YgName { get; set; } = "";
|
||||
public double Dangcheshu { get; set; }
|
||||
}
|
||||
|
||||
/// <summary>挡车工批量编辑:一个「车间 + 班次 + 机组」下的整组排班替换</summary>
|
||||
public class KtpbdcgBatchDto
|
||||
{
|
||||
public long DepId { get; set; }
|
||||
public Prod_Banci_Enum Banci { get; set; }
|
||||
public int Jizu { get; set; }
|
||||
/// <summary>该组下的全部挡车工排班(为空表示清空该组)</summary>
|
||||
public List<KtpbdcgReadDto_View> Items { get; set; } = new();
|
||||
}
|
||||
|
||||
// ==================== 值班长排班 ====================
|
||||
|
||||
/// <summary>值班长排班(列表/编辑)</summary>
|
||||
public class KtpbzbzReadDto_View
|
||||
{
|
||||
public long Id { get; set; }
|
||||
public long DepId { get; set; }
|
||||
public string DeptName { get; set; } = "";
|
||||
public Prod_Banci_Enum Banci { get; set; }
|
||||
public string BanciName { get; set; } = "";
|
||||
public long YgId { get; set; }
|
||||
public string YgName { get; set; } = "";
|
||||
}
|
||||
|
||||
/// <summary>机组下拉项(来源于机组车台)</summary>
|
||||
public class KtpbJizuOptionDto
|
||||
{
|
||||
public int Jizu { get; set; }
|
||||
public int ChetaiStart { get; set; }
|
||||
public int ChetaiEnd { get; set; }
|
||||
}
|
||||
@@ -0,0 +1,443 @@
|
||||
using F9WebAiTest.Application.Common;
|
||||
using F9WebAiTest.Application.Dtos.Prod;
|
||||
using F9WebAiTest.Domain.Common;
|
||||
using F9WebAiTest.Domain.Entities.Base;
|
||||
using F9WebAiTest.Domain.Entities.Prod;
|
||||
using F9WebAiTest.Domain.Enums.SYS.Departments;
|
||||
using F9WebAiTest.Domain.Enums.SYS.Employees;
|
||||
using SysDept = F9WebAiTest.Domain.Entities.SYS.Departments;
|
||||
using SysEmp = F9WebAiTest.Domain.Entities.SYS.Employees;
|
||||
|
||||
namespace F9WebAiTest.Application.Services.Prod;
|
||||
|
||||
/// <summary>
|
||||
/// 看台排班(生产-前缫):车头工 / 挡车工 / 值班长三类排班的查询与维护。
|
||||
/// 对应 F9 WinClient\F9.Business.Prod\QS\KTPB 下的 Page_KTPB 与三个编辑页。
|
||||
/// </summary>
|
||||
public interface IKtpbService
|
||||
{
|
||||
/// <summary>车间下拉(职责类型=前缫)</summary>
|
||||
Task<List<ChejianbanciDepOptionDto>> GetQianxianDepsAsync();
|
||||
/// <summary>指定车间的机组下拉(含车台范围,来源于机组车台)</summary>
|
||||
Task<List<KtpbJizuOptionDto>> GetJizuOptionsAsync(long depId);
|
||||
|
||||
// 车头工
|
||||
Task<PageResult<KtpbctgReadDto_View>> GetCtgPagedAsync(long depId, Prod_Banci_Enum? banci, int? jizu,
|
||||
string keyword, int pageIndex, int pageSize);
|
||||
Task<KtpbctgReadDto_View> GetCtgByIdAsync(long id);
|
||||
Task CreateCtgAsync(KtpbctgReadDto_View dto);
|
||||
Task UpdateCtgAsync(long id, KtpbctgReadDto_View dto);
|
||||
Task DeleteCtgAsync(long id);
|
||||
|
||||
// 挡车工
|
||||
Task<PageResult<KtpbdcgReadDto_View>> GetDcgPagedAsync(long depId, Prod_Banci_Enum? banci, int? jizu,
|
||||
string keyword, int pageIndex, int pageSize);
|
||||
/// <summary>取某个「车间+班次+机组」下的整组排班(批量编辑弹窗用)</summary>
|
||||
Task<List<KtpbdcgReadDto_View>> GetDcgGroupAsync(long depId, Prod_Banci_Enum banci, int jizu);
|
||||
/// <summary>整组替换:先删除该组旧排班,再按提交内容重建(挡车数由服务端重算)</summary>
|
||||
Task<int> SaveDcgBatchAsync(KtpbdcgBatchDto dto);
|
||||
Task DeleteDcgAsync(long id);
|
||||
|
||||
// 值班长
|
||||
Task<PageResult<KtpbzbzReadDto_View>> GetZbzPagedAsync(long depId, Prod_Banci_Enum? banci,
|
||||
string keyword, int pageIndex, int pageSize);
|
||||
Task<KtpbzbzReadDto_View> GetZbzByIdAsync(long id);
|
||||
Task CreateZbzAsync(KtpbzbzReadDto_View dto);
|
||||
Task UpdateZbzAsync(long id, KtpbzbzReadDto_View dto);
|
||||
Task DeleteZbzAsync(long id);
|
||||
}
|
||||
|
||||
public class KtpbService : IKtpbService
|
||||
{
|
||||
private readonly IRepository<KtpbCtg> _ctgRepo;
|
||||
private readonly IRepository<KtpbDcg> _dcgRepo;
|
||||
private readonly IRepository<KtpbZbz> _zbzRepo;
|
||||
private readonly IRepository<JizuChetai> _jzctRepo;
|
||||
private readonly IRepository<SysDept.Department> _deptRepo;
|
||||
private readonly IRepository<SysEmp.Employee> _empRepo;
|
||||
|
||||
public KtpbService(IRepository<KtpbCtg> ctgRepo, IRepository<KtpbDcg> dcgRepo, IRepository<KtpbZbz> zbzRepo,
|
||||
IRepository<JizuChetai> jzctRepo, IRepository<SysDept.Department> deptRepo,
|
||||
IRepository<SysEmp.Employee> empRepo)
|
||||
{
|
||||
_ctgRepo = ctgRepo;
|
||||
_dcgRepo = dcgRepo;
|
||||
_zbzRepo = zbzRepo;
|
||||
_jzctRepo = jzctRepo;
|
||||
_deptRepo = deptRepo;
|
||||
_empRepo = empRepo;
|
||||
}
|
||||
|
||||
// ==================== 下拉 ====================
|
||||
|
||||
public async Task<List<ChejianbanciDepOptionDto>> GetQianxianDepsAsync()
|
||||
{
|
||||
var depts = await _deptRepo.GetAllAsync();
|
||||
return depts
|
||||
.Where(d => d.DutyType == Department_DutyType_Enum.前缫)
|
||||
.OrderBy(d => d.SortOrder).ThenBy(d => d.Id)
|
||||
.Select(d => new ChejianbanciDepOptionDto { Id = d.Id, Name = d.Name })
|
||||
.ToList();
|
||||
}
|
||||
|
||||
public async Task<List<KtpbJizuOptionDto>> GetJizuOptionsAsync(long depId)
|
||||
{
|
||||
var list = await _jzctRepo.FindAsync(x => x.DepartmentId == depId);
|
||||
return list.OrderBy(x => x.Jizu)
|
||||
.Select(x => new KtpbJizuOptionDto
|
||||
{
|
||||
Jizu = x.Jizu,
|
||||
ChetaiStart = x.ChetaiStart,
|
||||
ChetaiEnd = x.ChetaiEnd
|
||||
})
|
||||
.ToList();
|
||||
}
|
||||
|
||||
// ==================== 车头工 ====================
|
||||
|
||||
public async Task<PageResult<KtpbctgReadDto_View>> GetCtgPagedAsync(long depId, Prod_Banci_Enum? banci,
|
||||
int? jizu, string keyword, int pageIndex, int pageSize)
|
||||
{
|
||||
if (pageIndex <= 0) pageIndex = 1;
|
||||
if (pageSize <= 0) pageSize = 20;
|
||||
|
||||
var deptDict = await GetDeptDictAsync();
|
||||
var empDict = await GetEmpDictAsync();
|
||||
|
||||
var all = await _ctgRepo.GetAllAsync();
|
||||
var q = all.AsEnumerable();
|
||||
if (depId > 0) q = q.Where(x => x.DeptId == depId);
|
||||
if (banci.HasValue) q = q.Where(x => x.Banci == banci.Value);
|
||||
if (jizu.HasValue && jizu.Value > 0) q = q.Where(x => x.Jizu == jizu.Value);
|
||||
|
||||
var views = q.OrderBy(x => x.DeptId).ThenBy(x => x.Banci).ThenBy(x => x.Jizu)
|
||||
.Select(x => ToCtgView(x, deptDict, empDict)).ToList();
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(keyword))
|
||||
{
|
||||
var kw = keyword.Trim();
|
||||
views = views.Where(x => x.DeptName.Contains(kw) || x.BanciName.Contains(kw)
|
||||
|| x.Jizu.ToString().Contains(kw) || x.Ygid1Name.Contains(kw) || x.Ygid2Name.Contains(kw)).ToList();
|
||||
}
|
||||
|
||||
return Paged(views, pageIndex, pageSize);
|
||||
}
|
||||
|
||||
public async Task<KtpbctgReadDto_View> GetCtgByIdAsync(long id)
|
||||
{
|
||||
var e = await _ctgRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
return ToCtgView(e, await GetDeptDictAsync(), await GetEmpDictAsync());
|
||||
}
|
||||
|
||||
public async Task CreateCtgAsync(KtpbctgReadDto_View dto)
|
||||
{
|
||||
await ValidateGroupAsync(dto.DepId, dto.Banci, dto.Jizu, 0);
|
||||
if (dto.Ygid1 <= 0) throw new ServiceException("请选择车头工1");
|
||||
|
||||
await _ctgRepo.AddAsync(new KtpbCtg
|
||||
{
|
||||
DeptId = dto.DepId,
|
||||
Banci = dto.Banci,
|
||||
Jizu = dto.Jizu,
|
||||
Ygid1 = dto.Ygid1,
|
||||
Ygid2 = dto.Ygid2
|
||||
});
|
||||
await _ctgRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
public async Task UpdateCtgAsync(long id, KtpbctgReadDto_View dto)
|
||||
{
|
||||
var e = await _ctgRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
await ValidateGroupAsync(dto.DepId, dto.Banci, dto.Jizu, id);
|
||||
if (dto.Ygid1 <= 0) throw new ServiceException("请选择车头工1");
|
||||
|
||||
e.DeptId = dto.DepId;
|
||||
e.Banci = dto.Banci;
|
||||
e.Jizu = dto.Jizu;
|
||||
e.Ygid1 = dto.Ygid1;
|
||||
e.Ygid2 = dto.Ygid2;
|
||||
await _ctgRepo.UpdateAsync(e);
|
||||
await _ctgRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
public async Task DeleteCtgAsync(long id)
|
||||
{
|
||||
var e = await _ctgRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
await _ctgRepo.DeleteAsync(e);
|
||||
await _ctgRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
// ==================== 挡车工 ====================
|
||||
|
||||
public async Task<PageResult<KtpbdcgReadDto_View>> GetDcgPagedAsync(long depId, Prod_Banci_Enum? banci,
|
||||
int? jizu, string keyword, int pageIndex, int pageSize)
|
||||
{
|
||||
if (pageIndex <= 0) pageIndex = 1;
|
||||
if (pageSize <= 0) pageSize = 20;
|
||||
|
||||
var deptDict = await GetDeptDictAsync();
|
||||
var empDict = await GetEmpDictAsync();
|
||||
|
||||
var all = await _dcgRepo.GetAllAsync();
|
||||
var q = all.AsEnumerable();
|
||||
if (depId > 0) q = q.Where(x => x.DeptId == depId);
|
||||
if (banci.HasValue) q = q.Where(x => x.Banci == banci.Value);
|
||||
if (jizu.HasValue && jizu.Value > 0) q = q.Where(x => x.Jizu == jizu.Value);
|
||||
|
||||
var views = q.OrderBy(x => x.DeptId).ThenBy(x => x.Banci).ThenBy(x => x.Jizu)
|
||||
.ThenBy(x => x.ChetaiStart)
|
||||
.Select(x => ToDcgView(x, deptDict, empDict)).ToList();
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(keyword))
|
||||
{
|
||||
var kw = keyword.Trim();
|
||||
views = views.Where(x => x.DeptName.Contains(kw) || x.BanciName.Contains(kw)
|
||||
|| x.YgName.Contains(kw) || x.Jizu.ToString().Contains(kw)
|
||||
|| x.ChetaiStart.ToString().Contains(kw) || x.ChetaiEnd.ToString().Contains(kw)).ToList();
|
||||
}
|
||||
|
||||
return Paged(views, pageIndex, pageSize);
|
||||
}
|
||||
|
||||
public async Task<List<KtpbdcgReadDto_View>> GetDcgGroupAsync(long depId, Prod_Banci_Enum banci, int jizu)
|
||||
{
|
||||
if (depId <= 0) throw new ServiceException("请选择车间");
|
||||
var deptDict = await GetDeptDictAsync();
|
||||
var empDict = await GetEmpDictAsync();
|
||||
var list = await _dcgRepo.FindAsync(x => x.DeptId == depId && x.Banci == banci && x.Jizu == jizu);
|
||||
return list.OrderBy(x => x.ChetaiStart).ThenBy(x => x.ChetaiEnd)
|
||||
.Select(x => ToDcgView(x, deptDict, empDict)).ToList();
|
||||
}
|
||||
|
||||
public async Task<int> SaveDcgBatchAsync(KtpbdcgBatchDto dto)
|
||||
{
|
||||
if (dto.DepId <= 0) throw new ServiceException("请选择车间");
|
||||
if (dto.Jizu <= 0) throw new ServiceException("请选择机组");
|
||||
|
||||
var items = dto.Items ?? new List<KtpbdcgReadDto_View>();
|
||||
foreach (var it in items)
|
||||
{
|
||||
if (it.YgId <= 0) throw new ServiceException("存在未选择挡车工的记录");
|
||||
if (it.ChetaiStart <= 0) throw new ServiceException($"挡车工「{it.YgName}」的起始车台必须大于 0");
|
||||
if (it.ChetaiEnd < it.ChetaiStart)
|
||||
throw new ServiceException($"挡车工「{it.YgName}」的结束车台不能小于起始车台");
|
||||
}
|
||||
|
||||
var jzct = await _jzctRepo.FirstOrDefaultAsync(x => x.DepartmentId == dto.DepId && x.Jizu == dto.Jizu);
|
||||
if (jzct != null)
|
||||
{
|
||||
foreach (var it in items)
|
||||
{
|
||||
if (it.ChetaiStart < jzct.ChetaiStart || it.ChetaiEnd > jzct.ChetaiEnd)
|
||||
throw new ServiceException(
|
||||
$"挡车工「{it.YgName}」的车台范围 {it.ChetaiStart}-{it.ChetaiEnd} 超出该机组车台范围 " +
|
||||
$"{jzct.ChetaiStart}-{jzct.ChetaiEnd}");
|
||||
}
|
||||
}
|
||||
|
||||
// 整组替换:先删后建(对齐 F9 BatchReplaceKtpbdcgCommand)
|
||||
var olds = await _dcgRepo.FindAsync(x => x.DeptId == dto.DepId && x.Banci == dto.Banci && x.Jizu == dto.Jizu);
|
||||
if (olds.Count > 0) await _dcgRepo.HardDeleteRangeAsync(olds);
|
||||
|
||||
var dangche = RecalcDangcheshu(items);
|
||||
foreach (var it in items)
|
||||
{
|
||||
await _dcgRepo.AddAsync(new KtpbDcg
|
||||
{
|
||||
DeptId = dto.DepId,
|
||||
Banci = dto.Banci,
|
||||
Jizu = dto.Jizu,
|
||||
ChetaiStart = it.ChetaiStart,
|
||||
ChetaiEnd = it.ChetaiEnd,
|
||||
YgId = it.YgId,
|
||||
Dangcheshu = dangche.GetValueOrDefault(BuildDcgKey(it.ChetaiStart, it.ChetaiEnd, it.YgId), 0)
|
||||
});
|
||||
}
|
||||
await _dcgRepo.SaveChangesAsync();
|
||||
return items.Count;
|
||||
}
|
||||
|
||||
public async Task DeleteDcgAsync(long id)
|
||||
{
|
||||
var e = await _dcgRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
await _dcgRepo.DeleteAsync(e);
|
||||
await _dcgRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 挡车数计算(移植 F9 Page_KTPBDCG_Edit.CalculateSingleDangcheshu):
|
||||
/// 每个车台默认权重 1;若该车台被多条记录共享,且同时是某记录的起始点与某记录的结束点(接壤车台),权重取 0.5。
|
||||
/// </summary>
|
||||
private static Dictionary<string, double> RecalcDangcheshu(List<KtpbdcgReadDto_View> records)
|
||||
{
|
||||
var result = new Dictionary<string, double>();
|
||||
if (records.Count == 0) return result;
|
||||
|
||||
var counts = new Dictionary<int, int>();
|
||||
var starts = new HashSet<int>();
|
||||
var ends = new HashSet<int>();
|
||||
foreach (var r in records)
|
||||
{
|
||||
starts.Add(r.ChetaiStart);
|
||||
ends.Add(r.ChetaiEnd);
|
||||
for (var i = r.ChetaiStart; i <= r.ChetaiEnd; i++)
|
||||
counts[i] = counts.GetValueOrDefault(i) + 1;
|
||||
}
|
||||
|
||||
foreach (var r in records)
|
||||
{
|
||||
double total = 0;
|
||||
for (var i = r.ChetaiStart; i <= r.ChetaiEnd; i++)
|
||||
{
|
||||
double weight = 1;
|
||||
if (counts.GetValueOrDefault(i) > 1 && starts.Contains(i) && ends.Contains(i)) weight = 0.5;
|
||||
total += weight;
|
||||
}
|
||||
result[BuildDcgKey(r.ChetaiStart, r.ChetaiEnd, r.YgId)] = Math.Round(total, 2);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
private static string BuildDcgKey(int start, int end, long ygId) => $"{start}-{end}-{ygId}";
|
||||
|
||||
// ==================== 值班长 ====================
|
||||
|
||||
public async Task<PageResult<KtpbzbzReadDto_View>> GetZbzPagedAsync(long depId, Prod_Banci_Enum? banci,
|
||||
string keyword, int pageIndex, int pageSize)
|
||||
{
|
||||
if (pageIndex <= 0) pageIndex = 1;
|
||||
if (pageSize <= 0) pageSize = 20;
|
||||
|
||||
var deptDict = await GetDeptDictAsync();
|
||||
var empDict = await GetEmpDictAsync();
|
||||
|
||||
var all = await _zbzRepo.GetAllAsync();
|
||||
var q = all.AsEnumerable();
|
||||
if (depId > 0) q = q.Where(x => x.DeptId == depId);
|
||||
if (banci.HasValue) q = q.Where(x => x.Banci == banci.Value);
|
||||
|
||||
var views = q.OrderBy(x => x.DeptId).ThenBy(x => x.Banci).ThenBy(x => x.Id)
|
||||
.Select(x => ToZbzView(x, deptDict, empDict)).ToList();
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(keyword))
|
||||
{
|
||||
var kw = keyword.Trim();
|
||||
views = views.Where(x => x.DeptName.Contains(kw) || x.BanciName.Contains(kw) || x.YgName.Contains(kw))
|
||||
.ToList();
|
||||
}
|
||||
|
||||
return Paged(views, pageIndex, pageSize);
|
||||
}
|
||||
|
||||
public async Task<KtpbzbzReadDto_View> GetZbzByIdAsync(long id)
|
||||
{
|
||||
var e = await _zbzRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
return ToZbzView(e, await GetDeptDictAsync(), await GetEmpDictAsync());
|
||||
}
|
||||
|
||||
public async Task CreateZbzAsync(KtpbzbzReadDto_View dto)
|
||||
{
|
||||
if (dto.DepId <= 0) throw new ServiceException("请选择车间");
|
||||
if (dto.YgId <= 0) throw new ServiceException("请选择值班长");
|
||||
|
||||
var dup = await _zbzRepo.AnyAsync(x => x.DeptId == dto.DepId && x.Banci == dto.Banci && x.YgId == dto.YgId);
|
||||
if (dup) throw new ServiceException("该车间该班次已存在此值班长排班");
|
||||
|
||||
await _zbzRepo.AddAsync(new KtpbZbz { DeptId = dto.DepId, Banci = dto.Banci, YgId = dto.YgId });
|
||||
await _zbzRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
public async Task UpdateZbzAsync(long id, KtpbzbzReadDto_View dto)
|
||||
{
|
||||
var e = await _zbzRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
if (dto.DepId <= 0) throw new ServiceException("请选择车间");
|
||||
if (dto.YgId <= 0) throw new ServiceException("请选择值班长");
|
||||
|
||||
var dup = await _zbzRepo.AnyAsync(x => x.Id != id && x.DeptId == dto.DepId
|
||||
&& x.Banci == dto.Banci && x.YgId == dto.YgId);
|
||||
if (dup) throw new ServiceException("该车间该班次已存在此值班长排班");
|
||||
|
||||
e.DeptId = dto.DepId;
|
||||
e.Banci = dto.Banci;
|
||||
e.YgId = dto.YgId;
|
||||
await _zbzRepo.UpdateAsync(e);
|
||||
await _zbzRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
public async Task DeleteZbzAsync(long id)
|
||||
{
|
||||
var e = await _zbzRepo.GetByIdAsync(id) ?? throw new ServiceException("记录不存在", 404);
|
||||
await _zbzRepo.DeleteAsync(e);
|
||||
await _zbzRepo.SaveChangesAsync();
|
||||
}
|
||||
|
||||
// ==================== 公共 ====================
|
||||
|
||||
/// <summary>车头工:同一「车间+班次+机组」只能有一条排班</summary>
|
||||
private async Task ValidateGroupAsync(long depId, Prod_Banci_Enum banci, int jizu, long excludeId)
|
||||
{
|
||||
if (depId <= 0) throw new ServiceException("请选择车间");
|
||||
if (jizu <= 0) throw new ServiceException("请选择机组");
|
||||
|
||||
var dup = await _ctgRepo.AnyAsync(x => x.Id != excludeId && x.DeptId == depId
|
||||
&& x.Banci == banci && x.Jizu == jizu);
|
||||
if (dup) throw new ServiceException("该车间该班次该机组已有车头工排班");
|
||||
}
|
||||
|
||||
private async Task<Dictionary<long, string>> GetDeptDictAsync()
|
||||
=> (await _deptRepo.GetAllAsync()).ToDictionary(d => d.Id, d => d.Name);
|
||||
|
||||
private async Task<Dictionary<long, string>> GetEmpDictAsync()
|
||||
=> (await _empRepo.GetAllAsync()).ToDictionary(e => e.Id, e => e.Name);
|
||||
|
||||
private static KtpbctgReadDto_View ToCtgView(KtpbCtg x, Dictionary<long, string> deptDict,
|
||||
Dictionary<long, string> empDict) => new()
|
||||
{
|
||||
Id = x.Id,
|
||||
DepId = x.DeptId,
|
||||
DeptName = deptDict.GetValueOrDefault(x.DeptId, ""),
|
||||
Banci = x.Banci,
|
||||
BanciName = x.Banci.ToString(),
|
||||
Jizu = x.Jizu,
|
||||
Ygid1 = x.Ygid1,
|
||||
Ygid1Name = empDict.GetValueOrDefault(x.Ygid1, ""),
|
||||
Ygid2 = x.Ygid2,
|
||||
Ygid2Name = empDict.GetValueOrDefault(x.Ygid2, "")
|
||||
};
|
||||
|
||||
private static KtpbdcgReadDto_View ToDcgView(KtpbDcg x, Dictionary<long, string> deptDict,
|
||||
Dictionary<long, string> empDict) => new()
|
||||
{
|
||||
Id = x.Id,
|
||||
DepId = x.DeptId,
|
||||
DeptName = deptDict.GetValueOrDefault(x.DeptId, ""),
|
||||
Banci = x.Banci,
|
||||
BanciName = x.Banci.ToString(),
|
||||
Jizu = x.Jizu,
|
||||
ChetaiStart = x.ChetaiStart,
|
||||
ChetaiEnd = x.ChetaiEnd,
|
||||
YgId = x.YgId,
|
||||
YgName = empDict.GetValueOrDefault(x.YgId, ""),
|
||||
Dangcheshu = x.Dangcheshu
|
||||
};
|
||||
|
||||
private static KtpbzbzReadDto_View ToZbzView(KtpbZbz x, Dictionary<long, string> deptDict,
|
||||
Dictionary<long, string> empDict) => new()
|
||||
{
|
||||
Id = x.Id,
|
||||
DepId = x.DeptId,
|
||||
DeptName = deptDict.GetValueOrDefault(x.DeptId, ""),
|
||||
Banci = x.Banci,
|
||||
BanciName = x.Banci.ToString(),
|
||||
YgId = x.YgId,
|
||||
YgName = empDict.GetValueOrDefault(x.YgId, "")
|
||||
};
|
||||
|
||||
private static PageResult<T> Paged<T>(List<T> all, int pageIndex, int pageSize) => new()
|
||||
{
|
||||
Items = all.Skip((pageIndex - 1) * pageSize).Take(pageSize).ToList(),
|
||||
Total = all.Count,
|
||||
PageIndex = pageIndex,
|
||||
PageSize = pageSize
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
using FreeSql.DataAnnotations;
|
||||
using F9WebAiTest.Domain.Common;
|
||||
using F9WebAiTest.Domain.Enums.SYS.Employees;
|
||||
|
||||
namespace F9WebAiTest.Domain.Entities.Prod;
|
||||
|
||||
// 看台排班(对应 F9 生产-前缫 的 KTPB 三张表:车头工 / 挡车工 / 值班长)
|
||||
// 排班以「车间 + 班次」为组织单元;挡车工/车头工再细分「机组」。
|
||||
|
||||
/// <summary>车头工看台排班(biz_prod_qs_ktpb_ctg)</summary>
|
||||
[Table(Name = "KtpbCtgs")]
|
||||
public class KtpbCtg : BaseEntity
|
||||
{
|
||||
public long DeptId { get; set; } // 车间(前缫车间)
|
||||
public Prod_Banci_Enum Banci { get; set; } // 班次(甲/乙)
|
||||
public int Jizu { get; set; } // 机组
|
||||
public long Ygid1 { get; set; } // 车头工1
|
||||
public long Ygid2 { get; set; } // 车头工2
|
||||
}
|
||||
|
||||
/// <summary>挡车工看台排班(biz_prod_qs_ktpb_dcg)</summary>
|
||||
[Table(Name = "KtpbDcgs")]
|
||||
public class KtpbDcg : BaseEntity
|
||||
{
|
||||
public long DeptId { get; set; } // 车间
|
||||
public Prod_Banci_Enum Banci { get; set; } // 班次
|
||||
public int Jizu { get; set; } // 机组
|
||||
public int ChetaiStart { get; set; } // 起始车台号
|
||||
public int ChetaiEnd { get; set; } // 结束车台号
|
||||
public long YgId { get; set; } // 挡车工
|
||||
public double Dangcheshu { get; set; } // 挡车数(相邻车台各 0.5 的口径,保存时重算)
|
||||
}
|
||||
|
||||
/// <summary>值班长排班(biz_prod_qs_ktpb_zbz)</summary>
|
||||
[Table(Name = "KtpbZbzs")]
|
||||
public class KtpbZbz : BaseEntity
|
||||
{
|
||||
public long DeptId { get; set; } // 车间
|
||||
public Prod_Banci_Enum Banci { get; set; } // 班次
|
||||
public long YgId { get; set; } // 值班长
|
||||
}
|
||||
@@ -718,7 +718,8 @@ public static class DbSeeder
|
||||
new (string Name, string Path, string Component, string Permission, string Icon, int Sort)[]
|
||||
{
|
||||
("落丝记录", "/prod/qianxian/lsjl", "prod/lsjl/index", "prod:lsjl:list", "Document", 1),
|
||||
("车间班次", "/prod/qianxian/chejianbanci", "base/chejianbanci/index", "prod:chejianbanci:list", "Timer", 2)
|
||||
("车间班次", "/prod/qianxian/chejianbanci", "base/chejianbanci/index", "prod:chejianbanci:list", "Timer", 2),
|
||||
("看台排班", "/prod/qianxian/ktpb", "prod/ktpb/index", "prod:ktpb:list", "Grid", 3)
|
||||
});
|
||||
|
||||
EnsureTopMenuWithChildren(fsql, snowflake, "/prod/houxian", "生产-后缫", "DataLine", 6,
|
||||
|
||||
@@ -7,6 +7,7 @@ using F9WebAiTest.Domain.Entities.Base;
|
||||
using F9WebAiTest.Domain.Entities.Prod;
|
||||
using F9WebAiTest.Domain.Enums.SYS.Employees;
|
||||
using SysDept = F9WebAiTest.Domain.Entities.SYS.Departments;
|
||||
using SysEmp = F9WebAiTest.Domain.Entities.SYS.Employees;
|
||||
|
||||
namespace F9WebAiTest.Infrastructure.Data;
|
||||
|
||||
@@ -20,6 +21,9 @@ public static class ProdSeedData
|
||||
{
|
||||
private const string JzctResource = "F9WebAiTest.Infrastructure.Data.SeedData.biz_prod_qs_jzct.json";
|
||||
private const string CjbcResource = "F9WebAiTest.Infrastructure.Data.SeedData.biz_prod_qs_cjbc.json";
|
||||
private const string KtpbCtgResource = "F9WebAiTest.Infrastructure.Data.SeedData.biz_prod_qs_ktpb_ctg.json";
|
||||
private const string KtpbDcgResource = "F9WebAiTest.Infrastructure.Data.SeedData.biz_prod_qs_ktpb_dcg.json";
|
||||
private const string KtpbZbzResource = "F9WebAiTest.Infrastructure.Data.SeedData.biz_prod_qs_ktpb_zbz.json";
|
||||
|
||||
private static readonly JsonSerializerOptions JsonOpts = new()
|
||||
{
|
||||
@@ -31,6 +35,10 @@ public static class ProdSeedData
|
||||
{
|
||||
SeedJizuChetai(fsql);
|
||||
SeedChejianBanci(fsql);
|
||||
// 看台排班(车头工 / 挡车工 / 值班长)
|
||||
SeedKtpbCtg(fsql);
|
||||
SeedKtpbDcg(fsql);
|
||||
SeedKtpbZbz(fsql);
|
||||
}
|
||||
|
||||
// ==================== 机组车台 ====================
|
||||
@@ -154,8 +162,161 @@ public static class ProdSeedData
|
||||
}
|
||||
}
|
||||
|
||||
// ==================== 车头工看台排班 ====================
|
||||
private static void SeedKtpbCtg(IFreeSql fsql)
|
||||
{
|
||||
try
|
||||
{
|
||||
var items = Load<KtpbCtgItem>(KtpbCtgResource);
|
||||
if (items.Count == 0) return;
|
||||
|
||||
var deptMap = BuildDeptMap(fsql);
|
||||
var empIds = BuildEmpIdSet(fsql);
|
||||
var existing = fsql.Select<KtpbCtg>().ToList()
|
||||
.GroupBy(x => (x.DeptId, x.Banci, x.Jizu))
|
||||
.ToDictionary(g => g.Key, g => g.First());
|
||||
|
||||
int added = 0, updated = 0, skipped = 0;
|
||||
foreach (var item in items)
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(item.DeletedAt)) { skipped++; continue; }
|
||||
if (!deptMap.TryGetValue(item.DepId, out var deptId)) { skipped++; continue; }
|
||||
if (!empIds.Contains(item.Ygid1)) { skipped++; continue; }
|
||||
|
||||
var ygid2 = empIds.Contains(item.Ygid2) ? item.Ygid2 : 0;
|
||||
var banci = (Prod_Banci_Enum)item.Banci;
|
||||
var key = (deptId, banci, item.Jizu);
|
||||
if (existing.TryGetValue(key, out var e))
|
||||
{
|
||||
if (e.Ygid1 != item.Ygid1 || e.Ygid2 != ygid2)
|
||||
{
|
||||
e.Ygid1 = item.Ygid1;
|
||||
e.Ygid2 = ygid2;
|
||||
fsql.Update<KtpbCtg>().SetSource(e).ExecuteAffrows();
|
||||
updated++;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
fsql.Insert(new KtpbCtg
|
||||
{
|
||||
DeptId = deptId,
|
||||
Banci = banci,
|
||||
Jizu = item.Jizu,
|
||||
Ygid1 = item.Ygid1,
|
||||
Ygid2 = ygid2
|
||||
}).ExecuteAffrows();
|
||||
added++;
|
||||
}
|
||||
}
|
||||
|
||||
Console.WriteLine($"[ProdSeed] 车头工看台排班:来源 {items.Count} 条,新增 {added} 条,更新 {updated} 条,跳过 {skipped} 条");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine($"[ProdSeed] 车头工看台排班导入跳过:{ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
// ==================== 挡车工看台排班 ====================
|
||||
private static void SeedKtpbDcg(IFreeSql fsql)
|
||||
{
|
||||
try
|
||||
{
|
||||
var items = Load<KtpbDcgItem>(KtpbDcgResource);
|
||||
if (items.Count == 0) return;
|
||||
|
||||
var deptMap = BuildDeptMap(fsql);
|
||||
var empIds = BuildEmpIdSet(fsql);
|
||||
// 已有排班的「车间+班次+机组」整组跳过,避免每次启动重复插入(人工维护的排班不被覆盖)
|
||||
var existGroups = fsql.Select<KtpbDcg>().ToList()
|
||||
.Select(x => (x.DeptId, x.Banci, x.Jizu))
|
||||
.ToHashSet();
|
||||
|
||||
int added = 0, skipped = 0;
|
||||
var handledGroups = new HashSet<(long, Prod_Banci_Enum, int)>();
|
||||
|
||||
foreach (var item in items)
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(item.DeletedAt)) { skipped++; continue; }
|
||||
if (!deptMap.TryGetValue(item.DepId, out var deptId)) { skipped++; continue; }
|
||||
if (!empIds.Contains(item.YgId)) { skipped++; continue; }
|
||||
if (item.ChetaiStart <= 0 || item.ChetaiEnd < item.ChetaiStart) { skipped++; continue; }
|
||||
|
||||
var banci = (Prod_Banci_Enum)item.Banci;
|
||||
var group = (deptId, banci, item.Jizu);
|
||||
if (existGroups.Contains(group)) { skipped++; continue; }
|
||||
|
||||
fsql.Insert(new KtpbDcg
|
||||
{
|
||||
DeptId = deptId,
|
||||
Banci = banci,
|
||||
Jizu = item.Jizu,
|
||||
ChetaiStart = item.ChetaiStart,
|
||||
ChetaiEnd = item.ChetaiEnd,
|
||||
YgId = item.YgId,
|
||||
Dangcheshu = item.Dangcheshu
|
||||
}).ExecuteAffrows();
|
||||
handledGroups.Add(group);
|
||||
added++;
|
||||
}
|
||||
|
||||
Console.WriteLine($"[ProdSeed] 挡车工看台排班:来源 {items.Count} 条,新增 {added} 条({handledGroups.Count} 组),跳过 {skipped} 条");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine($"[ProdSeed] 挡车工看台排班导入跳过:{ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
// ==================== 值班长看台排班 ====================
|
||||
private static void SeedKtpbZbz(IFreeSql fsql)
|
||||
{
|
||||
try
|
||||
{
|
||||
var items = Load<KtpbZbzItem>(KtpbZbzResource);
|
||||
if (items.Count == 0) return;
|
||||
|
||||
var deptMap = BuildDeptMap(fsql);
|
||||
var empIds = BuildEmpIdSet(fsql);
|
||||
var exist = fsql.Select<KtpbZbz>().ToList()
|
||||
.Select(x => (x.DeptId, x.Banci, x.YgId))
|
||||
.ToHashSet();
|
||||
|
||||
int added = 0, skipped = 0;
|
||||
foreach (var item in items)
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(item.DeletedAt)) { skipped++; continue; }
|
||||
if (!deptMap.TryGetValue(item.DepId, out var deptId)) { skipped++; continue; }
|
||||
if (!empIds.Contains(item.YgId)) { skipped++; continue; }
|
||||
|
||||
var banci = (Prod_Banci_Enum)item.Banci;
|
||||
if (!exist.Add((deptId, banci, item.YgId))) { skipped++; continue; }
|
||||
|
||||
fsql.Insert(new KtpbZbz
|
||||
{
|
||||
DeptId = deptId,
|
||||
Banci = banci,
|
||||
YgId = item.YgId
|
||||
}).ExecuteAffrows();
|
||||
added++;
|
||||
}
|
||||
|
||||
Console.WriteLine($"[ProdSeed] 值班长看台排班:来源 {items.Count} 条,新增 {added} 条,跳过 {skipped} 条");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine($"[ProdSeed] 值班长看台排班导入跳过:{ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
// ==================== 公共 ====================
|
||||
|
||||
/// <summary>本系统存在的职工 Id 集合(F9 职工导出时保留了原始雪花 Id,可直接比对)</summary>
|
||||
private static HashSet<long> BuildEmpIdSet(IFreeSql fsql)
|
||||
=> fsql.Select<SysEmp.Employee>().ToList().Select(e => e.Id).ToHashSet();
|
||||
|
||||
|
||||
/// <summary>建立 F9 部门 Id → 本系统部门 Id 的映射(以部门名称为桥梁)</summary>
|
||||
private static Dictionary<long, long> BuildDeptMap(IFreeSql fsql)
|
||||
{
|
||||
@@ -199,4 +360,37 @@ public static class ProdSeedData
|
||||
[JsonPropertyName("banci")] public int Banci { get; set; }
|
||||
[JsonPropertyName("kaoqin_dayhours")] public double KaoqinDayhours { get; set; }
|
||||
}
|
||||
|
||||
private class KtpbCtgItem
|
||||
{
|
||||
[JsonPropertyName("id")] public long Id { get; set; }
|
||||
[JsonPropertyName("deleted_at")] public string? DeletedAt { get; set; }
|
||||
[JsonPropertyName("dep_id")] public long DepId { get; set; }
|
||||
[JsonPropertyName("banci")] public int Banci { get; set; }
|
||||
[JsonPropertyName("jizu")] public int Jizu { get; set; }
|
||||
[JsonPropertyName("ygid_1")] public long Ygid1 { get; set; }
|
||||
[JsonPropertyName("ygid_2")] public long Ygid2 { get; set; }
|
||||
}
|
||||
|
||||
private class KtpbDcgItem
|
||||
{
|
||||
[JsonPropertyName("id")] public long Id { get; set; }
|
||||
[JsonPropertyName("deleted_at")] public string? DeletedAt { get; set; }
|
||||
[JsonPropertyName("dep_id")] public long DepId { get; set; }
|
||||
[JsonPropertyName("banci")] public int Banci { get; set; }
|
||||
[JsonPropertyName("jizu")] public int Jizu { get; set; }
|
||||
[JsonPropertyName("chetai_start")] public int ChetaiStart { get; set; }
|
||||
[JsonPropertyName("chetai_end")] public int ChetaiEnd { get; set; }
|
||||
[JsonPropertyName("yg_id")] public long YgId { get; set; }
|
||||
[JsonPropertyName("dangcheshu")] public double Dangcheshu { get; set; }
|
||||
}
|
||||
|
||||
private class KtpbZbzItem
|
||||
{
|
||||
[JsonPropertyName("id")] public long Id { get; set; }
|
||||
[JsonPropertyName("deleted_at")] public string? DeletedAt { get; set; }
|
||||
[JsonPropertyName("dep_id")] public long DepId { get; set; }
|
||||
[JsonPropertyName("banci")] public int Banci { get; set; }
|
||||
[JsonPropertyName("yg_id")] public long YgId { get; set; }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,422 +1,26 @@
|
||||
[
|
||||
{
|
||||
"id": 16003469039112192,
|
||||
"created_by": null,
|
||||
"created_at": "14/11/2025 11:52:04.367",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "14/11/2025 11:53:55.33",
|
||||
"dep_id": 101122,
|
||||
"jizu": 23424,
|
||||
"chetai_start": 324,
|
||||
"chetai_end": 2342
|
||||
},
|
||||
{
|
||||
"id": 16047842267238400,
|
||||
"created_by": null,
|
||||
"created_at": "14/11/2025 14:48:23.753",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "14/11/2025 15:26:50.25",
|
||||
"dep_id": 106,
|
||||
"jizu": 111,
|
||||
"chetai_start": 111,
|
||||
"chetai_end": 118
|
||||
},
|
||||
{
|
||||
"id": 16047909204135936,
|
||||
"created_by": null,
|
||||
"created_at": "14/11/2025 14:48:39.71",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "14/11/2025 14:48:48.147",
|
||||
"dep_id": 107,
|
||||
"jizu": 111,
|
||||
"chetai_start": 119,
|
||||
"chetai_end": 125
|
||||
},
|
||||
{
|
||||
"id": 16054811803783168,
|
||||
"created_by": null,
|
||||
"created_at": "14/11/2025 15:16:05.42",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "14/11/2025 15:26:47.48",
|
||||
"dep_id": 107,
|
||||
"jizu": 100,
|
||||
"chetai_start": 100,
|
||||
"chetai_end": 110
|
||||
},
|
||||
{
|
||||
"id": 17090359817408512,
|
||||
"created_by": null,
|
||||
"created_at": "17/11/2025 11:50:59.307",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "20/11/2025 17:47:04.083",
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 7,
|
||||
"chetai_start": 3,
|
||||
"chetai_end": 6
|
||||
},
|
||||
{
|
||||
"id": 17124677390438400,
|
||||
"created_by": null,
|
||||
"created_at": "17/11/2025 14:07:21.253",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "17/11/2025 15:44:43.493",
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 3
|
||||
},
|
||||
{
|
||||
"id": 17149134003769344,
|
||||
"created_by": null,
|
||||
"created_at": "17/11/2025 15:44:32.167",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "20/11/2025 17:47:08.097",
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 100,
|
||||
"chetai_start": 5,
|
||||
"chetai_end": 11
|
||||
},
|
||||
{
|
||||
"id": 17895860616564736,
|
||||
"created_by": null,
|
||||
"created_at": "19/11/2025 17:11:45.693",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "20/11/2025 17:47:05.973",
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 18
|
||||
},
|
||||
{
|
||||
"id": 18267185730293760,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:47:16.487",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 20
|
||||
},
|
||||
{
|
||||
"id": 18267223122513920,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:47:25.383",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 2,
|
||||
"chetai_start": 21,
|
||||
"chetai_end": 40
|
||||
},
|
||||
{
|
||||
"id": 18267258883149824,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:47:33.907",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 3,
|
||||
"chetai_start": 41,
|
||||
"chetai_end": 60
|
||||
},
|
||||
{
|
||||
"id": 18267293058338816,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:47:42.057",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 4,
|
||||
"chetai_start": 61,
|
||||
"chetai_end": 80
|
||||
},
|
||||
{
|
||||
"id": 18267333134913536,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:47:51.61",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 5,
|
||||
"chetai_start": 81,
|
||||
"chetai_end": 100
|
||||
},
|
||||
{
|
||||
"id": 18267372687200256,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:01.04",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 6,
|
||||
"chetai_start": 101,
|
||||
"chetai_end": 120
|
||||
},
|
||||
{
|
||||
"id": 18267414189838336,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:10.937",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 20
|
||||
},
|
||||
{
|
||||
"id": 18267443470274560,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:17.917",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 2,
|
||||
"chetai_start": 21,
|
||||
"chetai_end": 40
|
||||
},
|
||||
{
|
||||
"id": 18267488391270400,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:28.627",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 3,
|
||||
"chetai_start": 41,
|
||||
"chetai_end": 60
|
||||
},
|
||||
{
|
||||
"id": 18267530309144576,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:38.62",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 4,
|
||||
"chetai_start": 61,
|
||||
"chetai_end": 80
|
||||
},
|
||||
{
|
||||
"id": 18267562336849920,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:46.257",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 5,
|
||||
"chetai_start": 81,
|
||||
"chetai_end": 100
|
||||
},
|
||||
{
|
||||
"id": 18267593483751424,
|
||||
"created_by": null,
|
||||
"created_at": "20/11/2025 17:48:53.683",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 6,
|
||||
"chetai_start": 101,
|
||||
"chetai_end": 120
|
||||
},
|
||||
{
|
||||
"id": 18500840679542784,
|
||||
"created_by": null,
|
||||
"created_at": "21/11/2025 09:15:44.15",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "24/11/2025 14:30:02.643",
|
||||
"dep_id": 16043931070369792,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 100
|
||||
},
|
||||
{
|
||||
"id": 20436938137800704,
|
||||
"created_by": null,
|
||||
"created_at": "26/11/2025 17:29:05.753",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "10/12/2025 13:06:18.217",
|
||||
"dep_id": 16047387197837312,
|
||||
"jizu": 7,
|
||||
"chetai_start": 121,
|
||||
"chetai_end": 140
|
||||
},
|
||||
{
|
||||
"id": 25444260044083200,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:06:24.337",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308600831545344,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 20
|
||||
},
|
||||
{
|
||||
"id": 25444289462931456,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:06:31.34",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308600831545344,
|
||||
"jizu": 2,
|
||||
"chetai_start": 21,
|
||||
"chetai_end": 40
|
||||
},
|
||||
{
|
||||
"id": 25444329623392256,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:06:40.917",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308600831545344,
|
||||
"jizu": 3,
|
||||
"chetai_start": 41,
|
||||
"chetai_end": 60
|
||||
},
|
||||
{
|
||||
"id": 25444371641929728,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:06:50.933",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308600831545344,
|
||||
"jizu": 4,
|
||||
"chetai_start": 61,
|
||||
"chetai_end": 80
|
||||
},
|
||||
{
|
||||
"id": 25444402046439424,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:06:58.183",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308600831545344,
|
||||
"jizu": 5,
|
||||
"chetai_start": 81,
|
||||
"chetai_end": 100
|
||||
},
|
||||
{
|
||||
"id": 25444430567706624,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:04.983",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308600831545344,
|
||||
"jizu": 6,
|
||||
"chetai_start": 101,
|
||||
"chetai_end": 120
|
||||
},
|
||||
{
|
||||
"id": 25444457453195264,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:11.393",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": 1,
|
||||
"chetai_start": 1,
|
||||
"chetai_end": 20
|
||||
},
|
||||
{
|
||||
"id": 25444480718999552,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:16.94",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": 2,
|
||||
"chetai_start": 21,
|
||||
"chetai_end": 40
|
||||
},
|
||||
{
|
||||
"id": 25444507617071104,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:23.353",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": 3,
|
||||
"chetai_start": 41,
|
||||
"chetai_end": 60
|
||||
},
|
||||
{
|
||||
"id": 25444531084201984,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:28.947",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": 4,
|
||||
"chetai_start": 61,
|
||||
"chetai_end": 80
|
||||
},
|
||||
{
|
||||
"id": 25444554995929088,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:34.65",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": 5,
|
||||
"chetai_start": 81,
|
||||
"chetai_end": 100
|
||||
},
|
||||
{
|
||||
"id": 25444577833914368,
|
||||
"created_by": "余华",
|
||||
"created_at": "10/12/2025 13:07:40.093",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": null,
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": 6,
|
||||
"chetai_start": 101,
|
||||
"chetai_end": 120
|
||||
},
|
||||
{
|
||||
"id": 37410963145625600,
|
||||
"created_by": "余华",
|
||||
"created_at": "12/1/2026 13:37:48.69",
|
||||
"update_by": null,
|
||||
"updated_at": "1/1/1970 00:00:00",
|
||||
"deleted_at": "13/2/2026 13:59:24.617",
|
||||
"dep_id": 22308683820044288,
|
||||
"jizu": -1,
|
||||
"chetai_start": 0,
|
||||
"chetai_end": 0
|
||||
}
|
||||
]
|
||||
{"id":18267185730293760,"deleted_at":null,"dep_id":16043931070369792,"jizu":1,"chetai_start":1,"chetai_end":20},
|
||||
{"id":18267223122513920,"deleted_at":null,"dep_id":16043931070369792,"jizu":2,"chetai_start":21,"chetai_end":40},
|
||||
{"id":18267258883149824,"deleted_at":null,"dep_id":16043931070369792,"jizu":3,"chetai_start":41,"chetai_end":60},
|
||||
{"id":18267293058338816,"deleted_at":null,"dep_id":16043931070369792,"jizu":4,"chetai_start":61,"chetai_end":80},
|
||||
{"id":18267333134913536,"deleted_at":null,"dep_id":16043931070369792,"jizu":5,"chetai_start":81,"chetai_end":100},
|
||||
{"id":18267372687200256,"deleted_at":null,"dep_id":16043931070369792,"jizu":6,"chetai_start":101,"chetai_end":120},
|
||||
{"id":18267414189838336,"deleted_at":null,"dep_id":16047387197837312,"jizu":1,"chetai_start":1,"chetai_end":20},
|
||||
{"id":18267443470274560,"deleted_at":null,"dep_id":16047387197837312,"jizu":2,"chetai_start":21,"chetai_end":40},
|
||||
{"id":18267488391270400,"deleted_at":null,"dep_id":16047387197837312,"jizu":3,"chetai_start":41,"chetai_end":60},
|
||||
{"id":18267530309144576,"deleted_at":null,"dep_id":16047387197837312,"jizu":4,"chetai_start":61,"chetai_end":80},
|
||||
{"id":18267562336849920,"deleted_at":null,"dep_id":16047387197837312,"jizu":5,"chetai_start":81,"chetai_end":100},
|
||||
{"id":18267593483751424,"deleted_at":null,"dep_id":16047387197837312,"jizu":6,"chetai_start":101,"chetai_end":120},
|
||||
{"id":25444260044083200,"deleted_at":null,"dep_id":22308600831545344,"jizu":1,"chetai_start":1,"chetai_end":20},
|
||||
{"id":25444289462931456,"deleted_at":null,"dep_id":22308600831545344,"jizu":2,"chetai_start":21,"chetai_end":40},
|
||||
{"id":25444329623392256,"deleted_at":null,"dep_id":22308600831545344,"jizu":3,"chetai_start":41,"chetai_end":60},
|
||||
{"id":25444371641929728,"deleted_at":null,"dep_id":22308600831545344,"jizu":4,"chetai_start":61,"chetai_end":80},
|
||||
{"id":25444402046439424,"deleted_at":null,"dep_id":22308600831545344,"jizu":5,"chetai_start":81,"chetai_end":100},
|
||||
{"id":25444430567706624,"deleted_at":null,"dep_id":22308600831545344,"jizu":6,"chetai_start":101,"chetai_end":120},
|
||||
{"id":25444457453195264,"deleted_at":null,"dep_id":22308683820044288,"jizu":1,"chetai_start":1,"chetai_end":20},
|
||||
{"id":25444480718999552,"deleted_at":null,"dep_id":22308683820044288,"jizu":2,"chetai_start":21,"chetai_end":40},
|
||||
{"id":25444507617071104,"deleted_at":null,"dep_id":22308683820044288,"jizu":3,"chetai_start":41,"chetai_end":60},
|
||||
{"id":25444531084201984,"deleted_at":null,"dep_id":22308683820044288,"jizu":4,"chetai_start":61,"chetai_end":80},
|
||||
{"id":25444554995929088,"deleted_at":null,"dep_id":22308683820044288,"jizu":5,"chetai_start":81,"chetai_end":100},
|
||||
{"id":25444577833914368,"deleted_at":null,"dep_id":22308683820044288,"jizu":6,"chetai_start":101,"chetai_end":120}
|
||||
]
|
||||
|
||||
@@ -0,0 +1,35 @@
|
||||
[
|
||||
{"id":28679759856668672,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"ygid_1":25394251403628544,"ygid_2":25394252687085568},
|
||||
{"id":28679881613119488,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"ygid_1":25394250963226624,"ygid_2":25394262359150592},
|
||||
{"id":28680097309396992,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"ygid_1":25394277458644992,"ygid_2":25394289907339264},
|
||||
{"id":28680552307494912,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"ygid_1":25394262090715136,"ygid_2":25394283020292096},
|
||||
{"id":28680630204108800,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":3,"ygid_1":25394270579986432,"ygid_2":25394277022437376},
|
||||
{"id":28680704229380096,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"ygid_1":25394267270680576,"ygid_2":25394252900995072},
|
||||
{"id":28680809309278208,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":5,"ygid_1":25394253106515968,"ygid_2":25394287445282816},
|
||||
{"id":28680902095671296,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"ygid_1":25394255677624320,"ygid_2":25394257221128192},
|
||||
{"id":28681049068277760,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"ygid_1":25394255895728128,"ygid_2":25394256793309184},
|
||||
{"id":28681224268550144,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"ygid_1":25394271423041536,"ygid_2":25394275898363904},
|
||||
{"id":28681355063726080,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":3,"ygid_1":25394256373878784,"ygid_2":25394258567499776},
|
||||
{"id":28681491718344704,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"ygid_1":25394254591299584,"ygid_2":25394268763852800},
|
||||
{"id":28681656072146944,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":5,"ygid_1":25394257665724416,"ygid_2":25394262770192384},
|
||||
{"id":28681864378060800,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"ygid_1":25394271871832064,"ygid_2":25394298862178304},
|
||||
{"id":32345734678319104,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"ygid_1":25394253521752064,"ygid_2":25394263684550656},
|
||||
{"id":56622802173693952,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"ygid_1":25394269191671808,"ygid_2":25394322589356032},
|
||||
{"id":56622892196040704,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"ygid_1":25394266616369152,"ygid_2":25394277928407040},
|
||||
{"id":56623050757509120,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"ygid_1":25394267681722368,"ygid_2":25394272979128320},
|
||||
{"id":56623178239184896,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"ygid_1":25394317203869696,"ygid_2":25394331179290624},
|
||||
{"id":76302819312799744,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"ygid_1":25394318558629888,"ygid_2":25394285343936512},
|
||||
{"id":76303037706014720,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"ygid_1":25394277232152576,"ygid_2":25394292637831168},
|
||||
{"id":93614566272929792,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"ygid_1":93227931605667840,"ygid_2":25394275269218304},
|
||||
{"id":93614668416815104,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"ygid_1":93224498219716608,"ygid_2":93590450325164032},
|
||||
{"id":93614844455948288,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"ygid_1":93224782811631616,"ygid_2":93225053415542784},
|
||||
{"id":93624586561654784,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"ygid_1":25394252687085568,"ygid_2":25394298644074496},
|
||||
{"id":93624684989386752,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"ygid_1":25394252473176064,"ygid_2":25394352024981504},
|
||||
{"id":93624758398095360,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"ygid_1":25394313286389760,"ygid_2":25394334945775616},
|
||||
{"id":93624861590556672,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"ygid_1":25394261000196096,"ygid_2":25394320357986304},
|
||||
{"id":93624972055941120,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"ygid_1":25394301747859456,"ygid_2":25394321599500288},
|
||||
{"id":93625060534784000,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"ygid_1":25394318810288128,"ygid_2":25394343514738688},
|
||||
{"id":120347729640558592,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"ygid_1":93225232566849536,"ygid_2":93590965738016768},
|
||||
{"id":120348037049487360,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"ygid_1":93225456668512256,"ygid_2":25394269623685120},
|
||||
{"id":121079483326271488,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"ygid_1":93226261979074560,"ygid_2":93225788580564992}
|
||||
]
|
||||
@@ -0,0 +1,204 @@
|
||||
[
|
||||
{"id":120344961106317312,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"chetai_start":1,"chetai_end":4,"yg_id":89529295612940288,"dangcheshu":3.5},
|
||||
{"id":120344961139871744,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"chetai_start":4,"chetai_end":7,"yg_id":93233888171659264,"dangcheshu":3.5},
|
||||
{"id":120344961156648960,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"chetai_start":8,"chetai_end":10,"yg_id":87098603226533888,"dangcheshu":3},
|
||||
{"id":120344961173426176,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"chetai_start":11,"chetai_end":14,"yg_id":93241010255040512,"dangcheshu":3.5},
|
||||
{"id":120344961190203392,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"chetai_start":14,"chetai_end":17,"yg_id":93233703257378816,"dangcheshu":3.5},
|
||||
{"id":120344961206980608,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":1,"chetai_start":18,"chetai_end":20,"yg_id":93237556027592704,"dangcheshu":3},
|
||||
{"id":120389028775202816,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"chetai_start":1,"chetai_end":4,"yg_id":25394323948310528,"dangcheshu":3.5},
|
||||
{"id":120389028812951552,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"chetai_start":4,"chetai_end":7,"yg_id":25394323277221888,"dangcheshu":3.5},
|
||||
{"id":120389028833923072,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"chetai_start":8,"chetai_end":10,"yg_id":25394286870663168,"dangcheshu":3},
|
||||
{"id":120389028859088896,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"chetai_start":11,"chetai_end":14,"yg_id":25394273205620736,"dangcheshu":3.5},
|
||||
{"id":120389028880060416,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"chetai_start":14,"chetai_end":17,"yg_id":25394307603107840,"dangcheshu":3.5},
|
||||
{"id":120389028901031936,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":1,"chetai_start":18,"chetai_end":20,"yg_id":25394291484397568,"dangcheshu":3},
|
||||
{"id":120389304567468032,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"chetai_start":21,"chetai_end":24,"yg_id":25394274388414464,"dangcheshu":3.5},
|
||||
{"id":120389304592633856,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"chetai_start":24,"chetai_end":27,"yg_id":25394292184846336,"dangcheshu":3.5},
|
||||
{"id":120389304609411072,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"chetai_start":28,"chetai_end":30,"yg_id":25394272094130176,"dangcheshu":3},
|
||||
{"id":120389304626188288,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"chetai_start":31,"chetai_end":34,"yg_id":25394354193436672,"dangcheshu":3.5},
|
||||
{"id":120389304638771200,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"chetai_start":34,"chetai_end":37,"yg_id":25394302033072128,"dangcheshu":3.5},
|
||||
{"id":120389304655548416,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":2,"chetai_start":38,"chetai_end":40,"yg_id":25394303777902592,"dangcheshu":3},
|
||||
{"id":120389564396212224,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"chetai_start":41,"chetai_end":44,"yg_id":25394273868320768,"dangcheshu":3.5},
|
||||
{"id":120389564429766656,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"chetai_start":44,"chetai_end":47,"yg_id":25394300577648640,"dangcheshu":3.5},
|
||||
{"id":120389564446543872,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"chetai_start":48,"chetai_end":50,"yg_id":25394307166900224,"dangcheshu":3},
|
||||
{"id":120389564463321088,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"chetai_start":51,"chetai_end":54,"yg_id":25394267904020480,"dangcheshu":3.5},
|
||||
{"id":120389564480098304,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"chetai_start":54,"chetai_end":57,"yg_id":25394309872226304,"dangcheshu":3.5},
|
||||
{"id":120389564496875520,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":3,"chetai_start":58,"chetai_end":60,"yg_id":25394309482156032,"dangcheshu":3},
|
||||
{"id":120389903656685568,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"chetai_start":61,"chetai_end":64,"yg_id":25394308739764224,"dangcheshu":3.5},
|
||||
{"id":120389903681851392,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"chetai_start":64,"chetai_end":67,"yg_id":25394330747277312,"dangcheshu":3.5},
|
||||
{"id":120389903698628608,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"chetai_start":68,"chetai_end":70,"yg_id":25394326401978368,"dangcheshu":3},
|
||||
{"id":120389903715405824,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"chetai_start":71,"chetai_end":74,"yg_id":25394294764343296,"dangcheshu":3.5},
|
||||
{"id":120389903732183040,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"chetai_start":74,"chetai_end":77,"yg_id":55117587129831424,"dangcheshu":3.5},
|
||||
{"id":120389903748960256,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":4,"chetai_start":78,"chetai_end":80,"yg_id":25394285914361856,"dangcheshu":3},
|
||||
{"id":120390213137600512,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":5,"chetai_start":81,"chetai_end":84,"yg_id":25394264351444992,"dangcheshu":3.5},
|
||||
{"id":120390213166960640,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":5,"chetai_start":84,"chetai_end":87,"yg_id":25394303547215872,"dangcheshu":3.5},
|
||||
{"id":120390213183737856,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":5,"chetai_start":88,"chetai_end":90,"yg_id":25394324619399168,"dangcheshu":3},
|
||||
{"id":120390213204709376,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":5,"chetai_start":91,"chetai_end":94,"yg_id":56616898418184192,"dangcheshu":3.5},
|
||||
{"id":120390213221486592,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":5,"chetai_start":94,"chetai_end":97,"yg_id":25394335637835776,"dangcheshu":3.5},
|
||||
{"id":120390213238263808,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":5,"chetai_start":98,"chetai_end":100,"yg_id":25394308521660416,"dangcheshu":3},
|
||||
{"id":120404584362414080,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"chetai_start":1,"chetai_end":4,"yg_id":25394312703381504,"dangcheshu":3.5},
|
||||
{"id":120404584391774208,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"chetai_start":4,"chetai_end":7,"yg_id":25394315442262016,"dangcheshu":3.5},
|
||||
{"id":120404584408551424,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"chetai_start":8,"chetai_end":10,"yg_id":25394305950552064,"dangcheshu":3},
|
||||
{"id":120404584425328640,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"chetai_start":11,"chetai_end":14,"yg_id":25394326620082176,"dangcheshu":3.5},
|
||||
{"id":120404584442105856,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"chetai_start":14,"chetai_end":17,"yg_id":25394299948503040,"dangcheshu":3.5},
|
||||
{"id":120404584458883072,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":1,"chetai_start":18,"chetai_end":20,"yg_id":25394311185043456,"dangcheshu":3},
|
||||
{"id":120411788704485376,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"chetai_start":1,"chetai_end":4,"yg_id":25394278435917824,"dangcheshu":3.5},
|
||||
{"id":120411788729651200,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"chetai_start":4,"chetai_end":7,"yg_id":25394306164461568,"dangcheshu":3.5},
|
||||
{"id":120411788742234112,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"chetai_start":8,"chetai_end":10,"yg_id":25394335184850944,"dangcheshu":3},
|
||||
{"id":120411788759011328,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"chetai_start":11,"chetai_end":14,"yg_id":25394254381584384,"dangcheshu":3.5},
|
||||
{"id":120411788775788544,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"chetai_start":14,"chetai_end":17,"yg_id":25394264573743104,"dangcheshu":3.5},
|
||||
{"id":120411788792565760,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":1,"chetai_start":18,"chetai_end":20,"yg_id":25394261629341696,"dangcheshu":3},
|
||||
{"id":120413456527527936,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":3,"chetai_start":41,"chetai_end":45,"yg_id":25394325974159360,"dangcheshu":5},
|
||||
{"id":120413456552693760,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":3,"chetai_start":46,"chetai_end":50,"yg_id":25394257451814912,"dangcheshu":5},
|
||||
{"id":120413456569470976,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":3,"chetai_start":51,"chetai_end":55,"yg_id":25394253316231168,"dangcheshu":5},
|
||||
{"id":120413456586248192,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":3,"chetai_start":56,"chetai_end":60,"yg_id":25394259884511232,"dangcheshu":5},
|
||||
{"id":120414505472626688,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":5,"chetai_start":81,"chetai_end":85,"yg_id":25394284488298496,"dangcheshu":5},
|
||||
{"id":120414505501986816,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":5,"chetai_start":86,"chetai_end":90,"yg_id":25394258324230144,"dangcheshu":5},
|
||||
{"id":120414505518764032,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":5,"chetai_start":91,"chetai_end":95,"yg_id":25394308257419264,"dangcheshu":5},
|
||||
{"id":120414505531346944,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":5,"chetai_start":96,"chetai_end":100,"yg_id":25394265102225408,"dangcheshu":5},
|
||||
{"id":120415064866951168,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"chetai_start":101,"chetai_end":104,"yg_id":25394267052576768,"dangcheshu":3.5},
|
||||
{"id":120415064887922688,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"chetai_start":104,"chetai_end":107,"yg_id":25394265983029248,"dangcheshu":3.5},
|
||||
{"id":120415064908894208,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"chetai_start":108,"chetai_end":110,"yg_id":25394300376322048,"dangcheshu":3},
|
||||
{"id":120415064925671424,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"chetai_start":111,"chetai_end":114,"yg_id":25394315178020864,"dangcheshu":3.5},
|
||||
{"id":120415064942448640,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"chetai_start":114,"chetai_end":117,"yg_id":25394333142224896,"dangcheshu":3.5},
|
||||
{"id":120415064959225856,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":6,"chetai_start":118,"chetai_end":120,"yg_id":25394308953673728,"dangcheshu":3},
|
||||
{"id":120415827617910784,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"chetai_start":61,"chetai_end":64,"yg_id":25394276531703808,"dangcheshu":3.5},
|
||||
{"id":120415827634688000,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"chetai_start":64,"chetai_end":67,"yg_id":25394328620765184,"dangcheshu":3.5},
|
||||
{"id":120415827651465216,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"chetai_start":68,"chetai_end":70,"yg_id":25394277718691840,"dangcheshu":3},
|
||||
{"id":120415827668242432,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"chetai_start":71,"chetai_end":74,"yg_id":25394338246692864,"dangcheshu":3.5},
|
||||
{"id":120415827685019648,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"chetai_start":74,"chetai_end":77,"yg_id":25394316000104448,"dangcheshu":3.5},
|
||||
{"id":120415827705991168,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":4,"chetai_start":78,"chetai_end":80,"yg_id":25394288552579072,"dangcheshu":3},
|
||||
{"id":120416422688985088,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"chetai_start":21,"chetai_end":24,"yg_id":25394273654411264,"dangcheshu":3.5},
|
||||
{"id":120416422701568000,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"chetai_start":24,"chetai_end":27,"yg_id":25394288808431616,"dangcheshu":3.5},
|
||||
{"id":120416422705762304,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"chetai_start":28,"chetai_end":30,"yg_id":25394260790480896,"dangcheshu":3},
|
||||
{"id":120416422718345216,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"chetai_start":31,"chetai_end":34,"yg_id":25394336363450368,"dangcheshu":3.5},
|
||||
{"id":120416422726733824,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"chetai_start":34,"chetai_end":37,"yg_id":25394280528875520,"dangcheshu":3.5},
|
||||
{"id":120416422735122432,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"jizu":2,"chetai_start":38,"chetai_end":40,"yg_id":25394293594132480,"dangcheshu":3},
|
||||
{"id":120544922305564672,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":5,"chetai_start":81,"chetai_end":85,"yg_id":25394323059118080,"dangcheshu":5},
|
||||
{"id":120544922322341888,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":5,"chetai_start":86,"chetai_end":90,"yg_id":25394253727272960,"dangcheshu":5},
|
||||
{"id":120544922339119104,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":5,"chetai_start":91,"chetai_end":95,"yg_id":25394255010729984,"dangcheshu":5},
|
||||
{"id":120544922355896320,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":5,"chetai_start":96,"chetai_end":100,"yg_id":25394284916117504,"dangcheshu":5},
|
||||
{"id":120545630580903936,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"chetai_start":101,"chetai_end":104,"yg_id":25394268558331904,"dangcheshu":3.5},
|
||||
{"id":120545630606069760,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"chetai_start":104,"chetai_end":107,"yg_id":25394273444696064,"dangcheshu":3.5},
|
||||
{"id":120545630622846976,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"chetai_start":108,"chetai_end":110,"yg_id":25394336074043392,"dangcheshu":3},
|
||||
{"id":120545630639624192,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"chetai_start":111,"chetai_end":114,"yg_id":25394343724453888,"dangcheshu":3.5},
|
||||
{"id":120545630656401408,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"chetai_start":114,"chetai_end":117,"yg_id":25394294344912896,"dangcheshu":3.5},
|
||||
{"id":120545630668984320,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":6,"chetai_start":118,"chetai_end":120,"yg_id":25394282781216768,"dangcheshu":3},
|
||||
{"id":121885127797116928,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"chetai_start":21,"chetai_end":24,"yg_id":25394320131493888,"dangcheshu":3.5},
|
||||
{"id":121885127826477056,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"chetai_start":24,"chetai_end":27,"yg_id":25394353119694848,"dangcheshu":3.5},
|
||||
{"id":121885127843254272,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"chetai_start":28,"chetai_end":30,"yg_id":25394331602915328,"dangcheshu":3},
|
||||
{"id":121885127860031488,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"chetai_start":31,"chetai_end":34,"yg_id":102725859500101632,"dangcheshu":3.5},
|
||||
{"id":121885127876808704,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"chetai_start":34,"chetai_end":37,"yg_id":25394321809215488,"dangcheshu":3.5},
|
||||
{"id":121885127893585920,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":2,"chetai_start":38,"chetai_end":40,"yg_id":25394352679292928,"dangcheshu":3},
|
||||
{"id":121885246168764416,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"chetai_start":41,"chetai_end":44,"yg_id":58023703778168832,"dangcheshu":3.5},
|
||||
{"id":121885246189735936,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"chetai_start":44,"chetai_end":47,"yg_id":25394345465090048,"dangcheshu":3.5},
|
||||
{"id":121885246202318848,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"chetai_start":48,"chetai_end":50,"yg_id":25394310325211136,"dangcheshu":3},
|
||||
{"id":121885246219096064,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"chetai_start":51,"chetai_end":54,"yg_id":57706516936921088,"dangcheshu":3.5},
|
||||
{"id":121885246235873280,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"chetai_start":54,"chetai_end":57,"yg_id":36260154701778944,"dangcheshu":3.5},
|
||||
{"id":121885246252650496,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":3,"chetai_start":58,"chetai_end":60,"yg_id":89158837713506304,"dangcheshu":3},
|
||||
{"id":121885553049210880,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"chetai_start":41,"chetai_end":44,"yg_id":25394298417582080,"dangcheshu":3.5},
|
||||
{"id":121885553074376704,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"chetai_start":44,"chetai_end":47,"yg_id":25394331879739392,"dangcheshu":3.5},
|
||||
{"id":121885553086959616,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"chetai_start":48,"chetai_end":50,"yg_id":25394332085260288,"dangcheshu":3},
|
||||
{"id":121885553107931136,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"chetai_start":51,"chetai_end":54,"yg_id":25394322836819968,"dangcheshu":3.5},
|
||||
{"id":121885553124708352,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"chetai_start":54,"chetai_end":57,"yg_id":25394343061753856,"dangcheshu":3.5},
|
||||
{"id":121885553145679872,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":3,"chetai_start":58,"chetai_end":60,"yg_id":25394287898267648,"dangcheshu":3},
|
||||
{"id":121885819202965504,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"chetai_start":61,"chetai_end":64,"yg_id":25394336598331392,"dangcheshu":3.5},
|
||||
{"id":121885819228131328,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"chetai_start":64,"chetai_end":67,"yg_id":25394343292440576,"dangcheshu":3.5},
|
||||
{"id":121885819244908544,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"chetai_start":68,"chetai_end":70,"yg_id":25394351068680192,"dangcheshu":3},
|
||||
{"id":121885819270074368,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"chetai_start":71,"chetai_end":74,"yg_id":25394331397394432,"dangcheshu":3.5},
|
||||
{"id":121885819291045888,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"chetai_start":74,"chetai_end":77,"yg_id":25394308014149632,"dangcheshu":3.5},
|
||||
{"id":121885819312017408,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":4,"chetai_start":78,"chetai_end":80,"yg_id":25394351525859328,"dangcheshu":3},
|
||||
{"id":121885952749604864,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"chetai_start":81,"chetai_end":84,"yg_id":25394342315167744,"dangcheshu":3.5},
|
||||
{"id":121885952774770688,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"chetai_start":84,"chetai_end":87,"yg_id":25394307397586944,"dangcheshu":3.5},
|
||||
{"id":121885952791547904,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"chetai_start":88,"chetai_end":90,"yg_id":25394348786978816,"dangcheshu":3},
|
||||
{"id":121885952812519424,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"chetai_start":91,"chetai_end":94,"yg_id":25394310102913024,"dangcheshu":3.5},
|
||||
{"id":121885952829296640,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"chetai_start":94,"chetai_end":97,"yg_id":75481403743014912,"dangcheshu":3.5},
|
||||
{"id":121885952846073856,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":5,"chetai_start":98,"chetai_end":100,"yg_id":25394310966939648,"dangcheshu":3},
|
||||
{"id":121886067652562944,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"chetai_start":101,"chetai_end":104,"yg_id":25394251827253248,"dangcheshu":3.5},
|
||||
{"id":121886067673534464,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"chetai_start":104,"chetai_end":107,"yg_id":25394340423536640,"dangcheshu":3.5},
|
||||
{"id":121886067690311680,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"chetai_start":108,"chetai_end":110,"yg_id":25394301508784128,"dangcheshu":3},
|
||||
{"id":121886067707088896,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"chetai_start":111,"chetai_end":114,"yg_id":25394313785511936,"dangcheshu":3.5},
|
||||
{"id":121886067723866112,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"chetai_start":114,"chetai_end":117,"yg_id":25394260090032128,"dangcheshu":3.5},
|
||||
{"id":121886067740643328,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"jizu":6,"chetai_start":118,"chetai_end":120,"yg_id":25394254805209088,"dangcheshu":3},
|
||||
{"id":121887275310125056,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"chetai_start":61,"chetai_end":64,"yg_id":57707023516569600,"dangcheshu":3.5},
|
||||
{"id":121887275335290880,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"chetai_start":64,"chetai_end":67,"yg_id":55473100082384896,"dangcheshu":3.5},
|
||||
{"id":121887275352068096,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"chetai_start":68,"chetai_end":70,"yg_id":36260136813072384,"dangcheshu":3},
|
||||
{"id":121887275368845312,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"chetai_start":71,"chetai_end":74,"yg_id":56619152755920896,"dangcheshu":3.5},
|
||||
{"id":121887275385622528,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"chetai_start":74,"chetai_end":77,"yg_id":25394305396903936,"dangcheshu":3.5},
|
||||
{"id":121887275402399744,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":4,"chetai_start":78,"chetai_end":80,"yg_id":114291502120701952,"dangcheshu":3},
|
||||
{"id":123606871947874304,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"chetai_start":101,"chetai_end":104,"yg_id":84087718895685632,"dangcheshu":3.5},
|
||||
{"id":123606871968845824,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"chetai_start":104,"chetai_end":107,"yg_id":88552717080858624,"dangcheshu":3.5},
|
||||
{"id":123606871989817344,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"chetai_start":108,"chetai_end":110,"yg_id":93241166341869568,"dangcheshu":3},
|
||||
{"id":123606872006594560,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"chetai_start":111,"chetai_end":114,"yg_id":93238232686268416,"dangcheshu":3.5},
|
||||
{"id":123606872023371776,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"chetai_start":114,"chetai_end":117,"yg_id":84084713496514560,"dangcheshu":3.5},
|
||||
{"id":123606872040148992,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"jizu":6,"chetai_start":118,"chetai_end":120,"yg_id":84089998294388736,"dangcheshu":3},
|
||||
{"id":123662101523730432,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":81,"chetai_end":82,"yg_id":111640051850416128,"dangcheshu":2},
|
||||
{"id":123662102295482368,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":83,"chetai_end":84,"yg_id":121069184883888128,"dangcheshu":2},
|
||||
{"id":123662102370979840,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":85,"chetai_end":86,"yg_id":93228252994211840,"dangcheshu":2},
|
||||
{"id":123662102400339968,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":87,"chetai_end":88,"yg_id":93227633852026880,"dangcheshu":2},
|
||||
{"id":123662102425505792,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":89,"chetai_end":90,"yg_id":111639830290501632,"dangcheshu":2},
|
||||
{"id":123662102442283008,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":91,"chetai_end":92,"yg_id":93227022582550528,"dangcheshu":2},
|
||||
{"id":123662102467448832,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":93,"chetai_end":94,"yg_id":111640631461285888,"dangcheshu":2},
|
||||
{"id":123662102488420352,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":95,"chetai_end":96,"yg_id":111639603936497664,"dangcheshu":2},
|
||||
{"id":123662102509391872,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":97,"chetai_end":98,"yg_id":111640416700338176,"dangcheshu":2},
|
||||
{"id":123662102526169088,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":5,"chetai_start":99,"chetai_end":100,"yg_id":111639258053218304,"dangcheshu":2},
|
||||
{"id":123696286305095680,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"chetai_start":21,"chetai_end":24,"yg_id":58372032244486144,"dangcheshu":3.5},
|
||||
{"id":123696286464479232,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"chetai_start":24,"chetai_end":27,"yg_id":25394319879835648,"dangcheshu":3.5},
|
||||
{"id":123696286519005184,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"chetai_start":28,"chetai_end":30,"yg_id":25394312409780224,"dangcheshu":3},
|
||||
{"id":123696286539976704,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"chetai_start":31,"chetai_end":34,"yg_id":55473760022564864,"dangcheshu":3.5},
|
||||
{"id":123696286560948224,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"chetai_start":34,"chetai_end":37,"yg_id":55471125118849024,"dangcheshu":3.5},
|
||||
{"id":123696286569336832,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":2,"chetai_start":38,"chetai_end":40,"yg_id":55462259811422208,"dangcheshu":3},
|
||||
{"id":123712008896909312,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"chetai_start":21,"chetai_end":24,"yg_id":25394320567701504,"dangcheshu":3.5},
|
||||
{"id":123712008926269440,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"chetai_start":24,"chetai_end":27,"yg_id":25394333368717312,"dangcheshu":3.5},
|
||||
{"id":123712008947240960,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"chetai_start":28,"chetai_end":30,"yg_id":25394272303845376,"dangcheshu":3},
|
||||
{"id":123712008964018176,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"chetai_start":31,"chetai_end":34,"yg_id":25394288103788544,"dangcheshu":3.5},
|
||||
{"id":123712008984989696,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"chetai_start":34,"chetai_end":37,"yg_id":25394274837204992,"dangcheshu":3.5},
|
||||
{"id":123712009001766912,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":2,"chetai_start":38,"chetai_end":40,"yg_id":25394346626912256,"dangcheshu":3},
|
||||
{"id":123712112307474432,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"chetai_start":41,"chetai_end":44,"yg_id":25394262979907584,"dangcheshu":3.5},
|
||||
{"id":123712112332640256,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"chetai_start":44,"chetai_end":47,"yg_id":25394337118425088,"dangcheshu":3.5},
|
||||
{"id":123712112353611776,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"chetai_start":48,"chetai_end":50,"yg_id":25394302385393664,"dangcheshu":3},
|
||||
{"id":123712112374583296,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"chetai_start":51,"chetai_end":54,"yg_id":25394346350088192,"dangcheshu":3.5},
|
||||
{"id":123712112391360512,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"chetai_start":54,"chetai_end":57,"yg_id":25394342852038656,"dangcheshu":3.5},
|
||||
{"id":123712112408137728,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":3,"chetai_start":58,"chetai_end":60,"yg_id":25394287084572672,"dangcheshu":3},
|
||||
{"id":123715314398531584,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"chetai_start":61,"chetai_end":64,"yg_id":25394316927045632,"dangcheshu":3.5},
|
||||
{"id":123715314415308800,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"chetai_start":64,"chetai_end":67,"yg_id":25394330747277312,"dangcheshu":3.5},
|
||||
{"id":123715314432086016,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"chetai_start":68,"chetai_end":70,"yg_id":25394323495325696,"dangcheshu":3},
|
||||
{"id":123715314444668928,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"chetai_start":71,"chetai_end":74,"yg_id":25394303983423488,"dangcheshu":3.5},
|
||||
{"id":123715314457251840,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"chetai_start":74,"chetai_end":77,"yg_id":55117587129831424,"dangcheshu":3.5},
|
||||
{"id":123715314465640448,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":4,"chetai_start":78,"chetai_end":80,"yg_id":25394291484397568,"dangcheshu":3},
|
||||
{"id":123715494162206720,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"chetai_start":81,"chetai_end":84,"yg_id":25394328411049984,"dangcheshu":3.5},
|
||||
{"id":123715494187372544,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"chetai_start":84,"chetai_end":87,"yg_id":25394309238886400,"dangcheshu":3.5},
|
||||
{"id":123715494204149760,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"chetai_start":88,"chetai_end":90,"yg_id":25394301273903104,"dangcheshu":3},
|
||||
{"id":123715494216732672,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"chetai_start":91,"chetai_end":94,"yg_id":25394311449284608,"dangcheshu":3.5},
|
||||
{"id":123715494233509888,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"chetai_start":94,"chetai_end":97,"yg_id":25394338452213760,"dangcheshu":3.5},
|
||||
{"id":123715494262870016,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"jizu":5,"chetai_start":98,"chetai_end":100,"yg_id":25394319443628032,"dangcheshu":3},
|
||||
{"id":124085100756340736,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"chetai_start":1,"chetai_end":4,"yg_id":25394300791558144,"dangcheshu":3.5},
|
||||
{"id":124085100798283776,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"chetai_start":4,"chetai_end":7,"yg_id":25394348992499712,"dangcheshu":3.5},
|
||||
{"id":124085100819255296,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"chetai_start":8,"chetai_end":10,"yg_id":25394250522824704,"dangcheshu":3},
|
||||
{"id":124085100848615424,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"chetai_start":11,"chetai_end":14,"yg_id":25394251181330432,"dangcheshu":3.5},
|
||||
{"id":124085100873781248,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"chetai_start":14,"chetai_end":17,"yg_id":25394300154023936,"dangcheshu":3.5},
|
||||
{"id":124085100898947072,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":1,"chetai_start":18,"chetai_end":20,"yg_id":25394274627489792,"dangcheshu":3},
|
||||
{"id":124085260844535808,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"chetai_start":21,"chetai_end":24,"yg_id":25394297989763072,"dangcheshu":3.5},
|
||||
{"id":124085260886478848,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"chetai_start":24,"chetai_end":27,"yg_id":25394285700452352,"dangcheshu":3.5},
|
||||
{"id":124085260907450368,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"chetai_start":28,"chetai_end":30,"yg_id":25394258097737728,"dangcheshu":3},
|
||||
{"id":124085260924227584,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"chetai_start":31,"chetai_end":34,"yg_id":25394289043312640,"dangcheshu":3.5},
|
||||
{"id":124085260941004800,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"chetai_start":34,"chetai_end":37,"yg_id":25394260572377088,"dangcheshu":3.5},
|
||||
{"id":124085260957782016,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":2,"chetai_start":38,"chetai_end":40,"yg_id":25394276103884800,"dangcheshu":3},
|
||||
{"id":124085321473200128,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":3,"chetai_start":41,"chetai_end":45,"yg_id":25394275688648704,"dangcheshu":5},
|
||||
{"id":124085321494171648,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":3,"chetai_start":46,"chetai_end":50,"yg_id":25394257451814912,"dangcheshu":5},
|
||||
{"id":124085321510948864,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":3,"chetai_start":51,"chetai_end":55,"yg_id":25394267476201472,"dangcheshu":5},
|
||||
{"id":124085321523531776,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":3,"chetai_start":56,"chetai_end":60,"yg_id":25394259020484608,"dangcheshu":5},
|
||||
{"id":124085394332454912,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"chetai_start":61,"chetai_end":64,"yg_id":25394288347058176,"dangcheshu":3.5},
|
||||
{"id":124085394353426432,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"chetai_start":64,"chetai_end":67,"yg_id":25394266192744448,"dangcheshu":3.5},
|
||||
{"id":124085394395369472,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"chetai_start":68,"chetai_end":70,"yg_id":25394282345009152,"dangcheshu":3},
|
||||
{"id":124085394416340992,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"chetai_start":71,"chetai_end":74,"yg_id":25394284706402304,"dangcheshu":3.5},
|
||||
{"id":124085394433118208,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"chetai_start":74,"chetai_end":77,"yg_id":25394293271171072,"dangcheshu":3.5},
|
||||
{"id":124085394449895424,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"jizu":4,"chetai_start":78,"chetai_end":80,"yg_id":25394248987709440,"dangcheshu":3},
|
||||
{"id":124422175993106432,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":101,"chetai_end":103,"yg_id":93237880561864704,"dangcheshu":2.5},
|
||||
{"id":124422176030855168,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":103,"chetai_end":105,"yg_id":93590060657545216,"dangcheshu":2.5},
|
||||
{"id":124422176056020992,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":106,"chetai_end":108,"yg_id":93240184245587968,"dangcheshu":2.5},
|
||||
{"id":124422176081186816,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":108,"chetai_end":110,"yg_id":88556029159149568,"dangcheshu":2.5},
|
||||
{"id":124422176106352640,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":111,"chetai_end":113,"yg_id":93238706298687488,"dangcheshu":2.5},
|
||||
{"id":124422176131518464,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":113,"chetai_end":115,"yg_id":88553603400208384,"dangcheshu":2.5},
|
||||
{"id":124422176152489984,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":116,"chetai_end":118,"yg_id":93236409787224064,"dangcheshu":2.5},
|
||||
{"id":124422176181850112,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"jizu":6,"chetai_start":118,"chetai_end":120,"yg_id":93239113490108416,"dangcheshu":2.5}
|
||||
]
|
||||
@@ -0,0 +1,9 @@
|
||||
[
|
||||
{"id":30318522743656448,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"yg_id":25394296936992768},
|
||||
{"id":30318912478384128,"deleted_at":null,"dep_id":16043931070369792,"banci":1,"yg_id":25394278175870976},
|
||||
{"id":30318977318129664,"deleted_at":null,"dep_id":16047387197837312,"banci":1,"yg_id":25394284219863040},
|
||||
{"id":30574578740760576,"deleted_at":null,"dep_id":22308683820044288,"banci":1,"yg_id":25394286337986560},
|
||||
{"id":30574628829138944,"deleted_at":null,"dep_id":22308683820044288,"banci":2,"yg_id":25394249843347456},
|
||||
{"id":32372395503259648,"deleted_at":null,"dep_id":22308600831545344,"banci":1,"yg_id":25394250304720896},
|
||||
{"id":56641710280675328,"deleted_at":null,"dep_id":22308600831545344,"banci":2,"yg_id":25394284219863040}
|
||||
]
|
||||
@@ -0,0 +1,144 @@
|
||||
<script setup>
|
||||
/**
|
||||
* 职工选择弹窗(单选 / 多选)
|
||||
* 对应 WinForms 端的 F9ModalPageUserControl 职工选择页,数据源为 /api/sys/employee。
|
||||
*/
|
||||
import { ref, watch } from 'vue';
|
||||
import { ElMessage } from 'element-plus';
|
||||
import request from '../../utils/request';
|
||||
|
||||
const props = defineProps({
|
||||
modelValue: Boolean,
|
||||
title: { type: String, default: '选择职工' },
|
||||
multiple: Boolean,
|
||||
depId: { type: [Number, String], default: 0 },
|
||||
width: { type: String, default: '820px' },
|
||||
});
|
||||
const emit = defineEmits(['update:modelValue', 'confirm']);
|
||||
|
||||
const visible = ref(false);
|
||||
const loading = ref(false);
|
||||
const rows = ref([]);
|
||||
const total = ref(0);
|
||||
const keyword = ref('');
|
||||
const pageIndex = ref(1);
|
||||
const pageSize = ref(20);
|
||||
const current = ref(null);
|
||||
const selected = ref([]);
|
||||
|
||||
watch(() => props.modelValue, async (v) => {
|
||||
visible.value = v;
|
||||
if (!v) return;
|
||||
keyword.value = '';
|
||||
pageIndex.value = 1;
|
||||
current.value = null;
|
||||
selected.value = [];
|
||||
await query();
|
||||
});
|
||||
watch(visible, (v) => emit('update:modelValue', v));
|
||||
|
||||
async function query() {
|
||||
loading.value = true;
|
||||
try {
|
||||
const res = await request.get('/sys/employee', {
|
||||
params: {
|
||||
depId: props.depId || 0,
|
||||
like: keyword.value,
|
||||
pageIndex: pageIndex.value,
|
||||
pageSize: pageSize.value,
|
||||
},
|
||||
});
|
||||
rows.value = res.data?.items || [];
|
||||
total.value = Number(res.data?.total || 0);
|
||||
} catch {
|
||||
rows.value = [];
|
||||
total.value = 0;
|
||||
} finally {
|
||||
loading.value = false;
|
||||
}
|
||||
}
|
||||
|
||||
function onSearch() {
|
||||
pageIndex.value = 1;
|
||||
query();
|
||||
}
|
||||
function onPageChange(p) {
|
||||
pageIndex.value = p;
|
||||
query();
|
||||
}
|
||||
function onRowClick(row) {
|
||||
if (props.multiple) return;
|
||||
current.value = row;
|
||||
}
|
||||
function onRowDblClick(row) {
|
||||
if (props.multiple) return;
|
||||
current.value = row;
|
||||
confirm();
|
||||
}
|
||||
|
||||
function confirm() {
|
||||
const picked = props.multiple ? selected.value : current.value ? [current.value] : [];
|
||||
if (!picked.length) {
|
||||
ElMessage.warning('请选择职工');
|
||||
return;
|
||||
}
|
||||
visible.value = false;
|
||||
emit('confirm', props.multiple ? picked.map((x) => ({ ...x })) : { ...picked[0] });
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<el-dialog v-model="visible" :title="title" :width="width" append-to-body destroy-on-close>
|
||||
<div class="es-toolbar">
|
||||
<el-input
|
||||
v-model="keyword"
|
||||
placeholder="姓名 / 工号"
|
||||
clearable
|
||||
style="width: 200px"
|
||||
@keyup.enter="onSearch"
|
||||
@clear="onSearch"
|
||||
/>
|
||||
<el-button type="primary" @click="onSearch">查询</el-button>
|
||||
<span v-if="multiple" class="es-tip">已选 {{ selected.length }} 人</span>
|
||||
</div>
|
||||
|
||||
<el-table
|
||||
v-loading="loading"
|
||||
:data="rows"
|
||||
border
|
||||
size="small"
|
||||
height="400"
|
||||
highlight-current-row
|
||||
@row-click="onRowClick"
|
||||
@row-dblclick="onRowDblClick"
|
||||
@selection-change="selected = $event"
|
||||
>
|
||||
<el-table-column v-if="multiple" type="selection" width="45" />
|
||||
<el-table-column type="index" label="序号" width="55" />
|
||||
<el-table-column prop="name" label="姓名" width="110" />
|
||||
<el-table-column prop="code" label="工号" width="120" />
|
||||
<el-table-column prop="depName" label="部门" min-width="140" show-overflow-tooltip />
|
||||
<el-table-column prop="gangwei" label="岗位" min-width="120" show-overflow-tooltip />
|
||||
</el-table>
|
||||
|
||||
<el-pagination
|
||||
class="es-page"
|
||||
:current-page="pageIndex"
|
||||
:page-size="pageSize"
|
||||
:total="total"
|
||||
layout="total, prev, pager, next"
|
||||
@current-change="onPageChange"
|
||||
/>
|
||||
|
||||
<template #footer>
|
||||
<el-button @click="visible = false">取消</el-button>
|
||||
<el-button type="primary" @click="confirm">确定</el-button>
|
||||
</template>
|
||||
</el-dialog>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.es-toolbar { display: flex; align-items: center; gap: 8px; margin-bottom: 8px; }
|
||||
.es-tip { color: var(--el-text-color-secondary); font-size: 13px; }
|
||||
.es-page { margin-top: 10px; justify-content: flex-end; }
|
||||
</style>
|
||||
@@ -65,6 +65,7 @@ export const componentMap = {
|
||||
'prod/lsjl/index': () => import('../views/prod/lsjl/index.vue'),
|
||||
'prod/xdjy/index': () => import('../views/prod/xdjy/index.vue'),
|
||||
'prod/hbjy/index': () => import('../views/prod/hbjy/index.vue'),
|
||||
'prod/ktpb/index': () => import('../views/prod/ktpb/index.vue'),
|
||||
'notification/messages/index': () => import('../views/notification/messages/index.vue'),
|
||||
'notification/subscribe/index': () => import('../views/notification/subscribe/index.vue'),
|
||||
'notification/type/index': () => import('../views/notification/type/index.vue'),
|
||||
|
||||
@@ -0,0 +1,650 @@
|
||||
<script setup>
|
||||
/**
|
||||
* 看台排班(生产-前缫)
|
||||
* 对应 WinForms 端 WinClient\F9.Business.Prod\QS\KTPB\Page_KTPB
|
||||
* - 车头工:一个「车间+班次+机组」一条记录(2 名车头工)
|
||||
* - 挡车工:一个「车间+班次+机组」一组记录,按车台区间分派挡车工,挡车数自动计算
|
||||
* - 值班长:一个「车间+班次」可有多名值班长
|
||||
*/
|
||||
import { ref, reactive, computed, onMounted } from 'vue';
|
||||
import { ElMessage, ElMessageBox } from 'element-plus';
|
||||
import request from '../../../utils/request';
|
||||
import EmployeeSelect from '../../../components/select/EmployeeSelect.vue';
|
||||
|
||||
const TABS = [
|
||||
{ name: 'dcg', label: '挡车工' },
|
||||
{ name: 'ctg', label: '车头工' },
|
||||
{ name: 'zbz', label: '值班长' },
|
||||
];
|
||||
const BANCI = [
|
||||
{ value: 1, label: '甲班' },
|
||||
{ value: 2, label: '乙班' },
|
||||
];
|
||||
|
||||
const tab = ref('dcg');
|
||||
const deps = ref([]);
|
||||
const jizuOptions = ref([]);
|
||||
|
||||
const filter = reactive({ depId: 0, banci: 1, jizu: 0, keyword: '' });
|
||||
|
||||
const state = reactive({
|
||||
dcg: { rows: [], total: 0, loading: false, pageIndex: 1, pageSize: 20 },
|
||||
ctg: { rows: [], total: 0, loading: false, pageIndex: 1, pageSize: 20 },
|
||||
zbz: { rows: [], total: 0, loading: false, pageIndex: 1, pageSize: 20 },
|
||||
});
|
||||
const cur = computed(() => state[tab.value]);
|
||||
|
||||
const depName = computed(() => deps.value.find((d) => d.id === filter.depId)?.name || '');
|
||||
const banciName = computed(() => BANCI.find((b) => b.value === filter.banci)?.label || '');
|
||||
|
||||
// ==================== 通用查询 ====================
|
||||
|
||||
async function loadDeps() {
|
||||
const res = await request.get('/prod/ktpb/qianxian-deps');
|
||||
deps.value = res.data || [];
|
||||
if (deps.value.length && !filter.depId) filter.depId = deps.value[0].id;
|
||||
}
|
||||
|
||||
async function loadJizu() {
|
||||
if (!filter.depId) {
|
||||
jizuOptions.value = [];
|
||||
return;
|
||||
}
|
||||
const res = await request.get('/prod/ktpb/jizu-options', { params: { depId: filter.depId } });
|
||||
jizuOptions.value = res.data || [];
|
||||
if (!jizuOptions.value.some((x) => x.jizu === filter.jizu)) {
|
||||
filter.jizu = jizuOptions.value.length ? jizuOptions.value[0].jizu : 0;
|
||||
}
|
||||
}
|
||||
|
||||
async function loadList(resetPage = false) {
|
||||
const s = cur.value;
|
||||
if (resetPage) s.pageIndex = 1;
|
||||
s.loading = true;
|
||||
try {
|
||||
const res = await request.get(`/prod/ktpb/${tab.value}`, {
|
||||
params: {
|
||||
depId: filter.depId || 0,
|
||||
banci: filter.banci || null,
|
||||
jizu: tab.value === 'zbz' ? null : filter.jizu || null,
|
||||
like: filter.keyword,
|
||||
pageIndex: s.pageIndex,
|
||||
pageSize: s.pageSize,
|
||||
},
|
||||
});
|
||||
s.rows = res.data?.items || [];
|
||||
s.total = Number(res.data?.total || 0);
|
||||
} finally {
|
||||
s.loading = false;
|
||||
}
|
||||
}
|
||||
|
||||
async function onDepChange() {
|
||||
await loadJizu();
|
||||
await loadList(true);
|
||||
}
|
||||
async function onSearch() {
|
||||
await loadList(true);
|
||||
}
|
||||
async function onPageChange(p) {
|
||||
cur.value.pageIndex = p;
|
||||
await loadList();
|
||||
}
|
||||
async function onTabChange(name) {
|
||||
await loadList();
|
||||
}
|
||||
|
||||
onMounted(async () => {
|
||||
await loadDeps();
|
||||
await loadJizu();
|
||||
await loadList(true);
|
||||
});
|
||||
|
||||
// ==================== 挡车工:整组批量编辑 ====================
|
||||
|
||||
const dcgDlg = reactive({
|
||||
visible: false,
|
||||
loading: false,
|
||||
saving: false,
|
||||
depId: 0,
|
||||
banci: 1,
|
||||
jizu: 0,
|
||||
chetaiStart: 0,
|
||||
chetaiEnd: 0,
|
||||
rows: [],
|
||||
});
|
||||
|
||||
const dcgDepName = computed(() => deps.value.find((d) => d.id === dcgDlg.depId)?.name || '');
|
||||
const dcgBanciName = computed(() => BANCI.find((b) => b.value === dcgDlg.banci)?.label || '');
|
||||
const dcgTotalChetai = computed(() =>
|
||||
dcgDlg.chetaiStart && dcgDlg.chetaiEnd ? dcgDlg.chetaiEnd - dcgDlg.chetaiStart + 1 : 0
|
||||
);
|
||||
const dcgAssigned = computed(() => {
|
||||
const set = new Set();
|
||||
dcgDlg.rows.forEach((r) => {
|
||||
const s = Number(r.chetaiStart) || 0;
|
||||
const e = Number(r.chetaiEnd) || 0;
|
||||
for (let i = s; i <= e; i++) set.add(i);
|
||||
});
|
||||
return set.size;
|
||||
});
|
||||
|
||||
async function openDcgGroup() {
|
||||
if (!filter.depId) return ElMessage.warning('请先选择车间');
|
||||
if (!filter.jizu) return ElMessage.warning('请先选择机组');
|
||||
|
||||
const opt = jizuOptions.value.find((x) => x.jizu === filter.jizu);
|
||||
dcgDlg.depId = filter.depId;
|
||||
dcgDlg.banci = filter.banci;
|
||||
dcgDlg.jizu = filter.jizu;
|
||||
dcgDlg.chetaiStart = opt?.chetaiStart || 0;
|
||||
dcgDlg.chetaiEnd = opt?.chetaiEnd || 0;
|
||||
dcgDlg.visible = true;
|
||||
dcgDlg.loading = true;
|
||||
try {
|
||||
const res = await request.get('/prod/ktpb/dcg/group', {
|
||||
params: { depId: dcgDlg.depId, banci: dcgDlg.banci, jizu: dcgDlg.jizu },
|
||||
});
|
||||
dcgDlg.rows = (res.data || []).map((x) => ({
|
||||
id: x.id,
|
||||
ygId: x.ygId,
|
||||
ygName: x.ygName,
|
||||
chetaiStart: x.chetaiStart,
|
||||
chetaiEnd: x.chetaiEnd,
|
||||
dangcheshu: x.dangcheshu,
|
||||
}));
|
||||
recalcDangche(dcgDlg.rows);
|
||||
} finally {
|
||||
dcgDlg.loading = false;
|
||||
}
|
||||
}
|
||||
|
||||
function draftDcgRow(name, start, end) {
|
||||
dcgDlg.rows.push({ id: 0, ygId: 0, ygName: name, chetaiStart: start, chetaiEnd: end, dangcheshu: 0 });
|
||||
}
|
||||
|
||||
function appendEmployees(picked) {
|
||||
const exist = new Set(dcgDlg.rows.map((r) => String(r.ygId)));
|
||||
let next = dcgDlg.chetaiStart;
|
||||
if (dcgDlg.rows.length) {
|
||||
next = Math.max(...dcgDlg.rows.map((r) => Number(r.chetaiEnd) || 0)) + 1;
|
||||
}
|
||||
picked.forEach((e) => {
|
||||
if (exist.has(String(e.id))) return;
|
||||
if (next > dcgDlg.chetaiEnd) next = dcgDlg.chetaiEnd;
|
||||
draftDcgRow(e.name, next, next);
|
||||
exist.add(String(e.id));
|
||||
next += 1;
|
||||
});
|
||||
recalcDangche(dcgDlg.rows);
|
||||
}
|
||||
|
||||
function removeDcgRow(index) {
|
||||
dcgDlg.rows.splice(index, 1);
|
||||
recalcDangche(dcgDlg.rows);
|
||||
}
|
||||
|
||||
function clearDcgRows() {
|
||||
dcgDlg.rows = [];
|
||||
}
|
||||
|
||||
/**
|
||||
* 挡车数计算(与后端 KtpbService.RecalcDangcheshu 完全一致):
|
||||
* 单台车权重 1;若该车台被多条记录共享,且同时是某记录起点与某记录终点(接壤),权重 0.5。
|
||||
*/
|
||||
function recalcDangche(rows) {
|
||||
const counts = {};
|
||||
const starts = new Set();
|
||||
const ends = new Set();
|
||||
rows.forEach((r) => {
|
||||
const s = Number(r.chetaiStart) || 0;
|
||||
const e = Number(r.chetaiEnd) || 0;
|
||||
if (!s || e < s) return;
|
||||
starts.add(s);
|
||||
ends.add(e);
|
||||
for (let i = s; i <= e; i++) counts[i] = (counts[i] || 0) + 1;
|
||||
});
|
||||
rows.forEach((r) => {
|
||||
const s = Number(r.chetaiStart) || 0;
|
||||
const e = Number(r.chetaiEnd) || 0;
|
||||
let total = 0;
|
||||
for (let i = s; i <= e; i++) {
|
||||
let w = 1;
|
||||
if ((counts[i] || 0) > 1 && starts.has(i) && ends.has(i)) w = 0.5;
|
||||
total += w;
|
||||
}
|
||||
r.dangcheshu = Math.round(total * 100) / 100;
|
||||
});
|
||||
}
|
||||
|
||||
const empPicker = reactive({ visible: false, multiple: false, target: '' });
|
||||
|
||||
function pickEmployee(target) {
|
||||
empPicker.target = target;
|
||||
empPicker.multiple = target === 'dcg';
|
||||
empPicker.visible = true;
|
||||
}
|
||||
|
||||
function onEmployeePicked(picked) {
|
||||
if (empPicker.target === 'dcg') {
|
||||
appendEmployees(picked);
|
||||
} else if (empPicker.target === 'ctg1') {
|
||||
ctgForm.ygid1 = picked.id;
|
||||
ctgForm.ygid1Name = picked.name;
|
||||
} else if (empPicker.target === 'ctg2') {
|
||||
ctgForm.ygid2 = picked.id;
|
||||
ctgForm.ygid2Name = picked.name;
|
||||
} else if (empPicker.target === 'zbz') {
|
||||
zbzForm.ygId = picked.id;
|
||||
zbzForm.ygName = picked.name;
|
||||
}
|
||||
}
|
||||
|
||||
async function saveDcgGroup() {
|
||||
for (const r of dcgDlg.rows) {
|
||||
if (!r.ygId) return ElMessage.warning('存在未选择挡车工的记录');
|
||||
if (!r.chetaiStart) return ElMessage.warning(`挡车工「${r.ygName}」请填写起始车台`);
|
||||
if (!r.chetaiEnd || Number(r.chetaiEnd) < Number(r.chetaiStart)) {
|
||||
return ElMessage.warning(`挡车工「${r.ygName}」结束车台不能小于起始车台`);
|
||||
}
|
||||
if (Number(r.chetaiStart) < dcgDlg.chetaiStart || Number(r.chetaiEnd) > dcgDlg.chetaiEnd) {
|
||||
return ElMessage.warning(`挡车工「${r.ygName}」车台范围必须在本机组 ${dcgDlg.chetaiStart}-${dcgDlg.chetaiEnd} 内`);
|
||||
}
|
||||
}
|
||||
recalcDangche(dcgDlg.rows);
|
||||
dcgDlg.saving = true;
|
||||
try {
|
||||
const res = await request.post('/prod/ktpb/dcg/batch', {
|
||||
depId: dcgDlg.depId,
|
||||
banci: dcgDlg.banci,
|
||||
jizu: dcgDlg.jizu,
|
||||
items: dcgDlg.rows.map((r) => ({
|
||||
ygId: r.ygId,
|
||||
ygName: r.ygName,
|
||||
chetaiStart: Number(r.chetaiStart),
|
||||
chetaiEnd: Number(r.chetaiEnd),
|
||||
dangcheshu: r.dangcheshu,
|
||||
})),
|
||||
});
|
||||
ElMessage.success(res.message || '保存成功');
|
||||
dcgDlg.visible = false;
|
||||
await loadList();
|
||||
} finally {
|
||||
dcgDlg.saving = false;
|
||||
}
|
||||
}
|
||||
|
||||
async function deleteDcg(row) {
|
||||
await ElMessageBox.confirm(
|
||||
`确定删除「${row.deptName} ${row.banciName}班 机组${row.jizu}」中 ${row.ygName} 的排班吗?`,
|
||||
'提示',
|
||||
{ type: 'warning' }
|
||||
);
|
||||
await request.delete(`/prod/ktpb/dcg/${row.id}`);
|
||||
ElMessage.success('删除成功');
|
||||
await loadList();
|
||||
}
|
||||
|
||||
// ==================== 车头工 ====================
|
||||
|
||||
const ctgDlg = reactive({ visible: false, saving: false, id: 0 });
|
||||
const ctgForm = reactive({
|
||||
depId: 0,
|
||||
banci: 1,
|
||||
jizu: 0,
|
||||
ygid1: 0,
|
||||
ygid1Name: '',
|
||||
ygid2: 0,
|
||||
ygid2Name: '',
|
||||
});
|
||||
|
||||
function openCtg(row) {
|
||||
ctgDlg.id = row?.id || 0;
|
||||
ctgForm.depId = row?.depId || filter.depId;
|
||||
ctgForm.banci = row?.banci || filter.banci;
|
||||
ctgForm.jizu = row?.jizu || filter.jizu;
|
||||
ctgForm.ygid1 = row?.ygid1 || 0;
|
||||
ctgForm.ygid1Name = row?.ygid1Name || '';
|
||||
ctgForm.ygid2 = row?.ygid2 || 0;
|
||||
ctgForm.ygid2Name = row?.ygid2Name || '';
|
||||
ctgDlg.visible = true;
|
||||
}
|
||||
|
||||
async function saveCtg() {
|
||||
if (!ctgForm.depId) return ElMessage.warning('请选择车间');
|
||||
if (!ctgForm.jizu) return ElMessage.warning('请选择机组');
|
||||
if (!ctgForm.ygid1) return ElMessage.warning('请选择车头工1');
|
||||
ctgDlg.saving = true;
|
||||
try {
|
||||
const payload = {
|
||||
depId: ctgForm.depId,
|
||||
banci: ctgForm.banci,
|
||||
jizu: ctgForm.jizu,
|
||||
ygid1: ctgForm.ygid1,
|
||||
ygid2: ctgForm.ygid2 || 0,
|
||||
};
|
||||
if (ctgDlg.id) {
|
||||
await request.put(`/prod/ktpb/ctg/${ctgDlg.id}`, payload);
|
||||
ElMessage.success('修改成功');
|
||||
} else {
|
||||
await request.post('/prod/ktpb/ctg', payload);
|
||||
ElMessage.success('新增成功');
|
||||
}
|
||||
ctgDlg.visible = false;
|
||||
await loadList();
|
||||
} finally {
|
||||
ctgDlg.saving = false;
|
||||
}
|
||||
}
|
||||
|
||||
async function deleteCtg(row) {
|
||||
await ElMessageBox.confirm(`确定删除「${row.deptName} ${row.banciName}班 机组${row.jizu}」的车头工排班吗?`, '提示', {
|
||||
type: 'warning',
|
||||
});
|
||||
await request.delete(`/prod/ktpb/ctg/${row.id}`);
|
||||
ElMessage.success('删除成功');
|
||||
await loadList();
|
||||
}
|
||||
|
||||
// ==================== 值班长 ====================
|
||||
|
||||
const zbzDlg = reactive({ visible: false, saving: false, id: 0 });
|
||||
const zbzForm = reactive({ depId: 0, banci: 1, ygId: 0, ygName: '' });
|
||||
|
||||
function openZbz(row) {
|
||||
zbzDlg.id = row?.id || 0;
|
||||
zbzForm.depId = row?.depId || filter.depId;
|
||||
zbzForm.banci = row?.banci || filter.banci;
|
||||
zbzForm.ygId = row?.ygId || 0;
|
||||
zbzForm.ygName = row?.ygName || '';
|
||||
zbzDlg.visible = true;
|
||||
}
|
||||
|
||||
async function saveZbz() {
|
||||
if (!zbzForm.depId) return ElMessage.warning('请选择车间');
|
||||
if (!zbzForm.ygId) return ElMessage.warning('请选择值班长');
|
||||
zbzDlg.saving = true;
|
||||
try {
|
||||
const payload = { depId: zbzForm.depId, banci: zbzForm.banci, ygId: zbzForm.ygId };
|
||||
if (zbzDlg.id) {
|
||||
await request.put(`/prod/ktpb/zbz/${zbzDlg.id}`, payload);
|
||||
ElMessage.success('修改成功');
|
||||
} else {
|
||||
await request.post('/prod/ktpb/zbz', payload);
|
||||
ElMessage.success('新增成功');
|
||||
}
|
||||
zbzDlg.visible = false;
|
||||
await loadList();
|
||||
} finally {
|
||||
zbzDlg.saving = false;
|
||||
}
|
||||
}
|
||||
|
||||
async function deleteZbz(row) {
|
||||
await ElMessageBox.confirm(`确定删除「${row.deptName} ${row.banciName}班」值班长 ${row.ygName} 的排班吗?`, '提示', {
|
||||
type: 'warning',
|
||||
});
|
||||
await request.delete(`/prod/ktpb/zbz/${row.id}`);
|
||||
ElMessage.success('删除成功');
|
||||
await loadList();
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="ktpb-page">
|
||||
<el-card shadow="never">
|
||||
<el-tabs v-model="tab" @tab-change="onTabChange">
|
||||
<el-tab-pane v-for="t in TABS" :key="t.name" :label="t.label" :name="t.name" />
|
||||
</el-tabs>
|
||||
|
||||
<div class="toolbar">
|
||||
<span class="lbl">车间</span>
|
||||
<el-select v-model="filter.depId" placeholder="全部车间" clearable style="width: 160px" @change="onDepChange">
|
||||
<el-option v-for="d in deps" :key="d.id" :label="d.name" :value="d.id" />
|
||||
</el-select>
|
||||
|
||||
<span class="lbl">班次</span>
|
||||
<el-select v-model="filter.banci" style="width: 110px" @change="onSearch">
|
||||
<el-option v-for="b in BANCI" :key="b.value" :label="b.label" :value="b.value" />
|
||||
</el-select>
|
||||
|
||||
<template v-if="tab !== 'zbz'">
|
||||
<span class="lbl">机组</span>
|
||||
<el-select v-model="filter.jizu" placeholder="全部机组" clearable style="width: 130px" @change="onSearch">
|
||||
<el-option
|
||||
v-for="j in jizuOptions"
|
||||
:key="j.jizu"
|
||||
:label="`机组${j.jizu}(${j.chetaiStart}-${j.chetaiEnd})`"
|
||||
:value="j.jizu"
|
||||
/>
|
||||
</el-select>
|
||||
</template>
|
||||
|
||||
<el-input
|
||||
v-model="filter.keyword"
|
||||
placeholder="姓名 / 车台"
|
||||
clearable
|
||||
style="width: 180px"
|
||||
@keyup.enter="onSearch"
|
||||
@clear="onSearch"
|
||||
/>
|
||||
<el-button type="primary" @click="onSearch">查询</el-button>
|
||||
|
||||
<div class="right">
|
||||
<el-button v-if="tab === 'dcg'" type="primary" @click="openDcgGroup">排班维护(按机组)</el-button>
|
||||
<el-button v-else type="primary" @click="tab === 'ctg' ? openCtg(null) : openZbz(null)">新增</el-button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 挡车工 -->
|
||||
<el-table v-if="tab === 'dcg'" v-loading="state.dcg.loading" :data="state.dcg.rows" border size="small">
|
||||
<el-table-column type="index" label="序号" width="55" />
|
||||
<el-table-column prop="deptName" label="车间" min-width="120" show-overflow-tooltip />
|
||||
<el-table-column label="班次" width="80" align="center">
|
||||
<template #default="{ row }">{{ row.banciName }}班</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="jizu" label="机组" width="70" align="center" />
|
||||
<el-table-column prop="ygName" label="挡车工" width="110" />
|
||||
<el-table-column label="车台范围" width="110" align="center">
|
||||
<template #default="{ row }">{{ row.chetaiStart }} - {{ row.chetaiEnd }}</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="dangcheshu" label="挡车数" width="90" align="right" />
|
||||
<el-table-column label="操作" width="90" align="center" fixed="right">
|
||||
<template #default="{ row }">
|
||||
<el-button link type="danger" @click="deleteDcg(row)">删除</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<!-- 车头工 -->
|
||||
<el-table v-else-if="tab === 'ctg'" v-loading="state.ctg.loading" :data="state.ctg.rows" border size="small">
|
||||
<el-table-column type="index" label="序号" width="55" />
|
||||
<el-table-column prop="deptName" label="车间" min-width="120" show-overflow-tooltip />
|
||||
<el-table-column label="班次" width="80" align="center">
|
||||
<template #default="{ row }">{{ row.banciName }}班</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="jizu" label="机组" width="70" align="center" />
|
||||
<el-table-column prop="ygid1Name" label="车头工1" width="120" />
|
||||
<el-table-column prop="ygid2Name" label="车头工2" width="120" />
|
||||
<el-table-column label="操作" width="130" align="center" fixed="right">
|
||||
<template #default="{ row }">
|
||||
<el-button link type="primary" @click="openCtg(row)">修改</el-button>
|
||||
<el-button link type="danger" @click="deleteCtg(row)">删除</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<!-- 值班长 -->
|
||||
<el-table v-else v-loading="state.zbz.loading" :data="state.zbz.rows" border size="small">
|
||||
<el-table-column type="index" label="序号" width="55" />
|
||||
<el-table-column prop="deptName" label="车间" min-width="140" show-overflow-tooltip />
|
||||
<el-table-column label="班次" width="90" align="center">
|
||||
<template #default="{ row }">{{ row.banciName }}班</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="ygName" label="值班长" width="140" />
|
||||
<el-table-column label="操作" width="130" align="center" fixed="right">
|
||||
<template #default="{ row }">
|
||||
<el-button link type="primary" @click="openZbz(row)">修改</el-button>
|
||||
<el-button link type="danger" @click="deleteZbz(row)">删除</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<el-pagination
|
||||
class="pager"
|
||||
:current-page="cur.pageIndex"
|
||||
:page-size="cur.pageSize"
|
||||
:total="cur.total"
|
||||
layout="total, prev, pager, next, jumper"
|
||||
@current-change="onPageChange"
|
||||
/>
|
||||
</el-card>
|
||||
|
||||
<!-- ============ 挡车工整组排班 ============ -->
|
||||
<el-dialog v-model="dcgDlg.visible" title="挡车工排班维护" width="880px" destroy-on-close>
|
||||
<div class="dlg-head">
|
||||
<el-tag type="info">{{ dcgDepName }}</el-tag>
|
||||
<el-tag type="info">{{ dcgBanciName }}</el-tag>
|
||||
<el-tag type="info">机组 {{ dcgDlg.jizu }}(车台 {{ dcgDlg.chetaiStart }}-{{ dcgDlg.chetaiEnd }})</el-tag>
|
||||
<el-tag :type="dcgAssigned === dcgTotalChetai ? 'success' : 'warning'">
|
||||
已分配 {{ dcgAssigned }} / {{ dcgTotalChetai }} 台
|
||||
</el-tag>
|
||||
</div>
|
||||
|
||||
<div class="dlg-toolbar">
|
||||
<el-button type="primary" size="small" @click="pickEmployee('dcg')">添加挡车工</el-button>
|
||||
<el-button size="small" @click="clearDcgRows">清空</el-button>
|
||||
<span class="hint">车台结束号与下一行起始号接壤时,该车台各按 0.5 台计(挡车数自动计算)</span>
|
||||
</div>
|
||||
|
||||
<el-table v-loading="dcgDlg.loading" :data="dcgDlg.rows" border size="small" height="380">
|
||||
<el-table-column type="index" label="序号" width="55" />
|
||||
<el-table-column label="挡车工" min-width="150">
|
||||
<template #default="{ row, $index }">
|
||||
<span v-if="row.ygName">{{ row.ygName }}</span>
|
||||
<el-button v-else link type="primary" @click="pickEmployee('dcg')">选择</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="起始车台" width="120" align="center">
|
||||
<template #default="{ row }">
|
||||
<el-input-number
|
||||
v-model="row.chetaiStart"
|
||||
:min="dcgDlg.chetaiStart"
|
||||
:max="dcgDlg.chetaiEnd"
|
||||
:controls="false"
|
||||
size="small"
|
||||
style="width: 90px"
|
||||
@change="recalcDangche(dcgDlg.rows)"
|
||||
/>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="结束车台" width="120" align="center">
|
||||
<template #default="{ row }">
|
||||
<el-input-number
|
||||
v-model="row.chetaiEnd"
|
||||
:min="dcgDlg.chetaiStart"
|
||||
:max="dcgDlg.chetaiEnd"
|
||||
:controls="false"
|
||||
size="small"
|
||||
style="width: 90px"
|
||||
@change="recalcDangche(dcgDlg.rows)"
|
||||
/>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="dangcheshu" label="挡车数" width="90" align="right" />
|
||||
<el-table-column label="操作" width="80" align="center">
|
||||
<template #default="{ $index }">
|
||||
<el-button link type="danger" @click="removeDcgRow($index)">删除</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<template #footer>
|
||||
<el-button @click="dcgDlg.visible = false">取消</el-button>
|
||||
<el-button type="primary" :loading="dcgDlg.saving" @click="saveDcgGroup">保存</el-button>
|
||||
</template>
|
||||
</el-dialog>
|
||||
|
||||
<!-- ============ 车头工 ============ -->
|
||||
<el-dialog v-model="ctgDlg.visible" :title="ctgDlg.id ? '修改车头工排班' : '新增车头工排班'" width="520px">
|
||||
<el-form label-width="90px">
|
||||
<el-form-item label="车间">
|
||||
<el-select v-model="ctgForm.depId" placeholder="请选择车间" style="width: 100%">
|
||||
<el-option v-for="d in deps" :key="d.id" :label="d.name" :value="d.id" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="班次">
|
||||
<el-select v-model="ctgForm.banci" style="width: 100%">
|
||||
<el-option v-for="b in BANCI" :key="b.value" :label="b.label" :value="b.value" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="机组">
|
||||
<el-input-number v-model="ctgForm.jizu" :min="1" :max="99" :controls="false" style="width: 100%" />
|
||||
</el-form-item>
|
||||
<el-form-item label="车头工1">
|
||||
<el-input :model-value="ctgForm.ygid1Name" readonly placeholder="点击选择">
|
||||
<template #append>
|
||||
<el-button @click="pickEmployee('ctg1')">选择</el-button>
|
||||
</template>
|
||||
</el-input>
|
||||
</el-form-item>
|
||||
<el-form-item label="车头工2">
|
||||
<el-input :model-value="ctgForm.ygid2Name" readonly placeholder="点击选择(可空)">
|
||||
<template #append>
|
||||
<el-button @click="pickEmployee('ctg2')">选择</el-button>
|
||||
</template>
|
||||
</el-input>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
<template #footer>
|
||||
<el-button @click="ctgDlg.visible = false">取消</el-button>
|
||||
<el-button type="primary" :loading="ctgDlg.saving" @click="saveCtg">保存</el-button>
|
||||
</template>
|
||||
</el-dialog>
|
||||
|
||||
<!-- ============ 值班长 ============ -->
|
||||
<el-dialog v-model="zbzDlg.visible" :title="zbzDlg.id ? '修改值班长排班' : '新增值班长排班'" width="480px">
|
||||
<el-form label-width="90px">
|
||||
<el-form-item label="车间">
|
||||
<el-select v-model="zbzForm.depId" placeholder="请选择车间" style="width: 100%">
|
||||
<el-option v-for="d in deps" :key="d.id" :label="d.name" :value="d.id" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="班次">
|
||||
<el-select v-model="zbzForm.banci" style="width: 100%">
|
||||
<el-option v-for="b in BANCI" :key="b.value" :label="b.label" :value="b.value" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="值班长">
|
||||
<el-input :model-value="zbzForm.ygName" readonly placeholder="点击选择">
|
||||
<template #append>
|
||||
<el-button @click="pickEmployee('zbz')">选择</el-button>
|
||||
</template>
|
||||
</el-input>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
<template #footer>
|
||||
<el-button @click="zbzDlg.visible = false">取消</el-button>
|
||||
<el-button type="primary" :loading="zbzDlg.saving" @click="saveZbz">保存</el-button>
|
||||
</template>
|
||||
</el-dialog>
|
||||
|
||||
<EmployeeSelect
|
||||
v-model="empPicker.visible"
|
||||
:multiple="empPicker.multiple"
|
||||
:dep-id="dcgDlg.visible ? dcgDlg.depId : filter.depId"
|
||||
@confirm="onEmployeePicked"
|
||||
/>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.ktpb-page :deep(.el-card__body) { padding-top: 6px; }
|
||||
.toolbar { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; margin-bottom: 10px; }
|
||||
.toolbar .lbl { color: var(--el-text-color-regular); font-size: 13px; }
|
||||
.toolbar .right { margin-left: auto; }
|
||||
.pager { margin-top: 10px; justify-content: flex-end; }
|
||||
.dlg-head { display: flex; align-items: center; gap: 8px; margin-bottom: 10px; }
|
||||
.dlg-toolbar { display: flex; align-items: center; gap: 8px; margin-bottom: 8px; }
|
||||
.dlg-toolbar .hint { color: var(--el-text-color-secondary); font-size: 12px; }
|
||||
</style>
|
||||
+135
@@ -0,0 +1,135 @@
|
||||
# 工作进度-12:生产-前缫「看台排班」+ 机组车台/看台排班数据导入
|
||||
|
||||
> 时间:2026-10-22(承接工作进度-11)
|
||||
> 需求:仿照 `D:\AntaiProject - 副本` 生产-前缫的「机组车台 / 看台排班」,在本系统落地看台排班功能,并导入随附的 4 张表数据:
|
||||
> `biz_prod_qs_jzct`(机组车台)、`biz_prod_qs_ktpb_ctg`(车头工)、`biz_prod_qs_ktpb_dcg`(挡车工)、`biz_prod_qs_ktpb_zbz`(值班长)。
|
||||
> 参考实现:`WinClient\F9.Business.Prod\QS\KTPB\`(Page_KTPB、Page_KTPBCTG_Edit、Page_KTPBDCG_Edit、Page_KTPBZBZ_Edit)、`Application\CQRS\Business\PROD\QS\KTPB\`、`Domain\Entities\Business\PROD\QS\KTPB\`。
|
||||
|
||||
---
|
||||
|
||||
## 一、功能设计
|
||||
|
||||
```
|
||||
生产-前缫
|
||||
├── 落丝记录
|
||||
├── 车间班次
|
||||
└── 看台排班(新增) /prod/qianxian/ktpb
|
||||
顶部:车间(职责类型=前缫)+ 班次(甲/乙)+ 机组 + 关键字
|
||||
页签:挡车工 / 车头工 / 值班长
|
||||
├── 挡车工:按「车间+班次+机组」整组维护
|
||||
│ 弹窗内可批量添加挡车工(多选职工),逐行填起止车台,
|
||||
│ 挡车数自动计算(接壤车台各计 0.5),实时显示「已分配 x / y 台」
|
||||
├── 车头工:一个「车间+班次+机组」一条记录,含车头工1 / 车头工2
|
||||
└── 值班长:一个「车间+班次」可有多名值班长
|
||||
```
|
||||
|
||||
与 F9 的对应关系:
|
||||
| F9 | 本系统 |
|
||||
|---|---|
|
||||
| `Page_KTPB`(三个页签 + 车间/班次/机组过滤) | `views/prod/ktpb/index.vue` |
|
||||
| `Page_KTPBDCG_Edit`(整组批量编辑 + 挡车数计算) | 挡车工弹窗 + `POST /dcg/batch` |
|
||||
| `Page_KTPBCTG_Edit` / `Page_KTPBZBZ_Edit` | 车头工 / 值班长弹窗 |
|
||||
| `BatchReplaceKtpbdcgCommand` | `KtpbService.SaveDcgBatchAsync`(先删后建) |
|
||||
|
||||
**挡车数算法**(移植 `CalculateSingleDangcheshu`):每台车权重默认 1;若某车台被多条记录覆盖,且同时是某记录的起点与另一记录的终点(接壤),该车台权重取 0.5,最后四舍五入保留两位。前后端实现完全一致。
|
||||
|
||||
---
|
||||
|
||||
## 二、后端
|
||||
|
||||
### 2.1 实体(`Domain/Entities/PROD/Ktpb.cs`)
|
||||
|
||||
| 类 | 表 | 主要字段 |
|
||||
|---|---|---|
|
||||
| `KtpbCtg` | `KtpbCtgs` | DeptId、Banci、Jizu、Ygid1、Ygid2 |
|
||||
| `KtpbDcg` | `KtpbDcgs` | DeptId、Banci、Jizu、ChetaiStart、ChetaiEnd、YgId、Dangcheshu |
|
||||
| `KtpbZbz` | `KtpbZbzs` | DeptId、Banci、YgId |
|
||||
|
||||
### 2.2 服务与接口(`KtpbService` / `KtpbController`,路由 `api/prod/ktpb`)
|
||||
|
||||
```
|
||||
GET qianxian-deps 车间下拉(DutyType=前缫)
|
||||
GET jizu-options?depId= 机组下拉(含车台范围,取机组车台)
|
||||
GET ctg?depId=&banci=&jizu=&like= 车头工分页
|
||||
POST ctg | PUT ctg/{id} | DELETE ctg/{id}
|
||||
GET dcg?depId=&banci=&jizu=&like= 挡车工分页
|
||||
GET dcg/group?depId=&banci=&jizu= 某机组整组排班
|
||||
POST dcg/batch 整组替换(空集合=清空)
|
||||
DELETE dcg/{id}
|
||||
GET zbz?depId=&banci=&like= 值班长分页
|
||||
POST zbz | PUT zbz/{id} | DELETE zbz/{id}
|
||||
```
|
||||
|
||||
校验规则:
|
||||
- 车头工:同「车间+班次+机组」唯一,车头工1 必填。
|
||||
- 挡车工:起始车台>0、结束≥起始、必须落在该机组车台范围内;保存时服务端重算挡车数。
|
||||
- 值班长:同「车间+班次+值班长」不重复。
|
||||
|
||||
### 2.3 数据导入(`ProdSeedData`,幂等)
|
||||
|
||||
新增 3 个内嵌资源 `SeedData/biz_prod_qs_ktpb_ctg.json`、`_dcg.json`、`_zbz.json`,并把 `biz_prod_qs_jzct.json` 按本次导出数据重新生成。
|
||||
|
||||
映射规则:
|
||||
- **部门**:xlsx 中的 `dep_id` 是 F9 部门 Id,经 `BusinessSeedData.DeptData`(F9 Id → 部门名)映射到本系统 `Departments.Id`;
|
||||
- **职工**:F9 职工导出时保留了原始雪花 Id,本系统 `Employees.Id` 与之一致,直接按 Id 关联(不存在的职工行跳过);
|
||||
- **清洗**:剔除 `deleted_at` 非空的软删除行(4 张表中大量为测试/删除数据)、部门无法映射或不在前缫四车间的行、机组/车台号非法行;
|
||||
- **去重**:机组车台按「车间+机组」保留规范行(优先 `起始号 = (机组-1)*20+1`);车头工按「车间+班次+机组」;值班长按「车间+班次+值班长」;挡车工按整行;
|
||||
- **幂等**:机组车台按「车间+机组」upsert;车头工按「车间+班次+机组」upsert;挡车工按「车间+班次+机组」整组已存在则跳过;值班长按唯一键跳过。
|
||||
|
||||
导入结果(本次启动日志):
|
||||
|
||||
```
|
||||
[ProdSeed] 机组车台:来源 24 条,新增 0,更新 0(此前已导入)
|
||||
[ProdSeed] 车头工看台排班:来源 33 条,新增 33 条
|
||||
[ProdSeed] 挡车工看台排班:来源 202 条,新增 202 条(34 组)
|
||||
[ProdSeed] 值班长看台排班:来源 7 条,新增 7 条
|
||||
```
|
||||
|
||||
> 原始 xlsx 行数:机组车台 35、车头工 75、挡车工 4543、值班长 13;其中挡车工 4341 行是 F9 里已软删除的历史/测试数据,故有效数据仅 202 行。
|
||||
|
||||
### 2.4 菜单
|
||||
|
||||
`DbSeeder.SeedProdMenus` 在生产-前缫下新增第 3 个子菜单「看台排班」,权限标识 `prod:ktpb:list`,admin 自动授权。
|
||||
|
||||
---
|
||||
|
||||
## 三、前端
|
||||
|
||||
| 文件 | 说明 |
|
||||
|---|---|
|
||||
| `views/prod/ktpb/index.vue` | 看台排班主页面(三页签 + 过滤 + 分页 + 三个弹窗) |
|
||||
| `components/select/EmployeeSelect.vue` | 职工选择弹窗(单选/多选,支持按部门过滤与姓名/工号搜索) |
|
||||
| `router/index.js` | 注册 `prod/ktpb/index` 路由组件 |
|
||||
|
||||
前端交互要点:
|
||||
- 挡车工维护必须先在顶部选定「车间 + 机组」,弹窗内展示该机组车台范围;
|
||||
- 弹窗顶部实时显示「已分配 x / y 台」,未满额时标签变黄,避免漏排;
|
||||
- 起止车台用 `el-input-number` 限制在机组范围内,改动即刷新挡车数;
|
||||
- 车头工/值班长新建时默认带出当前过滤的车间与班次。
|
||||
|
||||
---
|
||||
|
||||
## 四、验证记录
|
||||
|
||||
| 项 | 结果 |
|
||||
|---|---|
|
||||
| `dotnet build` | ✅ 0 错误 |
|
||||
| `vite build` | ✅ 通过(仅既有体积/SignalR 注释警告) |
|
||||
| 菜单 | ✅ 生产-前缫 → 落丝记录 / 车间班次 / 看台排班 |
|
||||
| 车间下拉 | ✅ 前缫车间、前缫一~四车间 |
|
||||
| 机组下拉(前缫一车间) | ✅ 机组1-6,车台 1-20 / 21-40 / … / 101-120 |
|
||||
| 挡车工列表 | ✅ 202 条,姓名/车台/挡车数正确(3.5、3、3.5…) |
|
||||
| 车头工列表 | ✅ 33 条 |
|
||||
| 值班长列表 | ✅ 7 条 |
|
||||
| 整组保存 + 挡车数重算 | ✅ 行1 1-10、行2 10-20 → 9.5 / 10.5(接壤车台各 0.5) |
|
||||
| 超范围校验 | ✅ 车台 1-99 于机组1(1-20)返回 400「超出该机组车台范围 1-20」 |
|
||||
| 测试数据清理 | ✅ 临时数据删除后组内 0 行 |
|
||||
|
||||
---
|
||||
|
||||
## 五、说明与后续
|
||||
|
||||
1. 职工姓名沿用 F9 档案原文(部分带「宁兴」等后缀,如「谢群生宁兴」),属于基础数据层面的既有情况,本次未改动。
|
||||
2. 「机组车台」维护页面仍在 基础数据 下(`/base/jizuchetai`);F9 是放在生产-前缫组内。如需完全对齐,可把该菜单整体平移到生产-前缫(数据接口不变)。
|
||||
3. 挡车工排班目前按「整组替换」保存,没有保留历史版本;若需要留痕,可增加排班生效日期 + 版本表。
|
||||
4. 后续若要支持「按班组/按日期」排班(F9 另有班组维度),可在现有三张表上扩展 BanCi 组合键。
|
||||
Reference in New Issue
Block a user