mirror of https://github.com/jeecgboot/jeecg-boot
Merge pull request #125 from LQYBill/feat/purchaseOrderCreateFail
feat: purchase order result logspull/8040/head
commit
5bddfc27a4
|
@ -574,16 +574,17 @@ public class PurchaseOrderController {
|
|||
@GetMapping(value = "/createMabangPurchaseOrder")
|
||||
public Result<?> createMabangPurchaseOrder(@RequestParam("invoiceNumbers") List<String> invoiceNumbers) {
|
||||
log.info("Creating purchase order to Mabang for invoices : {} ", invoiceNumbers);
|
||||
Map<String, Responses> responsesMappedByInvoiceNumber = new HashMap<>();
|
||||
ExecutorService throttlingExecutorService = ThrottlingExecutorService.createExecutorService(DEFAULT_NUMBER_OF_THREADS,
|
||||
MABANG_API_RATE_LIMIT_PER_MINUTE, TimeUnit.MINUTES);
|
||||
// providersHistory lists the providers that have already been processed, if the current provider is in the list and has been processed within the last 10 seconds, the thread will sleep for 10 seconds
|
||||
AtomicReference<Map<String, LocalDateTime>> providersHistory = new AtomicReference<>(new HashMap<>());
|
||||
List<CompletableFuture<String>> future = invoiceNumbers.stream()
|
||||
List<CompletableFuture<Boolean>> future = invoiceNumbers.stream()
|
||||
.map(invoiceNumber -> CompletableFuture.supplyAsync(() -> {
|
||||
log.info("Invoice number : {}", invoiceNumber);
|
||||
List<SkuQuantity> skuQuantities = purchaseOrderService.getSkuQuantityByInvoiceNumber(invoiceNumber);
|
||||
if(skuQuantities.isEmpty()) {
|
||||
return null;
|
||||
return false;
|
||||
}
|
||||
Map<String, Integer> skuQuantityMap = skuQuantities.stream()
|
||||
.collect(Collectors.toMap(SkuQuantity::getErpCode, SkuQuantity::getQuantity));
|
||||
|
@ -592,30 +593,32 @@ public class PurchaseOrderController {
|
|||
.filter(entry -> entry.getValue() > 0)
|
||||
.collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
|
||||
InvoiceMetaData metaData = purchaseOrderService.getMetaDataFromInvoiceNumbers(invoiceNumber);
|
||||
List<String> errors = providerMabangService.addPurchaseOrderToMabang(skuQtyNotEmptyMap, metaData, providersHistory);
|
||||
return errors.isEmpty() ? invoiceNumber : errors.toString();
|
||||
Responses results = providerMabangService.addPurchaseOrderToMabang(skuQtyNotEmptyMap, metaData, providersHistory);
|
||||
if(responsesMappedByInvoiceNumber.get(invoiceNumber) != null) {
|
||||
responsesMappedByInvoiceNumber.get(invoiceNumber).getFailures().addAll(results.getFailures());
|
||||
responsesMappedByInvoiceNumber.get(invoiceNumber).getSuccesses().addAll(results.getSuccesses());
|
||||
} else {
|
||||
responsesMappedByInvoiceNumber.put(invoiceNumber, results);
|
||||
}
|
||||
return results.getFailures().isEmpty();
|
||||
},throttlingExecutorService))
|
||||
.collect(Collectors.toList());
|
||||
|
||||
List<String> results = future.stream().map(CompletableFuture::join).collect(Collectors.toList());
|
||||
long nbSuccesses = results.stream().filter(Invoice::isInvoiceNumber).count();
|
||||
List<Boolean> results = future.stream().map(CompletableFuture::join).collect(Collectors.toList());
|
||||
long nbSuccesses = results.stream().filter(Boolean::booleanValue).count();
|
||||
log.info("{}/{} purchase order requests have succeeded.", nbSuccesses, invoiceNumbers.size());
|
||||
|
||||
Map<String, List<String>> data = new HashMap<>();
|
||||
|
||||
List<String> failedInvoices = new ArrayList<>();
|
||||
List<String> successInvoices = new ArrayList<>();
|
||||
|
||||
results.forEach(result -> {
|
||||
if(isInvoiceNumber(result)) {
|
||||
successInvoices.add(result);
|
||||
} else {
|
||||
failedInvoices.add(result);
|
||||
List<String> groupIdsToDelete = new ArrayList<>();
|
||||
for(Map.Entry<String, Responses> entry : responsesMappedByInvoiceNumber.entrySet()) {
|
||||
if(!entry.getValue().getFailures().isEmpty()) {
|
||||
groupIdsToDelete.addAll(entry.getValue().getSuccesses());
|
||||
}
|
||||
});
|
||||
|
||||
data.put("fail", failedInvoices);
|
||||
data.put("success", successInvoices);
|
||||
return Result.OK(data);
|
||||
}
|
||||
if(!groupIdsToDelete.isEmpty()) {
|
||||
log.info("Deleting purchase orders that have been incompletely created in Mabang : {}", groupIdsToDelete);
|
||||
Responses groupIdsDeleteResult = providerMabangService.deletePurchaseOrderFromMabang(groupIdsToDelete);
|
||||
responsesMappedByInvoiceNumber.put("groupIdDelete", groupIdsDeleteResult);
|
||||
}
|
||||
return Result.OK(responsesMappedByInvoiceNumber);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
package org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase;
|
||||
|
||||
import org.jeecg.modules.business.domain.api.mabang.Request;
|
||||
|
||||
public class ChangePurchaseOrderRequest extends Request {
|
||||
public ChangePurchaseOrderRequest(ChangePurchaseOrderRequestBody body) {
|
||||
super(body);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChangePurchaseOrderResponse send() {
|
||||
String jsonString = rawSend().getBody();
|
||||
return ChangePurchaseOrderResponse.parse(jsonString);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,94 @@
|
|||
package org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase;
|
||||
|
||||
import com.alibaba.fastjson.JSONArray;
|
||||
import com.alibaba.fastjson.JSONObject;
|
||||
import org.jeecg.modules.business.domain.api.mabang.RequestBody;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Function;
|
||||
|
||||
public class ChangePurchaseOrderRequestBody implements RequestBody {
|
||||
private final String employeeName;
|
||||
private final String groupId;
|
||||
private final String actionType;
|
||||
private final String scrapOrder;
|
||||
|
||||
public ChangePurchaseOrderRequestBody(String employeeName, String groupId, String actionType, String scrapOrder) {
|
||||
this.employeeName = employeeName;
|
||||
this.groupId = groupId;
|
||||
this.actionType = actionType;
|
||||
this.scrapOrder = scrapOrder;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String api() {
|
||||
return "pur-do-change-purchase";
|
||||
}
|
||||
|
||||
@Override
|
||||
public JSONObject parameters() {
|
||||
JSONObject json = new JSONObject();
|
||||
putNonNull(json, "employeeName", employeeName);
|
||||
putNonNull(json, "groupId", groupId);
|
||||
putNonNull(json, "actionType", actionType);
|
||||
putNonNull(json, "scrapOrder", scrapOrder);
|
||||
return json;
|
||||
}
|
||||
|
||||
private <E> void putNonNull(JSONObject json, String key, E value) {
|
||||
if (value != null) {
|
||||
json.put(key, value);
|
||||
}
|
||||
}
|
||||
|
||||
private <E, T> void putNonNull(JSONObject json, String key, E value, Function<E, T> mapper) {
|
||||
if (value != null) {
|
||||
json.put(key, mapper.apply(value));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 操作类型:
|
||||
* 1标记完成采购单;
|
||||
* 2作废采购单;
|
||||
* 3修改采购单基础信息;
|
||||
* 4修改采购单商品信息;
|
||||
* 5添加采购单商品;
|
||||
* 6:修改采购单拓展属性(仅限“自定义分类”)
|
||||
*/
|
||||
public static enum ActionType {
|
||||
MARK_COMPLETE("1"),
|
||||
CANCEL("2"),
|
||||
CHANGE_BASIC_INFO("3"),
|
||||
CHANGE_PRODUCT_INFO("4"),
|
||||
ADD_PRODUCT("5"),
|
||||
CHANGE_EXPAND_PROPERTY("6");
|
||||
|
||||
private final String value;
|
||||
|
||||
ActionType(String value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
/**
|
||||
* 作废采购单商品类型:1.全部作废 2.部分作废 操作类型为2时必传
|
||||
*/
|
||||
public static enum ScrapOrder {
|
||||
ALL("1"),
|
||||
PART("2");
|
||||
|
||||
private final String value;
|
||||
|
||||
ScrapOrder(String value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
package org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.alibaba.fastjson.JSONObject;
|
||||
import lombok.Getter;
|
||||
import org.jeecg.modules.business.domain.api.mabang.Response;
|
||||
|
||||
@Getter
|
||||
public class ChangePurchaseOrderResponse extends Response {
|
||||
private final String message;
|
||||
|
||||
|
||||
private ChangePurchaseOrderResponse(Code status, String message) {
|
||||
super(status);
|
||||
this.message = message;
|
||||
}
|
||||
|
||||
public static ChangePurchaseOrderResponse parse(String json) {
|
||||
JSONObject jsonObject = JSON.parseObject(json);
|
||||
String code = jsonObject.getString("code");
|
||||
String message = jsonObject.getString("message");
|
||||
if (code.equals("200")) {
|
||||
return new ChangePurchaseOrderResponse(Code.SUCCESS, message);
|
||||
} else {
|
||||
return new ChangePurchaseOrderResponse(Code.ERROR, message);
|
||||
}
|
||||
}
|
||||
@Override
|
||||
public String toString() {
|
||||
return "AddPurchaseOrderResponse{" +
|
||||
"message='" + message + '\'' +
|
||||
'}';
|
||||
}
|
||||
}
|
|
@ -3,6 +3,7 @@ package org.jeecg.modules.business.service;
|
|||
import com.baomidou.mybatisplus.extension.service.IService;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoGetProvider.ProviderData;
|
||||
import org.jeecg.modules.business.vo.InvoiceMetaData;
|
||||
import org.jeecg.modules.business.vo.Responses;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
|
@ -17,5 +18,7 @@ public interface IProviderMabangService extends IService<ProviderData> {
|
|||
*/
|
||||
void saveProviderFromMabang(List<ProviderData> providerDataList);
|
||||
|
||||
List<String> addPurchaseOrderToMabang(Map<String, Integer> skuQuantities, InvoiceMetaData metaData, AtomicReference<Map<String, LocalDateTime>> providersHistory);
|
||||
Responses addPurchaseOrderToMabang(Map<String, Integer> skuQuantities, InvoiceMetaData metaData, AtomicReference<Map<String, LocalDateTime>> providersHistory);
|
||||
|
||||
Responses deletePurchaseOrderFromMabang(List<String> groupIds);
|
||||
}
|
||||
|
|
|
@ -9,6 +9,9 @@ import org.jeecg.modules.business.domain.api.mabang.purDoAddPurchase.AddPurchase
|
|||
import org.jeecg.modules.business.domain.api.mabang.purDoAddPurchase.AddPurchaseOrderRequestBody;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoAddPurchase.AddPurchaseOrderResponse;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoAddPurchase.SkuStockData;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase.ChangePurchaseOrderRequest;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase.ChangePurchaseOrderRequestBody;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase.ChangePurchaseOrderResponse;
|
||||
import org.jeecg.modules.business.domain.api.mabang.purDoGetProvider.ProviderData;
|
||||
import org.jeecg.modules.business.domain.job.ThrottlingExecutorService;
|
||||
import org.jeecg.modules.business.entity.Provider;
|
||||
|
@ -18,6 +21,7 @@ import org.jeecg.modules.business.service.IProviderService;
|
|||
import org.jeecg.modules.business.service.IPurchaseOrderService;
|
||||
import org.jeecg.modules.business.service.ISkuService;
|
||||
import org.jeecg.modules.business.vo.InvoiceMetaData;
|
||||
import org.jeecg.modules.business.vo.Responses;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
@ -33,6 +37,9 @@ import java.util.concurrent.TimeUnit;
|
|||
import java.util.concurrent.atomic.AtomicReference;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import static org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase.ChangePurchaseOrderRequestBody.ActionType.CANCEL;
|
||||
import static org.jeecg.modules.business.domain.api.mabang.purDoChangePurchase.ChangePurchaseOrderRequestBody.ScrapOrder.ALL;
|
||||
|
||||
/**
|
||||
* @Description: provider
|
||||
* @Author: jeecg-boot
|
||||
|
@ -76,9 +83,10 @@ public class ProviderMabangServiceImpl extends ServiceImpl<ProviderMabangMapper,
|
|||
*/
|
||||
@Transactional
|
||||
@Override
|
||||
public List<String> addPurchaseOrderToMabang(Map<String, Integer> skuQuantities, InvoiceMetaData metaData, AtomicReference<Map<String, LocalDateTime>> providersHistory) {
|
||||
public Responses addPurchaseOrderToMabang(Map<String, Integer> skuQuantities, InvoiceMetaData metaData, AtomicReference<Map<String, LocalDateTime>> providersHistory) {
|
||||
LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
|
||||
String mabangUsername = sysUser.getMabangUsername();
|
||||
Responses responses = new Responses();
|
||||
String content = metaData.getFilename();
|
||||
List<String> stockSkuList = new ArrayList<>();
|
||||
String stockSkus;
|
||||
|
@ -115,7 +123,8 @@ public class ProviderMabangServiceImpl extends ServiceImpl<ProviderMabangMapper,
|
|||
}
|
||||
if(skuDataList.isEmpty()) {
|
||||
log.error("Couldn't get SKU data from Mabang API for invoice : {}", metaData.getInvoiceCode());
|
||||
return Collections.singletonList("Couldn't get SKU data from Mabang API for invoice : " + metaData.getInvoiceCode());
|
||||
responses.addFailure("Couldn't get SKU data from Mabang API for invoice : " + metaData.getInvoiceCode());
|
||||
return responses;
|
||||
}
|
||||
|
||||
for(SkuData skuData : skuDataList) {
|
||||
|
@ -178,6 +187,7 @@ public class ProviderMabangServiceImpl extends ServiceImpl<ProviderMabangMapper,
|
|||
return false;
|
||||
}
|
||||
groupIds.add(response.getGroupId());
|
||||
responses.addSuccess(response.getGroupId());
|
||||
providersHistory.get().put(providerName, LocalDateTime.now());
|
||||
return true;
|
||||
}, throttlingExecutorService))
|
||||
|
@ -190,8 +200,37 @@ public class ProviderMabangServiceImpl extends ServiceImpl<ProviderMabangMapper,
|
|||
if(nbSuccesses == stockProviderMap.size()) {
|
||||
purchaseOrderService.updatePurchaseOrderStatus(metaData.getInvoiceCode(), true);
|
||||
purchaseOrderService.updatePurchaseOrderGroupIds(metaData.getInvoiceCode(), groupIds);
|
||||
return Collections.emptyList();
|
||||
}
|
||||
return errors;
|
||||
responses.setFailures(errors);
|
||||
return responses;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Responses deletePurchaseOrderFromMabang(List<String> groupIds) {
|
||||
LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
|
||||
String mabangUsername = sysUser.getMabangUsername();
|
||||
Responses groupIdsDeleteResult = new Responses();
|
||||
log.info("Deleting purchase orders from Mabang : {}", groupIds);
|
||||
// delete purchase order from Mabang via group_id
|
||||
ExecutorService throttlingExecutorService = ThrottlingExecutorService.createExecutorService(DEFAULT_NUMBER_OF_THREADS,
|
||||
MABANG_API_RATE_LIMIT_PER_MINUTE, TimeUnit.MINUTES);
|
||||
List<CompletableFuture<Boolean>> changeOrderFutures = groupIds.stream()
|
||||
.map(groupId -> CompletableFuture.supplyAsync(() -> {
|
||||
ChangePurchaseOrderRequestBody body = new ChangePurchaseOrderRequestBody(mabangUsername, groupId, CANCEL.getValue(), ALL.getValue());
|
||||
ChangePurchaseOrderRequest request = new ChangePurchaseOrderRequest(body);
|
||||
ChangePurchaseOrderResponse response = request.send();
|
||||
if(!response.success()) {
|
||||
log.error("Failed to delete purchase order from Mabang. GroupId : {} - Reason : {}", groupId, response.getMessage());
|
||||
groupIdsDeleteResult.addFailure(groupId);
|
||||
} else {
|
||||
groupIdsDeleteResult.addSuccess(groupId);
|
||||
}
|
||||
return response.success();
|
||||
}, throttlingExecutorService))
|
||||
.collect(Collectors.toList());
|
||||
List<Boolean> results = changeOrderFutures.stream().map(CompletableFuture::join).collect(Collectors.toList());
|
||||
long nbSuccesses = results.stream().filter(b -> b).count();
|
||||
log.info("{}/{} purchase orders deleted successfully from Mabang. GroupIds : {}", nbSuccesses, groupIds.size(), groupIds);
|
||||
return groupIdsDeleteResult;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue