Commit 4d2dea9b by yubin

导入无库存插入-库存 加导入手动标识 导入日志

parent c5a19854
...@@ -117,5 +117,5 @@ public interface InventoryMapper ...@@ -117,5 +117,5 @@ public interface InventoryMapper
public List<java.util.Map<String, String>> selectInventoryTopTenByAmount(); public List<java.util.Map<String, String>> selectInventoryTopTenByAmount();
public List<java.util.Map<String, String>> selectInventoryTopTenByQuantity(); public List<java.util.Map<String, String>> selectInventoryTopTenByQuantity();
public void batchUpdateInventory(List<Inventory> inventoryList); public int batchUpdateInventory(List<Inventory> inventoryList);
} }
package com.ruoyi.inventory.utils; package com.ruoyi.inventory.utils;
import com.ruoyi.inventory.domain.Inventory; import com.ruoyi.inventory.domain.Inventory;
import com.ruoyi.common.utils.StringUtils;
import org.apache.commons.collections4.CollectionUtils;
import java.util.AbstractMap; import java.util.*;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.CopyOnWriteArrayList;
/** /**
* 库存映射全局缓存(解决导入新增库存即时可见问题 * 库存映射全局缓存(适配同维度多库存场景
*/ */
public class InventoryCache { public class InventoryCache {
// 并发安全Map,Key=物料ID_库位ID_库存类型,Value=库存对象 // 重构:维度Key → 同维度下的所有库存列表
private static final Map<String, Inventory> INVENTORY_MAP = new ConcurrentHashMap<>(); private static final Map<String, List<Inventory>> INVENTORY_GROUP_MAP = new ConcurrentHashMap<>();
// 添加库存(直接存对象,避免参数不匹配) // ========== 核心方法 ==========
/**
* 批量初始化缓存(从数据库加载全量库存时调用)
* @param allInventory 全量库存列表
*/
public static void init(List<Inventory> allInventory) {
if (CollectionUtils.isEmpty(allInventory)) {
clear();
return;
}
INVENTORY_GROUP_MAP.clear();
for (Inventory inv : allInventory) {
String key = buildInventoryKey(inv);
INVENTORY_GROUP_MAP.computeIfAbsent(key, k -> new CopyOnWriteArrayList<>()).add(inv);
}
}
/**
* 添加单条库存到缓存(自动按维度分组)
* @param inventory 库存对象
*/
public static void addInventory(Inventory inventory) {
if (inventory == null) {
return;
}
String key = buildInventoryKey(inventory);
INVENTORY_GROUP_MAP.computeIfAbsent(key, k -> new CopyOnWriteArrayList<>()).add(inventory);
}
/**
* 更新缓存中的库存对象(按库存ID匹配)
* @param inventory 待更新的库存对象
*/
public static void updateInventory(Inventory inventory) {
if (inventory == null || StringUtils.isBlank(inventory.getId())) {
return;
}
String key = buildInventoryKey(inventory);
List<Inventory> invList = INVENTORY_GROUP_MAP.get(key);
if (CollectionUtils.isEmpty(invList)) {
return;
}
// 替换同ID的库存对象
for (int i = 0; i < invList.size(); i++) {
if (inventory.getId().equals(invList.get(i).getId())) {
invList.set(i, inventory);
break;
}
}
}
/**
* 移除指定维度下的指定库存
* @param inventory 待移除的库存对象
*/
public static void removeInventory(Inventory inventory) {
if (inventory == null || StringUtils.isBlank(inventory.getId())) {
return;
}
String key = buildInventoryKey(inventory);
List<Inventory> invList = INVENTORY_GROUP_MAP.get(key);
if (CollectionUtils.isEmpty(invList)) {
return;
}
invList.removeIf(inv -> inventory.getId().equals(inv.getId()));
// 若维度下无库存,删除该维度Key
if (invList.isEmpty()) {
INVENTORY_GROUP_MAP.remove(key);
}
}
/**
* 按维度Key获取库存列表
* @param key 维度Key(物料ID_库位ID_库存类型)
* @return 同维度下的所有库存
*/
public static List<Inventory> getInventoryListByKey(String key) {
return INVENTORY_GROUP_MAP.getOrDefault(key, Collections.emptyList());
}
/**
* 获取全量缓存(供扣减逻辑调用)
* @return 维度Key → 库存列表
*/
public static Map<String, List<Inventory>> getAllGroup() {
return new HashMap<>(INVENTORY_GROUP_MAP); // 返回拷贝,避免外部修改
}
/**
* 清空缓存
*/
public static void clear() {
INVENTORY_GROUP_MAP.clear();
}
// ========== 辅助方法 ==========
/**
* 构建库存维度Key:物料ID_库位ID_库存类型
*/
public static String buildInventoryKey(Inventory inventory) {
if (inventory == null) {
return "";
}
return String.join("_",
StringUtils.trimToEmpty(inventory.getMaterialId()),
StringUtils.trimToEmpty(inventory.getLocationId()),
Optional.ofNullable(inventory.getInventoryType()).map(String::valueOf).orElse("")
);
}
/**
* 重载:手动构建维度Key
*/
public static String buildInventoryKey(String materialId, String locationId, String inventoryType) {
return String.join("_",
StringUtils.trimToEmpty(materialId),
StringUtils.trimToEmpty(locationId),
StringUtils.trimToEmpty(inventoryType)
);
}
// ========== 兼容原有方法(避免改动业务层) ==========
@Deprecated // 标记为过时,建议使用新方法
public static void addInventory(String key, Inventory inventory) { public static void addInventory(String key, Inventory inventory) {
INVENTORY_MAP.put(key, inventory); INVENTORY_GROUP_MAP.computeIfAbsent(key, k -> new CopyOnWriteArrayList<>()).add(inventory);
} }
// 获取库存 @Deprecated
public static Inventory getInventory(String key) { public static Inventory getInventory(String key) {
return INVENTORY_MAP.get(key); List<Inventory> invList = INVENTORY_GROUP_MAP.get(key);
return CollectionUtils.isEmpty(invList) ? null : invList.get(0);
} }
// 清空缓存 @Deprecated
public static void clear() { public static void removeInventory(String key) {
INVENTORY_MAP.clear(); INVENTORY_GROUP_MAP.remove(key);
} }
// 获取全部缓存(核心:供loadInventoryGroupMap直接读取) @Deprecated
public static Map<String, Inventory> getAll() { public static void removeInventory(String key, String inventoryId) {
return INVENTORY_MAP; List<Inventory> invList = INVENTORY_GROUP_MAP.get(key);
if (CollectionUtils.isEmpty(invList)) {
return;
}
invList.removeIf(inv -> inventoryId.equals(inv.getId()));
if (invList.isEmpty()) {
INVENTORY_GROUP_MAP.remove(key);
}
} }
@Deprecated
public static Map<String, Inventory> getAll() {
// 兼容原有逻辑:维度Key → 第一个库存对象(仅临时兼容)
Map<String, Inventory> oldMap = new ConcurrentHashMap<>();
for (Map.Entry<String, List<Inventory>> entry : INVENTORY_GROUP_MAP.entrySet()) {
List<Inventory> invList = entry.getValue();
if (!CollectionUtils.isEmpty(invList)) {
oldMap.put(entry.getKey(), invList.get(0));
}
}
return oldMap;
}
} }
\ No newline at end of file
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论