cyril.tsui 2 days ago
parent
commit
dabac211c1
7 changed files with 359 additions and 47 deletions
  1. +95
    -3
      src/main/java/com/ffii/fpsms/modules/master/service/ItemsService.kt
  2. +34
    -1
      src/main/java/com/ffii/fpsms/modules/master/web/ItemsController.kt
  3. +1
    -0
      src/main/java/com/ffii/fpsms/modules/pickOrder/enums/PickOrderEnum.kt
  4. +194
    -41
      src/main/java/com/ffii/fpsms/modules/pickOrder/service/PickOrderService.kt
  5. +19
    -1
      src/main/java/com/ffii/fpsms/modules/pickOrder/web/PickOrderController.kt
  6. +1
    -0
      src/main/java/com/ffii/fpsms/modules/pickOrder/web/models/ConsoPickOrderResponse.kt
  7. +15
    -1
      src/main/java/com/ffii/fpsms/modules/user/web/UserController.java

+ 95
- 3
src/main/java/com/ffii/fpsms/modules/master/service/ItemsService.kt View File

@@ -38,18 +38,110 @@ open class ItemsService(
+ " concat(i.code , ' - ' , i.name) as label, " + " concat(i.code , ' - ' , i.name) as label, "
+ " uc.id as uomId, " + " uc.id as uomId, "
+ " uc.code as uom, " + " uc.code as uom, "
+ " COALESCE(inv.onHandQty, 0) - COALESCE(inv.onHoldQty, 0) - COALESCE(inv.unavailableQty, 0) as currentStockBalance "
+ " uc.udfudesc as uomDesc, "
+ " COALESCE(inv.availableQty, 0) as currentStockBalance "
+ " from items i " + " from items i "
+ " left join item_uom iu on iu.itemId = i.id and iu.deleted = false and iu.salesUnit = true " + " left join item_uom iu on iu.itemId = i.id and iu.deleted = false and iu.salesUnit = true "
+ " left join uom_conversion uc on uc.id = iu.uomId " + " left join uom_conversion uc on uc.id = iu.uomId "
+ " left join inventory inv on inv.itemId = i.id "
+ " left join ("
+ " SELECT "
+ " il.itemId, "
+ " SUM(COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) / "
+ " COALESCE(MAX(iu_ratio.ratioN) / MAX(iu_ratio.ratioD), 1) as availableQty "
+ " FROM inventory_lot_line ill "
+ " JOIN inventory_lot il ON il.id = ill.inventoryLotId "
+ " LEFT JOIN item_uom iu_ratio ON iu_ratio.itemId = il.itemId AND iu_ratio.deleted = false AND iu_ratio.salesUnit = true "
+ " WHERE ill.status = 'available' "
+ " AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0 "
+ " AND (il.expiryDate IS NULL OR il.expiryDate >= CURDATE()) "
+ " GROUP BY il.itemId "
+ " ) inv ON inv.itemId = i.id "
+ " where i.deleted = false " + " where i.deleted = false "
+ " and i.type = :type " + " and i.type = :type "
) )


return jdbcDao.queryForList(sql.toString(), args); return jdbcDao.queryForList(sql.toString(), args);
} }

