|
|
|
@@ -14,9 +14,45 @@ import com.ffii.fpsms.modules.stock.entity.enum.InventoryLotLineStatus |
|
|
|
import org.springframework.data.repository.query.Param |
|
|
|
import java.time.LocalDate |
|
|
|
import org.springframework.data.jpa.repository.EntityGraph |
|
|
|
import java.math.BigDecimal |
|
|
|
@Repository |
|
|
|
interface InventoryLotLineRepository : AbstractRepository<InventoryLotLine, Long> { |
|
|
|
|
|
|
|
/** |
|
|
|
* Workbench pick: one conditional atomic UPDATE — winner updates row, loser gets 0 rows. |
|
|
|
* - Requires expected [BaseEntity.version] (optimistic row lock). |
|
|
|
* - No-hold rule: pickable only if (in - out) >= delta (ignore holdQty). |
|
|
|
* - Recomputes [InventoryLotLine.status] in SQL (same rules as [InventoryLotLineService.deriveInventoryLotLineStatus]). |
|
|
|
* - Bumps version in SQL so no stale JPA save is needed on this row afterward. |
|
|
|
*/ |
|
|
|
/* |
|
|
|
@Modifying(clearAutomatically = true, flushAutomatically = true) |
|
|
|
@Transactional |
|
|
|
@Query( |
|
|
|
value = """ |
|
|
|
UPDATE inventory_lot_line ill |
|
|
|
SET ill.outQty = COALESCE(ill.outQty, 0) + :delta, |
|
|
|
ill.status = CASE |
|
|
|
WHEN LOWER(COALESCE(ill.status, '')) = 'available' |
|
|
|
AND (COALESCE(ill.inQty, 0) - (COALESCE(ill.outQty, 0) + :delta)) > 0 |
|
|
|
THEN 'available' |
|
|
|
ELSE 'unavailable' |
|
|
|
END, |
|
|
|
ill.version = ill.version + 1, |
|
|
|
ill.modified = CURRENT_TIMESTAMP |
|
|
|
WHERE ill.id = :id |
|
|
|
AND ill.deleted = 0 |
|
|
|
AND ill.version = :expectedVersion |
|
|
|
AND (COALESCE(ill.inQty, 0) - COALESCE(ill.outQty, 0)) >= :delta |
|
|
|
""", |
|
|
|
nativeQuery = true |
|
|
|
) |
|
|
|
fun incrementOutQtyIfAvailable( |
|
|
|
@Param("id") id: Long, |
|
|
|
@Param("delta") delta: BigDecimal, |
|
|
|
@Param("expectedVersion") expectedVersion: Int, |
|
|
|
): Int |
|
|
|
*/ |
|
|
|
fun findByIdAndDeletedIsFalse(id: Serializable): InventoryLotLine; |
|
|
|
|
|
|
|
fun findInventoryLotLineInfoByInventoryLotItemIdIn(ids: List<Serializable>): List<InventoryLotLineInfo> |
|
|
|
@@ -96,7 +132,10 @@ interface InventoryLotLineRepository : AbstractRepository<InventoryLotLine, Long |
|
|
|
AND ill.status = 'available' |
|
|
|
""") |
|
|
|
fun findAllByWarehouseIdInAndDeletedIsFalseAndStatusIsAvailable(@Param("warehouseIds") warehouseIds: List<Long>): List<InventoryLotLine> |
|
|
|
|
|
|
|
@EntityGraph( |
|
|
|
type = EntityGraph.EntityGraphType.FETCH, |
|
|
|
attributePaths = ["inventoryLot", "inventoryLot.item", "warehouse", "stockUom", "stockUom.uom"] |
|
|
|
) |
|
|
|
@Query(""" |
|
|
|
SELECT ill FROM InventoryLotLine ill |
|
|
|
WHERE ill.deleted = false |
|
|
|
|