fix(firstleg): project completed loading lists from actual picked cargo

This commit is contained in:
2026-10-04 18:04:21 +08:00
parent cbd5dc0ca2
commit 22133fe604
2 changed files with 231 additions and 5 deletions
@@ -19,6 +19,35 @@ import java.util.List;
/** 基于共享装柜计划表提供清单查询投影和状态推进持久化操作。 */
@Mapper
public interface LoadingListQueryMapper {
// Completed projections use the same settled physical scope as LoadingCompletedEventMapper.
// Keep skipped plan rows for history and for the unfinished preload projection.
String ITEM_SCOPE = """
AND (p.plan_status != 'COMPLETED' OR EXISTS (
SELECT 1 FROM fl_loading_pick_item actual_pick
JOIN fl_loading_pick_task actual_task ON actual_task.id=actual_pick.pick_task_id
WHERE actual_task.loading_plan_id=p.id AND actual_pick.loading_plan_item_id=i.id
AND actual_pick.item_status IN ('PICKED','PARTIAL')
AND actual_pick.picked_package_count > 0
AND actual_pick.picked_package_count=i.package_count))
""";
String PALLET_ITEM_SCOPE = """
AND (p.plan_status != 'COMPLETED' OR EXISTS (
SELECT 1 FROM fl_loading_pick_item actual_pick
JOIN fl_loading_pick_task actual_task ON actual_task.id=actual_pick.pick_task_id
WHERE actual_task.loading_plan_id=p.id AND actual_pick.loading_plan_item_id=pallet_item.id
AND actual_pick.item_status IN ('PICKED','PARTIAL')
AND actual_pick.picked_package_count > 0
AND actual_pick.picked_package_count=pallet_item.package_count))
""";
String CUSTOMER_ACTUAL_SCOPE = """
AND EXISTS (
SELECT 1 FROM fl_loading_pick_item actual_pick
JOIN fl_loading_pick_task actual_task ON actual_task.id=actual_pick.pick_task_id
WHERE actual_task.loading_plan_id=p.id AND actual_pick.loading_plan_item_id=customer_item.id
AND actual_pick.item_status IN ('PICKED','PARTIAL')
AND actual_pick.picked_package_count > 0
AND actual_pick.picked_package_count=customer_item.package_count)
""";
String AGGREGATE_COLUMNS = """
p.id AS plan_id, p.plan_no, p.container_booking_id, p.plan_status, p.remark,
p.created_by, p.created_by_name, p.created_at, p.version,
@@ -50,28 +79,36 @@ public interface LoadingListQueryMapper {
FROM fl_dropship_pallet_carton carton
WHERE EXISTS (SELECT 1 FROM fl_loading_plan_item pallet_item
WHERE pallet_item.loading_plan_id=p.id AND pallet_item.deleted=0
AND pallet_item.pallet_id=carton.pallet_id)), 0) AS total_package_count,
AND pallet_item.pallet_id=carton.pallet_id
""" + PALLET_ITEM_SCOPE + """
)), 0) AS total_package_count,
COALESCE(SUM(CASE WHEN i.pallet_id IS NULL THEN i.gross_weight_kg ELSE 0 END), 0)
+ COALESCE((SELECT SUM(inbound.actual_gross_weight_kg/NULLIF(inbound.total_package_count,0))
FROM fl_dropship_pallet_carton carton
JOIN fl_inbound_order inbound ON inbound.id=carton.inbound_id AND inbound.tenant_id=carton.tenant_id
WHERE EXISTS (SELECT 1 FROM fl_loading_plan_item pallet_item
WHERE pallet_item.loading_plan_id=p.id AND pallet_item.deleted=0
AND pallet_item.pallet_id=carton.pallet_id)), 0) AS total_gross_weight_kg,
AND pallet_item.pallet_id=carton.pallet_id
""" + PALLET_ITEM_SCOPE + """
)), 0) AS total_gross_weight_kg,
COALESCE(SUM(CASE WHEN i.pallet_id IS NULL THEN i.net_weight_kg ELSE 0 END), 0)
+ COALESCE((SELECT SUM(inbound.actual_net_weight_kg/NULLIF(inbound.total_package_count,0))
FROM fl_dropship_pallet_carton carton
JOIN fl_inbound_order inbound ON inbound.id=carton.inbound_id AND inbound.tenant_id=carton.tenant_id
WHERE EXISTS (SELECT 1 FROM fl_loading_plan_item pallet_item
WHERE pallet_item.loading_plan_id=p.id AND pallet_item.deleted=0
AND pallet_item.pallet_id=carton.pallet_id)), 0) AS total_net_weight_kg,
AND pallet_item.pallet_id=carton.pallet_id
""" + PALLET_ITEM_SCOPE + """
)), 0) AS total_net_weight_kg,
COALESCE(SUM(CASE WHEN i.pallet_id IS NULL THEN i.volume_cbm ELSE 0 END), 0)
+ COALESCE((SELECT SUM(inbound.actual_volume_cbm/NULLIF(inbound.total_package_count,0))
FROM fl_dropship_pallet_carton carton
JOIN fl_inbound_order inbound ON inbound.id=carton.inbound_id AND inbound.tenant_id=carton.tenant_id
WHERE EXISTS (SELECT 1 FROM fl_loading_plan_item pallet_item
WHERE pallet_item.loading_plan_id=p.id AND pallet_item.deleted=0
AND pallet_item.pallet_id=carton.pallet_id)), 0) AS total_volume_cbm,
AND pallet_item.pallet_id=carton.pallet_id
""" + PALLET_ITEM_SCOPE + """
)), 0) AS total_volume_cbm,
COALESCE(SUM(i.product_quantity), 0) AS total_quantity
""";
@@ -115,8 +152,11 @@ public interface LoadingListQueryMapper {
FROM fl_loading_plan p
JOIN fl_container_booking b ON b.id = p.container_booking_id
LEFT JOIN fl_loading_plan_item i ON i.loading_plan_id = p.id AND i.deleted = 0
""" + ITEM_SCOPE + """
WHERE p.plan_status = 'COMPLETED'
<if test="query.customerId != null">AND EXISTS (SELECT 1 FROM fl_loading_plan_item customer_item WHERE customer_item.loading_plan_id = p.id AND customer_item.deleted = 0 AND customer_item.account_id = #{query.customerId})</if>
<if test="query.customerId != null">AND EXISTS (SELECT 1 FROM fl_loading_plan_item customer_item WHERE customer_item.loading_plan_id = p.id AND customer_item.deleted = 0 AND customer_item.account_id = #{query.customerId}
""" + CUSTOMER_ACTUAL_SCOPE + """
)</if>
<if test="query.keyword != null and query.keyword != ''">
AND (p.plan_no LIKE CONCAT('%', #{query.keyword}, '%')
OR b.container_no LIKE CONCAT('%', #{query.keyword}, '%')
@@ -138,6 +178,7 @@ public interface LoadingListQueryMapper {
FROM fl_loading_plan p
JOIN fl_container_booking b ON b.id = p.container_booking_id
LEFT JOIN fl_loading_plan_item i ON i.loading_plan_id = p.id AND i.deleted = 0
""" + ITEM_SCOPE + """
WHERE p.id = #{planId}
GROUP BY
""" + AGGREGATE_GROUP)
@@ -149,6 +190,7 @@ public interface LoadingListQueryMapper {
FROM fl_loading_plan p
JOIN fl_container_booking b ON b.id = p.container_booking_id
LEFT JOIN fl_loading_plan_item i ON i.loading_plan_id = p.id AND i.deleted = 0
""" + ITEM_SCOPE + """
WHERE p.container_booking_id = #{bookingId}
GROUP BY
""" + AGGREGATE_GROUP)
@@ -224,6 +266,7 @@ public interface LoadingListQueryMapper {
JOIN fl_container_booking b ON b.id=p.container_booking_id AND b.record_status='ACTIVE'
LEFT JOIN fl_inbound_order inbound ON inbound.id=i.inbound_id AND inbound.tenant_id=i.account_id
WHERE i.loading_plan_id = #{planId} AND i.deleted = 0
""" + ITEM_SCOPE + """
ORDER BY i.load_sequence, i.id
""")
List<ItemRow> selectItems(@Param("planId") long planId);