open fun getPickOrderItemsByPage(args: Map<String, Any>): List<Map<String, Any>> {
try {
println("=== Debug: getPickOrderItemsByPage in ItemsService ===")
println("Args: $args")
val sql = StringBuilder(
"""
SELECT
CONCAT(po.id, '-', pol.itemId) as id,
po.id as pickOrderId,
po.code as pickOrderCode,
pol.itemId,
i.code as itemCode,
i.name as itemName,
pol.qty as requiredQty,
COALESCE(inv.availableQty, 0) as currentStock,
COALESCE(uc.udfudesc, 'N/A') as unit,
po.targetDate,
po.status,
po.consoCode,
po.assignTo
FROM pick_order po
JOIN pick_order_line pol ON pol.poId = po.id
JOIN items i ON i.id = pol.itemId
LEFT JOIN uom_conversion uc ON uc.id = pol.uomId
LEFT JOIN (
SELECT
il.itemId,
SUM(COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) /
COALESCE(MAX(iu_ratio.ratioN) / MAX(iu_ratio.ratioD), 1) as availableQty
FROM inventory_lot_line ill
JOIN inventory_lot il ON il.id = ill.inventoryLotId
LEFT JOIN item_uom iu_ratio ON iu_ratio.itemId = il.itemId AND iu_ratio.deleted = false AND iu_ratio.salesUnit = true
WHERE ill.status = 'available'
AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0
AND (il.expiryDate IS NULL OR il.expiryDate >= CURDATE())
GROUP BY il.itemId
) inv ON inv.itemId = pol.itemId
WHERE po.deleted = false
AND po.consoCode IS NULL
"""
)
if (args.containsKey("itemCode")) {
sql.append(" AND i.code LIKE :itemCode ")
}
if (args.containsKey("itemName")) {
sql.append(" AND i.name LIKE :itemName ")
}
if (args.containsKey("status")) {
sql.append(" AND po.status = :status ")
}
if (args.containsKey("targetDateFrom")) {
sql.append(" AND po.targetDate >= :targetDateFrom ")
}
if (args.containsKey("targetDateTo")) {
sql.append(" AND po.targetDate <= :targetDateTo ")
}
sql.append(" ORDER BY po.targetDate DESC, i.name ASC ")
val finalSql = sql.toString()
println("Final SQL: $finalSql")
println("SQL args: $args")
val result = jdbcDao.queryForList(finalSql, args)
println("Query result size: ${result.size}")
return result
} catch (e: Exception) {
println("Error in getPickOrderItemsByPage: ${e.message}")
e.printStackTrace()
throw e
}
}
open fun getRoughScheduleList(): List<Map<String, Any>> { open fun getRoughScheduleList(): List<Map<String, Any>> {
val now = LocalDateTime.now() val now = LocalDateTime.now()
val lastMonthStart = now.minusMonths(1).withDayOfMonth(1).withHour(0).withMinute(0).withSecond(0) // Start of last month val lastMonthStart = now.minusMonths(1).withDayOfMonth(1).withHour(0).withMinute(0).withSecond(0) // Start of last month


+ 34
- 1
src/main/java/com/ffii/fpsms/modules/master/web/ItemsController.kt View File

@@ -60,7 +60,40 @@ class ItemsController(


return RecordsRes(paginatedList as List<Map<String, Any>>, fullList.size) return RecordsRes(paginatedList as List<Map<String, Any>>, fullList.size)
} }

@GetMapping("/pickOrderItems")
fun getPickOrderItemsByPage(request: HttpServletRequest): RecordsRes<Map<String, Any>> {
try {
println("=== Debug: getPickOrderItemsByPage ===")
println("Request parameters: ${request.parameterMap}")
val criteriaArgs = CriteriaArgsBuilder.withRequest(request)
.addStringLike("itemCode")
.addStringLike("itemName")
.addString("status")
.addString("targetDateFrom")
.addString("targetDateTo")
.build()
println("Criteria args: $criteriaArgs")
val pageSize = request.getParameter("pageSize")?.toIntOrNull() ?: 10
val pageNum = request.getParameter("pageNum")?.toIntOrNull() ?: 1
println("Page size: $pageSize, Page num: $pageNum")
val fullList = itemsService.getPickOrderItemsByPage(criteriaArgs)
println("Full list size: ${fullList.size}")
val paginatedList = PagingUtils.getPaginatedList(fullList, pageSize, pageNum)
println("Paginated list size: ${paginatedList.size}")
return RecordsRes(paginatedList, fullList.size)
} catch (e: Exception) {
println("Error in getPickOrderItemsByPage: ${e.message}")
e.printStackTrace()
throw e
}
}
@GetMapping("/details/{id}") @GetMapping("/details/{id}")
fun getItems(@PathVariable id: Long): ItemWithQcResponse { fun getItems(@PathVariable id: Long): ItemWithQcResponse {
return itemsService.getItem(id) return itemsService.getItem(id)


+ 1
- 0
src/main/java/com/ffii/fpsms/modules/pickOrder/enums/PickOrderEnum.kt View File

@@ -3,6 +3,7 @@ package com.ffii.fpsms.modules.pickOrder.enums
enum class PickOrderStatus(val value: String) { enum class PickOrderStatus(val value: String) {
PENDING ("pending"), PENDING ("pending"),
CONSOLIDATED ("consolidated"), CONSOLIDATED ("consolidated"),
ASSIGNED ("assigned"),
RELEASED ("released"), RELEASED ("released"),
PICKING ("picking"), PICKING ("picking"),
COMPLETED ("completed"); COMPLETED ("completed");


+ 194
- 41
src/main/java/com/ffii/fpsms/modules/pickOrder/service/PickOrderService.kt View File

@@ -127,12 +127,11 @@ open class PickOrderService(
val total = response.totalElements val total = response.totalElements
return RecordsRes<PickOrderInfo>(records, total.toInt()) return RecordsRes<PickOrderInfo>(records, total.toInt())
} }




open fun getPickOrdersWithStockBalanceByPage(request: SearchPickOrderRequest): RecordsRes<GetPickOrderInfo> { open fun getPickOrdersWithStockBalanceByPage(request: SearchPickOrderRequest): RecordsRes<GetPickOrderInfo> {
val pageable = PageRequest.of(request.pageNum ?: 0, request.pageSize ?: 10); val pageable = PageRequest.of(request.pageNum ?: 0, request.pageSize ?: 10);
// First get the basic pick order info for pagination // First get the basic pick order info for pagination
val response = pickOrderRepository.findPickOrderInfoByConditionsAndPageable( val response = pickOrderRepository.findPickOrderInfoByConditionsAndPageable(
code = request.code ?: "all", code = request.code ?: "all",
@@ -143,27 +142,27 @@ open class PickOrderService(
itemName = request.itemName ?: "all", itemName = request.itemName ?: "all",
pageable = pageable pageable = pageable
) )
val records = response.content val records = response.content
val pickOrderIds = records.mapNotNull { it.id } val pickOrderIds = records.mapNotNull { it.id }
if (pickOrderIds.isEmpty()) { if (pickOrderIds.isEmpty()) {
return RecordsRes(emptyList(), 0) return RecordsRes(emptyList(), 0)
} }
// Get full pick orders with relationships // Get full pick orders with relationships
val fullPickOrders = pickOrderRepository.findAllByIdIn(pickOrderIds) val fullPickOrders = pickOrderRepository.findAllByIdIn(pickOrderIds)
// Get all item IDs // Get all item IDs
val itemIds = fullPickOrders val itemIds = fullPickOrders
.flatMap { it.pickOrderLines } .flatMap { it.pickOrderLines }
.mapNotNull { it.item?.id } .mapNotNull { it.item?.id }
.distinct() .distinct()
// Get inventory data // Get inventory data
val today = LocalDate.now() val today = LocalDate.now()
val zero = BigDecimal.ZERO val zero = BigDecimal.ZERO
val inventories = if (itemIds.isNotEmpty()) { val inventories = if (itemIds.isNotEmpty()) {
inventoryLotLineService inventoryLotLineService
.allInventoryLotLinesByItemIdIn(itemIds) .allInventoryLotLinesByItemIdIn(itemIds)
@@ -174,12 +173,12 @@ open class PickOrderService(
} else { } else {
emptyMap() emptyMap()
} }
// Build response (removed suggestions) // Build response (removed suggestions)
val pickOrderInfos = fullPickOrders.map { po -> val pickOrderInfos = fullPickOrders.map { po ->
val pickOrderLineInfos = po.pickOrderLines.map { pol -> val pickOrderLineInfos = po.pickOrderLines.map { pol ->
val inventory = pol.item?.id?.let { inventories[it] } val inventory = pol.item?.id?.let { inventories[it] }
GetPickOrderLineInfo( GetPickOrderLineInfo(
id = pol.id, id = pol.id,
itemId = pol.item?.id, itemId = pol.item?.id,
@@ -192,20 +191,87 @@ open class PickOrderService(
suggestedList = emptyList() // Empty list since you don't need suggestions suggestedList = emptyList() // Empty list since you don't need suggestions
) )
} }
GetPickOrderInfo( GetPickOrderInfo(
id = po.id, id = po.id,
code = po.code, code = po.code,
targetDate = po.targetDate, targetDate = po.targetDate,
type = po.type?.value, type = po.type?.value,
status = po.status?.value, status = po.status?.value,
assignTo = po.assignTo?.id,
pickOrderLines = pickOrderLineInfos pickOrderLines = pickOrderLineInfos
) )
} }
val total = response.totalElements val total = response.totalElements
return RecordsRes(pickOrderInfos, total.toInt()) return RecordsRes(pickOrderInfos, total.toInt())
} }

open fun assignPickOrders(pickOrderIds: List<Long>, assignTo: Long): MessageResponse {
try {
val pickOrders = pickOrderRepository.findAllById(pickOrderIds)
val user = userService.find(assignTo).orElse(null) // 获取用户对象

pickOrders.forEach { pickOrder ->
pickOrder.assignTo = user // 使用 User 对象而不是 Long
pickOrder.status = PickOrderStatus.ASSIGNED // 使用枚举值
}

pickOrderRepository.saveAll(pickOrders)

return MessageResponse(
id = null,
name = "Pick orders assigned successfully",
code = "SUCCESS",
type = "pickorder",
message = "Pick orders assigned successfully",
errorPosition = null
)
} catch (e: Exception) {
return MessageResponse(
id = null,
name = "Failed to assign pick orders",
code = "ERROR",
type = "pickorder",
message = "Failed to assign pick orders: ${e.message}",
errorPosition = null
)
}
}

open fun releasePickOrders(pickOrderIds: List<Long>, assignTo: Long): MessageResponse {
try {
val pickOrders = pickOrderRepository.findAllById(pickOrderIds)
val user = userService.find(assignTo).orElse(null) // 获取用户对象

pickOrders.forEach { pickOrder ->
pickOrder.assignTo = user // 使用 User 对象而不是 Long
pickOrder.status = PickOrderStatus.RELEASED // 使用枚举值
}

pickOrderRepository.saveAll(pickOrders)

return MessageResponse(
id = null,
name = "Pick orders released successfully",
code = "SUCCESS",
type = "pickorder",
message = "Pick orders released successfully",
errorPosition = null
)
} catch (e: Exception) {
return MessageResponse(
id = null,
name = "Failed to release pick orders",
code = "ERROR",
type = "pickorder",
message = "Failed to release pick orders: ${e.message}",
errorPosition = null
)
}
}


open fun getConsoPickOrderList(args: MutableMap<String, Any>): List<Map<String, Any>> { open fun getConsoPickOrderList(args: MutableMap<String, Any>): List<Map<String, Any>> {
val sql = StringBuilder( val sql = StringBuilder(
"select" "select"
@@ -525,7 +591,7 @@ open class PickOrderService(
itemCode = pol.item?.code, itemCode = pol.item?.code,
itemName = pol.item?.name, itemName = pol.item?.name,
// availableQty = inventory?.availableQty, // availableQty = inventory?.availableQty,
availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) },
availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) },
// availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) * (itemUom?.ratioN ?: one) * (itemUom?.ratioD ?: one) }, // availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) * (itemUom?.ratioN ?: one) * (itemUom?.ratioD ?: one) },
requiredQty = pol.qty, requiredQty = pol.qty,
uomCode = pol.uom?.code, uomCode = pol.uom?.code,
@@ -623,7 +689,7 @@ open class PickOrderService(
itemCode = pol.item?.code, itemCode = pol.item?.code,
itemName = pol.item?.name, itemName = pol.item?.name,
// availableQty = inventory?.availableQty, // availableQty = inventory?.availableQty,
availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) },
availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) },
// availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) * (itemUom?.ratioN ?: one) * (itemUom?.ratioD ?: one) }, // availableQty = inventory?.sumOf { i -> (i.availableQty ?: zero) * (itemUom?.ratioN ?: one) * (itemUom?.ratioD ?: one) },
requiredQty = pol.qty, requiredQty = pol.qty,
uomCode = pol.uom?.code, uomCode = pol.uom?.code,
@@ -636,10 +702,11 @@ open class PickOrderService(
// Return // Return
GetPickOrderInfo( GetPickOrderInfo(
id = po.id, id = po.id,
code = po.code,
code = po.code,
targetDate = po.targetDate, targetDate = po.targetDate,
type = po.type?.value, type = po.type?.value,
status = po.status?.value, status = po.status?.value,
assignTo = po.assignTo?.id,
pickOrderLines = releasePickOrderLineInfos pickOrderLines = releasePickOrderLineInfos
) )
} }
@@ -677,9 +744,9 @@ open class PickOrderService(
val releasedPickOrderIds = allPickOrders val releasedPickOrderIds = allPickOrders
.filter { it.status == PickOrderStatus.RELEASED } .filter { it.status == PickOrderStatus.RELEASED }
.map { it.id!! } .map { it.id!! }
println("All released pick order IDs: $releasedPickOrderIds") println("All released pick order IDs: $releasedPickOrderIds")
// 如果没有任何已发布的 Pick Orders,返回空结果 // 如果没有任何已发布的 Pick Orders,返回空结果
if (releasedPickOrderIds.isEmpty()) { if (releasedPickOrderIds.isEmpty()) {
return GetPickOrderInfoResponse( return GetPickOrderInfoResponse(
@@ -687,18 +754,18 @@ open class PickOrderService(
items = emptyList() items = emptyList()
) )
} }
// 重用现有的 getPickOrdersInfo 方法 // 重用现有的 getPickOrdersInfo 方法
return getPickOrdersInfo(releasedPickOrderIds) return getPickOrdersInfo(releasedPickOrderIds)
} }


open fun getPickOrderLineLotDetails(pickOrderLineId: Long): List<Map<String, Any>> { open fun getPickOrderLineLotDetails(pickOrderLineId: Long): List<Map<String, Any>> {
val today = LocalDate.now() val today = LocalDate.now()
println("=== Debug: getPickOrderLineLotDetails ===") println("=== Debug: getPickOrderLineLotDetails ===")
println("pickOrderLineId: $pickOrderLineId") println("pickOrderLineId: $pickOrderLineId")
println("today: $today") println("today: $today")
// 检查具体的数量字段值 // 检查具体的数量字段值
val quantityCheckSql = """ val quantityCheckSql = """
SELECT SELECT
@@ -716,13 +783,13 @@ open class PickOrderService(
WHERE spl.pickOrderLineId = :pickOrderLineId WHERE spl.pickOrderLineId = :pickOrderLineId
AND ill.status = 'available' AND ill.status = 'available'
""".trimIndent() """.trimIndent()
val quantityCheckResult = jdbcDao.queryForList(quantityCheckSql, mapOf("pickOrderLineId" to pickOrderLineId)) val quantityCheckResult = jdbcDao.queryForList(quantityCheckSql, mapOf("pickOrderLineId" to pickOrderLineId))
println("Quantity check result:") println("Quantity check result:")
quantityCheckResult.forEach { row -> quantityCheckResult.forEach { row ->
println("Row: $row") println("Row: $row")
} }
// 检查日期条件 // 检查日期条件
val dateCheckSql = """ val dateCheckSql = """
SELECT SELECT
@@ -740,13 +807,14 @@ open class PickOrderService(
AND ill.status = 'available' AND ill.status = 'available'
AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0 AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0
""".trimIndent() """.trimIndent()
val dateCheckResult = jdbcDao.queryForList(dateCheckSql, mapOf("pickOrderLineId" to pickOrderLineId, "today" to today))

val dateCheckResult =
jdbcDao.queryForList(dateCheckSql, mapOf("pickOrderLineId" to pickOrderLineId, "today" to today))
println("Date check result:") println("Date check result:")
dateCheckResult.forEach { row -> dateCheckResult.forEach { row ->
println("Row: $row") println("Row: $row")
} }
// 检查 warehouse JOIN // 检查 warehouse JOIN
val warehouseCheckSql = """ val warehouseCheckSql = """
SELECT SELECT
@@ -764,13 +832,14 @@ open class PickOrderService(
AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0 AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0
AND (il.expiryDate IS NULL OR il.expiryDate >= :today) AND (il.expiryDate IS NULL OR il.expiryDate >= :today)
""".trimIndent() """.trimIndent()
val warehouseCheckResult = jdbcDao.queryForList(warehouseCheckSql, mapOf("pickOrderLineId" to pickOrderLineId, "today" to today))

val warehouseCheckResult =
jdbcDao.queryForList(warehouseCheckSql, mapOf("pickOrderLineId" to pickOrderLineId, "today" to today))
println("Warehouse check result count: ${warehouseCheckResult.size}") println("Warehouse check result count: ${warehouseCheckResult.size}")
warehouseCheckResult.forEach { row -> warehouseCheckResult.forEach { row ->
println("Warehouse Row: $row") println("Warehouse Row: $row")
} }
// 检查 uom_conversion JOIN - 使用 LEFT JOIN 并检查 stockItemUomId // 检查 uom_conversion JOIN - 使用 LEFT JOIN 并检查 stockItemUomId
val uomCheckSql = """ val uomCheckSql = """
SELECT SELECT
@@ -789,13 +858,14 @@ open class PickOrderService(
AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0 AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0) - COALESCE(ill.holdQty, 0)) > 0
AND (il.expiryDate IS NULL OR il.expiryDate >= :today) AND (il.expiryDate IS NULL OR il.expiryDate >= :today)
""".trimIndent() """.trimIndent()
val uomCheckResult = jdbcDao.queryForList(uomCheckSql, mapOf("pickOrderLineId" to pickOrderLineId, "today" to today))

val uomCheckResult =
jdbcDao.queryForList(uomCheckSql, mapOf("pickOrderLineId" to pickOrderLineId, "today" to today))
println("UOM check result count: ${uomCheckResult.size}") println("UOM check result count: ${uomCheckResult.size}")
uomCheckResult.forEach { row -> uomCheckResult.forEach { row ->
println("UOM Row: $row") println("UOM Row: $row")
} }
// 修改查询,通过 item_uom 表获取 UOM 信息 // 修改查询,通过 item_uom 表获取 UOM 信息
val sql = """ val sql = """
SELECT SELECT
@@ -833,27 +903,22 @@ open class PickOrderService(
END, END,
il.expiryDate ASC il.expiryDate ASC
""".trimIndent() """.trimIndent()
val params = mapOf( val params = mapOf(
"pickOrderLineId" to pickOrderLineId, "pickOrderLineId" to pickOrderLineId,
"today" to today "today" to today
) )
val result = jdbcDao.queryForList(sql, params) val result = jdbcDao.queryForList(sql, params)
println("Final result count: ${result.size}") println("Final result count: ${result.size}")
result.forEach { row -> result.forEach { row ->
println("Final Row: $row") println("Final Row: $row")
} }
return result return result
} }








@Transactional(rollbackFor = [java.lang.Exception::class]) @Transactional(rollbackFor = [java.lang.Exception::class])
open fun releaseConsoPickOrderAction(request: ReleaseConsoPickOrderRequest): ReleasePickOrderInfoResponse { open fun releaseConsoPickOrderAction(request: ReleaseConsoPickOrderRequest): ReleasePickOrderInfoResponse {
val zero = BigDecimal.ZERO val zero = BigDecimal.ZERO
@@ -908,6 +973,94 @@ open class PickOrderService(
return releaseConsoPickOrderInfo(request.consoCode) return releaseConsoPickOrderInfo(request.consoCode)
} }


@Transactional(rollbackFor = [java.lang.Exception::class])
open fun releaseAssignedPickOrders(pickOrderIds: List<Long>, assignTo: Long): MessageResponse {
try {
val zero = BigDecimal.ZERO
val releasedBy = SecurityUtils.getUser().getOrNull()
val user = userService.find(assignTo).orElse(null)
val pickOrders = pickOrderRepository.findAllByIdInAndStatus(pickOrderIds, PickOrderStatus.ASSIGNED)
if (pickOrders.isEmpty()) {
return MessageResponse(
id = null,
name = "No assigned pick orders found",
code = "ERROR",
type = "pickorder",
message = "No assigned pick orders found with the provided IDs",
errorPosition = null
)
}
pickOrders.forEach { pickOrder ->
pickOrder.apply {
this.releasedBy = releasedBy
status = PickOrderStatus.RELEASED
this.assignTo = user
}
}
val suggestions = suggestedPickLotService.suggestionForPickOrders(
SuggestedPickLotForPoRequest(pickOrders = pickOrders)
)
val currUser = SecurityUtils.getUser().orElseThrow()
val stockOut = StockOut().apply {
this.type = "job"
this.consoPickOrderCode = null // 单个 pick orders 没有 consoCode
this.status = StockOutStatus.PENDING.status
this.handler = currUser.id
}
stockOutRepository.save(stockOut)
val saveSuggestedPickLots = suggestedPickLotService.saveAll(suggestions.suggestedList)
pickOrderRepository.saveAll(pickOrders)
val inventoryLotLines = inventoryLotLineRepository.findAllByIdIn(
saveSuggestedPickLots.mapNotNull { it.suggestedLotLine?.id }
)
saveSuggestedPickLots.forEach { lot ->
if (lot.suggestedLotLine != null && lot.suggestedLotLine?.id != null && lot.suggestedLotLine!!.id!! > 0) {
val lineIndex = inventoryLotLines.indexOf(lot.suggestedLotLine)
if (lineIndex >= 0) {
inventoryLotLines[lineIndex].holdQty =
(inventoryLotLines[lineIndex].holdQty ?: zero).plus(lot.qty ?: zero)
}
}
}
inventoryLotLineRepository.saveAll(inventoryLotLines)
return MessageResponse(
id = null,
name = "Pick orders released successfully with inventory management",
code = "SUCCESS",
type = "pickorder",
message = "Pick orders released successfully with inventory management",
errorPosition = null
)
} catch (e: Exception) {
return MessageResponse(
id = null,
name = "Failed to release pick orders",
code = "ERROR",
type = "pickorder",
message = "Failed to release pick orders: ${e.message}",
errorPosition = null
)
}
}
@Throws(IOException::class) @Throws(IOException::class)
@Transactional @Transactional
open fun completeStockOut(consoCode: String): MessageResponse { open fun completeStockOut(consoCode: String): MessageResponse {
@@ -939,8 +1092,8 @@ open class PickOrderService(
} else { } else {
return MessageResponse( return MessageResponse(
id = stockOut.id, id = stockOut.id,
name = stockOut.consoPickOrderCode ?: stockOut.deliveryOrderCode,
code = stockOut.consoPickOrderCode ?: stockOut.deliveryOrderCode,
name = stockOut.consoPickOrderCode ?: stockOut.deliveryOrderCode, // 修复:使用 stockOut 而不是 savedStockOut
code = stockOut.consoPickOrderCode ?: stockOut.deliveryOrderCode, // 修复:使用 stockOut 而不是 savedStockOut
type = stockOut.type, type = stockOut.type,
message = "not completed", message = "not completed",
errorPosition = null, errorPosition = null,


+ 19
- 1
src/main/java/com/ffii/fpsms/modules/pickOrder/web/PickOrderController.kt View File

@@ -63,7 +63,20 @@ class PickOrderController(
val paginatedList = PagingUtils.getPaginatedList(fullList,pageSize, pageNum) val paginatedList = PagingUtils.getPaginatedList(fullList,pageSize, pageNum)
return RecordsRes(paginatedList, fullList.size) return RecordsRes(paginatedList, fullList.size)
} }
@PostMapping("/assign")
fun assignPickOrders(@RequestBody request: Map<String, Any>): MessageResponse {
val pickOrderIds = (request["pickOrderIds"] as List<*>).map { it.toString().toLong() }
val assignTo = request["assignTo"].toString().toLong()
return pickOrderService.assignPickOrders(pickOrderIds, assignTo)
}


// Release Pick Orders (without consoCode)
@PostMapping("/release")
fun releasePickOrders(@RequestBody request: Map<String, Any>): MessageResponse {
val pickOrderIds = (request["pickOrderIds"] as List<*>).map { it.toString().toLong() }
val assignTo = request["assignTo"].toString().toLong()
return pickOrderService.releasePickOrders(pickOrderIds, assignTo)
}
@GetMapping("/get-pickorder-line-byPage") @GetMapping("/get-pickorder-line-byPage")
fun getPickOrderLine(request: HttpServletRequest): RecordsRes<Map<String, Any>> { fun getPickOrderLine(request: HttpServletRequest): RecordsRes<Map<String, Any>> {
val criteriaArgs = CriteriaArgsBuilder.withRequest(request) val criteriaArgs = CriteriaArgsBuilder.withRequest(request)
@@ -112,7 +125,12 @@ class PickOrderController(
fun releaseConsoPickOrderAction(@Valid @RequestBody request: ReleaseConsoPickOrderRequest): ReleasePickOrderInfoResponse { fun releaseConsoPickOrderAction(@Valid @RequestBody request: ReleaseConsoPickOrderRequest): ReleasePickOrderInfoResponse {
return pickOrderService.releaseConsoPickOrderAction(request) return pickOrderService.releaseConsoPickOrderAction(request)
} }

@PostMapping("/release-assigned")
fun releaseAssignedPickOrders(@RequestBody request: Map<String, Any>): MessageResponse {
val pickOrderIds = (request["pickOrderIds"] as List<*>).map { it.toString().toLong() }
val assignTo = request["assignTo"].toString().toLong()
return pickOrderService.releaseAssignedPickOrders(pickOrderIds, assignTo)
}
// Start Pick Order // Start Pick Order
@GetMapping("/pickConso/{consoCode}") @GetMapping("/pickConso/{consoCode}")
fun pickConsoPickOrderInfo(@PathVariable consoCode: String): ReleasePickOrderInfoResponse { fun pickConsoPickOrderInfo(@PathVariable consoCode: String): ReleasePickOrderInfoResponse {


+ 1
- 0
src/main/java/com/ffii/fpsms/modules/pickOrder/web/models/ConsoPickOrderResponse.kt View File

@@ -34,6 +34,7 @@ data class GetPickOrderInfo(
val targetDate: LocalDateTime?, val targetDate: LocalDateTime?,
val type: String?, val type: String?,
val status: String?, val status: String?,
val assignTo: Long?,
val pickOrderLines: List<GetPickOrderLineInfo> val pickOrderLines: List<GetPickOrderLineInfo>
) )




+ 15
- 1
src/main/java/com/ffii/fpsms/modules/user/web/UserController.java View File

@@ -9,7 +9,6 @@ import com.ffii.fpsms.modules.user.entity.projections.UserCombo;
import com.ffii.fpsms.modules.user.service.pojo.UserRecord; import com.ffii.fpsms.modules.user.service.pojo.UserRecord;
import org.apache.commons.logging.Log; import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory; import org.apache.commons.logging.LogFactory;
import org.hibernate.mapping.Any;
import org.springframework.http.HttpStatus; import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity; import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize; import org.springframework.security.access.prepost.PreAuthorize;
@@ -91,6 +90,21 @@ public class UserController{
.toList(); .toList();
return ResponseEntity.ok(namelist); return ResponseEntity.ok(namelist);
} }
@GetMapping("/new-name-list")
public ResponseEntity<List<Map<String, Object>>> newnamelist() {
SearchUserReq req = new SearchUserReq();
List<Map<String, Object>> newnamelist = userService.search(req).stream()
.map(user -> {
Map<String, Object> map = new HashMap<>();
map.put("id", user.getId());
map.put("name", user.getName());
map.put("title", user.getTitle());
map.put("department", user.getDepartment());
return map;
})
.toList();
return ResponseEntity.ok(newnamelist);
}
// @Operation(summary = "load user data", responses = { @ApiResponse(responseCode = "200"), // @Operation(summary = "load user data", responses = { @ApiResponse(responseCode = "200"),
// @ApiResponse(responseCode = "404", content = @Content) }) // @ApiResponse(responseCode = "404", content = @Content) })
@GetMapping("/{id}") @GetMapping("/{id}")


Loading…
Cancel
Save