|
|
@@ -19,6 +19,63 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
_userManager = userManager;
|
|
|
}
|
|
|
|
|
|
+ /// <summary>
|
|
|
+ /// 主表 WorkOrdMaster 按工单号 +「公司域或租户 id」匹配:<c>domain</c> 可为原 <c>Domain</c> 列,或与 <c>tenant_id</c> 相同的字符串(列表已做 COALESCE 回传)。
|
|
|
+ /// </summary>
|
|
|
+ private const string SqlWorkOrdMasterMatchDomainOrTenant = """
|
|
|
+ WorkOrd = @WorkOrd AND (
|
|
|
+ TRIM(IFNULL(`Domain`, '')) = TRIM(@Domain)
|
|
|
+ OR (
|
|
|
+ TRIM(IFNULL(`Domain`, '')) = ''
|
|
|
+ AND TRIM(@Domain) <> ''
|
|
|
+ AND CAST(IFNULL(tenant_id, 0) AS CHAR) = TRIM(@Domain)
|
|
|
+ )
|
|
|
+ )
|
|
|
+ """;
|
|
|
+
|
|
|
+ /// <summary>带表别名的 WorkOrdMaster 匹配(参数 <c>alias</c> 为表别名,如 a、w)。</summary>
|
|
|
+ private static string SqlWorkOrdMasterMatchDomainOrTenantAliased(string alias) => $"""
|
|
|
+ {alias}.WorkOrd = @WorkOrd AND (
|
|
|
+ TRIM(IFNULL({alias}.`Domain`, '')) = TRIM(@Domain)
|
|
|
+ OR (
|
|
|
+ TRIM(IFNULL({alias}.`Domain`, '')) = ''
|
|
|
+ AND TRIM(@Domain) <> ''
|
|
|
+ AND CAST(IFNULL({alias}.tenant_id, 0) AS CHAR) = TRIM(@Domain)
|
|
|
+ )
|
|
|
+ )
|
|
|
+ """;
|
|
|
+
|
|
|
+ /// <summary>子表(工序/明细)按工单号 + 域或主表租户匹配。</summary>
|
|
|
+ private static string SqlWorkOrdChildMatchDomainOrTenant(string childAlias, string masterAlias) => $"""
|
|
|
+ {childAlias}.WorkOrd = @WorkOrd AND (
|
|
|
+ TRIM(IFNULL({childAlias}.`Domain`, '')) = TRIM(@Domain)
|
|
|
+ OR EXISTS (
|
|
|
+ SELECT 1 FROM WorkOrdMaster {masterAlias}
|
|
|
+ WHERE {masterAlias}.WorkOrd = {childAlias}.WorkOrd
|
|
|
+ AND (
|
|
|
+ TRIM(IFNULL({masterAlias}.`Domain`, '')) = TRIM(@Domain)
|
|
|
+ OR (
|
|
|
+ TRIM(IFNULL({masterAlias}.`Domain`, '')) = ''
|
|
|
+ AND TRIM(@Domain) <> ''
|
|
|
+ AND CAST(IFNULL({masterAlias}.tenant_id, 0) AS CHAR) = TRIM(@Domain)
|
|
|
+ )
|
|
|
+ )
|
|
|
+ )
|
|
|
+ )
|
|
|
+ """;
|
|
|
+
|
|
|
+ /// <summary>按主键 +「公司域或租户 id」匹配(状态更新等)。</summary>
|
|
|
+ private const string SqlWorkOrdMasterMatchRecIdAndDomainOrTenant = """
|
|
|
+ RecID = @Id AND (
|
|
|
+ TRIM(IFNULL(`Domain`, '')) = TRIM(@Domain)
|
|
|
+ OR (
|
|
|
+ TRIM(IFNULL(`Domain`, '')) = ''
|
|
|
+ AND TRIM(@Domain) <> ''
|
|
|
+ AND CAST(IFNULL(tenant_id, 0) AS CHAR) = TRIM(@Domain)
|
|
|
+ )
|
|
|
+ )
|
|
|
+ """;
|
|
|
+
|
|
|
// ══════════════════════════════════════════════════════════════
|
|
|
// 列表 GET /api/Production/scheduling/list
|
|
|
// ══════════════════════════════════════════════════════════════
|
|
|
@@ -27,7 +84,8 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
[HttpGet("scheduling/list")]
|
|
|
public async Task<object> GetList([FromQuery] WorkOrderSchedulingListInput input)
|
|
|
{
|
|
|
- const string C = "utf8mb4_general_ci";
|
|
|
+ //const string C = "utf8mb4_general_ci";
|
|
|
+ const string C = "utf8mb4_0900_ai_ci";
|
|
|
var pars = new List<SugarParameter>();
|
|
|
|
|
|
var innerWhere = new List<string>
|
|
|
@@ -37,17 +95,17 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
|
|
|
if (!string.IsNullOrWhiteSpace(input.WorkOrd))
|
|
|
{
|
|
|
- innerWhere.Add($"(a.WorkOrd COLLATE {C}) LIKE @WorkOrd");
|
|
|
+ innerWhere.Add($"a.WorkOrd LIKE @WorkOrd");
|
|
|
pars.Add(new SugarParameter("@WorkOrd", $"%{input.WorkOrd.Trim()}%"));
|
|
|
}
|
|
|
if (!string.IsNullOrWhiteSpace(input.LotSerial))
|
|
|
{
|
|
|
- innerWhere.Add($"(a.LotSerial COLLATE {C}) LIKE @LotSerial");
|
|
|
+ innerWhere.Add($"a.LotSerial LIKE @LotSerial");
|
|
|
pars.Add(new SugarParameter("@LotSerial", $"%{input.LotSerial.Trim()}%"));
|
|
|
}
|
|
|
if (!string.IsNullOrWhiteSpace(input.ItemNum))
|
|
|
{
|
|
|
- innerWhere.Add($"(a.ItemNum COLLATE {C}) LIKE @ItemNum");
|
|
|
+ innerWhere.Add($"a.ItemNum LIKE @ItemNum");
|
|
|
pars.Add(new SugarParameter("@ItemNum", $"%{input.ItemNum.Trim()}%"));
|
|
|
}
|
|
|
if (!string.IsNullOrWhiteSpace(input.StartDateFrom))
|
|
|
@@ -89,29 +147,29 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
s.PlanDate AS PlanDate,
|
|
|
s.ProdDate AS ProdDate,
|
|
|
LOWER(a.Status) AS Status,
|
|
|
- a.`Domain` AS Domain,
|
|
|
+ COALESCE(NULLIF(TRIM(a.`Domain`), ''), IFNULL(CAST(a.tenant_id AS CHAR), '')) AS Domain,
|
|
|
a.Urgent AS Urgent
|
|
|
FROM WorkOrdMaster a
|
|
|
- LEFT JOIN ItemMaster b ON a.ItemNum COLLATE {C} = b.ItemNum COLLATE {C}
|
|
|
+ LEFT JOIN ItemMaster b ON a.ItemNum = b.ItemNum
|
|
|
LEFT JOIN ReplenishmentWeekPlan r
|
|
|
- ON a.WorkOrd COLLATE {C} = r.ProductionOrder COLLATE {C}
|
|
|
- AND CAST(a.`Domain` AS CHAR(64)) COLLATE {C} = CAST(r.factory_id AS CHAR(64)) COLLATE {C}
|
|
|
- LEFT JOIN crm_seorder se ON se.bill_no COLLATE {C} = a.SalesJob COLLATE {C}
|
|
|
- LEFT JOIN CustMaster cm ON cm.Cust COLLATE {C} = se.custom_no COLLATE {C}
|
|
|
+ ON a.WorkOrd = r.ProductionOrder
|
|
|
+ AND CAST(a.`Domain` AS CHAR(64)) = CAST(r.factory_id AS CHAR(64))
|
|
|
+ LEFT JOIN crm_seorder se ON se.bill_no = a.SalesJob
|
|
|
+ LEFT JOIN CustMaster cm ON cm.Cust = se.custom_no
|
|
|
LEFT JOIN (
|
|
|
SELECT `Domain`, WorkOrds, MIN(PlanDate) AS PlanDate, MIN(ProdDate) AS ProdDate
|
|
|
FROM PeriodSequenceDet
|
|
|
GROUP BY `Domain`, WorkOrds
|
|
|
- ) s ON CAST(a.`Domain` AS CHAR(64)) COLLATE {C} = CAST(s.`Domain` AS CHAR(64)) COLLATE {C}
|
|
|
- AND a.WorkOrd COLLATE {C} = s.WorkOrds COLLATE {C}
|
|
|
+ ) s ON CAST(a.`Domain` AS CHAR(64)) = CAST(s.`Domain` AS CHAR(64))
|
|
|
+ AND a.WorkOrd = s.WorkOrds
|
|
|
LEFT JOIN (
|
|
|
SELECT morder_no, MAX(create_time) AS checktime
|
|
|
FROM b_examine_result
|
|
|
GROUP BY morder_no
|
|
|
- ) exm ON exm.morder_no COLLATE {C} = a.WorkOrd COLLATE {C}
|
|
|
+ ) exm ON exm.morder_no = a.WorkOrd
|
|
|
LEFT JOIN WorkOrdInStorage ins
|
|
|
- ON a.WorkOrd COLLATE {C} = ins.WorkOrd COLLATE {C}
|
|
|
- AND ins.Remark COLLATE {C} = '工单预留' COLLATE {C}
|
|
|
+ ON a.WorkOrd = ins.WorkOrd
|
|
|
+ AND ins.Remark = '工单预留'
|
|
|
WHERE {innerWhere}
|
|
|
""";
|
|
|
|
|
|
@@ -125,10 +183,17 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
if (string.IsNullOrWhiteSpace(workOrd) || string.IsNullOrWhiteSpace(domain))
|
|
|
throw Oops.Oh("工单号与公司域名不能为空");
|
|
|
|
|
|
- const string sql = """
|
|
|
- SELECT WorkOrd, ItemNum, QtyOrded, Priority, LotSerial, IFNULL(Urgent, 0) AS Urgent
|
|
|
- FROM WorkOrdMaster
|
|
|
- WHERE WorkOrd = @WorkOrd AND `Domain` = @Domain
|
|
|
+ string sql = $"""
|
|
|
+ SELECT
|
|
|
+ a.WorkOrd,
|
|
|
+ a.ItemNum,
|
|
|
+ a.QtyOrded,
|
|
|
+ a.Priority,
|
|
|
+ a.LotSerial,
|
|
|
+ IFNULL(a.Urgent, 0) AS Urgent,
|
|
|
+ DATE(a.OrdDate) AS OrdDate
|
|
|
+ FROM WorkOrdMaster a
|
|
|
+ WHERE {SqlWorkOrdMasterMatchDomainOrTenantAliased("a")}
|
|
|
LIMIT 1
|
|
|
""";
|
|
|
var row = (await _db.Ado.SqlQueryAsync<WorkOrderEditPreviewRow>(sql, new { WorkOrd = workOrd.Trim(), Domain = domain.Trim() }))
|
|
|
@@ -146,7 +211,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
if (string.IsNullOrWhiteSpace(workOrd) || string.IsNullOrWhiteSpace(domain))
|
|
|
throw Oops.Oh("工单号与公司域名不能为空");
|
|
|
|
|
|
- const string masterSql = """
|
|
|
+ string masterSql = $"""
|
|
|
SELECT
|
|
|
a.WorkOrd,
|
|
|
a.QtyOrded,
|
|
|
@@ -160,13 +225,13 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
IFNULL(a.Remark, '') AS Remark
|
|
|
FROM WorkOrdMaster a
|
|
|
LEFT JOIN ItemMaster b ON a.ItemNum = b.ItemNum
|
|
|
- WHERE a.WorkOrd = @WorkOrd AND a.`Domain` = @Domain
|
|
|
+ WHERE {SqlWorkOrdMasterMatchDomainOrTenantAliased("a")}
|
|
|
LIMIT 1
|
|
|
""";
|
|
|
var master = (await _db.Ado.SqlQueryAsync<WorkOrderViewMasterRow>(masterSql, new { WorkOrd = workOrd.Trim(), Domain = domain.Trim() }))
|
|
|
.FirstOrDefault() ?? throw Oops.Oh("工单不存在");
|
|
|
|
|
|
- const string routingSql = """
|
|
|
+ string routingSql = $"""
|
|
|
SELECT
|
|
|
r.OP AS Op,
|
|
|
r.Descr AS Descr,
|
|
|
@@ -178,16 +243,16 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
IFNULL(r.QtyScrap, 0) AS QtyScrap,
|
|
|
r.Status AS Status
|
|
|
FROM WorkOrdRouting r
|
|
|
- WHERE r.WorkOrd = @WorkOrd AND r.`Domain` = @Domain
|
|
|
- ORDER BY r.Line, r.ColumnNum
|
|
|
+ WHERE {SqlWorkOrdChildMatchDomainOrTenant("r", "m")}
|
|
|
+ ORDER BY (r.OP + 0) ASC, r.OP ASC, r.Line ASC, r.ColumnNum ASC
|
|
|
""";
|
|
|
var routings = await _db.Ado.SqlQueryAsync<WorkOrderViewRoutingRow>(routingSql, new { WorkOrd = workOrd.Trim(), Domain = domain.Trim() });
|
|
|
|
|
|
- const string detailSql = """
|
|
|
- SELECT ItemNum, Op, QtyRequired, IFNULL(FrozenBOMQty, 0) AS FrozenBOMQty
|
|
|
- FROM WorkOrdDetail
|
|
|
- WHERE WorkOrd = @WorkOrd AND `Domain` = @Domain
|
|
|
- ORDER BY LineNum
|
|
|
+ string detailSql = $"""
|
|
|
+ SELECT d.ItemNum, d.Op, d.QtyRequired, IFNULL(d.FrozenBOMQty, 0) AS FrozenBOMQty
|
|
|
+ FROM WorkOrdDetail d
|
|
|
+ WHERE {SqlWorkOrdChildMatchDomainOrTenant("d", "m")}
|
|
|
+ ORDER BY d.LineNum
|
|
|
""";
|
|
|
var details = await _db.Ado.SqlQueryAsync<WorkOrderViewDetailRow>(detailSql, new { WorkOrd = workOrd.Trim(), Domain = domain.Trim() });
|
|
|
|
|
|
@@ -204,11 +269,11 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
if (string.IsNullOrWhiteSpace(workOrd) || string.IsNullOrWhiteSpace(domain))
|
|
|
throw Oops.Oh("工单号与公司域名不能为空");
|
|
|
|
|
|
- const string sql = """
|
|
|
- SELECT ItemNum, Op, QtyRequired, IFNULL(FrozenBOMQty, 0) AS FrozenBOMQty
|
|
|
- FROM WorkOrdDetail
|
|
|
- WHERE WorkOrd = @WorkOrd AND `Domain` = @Domain
|
|
|
- ORDER BY LineNum
|
|
|
+ string sql = $"""
|
|
|
+ SELECT d.ItemNum, d.Op, d.QtyRequired, IFNULL(d.FrozenBOMQty, 0) AS FrozenBOMQty
|
|
|
+ FROM WorkOrdDetail d
|
|
|
+ WHERE {SqlWorkOrdChildMatchDomainOrTenant("d", "m")}
|
|
|
+ ORDER BY d.LineNum
|
|
|
""";
|
|
|
var list = await _db.Ado.SqlQueryAsync<WorkOrderViewDetailRow>(sql, new { WorkOrd = workOrd.Trim(), Domain = domain.Trim() });
|
|
|
return new { list };
|
|
|
@@ -221,7 +286,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
if (string.IsNullOrWhiteSpace(workOrd) || string.IsNullOrWhiteSpace(domain))
|
|
|
throw Oops.Oh("工单号与公司域名不能为空");
|
|
|
|
|
|
- const string sql = """
|
|
|
+ string sql = $"""
|
|
|
SELECT
|
|
|
r.OP AS Op,
|
|
|
r.Descr AS Descr,
|
|
|
@@ -233,8 +298,8 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
IFNULL(r.QtyScrap, 0) AS QtyScrap,
|
|
|
r.Status AS Status
|
|
|
FROM WorkOrdRouting r
|
|
|
- WHERE r.WorkOrd = @WorkOrd AND r.`Domain` = @Domain
|
|
|
- ORDER BY r.Line, r.ColumnNum
|
|
|
+ WHERE {SqlWorkOrdChildMatchDomainOrTenant("r", "m")}
|
|
|
+ ORDER BY (r.OP + 0) ASC, r.OP ASC, r.Line ASC, r.ColumnNum ASC
|
|
|
""";
|
|
|
var list = await _db.Ado.SqlQueryAsync<WorkOrderViewRoutingRow>(sql, new { WorkOrd = workOrd.Trim(), Domain = domain.Trim() });
|
|
|
return new { list };
|
|
|
@@ -253,7 +318,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
var w = workOrd.Trim();
|
|
|
var d = domain.Trim();
|
|
|
|
|
|
- const string masterSql = """
|
|
|
+ string masterSql = $"""
|
|
|
SELECT
|
|
|
a.WorkOrd,
|
|
|
a.QtyOrded,
|
|
|
@@ -266,7 +331,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
LOWER(a.Status) AS Status
|
|
|
FROM WorkOrdMaster a
|
|
|
LEFT JOIN ItemMaster b ON a.ItemNum = b.ItemNum
|
|
|
- WHERE a.WorkOrd = @WorkOrd AND a.`Domain` = @Domain
|
|
|
+ WHERE {SqlWorkOrdMasterMatchDomainOrTenantAliased("a")}
|
|
|
LIMIT 1
|
|
|
""";
|
|
|
var master = (await _db.Ado.SqlQueryAsync<WorkOrderTraceMasterRow>(masterSql, new { WorkOrd = w, Domain = d }))
|
|
|
@@ -562,7 +627,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
};
|
|
|
|
|
|
var n = await _db.Ado.ExecuteCommandAsync(
|
|
|
- """
|
|
|
+ $"""
|
|
|
UPDATE WorkOrdMaster
|
|
|
SET QtyOrded = COALESCE(@QtyOrded, QtyOrded),
|
|
|
Priority = COALESCE(@Priority, Priority),
|
|
|
@@ -570,7 +635,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
Urgent = COALESCE(@Urgent, Urgent),
|
|
|
UpdateUser = @UpdateUser,
|
|
|
UpdateTime = @UpdateTime
|
|
|
- WHERE WorkOrd = @WorkOrd AND `Domain` = @Domain
|
|
|
+ WHERE {SqlWorkOrdMasterMatchDomainOrTenant}
|
|
|
""",
|
|
|
pars);
|
|
|
|
|
|
@@ -598,12 +663,12 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
new("@Domain", input.Domain.Trim())
|
|
|
};
|
|
|
var n = await _db.Ado.ExecuteCommandAsync(
|
|
|
- """
|
|
|
+ $"""
|
|
|
UPDATE WorkOrdMaster
|
|
|
SET Status = @Status,
|
|
|
UpdateUser = @UpdateUser,
|
|
|
UpdateTime = @UpdateTime
|
|
|
- WHERE RecID = @Id AND `Domain` = @Domain
|
|
|
+ WHERE {SqlWorkOrdMasterMatchRecIdAndDomainOrTenant}
|
|
|
""",
|
|
|
pars);
|
|
|
if (n == 0)
|
|
|
@@ -633,50 +698,78 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
{
|
|
|
var workOrd = input.WorkOrd.Trim();
|
|
|
var domain = input.Domain.Trim();
|
|
|
+ var createUser = (_userManager.Account ?? "system").Trim();
|
|
|
+ if (createUser.Length > 24)
|
|
|
+ createUser = createUser[..24];
|
|
|
+
|
|
|
var pars = new List<SugarParameter>
|
|
|
{
|
|
|
new("@WorkOrd", workOrd),
|
|
|
- new("@Domain", domain)
|
|
|
+ new("@Domain", domain),
|
|
|
+ new("@CreateUser", createUser)
|
|
|
};
|
|
|
|
|
|
await _db.Ado.BeginTranAsync();
|
|
|
try
|
|
|
{
|
|
|
await _db.Ado.ExecuteCommandAsync(
|
|
|
- """
|
|
|
- DELETE FROM WorkOrdRouting
|
|
|
- WHERE WorkOrd = @WorkOrd AND CAST(`Domain` AS CHAR(64)) COLLATE utf8mb4_general_ci = CAST(@Domain AS CHAR(64)) COLLATE utf8mb4_general_ci
|
|
|
+ $"""
|
|
|
+ DELETE FROM WorkOrdRouting rr
|
|
|
+ WHERE {SqlWorkOrdChildMatchDomainOrTenant("rr", "m")}
|
|
|
""",
|
|
|
pars);
|
|
|
|
|
|
+ // 业务口径:由 RoutingOpDetail + ProdLineDetail 重算工单工艺路线(MySQL)。
|
|
|
+ // 与历史脚本一致:DELETE 仍按工单 + 域/租户匹配,避免误删其它域数据。
|
|
|
await _db.Ado.ExecuteCommandAsync(
|
|
|
- """
|
|
|
+ $"""
|
|
|
INSERT INTO WorkOrdRouting (
|
|
|
- `Domain`, Descr, MilestoneOp, WorkOrd, OP, ParentOp, RunTime, ItemNum, QtyOrded, OverlapUnits, Status, IsActive, CommentIndex, CreateTime, StdOp, PackingQty, WorkOrdMasterRecID
|
|
|
+ `Descr`, `Domain`, `ChargeCode`, `Machine`, `RunCrew`, `MilestoneOp`, `OP`, `StdOp`, `ItemNum`, `WorkCtr`,
|
|
|
+ `Ufld1`, `Ufld3`, `Setup`, `MachinesperOp`, `Labor`, `RunTime`, `MachBdnRate`, `WorkCode`, `StdSetupTime`, `Engineer`,
|
|
|
+ `WorkOrd`, `WorkOrdMasterRecID`, `ERPfld1`, `QtyOrded`, `ProcessOut`, `ProcessOutDay`, `ProcessOutSupp`,
|
|
|
+ `IsActive`, `Status`, `ProdLine`, `CreateTime`, `CreateUser`, `tenant_id`,`CommentIndex`,`WaitTime`
|
|
|
)
|
|
|
SELECT
|
|
|
- w.`Domain`,
|
|
|
- r.Descr,
|
|
|
- r.MilestoneOp,
|
|
|
- w.WorkOrd,
|
|
|
- r.OP,
|
|
|
- r.ParentOp,
|
|
|
- r.RunTime,
|
|
|
- w.ItemNum,
|
|
|
- w.QtyOrded,
|
|
|
- r.OverlapUnits,
|
|
|
- w.Status,
|
|
|
- 1,
|
|
|
- r.CommentIndex,
|
|
|
- NOW(),
|
|
|
- r.StdOp,
|
|
|
- r.PackingQty,
|
|
|
- w.RecID
|
|
|
+ a.`Descr`,
|
|
|
+ LEFT(TRIM(COALESCE(NULLIF(TRIM(IFNULL(w.`Domain`, '')), ''), NULLIF(TRIM(IFNULL(a.`Domain`, '')), ''), ' ')), 8),
|
|
|
+ '',
|
|
|
+ b.`InternalEquipmentCode`,
|
|
|
+ IFNULL(b.`StandardStaffCount`, 0),
|
|
|
+ CAST(IFNULL(a.`MilestoneOp`, 0) AS UNSIGNED),
|
|
|
+ IFNULL(a.`Op`, 0),
|
|
|
+ a.`StdOp`,
|
|
|
+ a.`RoutingCode`,
|
|
|
+ LEFT(IFNULL(b.`Site`, ''), 8),
|
|
|
+ '',
|
|
|
+ '',
|
|
|
+ IFNULL(a.`UDeci1`, 0),
|
|
|
+ IFNULL(a.`UDeci2`, 0),
|
|
|
+ IFNULL(a.`UDeci3`, 0),
|
|
|
+ IFNULL(a.`UDeci3`, 0) / 3600.0,
|
|
|
+ IFNULL(b.`Rate`, 0),
|
|
|
+ b.`OpType`,
|
|
|
+ IFNULL(b.`SetupTime`, 0),
|
|
|
+ b.`SkillNo`,
|
|
|
+ w.`WorkOrd`,
|
|
|
+ w.`RecID`,
|
|
|
+ w.`ERPfld1`,
|
|
|
+ IFNULL(w.`QtyOrded`, 0),
|
|
|
+ CAST(IFNULL(a.`UDeci5`, 0) AS SIGNED),
|
|
|
+ IFNULL(a.`ProcessOutDay`, 0),
|
|
|
+ a.`ProcessOutSupp`,
|
|
|
+ b'1',
|
|
|
+ 'r',
|
|
|
+ LEFT(IFNULL(b.`Line`, ''), 8),
|
|
|
+ NOW(3),
|
|
|
+ @CreateUser,
|
|
|
+ w.`tenant_id`,CAST(IFNULL(a.`MilestoneOp`, 0) AS UNSIGNED),0
|
|
|
FROM WorkOrdMaster w
|
|
|
- LEFT JOIN RoutingOpDetail r ON w.ItemNum COLLATE utf8mb4_general_ci = r.RoutingCode COLLATE utf8mb4_general_ci
|
|
|
- WHERE w.WorkOrd = @WorkOrd
|
|
|
- AND CAST(w.`Domain` AS CHAR(64)) COLLATE utf8mb4_general_ci = CAST(@Domain AS CHAR(64)) COLLATE utf8mb4_general_ci
|
|
|
- AND r.MilestoneOp IS NOT NULL
|
|
|
+ LEFT JOIN RoutingOpDetail a ON w.`ItemNum` = a.`RoutingCode`
|
|
|
+ LEFT JOIN ProdLineDetail b ON a.`RoutingCode` = b.`Part` AND a.`Op` = b.`Op`
|
|
|
+ WHERE w.`WorkOrd` = @WorkOrd
|
|
|
+ AND {SqlWorkOrdMasterMatchDomainOrTenantAliased("w")}
|
|
|
+ AND IFNULL(a.`IsActive`, 0) = 1
|
|
|
+ AND a.`MilestoneOp` IS NOT NULL
|
|
|
""",
|
|
|
pars);
|
|
|
|
|
|
@@ -700,12 +793,12 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
{
|
|
|
var account = _userManager.Account ?? "system";
|
|
|
var n = await _db.Ado.ExecuteCommandAsync(
|
|
|
- """
|
|
|
+ $"""
|
|
|
UPDATE WorkOrdMaster
|
|
|
SET Urgent = @Urgent,
|
|
|
UpdateUser = @UpdateUser,
|
|
|
UpdateTime = @UpdateTime
|
|
|
- WHERE WorkOrd = @WorkOrd AND `Domain` = @Domain
|
|
|
+ WHERE {SqlWorkOrdMasterMatchDomainOrTenant}
|
|
|
""",
|
|
|
new List<SugarParameter>
|
|
|
{
|
|
|
@@ -750,6 +843,7 @@ public class WorkOrderSchedulingService : IDynamicApiController, ITransient
|
|
|
public string? Priority { get; set; }
|
|
|
public string? LotSerial { get; set; }
|
|
|
public int Urgent { get; set; }
|
|
|
+ public DateTime? OrdDate { get; set; }
|
|
|
}
|
|
|
|
|
|
private sealed class WorkOrderViewMasterRow
|