mirror of https://github.com/jeecgboot/jeecg-boot
parent
556820e0e2
commit
58b11bac0b
|
@ -24,6 +24,7 @@ public class ChangeOrderRequestBody implements RequestBody {
|
||||||
|
|
||||||
private final static String DEFAULT_WAREHOUSE_NAME = "SZBA宝安仓";
|
private final static String DEFAULT_WAREHOUSE_NAME = "SZBA宝安仓";
|
||||||
|
|
||||||
|
@Getter
|
||||||
public enum OperationType {
|
public enum OperationType {
|
||||||
MODIFY(1),
|
MODIFY(1),
|
||||||
REMOVE(2),
|
REMOVE(2),
|
||||||
|
|
|
@ -0,0 +1,15 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.dochangeorder;
|
||||||
|
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.Request;
|
||||||
|
|
||||||
|
public class ChangeWarehouseRequest extends Request {
|
||||||
|
public ChangeWarehouseRequest(ChangeWarehouseRequestBody body) {
|
||||||
|
super(body);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ChangeOrderResponse send() {
|
||||||
|
String jsonString = rawSend().getBody();
|
||||||
|
return ChangeOrderResponse.parse(jsonString);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,75 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.dochangeorder;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.JSONArray;
|
||||||
|
import com.alibaba.fastjson.JSONObject;
|
||||||
|
import lombok.Getter;
|
||||||
|
import lombok.Setter;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.RequestBody;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.getorderlist.Order;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.getorderlist.OrderItem;
|
||||||
|
|
||||||
|
import java.util.function.Function;
|
||||||
|
|
||||||
|
import static org.jeecg.modules.business.domain.api.mabang.dochangeorder.ChangeOrderRequestBody.OperationType;
|
||||||
|
@Getter
|
||||||
|
@Setter
|
||||||
|
public class ChangeWarehouseRequestBody implements RequestBody {
|
||||||
|
private Order order;
|
||||||
|
private String platformOrderId;
|
||||||
|
private String warehouseName;
|
||||||
|
private String recipient;
|
||||||
|
private String street1;
|
||||||
|
private String street2;
|
||||||
|
|
||||||
|
public ChangeWarehouseRequestBody(Order order, String warehouseName) {
|
||||||
|
this.platformOrderId = order.getPlatformOrderId();
|
||||||
|
this.warehouseName = warehouseName;
|
||||||
|
this.recipient = order.getRecipient();
|
||||||
|
this.street1 = order.getAddress();
|
||||||
|
this.street2 = order.getAddress2();
|
||||||
|
this.order = order;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String api() {
|
||||||
|
return "order-do-change-order";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public JSONObject parameters() {
|
||||||
|
JSONObject json = new JSONObject();
|
||||||
|
JSONArray stockDataArray = new JSONArray();
|
||||||
|
putNonNull(json, "platformOrderId", platformOrderId);
|
||||||
|
putNonNull(json, "buyerName", recipient);
|
||||||
|
putNonNull(json, "street1", street1);
|
||||||
|
putNonNull(json, "street2", street2);
|
||||||
|
if(order.getOrderItems() != null && !order.getOrderItems().isEmpty()) {
|
||||||
|
for(OrderItem orderItem : order.getOrderItems()) {
|
||||||
|
if(!isSkuValidFormat(orderItem.getErpCode()))
|
||||||
|
continue;
|
||||||
|
JSONObject stockData = new JSONObject();
|
||||||
|
stockData.put("type", OperationType.MODIFY.getCode());
|
||||||
|
stockData.put("stockSku", orderItem.getErpCode());
|
||||||
|
stockData.put("warehouseName", warehouseName);
|
||||||
|
stockData.put("erpOrderItemId", orderItem.getErpOrderItemId());
|
||||||
|
stockDataArray.add(stockData);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
putNonNull(json, "stockData", stockDataArray.toJSONString());
|
||||||
|
return json;
|
||||||
|
}
|
||||||
|
private boolean isSkuValidFormat(String sku) {
|
||||||
|
return sku != null && !sku.matches("^[0-9]+$");
|
||||||
|
}
|
||||||
|
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));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -89,6 +89,16 @@ public class Order {
|
||||||
*/
|
*/
|
||||||
@JSONField(name = "postCode")
|
@JSONField(name = "postCode")
|
||||||
private String postcode;
|
private String postcode;
|
||||||
|
/**
|
||||||
|
* 买家地址1
|
||||||
|
*/
|
||||||
|
@JSONField(name = "street1")
|
||||||
|
private String address;
|
||||||
|
/**
|
||||||
|
* 买家地址2
|
||||||
|
*/
|
||||||
|
@JSONField(name = "street2")
|
||||||
|
private String address2;
|
||||||
/**
|
/**
|
||||||
* 税号
|
* 税号
|
||||||
*/
|
*/
|
||||||
|
@ -127,6 +137,10 @@ public class Order {
|
||||||
@TableField(exist = false)
|
@TableField(exist = false)
|
||||||
private List<OrderItem> orderItems;
|
private List<OrderItem> orderItems;
|
||||||
|
|
||||||
|
@JSONField(name = "orderTypeNew")
|
||||||
|
@TableField(exist = false)
|
||||||
|
private OrderTypeNew orderType;
|
||||||
|
|
||||||
@JSONField(name = "phone1")
|
@JSONField(name = "phone1")
|
||||||
private String phone1;
|
private String phone1;
|
||||||
|
|
||||||
|
|
|
@ -24,6 +24,11 @@ public class OrderItem {
|
||||||
@JSONField(name = "originOrderId")
|
@JSONField(name = "originOrderId")
|
||||||
private String originOrderId;
|
private String originOrderId;
|
||||||
|
|
||||||
|
@JSONField(name="erpOrderItemId")
|
||||||
|
private String erpOrderItemId;
|
||||||
|
@JSONField(name = "stockWarehouseName")
|
||||||
|
private String warehouseName;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 1 = 有货
|
* 1 = 有货
|
||||||
* 2 = 缺货
|
* 2 = 缺货
|
||||||
|
|
|
@ -0,0 +1,12 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.getorderlist;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.annotation.JSONField;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class OrderTypeLabel {
|
||||||
|
@JSONField(name = "typeId")
|
||||||
|
private String typeId;
|
||||||
|
@JSONField(name = "name")
|
||||||
|
private String name;
|
||||||
|
}
|
|
@ -0,0 +1,12 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.getorderlist;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.annotation.JSONField;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class OrderTypeNew {
|
||||||
|
@JSONField(name = "normalLabels")
|
||||||
|
private OrderTypeLabel[] normalLabels;
|
||||||
|
@JSONField(name = "abnormalLabels")
|
||||||
|
private OrderTypeLabel[] abnormalLabels;
|
||||||
|
}
|
|
@ -13,7 +13,7 @@ import java.util.function.Function;
|
||||||
public class OrderSuspendRequestBody implements RequestBody {
|
public class OrderSuspendRequestBody implements RequestBody {
|
||||||
|
|
||||||
private String platformOrderId;
|
private String platformOrderId;
|
||||||
private final String abnormal_label_name = "客户要求暂时不处理";
|
private String abnormal_label_name = "客户要求暂时不处理";
|
||||||
private String description;
|
private String description;
|
||||||
|
|
||||||
public OrderSuspendRequestBody(String platformOrderId, String description) {
|
public OrderSuspendRequestBody(String platformOrderId, String description) {
|
||||||
|
|
|
@ -0,0 +1,30 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.JSON;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.Request;
|
||||||
|
import org.springframework.http.ResponseEntity;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class contains some key information and necessary procedures
|
||||||
|
* to send a request to mabang "order-do-order-abnormal" API, for example: target URL,
|
||||||
|
* correspondent HTTP method, procedure to generate authorization.
|
||||||
|
* <p>
|
||||||
|
* One can use static method {@code sendRequest} to send request with body,
|
||||||
|
* and then get respective response. Or use instance of this class, see below.
|
||||||
|
* <p>
|
||||||
|
*/
|
||||||
|
@Slf4j
|
||||||
|
public class OrderToNormalRequest extends Request {
|
||||||
|
|
||||||
|
public OrderToNormalRequest(OrderToNormalRequestBody body) {
|
||||||
|
super(body);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public OrderToNormalResponse send() {
|
||||||
|
ResponseEntity<String> res = rawSend();
|
||||||
|
return OrderToNormalResponse.parse(JSON.parseObject(res.getBody()));
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,41 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.JSONObject;
|
||||||
|
import lombok.Getter;
|
||||||
|
import lombok.Setter;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.RequestBody;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.function.Function;
|
||||||
|
|
||||||
|
@Getter
|
||||||
|
@Setter
|
||||||
|
public class OrderToNormalRequestBody implements RequestBody {
|
||||||
|
|
||||||
|
private String platformOrderId;
|
||||||
|
|
||||||
|
public OrderToNormalRequestBody(String platformOrderId) {
|
||||||
|
this.platformOrderId = platformOrderId;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public String api() {
|
||||||
|
return "order-do-order-normal";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Map<String, Object> parameters() {
|
||||||
|
JSONObject json = new JSONObject();
|
||||||
|
putNonNull(json, "platformOrderId", platformOrderId);
|
||||||
|
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));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,11 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class represents error that is returned by target order-do-order-abnormal API
|
||||||
|
* Message will contain error details.
|
||||||
|
*/
|
||||||
|
public class OrderToNormalRequestErrorException extends RuntimeException {
|
||||||
|
public OrderToNormalRequestErrorException(String msg) {
|
||||||
|
super(msg);
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,45 @@
|
||||||
|
package org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.JSONObject;
|
||||||
|
import lombok.Getter;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.Response;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Immutable object
|
||||||
|
*/
|
||||||
|
@Slf4j
|
||||||
|
@Getter
|
||||||
|
public class OrderToNormalResponse extends Response {
|
||||||
|
private final String message;
|
||||||
|
|
||||||
|
OrderToNormalResponse(Code successCode, String message) {
|
||||||
|
super(successCode);
|
||||||
|
this.message = message;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Make an instance by parsing json, it only checks validity of code.
|
||||||
|
* if json is not valid, return null
|
||||||
|
*
|
||||||
|
* @param json the json to parse
|
||||||
|
* @return Instance
|
||||||
|
* @throws OrderToNormalRequestErrorException if response code represents error.
|
||||||
|
*/
|
||||||
|
public static OrderToNormalResponse parse(JSONObject json) throws OrderToNormalRequestErrorException {
|
||||||
|
log.debug("Constructing a response by json.");
|
||||||
|
String code = json.getString("code");
|
||||||
|
String message = json.getString("message");
|
||||||
|
if (code.equals("200"))
|
||||||
|
return new OrderToNormalResponse(Code.SUCCESS, message);
|
||||||
|
else
|
||||||
|
return new OrderToNormalResponse(Code.ERROR, message);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "OrderToNormalResponse{" +
|
||||||
|
", code=" + this.success() +
|
||||||
|
'}';
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,12 @@
|
||||||
|
package org.jeecg.modules.business.domain.job;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class ChangeWareHouseParam {
|
||||||
|
private String shop;
|
||||||
|
private List<String> skus;
|
||||||
|
private List<String> countries;
|
||||||
|
}
|
|
@ -0,0 +1,192 @@
|
||||||
|
package org.jeecg.modules.business.domain.job;
|
||||||
|
|
||||||
|
import com.google.common.collect.Lists;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.codehaus.jettison.json.JSONArray;
|
||||||
|
import org.codehaus.jettison.json.JSONException;
|
||||||
|
import org.codehaus.jettison.json.JSONObject;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.dochangeorder.*;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.getorderlist.*;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.orderDoOrderAbnormal.OrderSuspendRequest;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.orderDoOrderAbnormal.OrderSuspendRequestBody;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.orderDoOrderAbnormal.OrderSuspendResponse;
|
||||||
|
import org.jeecg.modules.business.service.IPlatformOrderService;
|
||||||
|
import org.jeecg.modules.business.vo.Responses;
|
||||||
|
import org.quartz.Job;
|
||||||
|
import org.quartz.JobDataMap;
|
||||||
|
import org.quartz.JobExecutionContext;
|
||||||
|
import org.quartz.JobExecutionException;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
|
||||||
|
import java.text.Normalizer;
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
import java.util.concurrent.ExecutorService;
|
||||||
|
import java.util.concurrent.Executors;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
import static java.util.stream.Collectors.toList;
|
||||||
|
|
||||||
|
@Slf4j
|
||||||
|
public class ChangeWarehouseJob implements Job {
|
||||||
|
@Autowired
|
||||||
|
private IPlatformOrderService platformOrderService;
|
||||||
|
|
||||||
|
private static final Integer DEFAULT_NUMBER_OF_DAYS = 5;
|
||||||
|
private static final Integer DEFAULT_NUMBER_OF_THREADS = 10;
|
||||||
|
private final String DEFAULT_WAREHOUSE_NAME = "法国巴黎仓库-唯客路";
|
||||||
|
private final String DEFAULT_ABNORMAL_LABEL_NAME = "AC海外仓非法国比利时不发货";
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void execute(JobExecutionContext context) throws JobExecutionException {
|
||||||
|
log.info("Executing ChangeWarehouseJob...");
|
||||||
|
LocalDateTime endDateTime = LocalDateTime.now();
|
||||||
|
LocalDateTime startDateTime = endDateTime.minusDays(DEFAULT_NUMBER_OF_DAYS);
|
||||||
|
List<String> allSkus = new ArrayList<>();
|
||||||
|
List<ChangeWareHouseParam> changeWareHouseParams = new ArrayList<>();
|
||||||
|
|
||||||
|
JobDataMap jobDataMap = context.getMergedJobDataMap();
|
||||||
|
String parameter = ((String) jobDataMap.get("parameter"));
|
||||||
|
if (parameter != null) {
|
||||||
|
try {
|
||||||
|
JSONObject jsonObject = new JSONObject(parameter);
|
||||||
|
if (!jsonObject.isNull("startDateTime")) {
|
||||||
|
String startDateStr = jsonObject.getString("startDateTime");
|
||||||
|
startDateTime = LocalDateTime.parse(startDateStr);
|
||||||
|
}
|
||||||
|
if (!jsonObject.isNull("endDateTime")) {
|
||||||
|
String endDateStr = jsonObject.getString("endDateTime");
|
||||||
|
endDateTime = LocalDateTime.parse(endDateStr);
|
||||||
|
}
|
||||||
|
if (!jsonObject.isNull("data")) {
|
||||||
|
JSONArray dataJsonArray = jsonObject.getJSONArray("data");
|
||||||
|
for (int i = 0; i < dataJsonArray.length(); i++) {
|
||||||
|
JSONObject object = dataJsonArray.getJSONObject(i);
|
||||||
|
ChangeWareHouseParam param = new ChangeWareHouseParam();
|
||||||
|
if(!object.isNull("shop")) {
|
||||||
|
param.setShop(object.getString("shop"));
|
||||||
|
}
|
||||||
|
if(!object.isNull("skus")) {
|
||||||
|
JSONArray skusJsonArray = object.getJSONArray("skus");
|
||||||
|
List<String> skus = new ArrayList<>();
|
||||||
|
for(int j = 0; j < skusJsonArray.length(); j++) {
|
||||||
|
skus.add(skusJsonArray.getString(j));
|
||||||
|
}
|
||||||
|
param.setSkus(skus);
|
||||||
|
allSkus.addAll(skus);
|
||||||
|
}
|
||||||
|
if(!object.isNull("countries")) {
|
||||||
|
List<String> countries = new ArrayList<>();
|
||||||
|
JSONArray countriesJsonArray = object.getJSONArray("countries");
|
||||||
|
for (int j = 0; j < countriesJsonArray.length(); j++) {
|
||||||
|
countries.add(countriesJsonArray.getString(j));
|
||||||
|
}
|
||||||
|
param.setCountries(countries);
|
||||||
|
}
|
||||||
|
changeWareHouseParams.add(param);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (JSONException e) {
|
||||||
|
log.error("Error while parsing parameter as JSON, falling back to default parameters.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!endDateTime.isAfter(startDateTime)) {
|
||||||
|
throw new RuntimeException("EndDateTime must be strictly greater than StartDateTime !");
|
||||||
|
}
|
||||||
|
ExecutorService executor = Executors.newFixedThreadPool(DEFAULT_NUMBER_OF_THREADS);
|
||||||
|
|
||||||
|
List<String> platformOrderIds = new ArrayList<>();
|
||||||
|
List<String> ordersToSetAbnormal = new ArrayList<>();
|
||||||
|
for(ChangeWareHouseParam param: changeWareHouseParams) {
|
||||||
|
List<String> poIds = platformOrderService.fetchUninvoicedOrdersWithSkusInCountry(startDateTime, endDateTime, param.getShop(), param.getSkus(), param.getCountries());
|
||||||
|
List<String> abnormalPoIds = platformOrderService.fetchUninvoicedOrdersWithSkusNotInCountry(startDateTime, endDateTime, param.getShop(), allSkus, param.getCountries());
|
||||||
|
platformOrderIds.addAll(poIds);
|
||||||
|
ordersToSetAbnormal.addAll(abnormalPoIds);
|
||||||
|
}
|
||||||
|
|
||||||
|
// fetch orders from mabang
|
||||||
|
log.info("Fetching orders from mabang...");
|
||||||
|
List<List<String>> platformOrderIdLists = Lists.partition(platformOrderIds, 10);
|
||||||
|
List<Order> mabangOrders = new ArrayList<>();
|
||||||
|
List<OrderListRequestBody> requests = new ArrayList<>();
|
||||||
|
for (List<String> platformOrderIdList : platformOrderIdLists) {
|
||||||
|
requests.add(new OrderListRequestBody().setPlatformOrderIds(platformOrderIdList));
|
||||||
|
}
|
||||||
|
List<CompletableFuture<Boolean>> completableFutures = requests.stream()
|
||||||
|
.map(request -> CompletableFuture.supplyAsync(() -> {
|
||||||
|
boolean success = false;
|
||||||
|
try {
|
||||||
|
OrderListRawStream rawStream = new OrderListRawStream(request);
|
||||||
|
OrderListStream stream = new OrderListStream(rawStream);
|
||||||
|
List<Order> orders = stream.all();
|
||||||
|
mabangOrders.addAll(orders);
|
||||||
|
success = !orders.isEmpty();
|
||||||
|
} catch (RuntimeException e) {
|
||||||
|
log.error("Error while fetching orders from mabang: {}", e.getMessage());
|
||||||
|
}
|
||||||
|
return success;
|
||||||
|
}, executor))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
List<Boolean> fetchResults = completableFutures.stream().map(CompletableFuture::join).collect(Collectors.toList());
|
||||||
|
long fetchSuccessCount = fetchResults.stream().filter(Boolean::booleanValue).count();
|
||||||
|
log.info("Successfully fetched {} out of {} orders from mabang.", fetchSuccessCount, fetchResults.size());
|
||||||
|
|
||||||
|
log.info("Updating recipients info...");
|
||||||
|
replaceOrdersAccents(mabangOrders);
|
||||||
|
|
||||||
|
log.info("Updating warehouse name...");
|
||||||
|
List<CompletableFuture<Boolean>> futures = mabangOrders.stream()
|
||||||
|
.map(order -> CompletableFuture.supplyAsync(() -> {
|
||||||
|
ChangeWarehouseRequestBody body = new ChangeWarehouseRequestBody(order, DEFAULT_WAREHOUSE_NAME);
|
||||||
|
ChangeWarehouseRequest request = new ChangeWarehouseRequest(body);
|
||||||
|
ChangeOrderResponse response = request.send();
|
||||||
|
return response.success();
|
||||||
|
}, executor))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
List<Boolean> results = futures.stream().map(CompletableFuture::join).collect(Collectors.toList());
|
||||||
|
long successCount = results.stream().filter(Boolean::booleanValue).count();
|
||||||
|
log.info("Successfully changed warehouse for {} out of {} orders.", successCount, results.size());
|
||||||
|
|
||||||
|
log.info("Setting orders to abnormal...");
|
||||||
|
Responses responses = new Responses();
|
||||||
|
List<CompletableFuture<Responses>> abnormalFutures = ordersToSetAbnormal.stream()
|
||||||
|
.map(id -> CompletableFuture.supplyAsync(() -> {
|
||||||
|
OrderSuspendRequestBody body = new OrderSuspendRequestBody(id, "");
|
||||||
|
body.setAbnormal_label_name(DEFAULT_ABNORMAL_LABEL_NAME);
|
||||||
|
OrderSuspendRequest request = new OrderSuspendRequest(body);
|
||||||
|
OrderSuspendResponse response = request.send();
|
||||||
|
Responses r = new Responses();
|
||||||
|
if(response.success())
|
||||||
|
r.addSuccess(id);
|
||||||
|
else
|
||||||
|
r.addFailure(id);
|
||||||
|
return r;
|
||||||
|
}, executor))
|
||||||
|
.collect(toList());
|
||||||
|
List<Responses> abnormalResults = abnormalFutures.stream()
|
||||||
|
.map(CompletableFuture::join)
|
||||||
|
.collect(toList());
|
||||||
|
abnormalResults.forEach(r -> {
|
||||||
|
responses.getSuccesses().addAll(r.getSuccesses());
|
||||||
|
responses.getFailures().addAll(r.getFailures());
|
||||||
|
});
|
||||||
|
log.info("Successfully set {}/{} orders to abnormal.", responses.getSuccesses().size(), ordersToSetAbnormal.size());
|
||||||
|
executor.shutdown();
|
||||||
|
}
|
||||||
|
public void replaceOrdersAccents(List<Order> orders) {
|
||||||
|
for(Order order: orders) {
|
||||||
|
order.setRecipient(stripAccents(order.getRecipient()));
|
||||||
|
order.setAddress(stripAccents(order.getAddress()));
|
||||||
|
order.setAddress2(stripAccents(order.getAddress2()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
public String stripAccents(String input) {
|
||||||
|
input = Normalizer.normalize(input, Normalizer.Form.NFD);
|
||||||
|
input = input.replaceAll("[^\\p{ASCII}]", "");
|
||||||
|
return input;
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,183 @@
|
||||||
|
package org.jeecg.modules.business.domain.job;
|
||||||
|
|
||||||
|
import com.google.common.collect.Lists;
|
||||||
|
import freemarker.template.Template;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.codehaus.jettison.json.JSONArray;
|
||||||
|
import org.codehaus.jettison.json.JSONException;
|
||||||
|
import org.codehaus.jettison.json.JSONObject;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.getorderlist.*;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal.OrderToNormalRequest;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal.OrderToNormalRequestBody;
|
||||||
|
import org.jeecg.modules.business.domain.api.mabang.orderDoOrderNormal.OrderToNormalResponse;
|
||||||
|
import org.jeecg.modules.business.entity.PlatformOrder;
|
||||||
|
import org.jeecg.modules.business.entity.PlatformOrderContent;
|
||||||
|
import org.jeecg.modules.business.service.EmailService;
|
||||||
|
import org.jeecg.modules.business.service.IPlatformOrderService;
|
||||||
|
import org.quartz.Job;
|
||||||
|
import org.quartz.JobDataMap;
|
||||||
|
import org.quartz.JobExecutionContext;
|
||||||
|
import org.quartz.JobExecutionException;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.core.env.Environment;
|
||||||
|
import org.springframework.ui.freemarker.FreeMarkerTemplateUtils;
|
||||||
|
import org.springframework.web.servlet.view.freemarker.FreeMarkerConfigurer;
|
||||||
|
|
||||||
|
import javax.mail.Authenticator;
|
||||||
|
import javax.mail.PasswordAuthentication;
|
||||||
|
import javax.mail.Session;
|
||||||
|
import java.time.LocalDate;
|
||||||
|
import java.util.*;
|
||||||
|
import java.util.concurrent.CompletableFuture;
|
||||||
|
import java.util.concurrent.ExecutorService;
|
||||||
|
import java.util.concurrent.Executors;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
@Slf4j
|
||||||
|
public class SetOrderToNormalJob implements Job {
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private EmailService emailService;
|
||||||
|
@Autowired
|
||||||
|
private IPlatformOrderService platformOrderService;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
Environment env;
|
||||||
|
@Autowired
|
||||||
|
private FreeMarkerConfigurer freemarkerConfigurer;
|
||||||
|
|
||||||
|
private static final Integer DEFAULT_NUMBER_OF_THREADS = 10;
|
||||||
|
private final String WAREHOUSE_NAME = "法国巴黎仓库-唯客路";
|
||||||
|
private final String ABNORMAL_LABEL_NAME = "自动创建SKU的订单";
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void execute(JobExecutionContext context) throws JobExecutionException {
|
||||||
|
log.info("Executing SetOrderToNormalJob...");
|
||||||
|
JobDataMap jobDataMap = context.getMergedJobDataMap();
|
||||||
|
String parameter = ((String) jobDataMap.get("parameter"));
|
||||||
|
|
||||||
|
List<String> skus = new ArrayList<>();
|
||||||
|
List<String> shops = new ArrayList<>();
|
||||||
|
if (parameter != null) {
|
||||||
|
try {
|
||||||
|
JSONObject jsonObject = new JSONObject(parameter);
|
||||||
|
if(!jsonObject.isNull("skus")) {
|
||||||
|
JSONArray skusJsonArray = jsonObject.getJSONArray("skus");
|
||||||
|
for (int i = 0; i < skusJsonArray.length(); i++) {
|
||||||
|
skus.add(skusJsonArray.getString(i));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(!jsonObject.isNull("shops")) {
|
||||||
|
JSONArray shopsJsonArray = jsonObject.getJSONArray("shops");
|
||||||
|
for (int i = 0; i < shopsJsonArray.length(); i++) {
|
||||||
|
shops.add(shopsJsonArray.getString(i));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (JSONException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
List<String> orderIds = platformOrderService.findReadyAbnormalOrders(skus, shops);
|
||||||
|
List<String> orderIdsWithSkus = platformOrderService.findReadyAbnormalOrdersWithSkus(skus);
|
||||||
|
List<String> orderReadyWithSkus = orderIds.stream()
|
||||||
|
.filter(orderIdsWithSkus::contains)
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
if(!orderReadyWithSkus.isEmpty()) {
|
||||||
|
Map<PlatformOrder, List<PlatformOrderContent>> orderContents = platformOrderService.fetchOrderData(orderReadyWithSkus);
|
||||||
|
// Remove orders that contains sku from "skus" list and have wrong warehouse
|
||||||
|
for(Map.Entry<PlatformOrder, List<PlatformOrderContent>> entry : orderContents.entrySet()) {
|
||||||
|
for(PlatformOrderContent content : entry.getValue()) {
|
||||||
|
if(!content.getWarehouseName().equals(WAREHOUSE_NAME)) {
|
||||||
|
orderIds.remove(content.getPlatformOrderId());
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ExecutorService executor = Executors.newFixedThreadPool(DEFAULT_NUMBER_OF_THREADS);
|
||||||
|
|
||||||
|
List<String> platform_order_ids = platformOrderService.listByIds(orderIds).stream()
|
||||||
|
.map(PlatformOrder::getPlatformOrderId)
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
List<Order> mabangOrders = new ArrayList<>();
|
||||||
|
|
||||||
|
List<List<String>> partitionedPlatformOrderIds = Lists.partition(platform_order_ids, 10);
|
||||||
|
List<OrderListRequestBody> requests = new ArrayList<>();
|
||||||
|
for (List<String> platformOrderIdList : partitionedPlatformOrderIds) {
|
||||||
|
requests.add(new OrderListRequestBody().setPlatformOrderIds(platformOrderIdList));
|
||||||
|
}
|
||||||
|
// Fetch orders from mabang
|
||||||
|
List<CompletableFuture<Boolean>> mabangFutures = requests.stream()
|
||||||
|
.map(request -> CompletableFuture.supplyAsync(() -> {
|
||||||
|
boolean success = false;
|
||||||
|
OrderListRawStream rawStream = new OrderListRawStream(request);
|
||||||
|
OrderListStream stream = new OrderListStream(rawStream);
|
||||||
|
List<Order> orders = stream.all();
|
||||||
|
mabangOrders.addAll(orders);
|
||||||
|
success = !orders.isEmpty();
|
||||||
|
return success;
|
||||||
|
}, executor))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
List<Boolean> fetchResults = mabangFutures.stream().map(CompletableFuture::join).collect(Collectors.toList());
|
||||||
|
long fetchSuccessCount = fetchResults.stream().filter(Boolean::booleanValue).count();
|
||||||
|
log.info("Successfully fetched {} out of {} orders groups from mabang.", fetchSuccessCount, fetchResults.size());
|
||||||
|
|
||||||
|
List<String> poIdsToSetNormal = new ArrayList<>();
|
||||||
|
if(!mabangOrders.isEmpty()) {
|
||||||
|
for(Order order : mabangOrders) {
|
||||||
|
OrderTypeLabel[] labels = order.getOrderType().getAbnormalLabels();
|
||||||
|
if(labels.length > 1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if(labels[0].getName().equals(ABNORMAL_LABEL_NAME)) {
|
||||||
|
poIdsToSetNormal.add(order.getPlatformOrderId());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
List<CompletableFuture<Boolean>> futures = poIdsToSetNormal.stream()
|
||||||
|
.map(orderId -> CompletableFuture.supplyAsync(() -> {
|
||||||
|
log.info("Setting order {} to normal", orderId);
|
||||||
|
OrderToNormalRequestBody requestBody = new OrderToNormalRequestBody(orderId);
|
||||||
|
OrderToNormalRequest request = new OrderToNormalRequest(requestBody);
|
||||||
|
OrderToNormalResponse response = request.send();
|
||||||
|
return response.success();
|
||||||
|
}, executor))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
List<Boolean> results = futures.stream()
|
||||||
|
.map(CompletableFuture::join)
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
long successCount = results.stream().filter(Boolean::booleanValue).count();
|
||||||
|
log.info("Successfully set {}/{} orders to normal", successCount, poIdsToSetNormal.size());
|
||||||
|
|
||||||
|
executor.shutdown();
|
||||||
|
|
||||||
|
// send list of order ids by mail
|
||||||
|
if(!poIdsToSetNormal.isEmpty()) {
|
||||||
|
String subject = "[" + LocalDate.now() + "] Set Orders To Normal Job Report";
|
||||||
|
String destEmail = env.getProperty("spring.mail.username");
|
||||||
|
Properties prop = emailService.getMailSender();
|
||||||
|
Map<String, Object> templateModel = new HashMap<>();
|
||||||
|
templateModel.put("orderIds", poIdsToSetNormal);
|
||||||
|
templateModel.put("count", poIdsToSetNormal.size());
|
||||||
|
Session session = Session.getInstance(prop, new Authenticator() {
|
||||||
|
@Override
|
||||||
|
protected PasswordAuthentication getPasswordAuthentication() {
|
||||||
|
return new PasswordAuthentication(env.getProperty("spring.mail.username"), env.getProperty("spring.mail.password"));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
try {
|
||||||
|
freemarkerConfigurer = emailService.freemarkerClassLoaderConfig();
|
||||||
|
Template freemarkerTemplate = freemarkerConfigurer.getConfiguration()
|
||||||
|
.getTemplate("admin/ordersSetToNormalJobReport.ftl");
|
||||||
|
String htmlBody = FreeMarkerTemplateUtils.processTemplateIntoString(freemarkerTemplate, templateModel);
|
||||||
|
emailService.sendSimpleMessage(destEmail, subject, htmlBody, session);
|
||||||
|
log.info("Mail sent successfully !");
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("Error while sending Set Orders To Normal Job report mail !");
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -139,6 +139,12 @@ public class PlatformOrderContent implements Serializable {
|
||||||
@Excel(name = "商品多属性", width = 15)
|
@Excel(name = "商品多属性", width = 15)
|
||||||
@ApiModelProperty(value = "商品多属性")
|
@ApiModelProperty(value = "商品多属性")
|
||||||
private java.lang.String customizationData;
|
private java.lang.String customizationData;
|
||||||
|
/**
|
||||||
|
* 仓库
|
||||||
|
*/
|
||||||
|
@Excel(name = "Warehouse name", width = 15)
|
||||||
|
@ApiModelProperty(value = "添加的商品仓库")
|
||||||
|
private String warehouseName;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
|
|
|
@ -224,4 +224,11 @@ public interface PlatformOrderMapper extends BaseMapper<PlatformOrder> {
|
||||||
void anonymizePersonalData(@Param("period") int indirectClientAnonymizationPeriod);
|
void anonymizePersonalData(@Param("period") int indirectClientAnonymizationPeriod);
|
||||||
|
|
||||||
List<PlatformOrderOption> ordersByShop(@Param("shopID") String shopID);
|
List<PlatformOrderOption> ordersByShop(@Param("shopID") String shopID);
|
||||||
|
|
||||||
|
List<String> fetchUninvoicedOrdersWithSkusInCountry(@Param("startDate") LocalDateTime startDateTime, @Param("endDate") LocalDateTime endDateTime, @Param("shop") String shop, @Param("skus") List<String> skus, @Param("countries") List<String> countries);
|
||||||
|
List<String> fetchUninvoicedOrdersWithSkusNotInCountry(@Param("startDate") LocalDateTime startDateTime, @Param("endDate") LocalDateTime endDateTime, @Param("shop") String shop, @Param("skus") List<String> skus, @Param("countries") List<String> countries);
|
||||||
|
|
||||||
|
List<String> findReadyAbnormalOrders(@Param("skus") List<String> skus, @Param("shops") List<String> shops);
|
||||||
|
|
||||||
|
List<String> findReadyAbnormalOrdersWithSkus(@Param("skus") List<String> skus);
|
||||||
}
|
}
|
||||||
|
|
|
@ -195,14 +195,14 @@
|
||||||
INSERT INTO platform_order_content(
|
INSERT INTO platform_order_content(
|
||||||
id, create_by, create_time,
|
id, create_by, create_time,
|
||||||
update_by, update_time, platform_order_id,
|
update_by, update_time, platform_order_id,
|
||||||
sku_id, quantity, erp_status, product_available, customization_data)
|
sku_id, quantity, erp_status, product_available, customization_data, warehouse_name)
|
||||||
VALUES
|
VALUES
|
||||||
<foreach collection="items" separator="," open="" close="" item="item" index="index">
|
<foreach collection="items" separator="," open="" close="" item="item" index="index">
|
||||||
(
|
(
|
||||||
UUID(), 'Mabang API', NOW(),
|
UUID(), 'Mabang API', NOW(),
|
||||||
'Mabang API', NOW(), #{item.platformOrderId},
|
'Mabang API', NOW(), #{item.platformOrderId},
|
||||||
skuErpToId(#{item.erpCode}), #{item.quantity}, #{item.erpStatus},
|
skuErpToId(#{item.erpCode}), #{item.quantity}, #{item.erpStatus},
|
||||||
#{item.productAvailable}, #{item.specifics})
|
#{item.productAvailable}, #{item.specifics}, #{item.warehouseName})
|
||||||
</foreach>
|
</foreach>
|
||||||
</insert>
|
</insert>
|
||||||
|
|
||||||
|
|
|
@ -898,4 +898,170 @@
|
||||||
WHERE shop_id = #{shopID}
|
WHERE shop_id = #{shopID}
|
||||||
AND erp_status IN (1,2,3)
|
AND erp_status IN (1,2,3)
|
||||||
</select>
|
</select>
|
||||||
|
<select id="fetchUninvoicedOrdersWithSkusInCountry" resultType="java.lang.String">
|
||||||
|
SELECT po.platform_order_id
|
||||||
|
FROM platform_order po
|
||||||
|
JOIN shop ON po.shop_id = shop.id
|
||||||
|
JOIN country c ON po.country = c.name_en
|
||||||
|
JOIN platform_order_content poc ON po.id = poc.platform_order_id
|
||||||
|
JOIN sku s ON poc.sku_id = s.id
|
||||||
|
WHERE po.erp_status IN (1,2)
|
||||||
|
AND po.can_send = 2
|
||||||
|
AND c.code IN
|
||||||
|
<foreach
|
||||||
|
collection="countries"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="country"
|
||||||
|
>
|
||||||
|
#{country}
|
||||||
|
</foreach>
|
||||||
|
AND shop.erp_code = #{shop}
|
||||||
|
AND s.erp_code IN
|
||||||
|
<foreach
|
||||||
|
collection="skus"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="sku"
|
||||||
|
>
|
||||||
|
#{sku}
|
||||||
|
</foreach>
|
||||||
|
AND order_time >= #{startDate}
|
||||||
|
AND order_time <= #{endDate}
|
||||||
|
AND shipping_invoice_number IS NULL;
|
||||||
|
</select>
|
||||||
|
<select id="fetchUninvoicedOrdersWithSkusNotInCountry" resultType="java.lang.String">
|
||||||
|
SELECT po.platform_order_id
|
||||||
|
FROM platform_order po
|
||||||
|
JOIN shop ON po.shop_id = shop.id
|
||||||
|
JOIN country c ON po.country = c.name_en
|
||||||
|
JOIN platform_order_content poc ON po.id = poc.platform_order_id
|
||||||
|
JOIN sku s ON poc.sku_id = s.id
|
||||||
|
WHERE po.erp_status IN (1,2)
|
||||||
|
AND po.can_send = 2
|
||||||
|
AND c.code NOT IN
|
||||||
|
<foreach
|
||||||
|
collection="countries"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="country"
|
||||||
|
>
|
||||||
|
#{country}
|
||||||
|
</foreach>
|
||||||
|
AND shop.erp_code = #{shop}
|
||||||
|
AND s.erp_code IN
|
||||||
|
<foreach
|
||||||
|
collection="skus"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="sku"
|
||||||
|
>
|
||||||
|
#{sku}
|
||||||
|
</foreach>
|
||||||
|
AND order_time >= #{startDate}
|
||||||
|
AND order_time <= #{endDate}
|
||||||
|
AND shipping_invoice_number IS NULL;
|
||||||
|
</select>
|
||||||
|
<select id="findReadyAbnormalOrders" resultType="java.lang.String">
|
||||||
|
WITH skusInAbnormalOrders AS (
|
||||||
|
SELECT poc.sku_id , poc.platform_order_id, poc.erp_status
|
||||||
|
FROM platform_order po
|
||||||
|
JOIN platform_order_content poc ON po.id = poc.platform_order_id
|
||||||
|
JOIN shop s ON po.shop_id = s.id
|
||||||
|
WHERE can_send = 2
|
||||||
|
AND po.erp_status IN (1,2)
|
||||||
|
AND po.order_time >= NOW() - INTERVAL 5 DAY
|
||||||
|
AND s.erp_code IN
|
||||||
|
<foreach
|
||||||
|
collection="shops"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="shop">
|
||||||
|
#{shop}
|
||||||
|
</foreach>
|
||||||
|
),
|
||||||
|
orders_with_bad_sku AS (
|
||||||
|
SELECT DISTINCT
|
||||||
|
CASE
|
||||||
|
WHEN s.id IS NULL AND sao.erp_status <> 5 THEN sao.platform_order_id
|
||||||
|
END as order_id
|
||||||
|
FROM skusInAbnormalOrders sao
|
||||||
|
LEFT JOIN sku s ON sao.sku_id = s.id
|
||||||
|
),
|
||||||
|
ac_orders AS (
|
||||||
|
SELECT DISTINCT poc.platform_order_id as id
|
||||||
|
FROM platform_order_content poc
|
||||||
|
JOIN sku s ON poc.sku_id = s.id
|
||||||
|
JOIN platform_order po ON poc.platform_order_id = po.id
|
||||||
|
WHERE po.can_send IN (1,2)
|
||||||
|
AND po.can_send = 2
|
||||||
|
AND po.order_time >= NOW() - INTERVAL 5 DAY
|
||||||
|
AND s.erp_code IN
|
||||||
|
<foreach
|
||||||
|
collection="skus"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="sku">
|
||||||
|
#{sku}
|
||||||
|
</foreach>
|
||||||
|
AND poc.erp_status <> 5
|
||||||
|
AND poc.warehouse_name != '法国巴黎仓库-唯客路'
|
||||||
|
),
|
||||||
|
orders_ready AS (
|
||||||
|
SELECT po.id as id
|
||||||
|
FROM platform_order po
|
||||||
|
JOIN shop s ON po.shop_id = s.id
|
||||||
|
LEFT JOIN orders_with_bad_sku owbs ON po.id = owbs.order_id
|
||||||
|
WHERE owbs.order_id IS NULL
|
||||||
|
AND po.erp_status IN (1,2)
|
||||||
|
AND po.can_send = 2
|
||||||
|
AND po.order_time >= NOW() - INTERVAL 5 DAY
|
||||||
|
AND s.erp_code IN
|
||||||
|
<foreach
|
||||||
|
collection="shops"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="shop">
|
||||||
|
#{shop}
|
||||||
|
</foreach>
|
||||||
|
)
|
||||||
|
SELECT ors.id
|
||||||
|
FROM orders_ready ors
|
||||||
|
WHERE ors.id NOT IN (SELECT * FROM ac_orders);
|
||||||
|
</select>
|
||||||
|
<select id="findReadyAbnormalOrdersWithSkus" resultType="java.lang.String">
|
||||||
|
SELECT DISTINCT poc.platform_order_id
|
||||||
|
FROM platform_order_content poc
|
||||||
|
JOIN sku s ON poc.sku_id = s.id
|
||||||
|
JOIN platform_order po ON poc.platform_order_id = po.id
|
||||||
|
WHERE po.can_send IN (1,2)
|
||||||
|
AND po.can_send = 2
|
||||||
|
AND po.order_time >= NOW() - INTERVAL 5 DAY
|
||||||
|
AND s.erp_code IN
|
||||||
|
<foreach
|
||||||
|
collection="skus"
|
||||||
|
separator=","
|
||||||
|
open="("
|
||||||
|
close=")"
|
||||||
|
index="index"
|
||||||
|
item="sku">
|
||||||
|
#{sku}
|
||||||
|
</foreach>
|
||||||
|
AND poc.erp_status <> 5
|
||||||
|
AND poc.warehouse_name = '法国巴黎仓库-唯客路';
|
||||||
|
</select>
|
||||||
</mapper>
|
</mapper>
|
||||||
|
|
|
@ -248,4 +248,11 @@ public interface IPlatformOrderService extends IService<PlatformOrder> {
|
||||||
void anonymizePersonalData(int indirectClientAnonymizationPeriod);
|
void anonymizePersonalData(int indirectClientAnonymizationPeriod);
|
||||||
|
|
||||||
List<PlatformOrderOption> ordersByShop(String shopID);
|
List<PlatformOrderOption> ordersByShop(String shopID);
|
||||||
|
|
||||||
|
List<String> fetchUninvoicedOrdersWithSkusInCountry(LocalDateTime startDateTime, LocalDateTime endDateTime, String shop, List<String> skus, List<String> countries);
|
||||||
|
List<String> fetchUninvoicedOrdersWithSkusNotInCountry(LocalDateTime startDateTime, LocalDateTime endDateTime, String shop, List<String> skus, List<String> countries);
|
||||||
|
|
||||||
|
List<String> findReadyAbnormalOrders(List<String> skus, List<String> shops);
|
||||||
|
|
||||||
|
List<String> findReadyAbnormalOrdersWithSkus(List<String> skus);
|
||||||
}
|
}
|
||||||
|
|
|
@ -501,4 +501,23 @@ public class PlatformOrderServiceImpl extends ServiceImpl<PlatformOrderMapper, P
|
||||||
public List<PlatformOrderOption> ordersByShop(String shopID) {
|
public List<PlatformOrderOption> ordersByShop(String shopID) {
|
||||||
return platformOrderMap.ordersByShop(shopID);
|
return platformOrderMap.ordersByShop(shopID);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<String> fetchUninvoicedOrdersWithSkusInCountry(LocalDateTime startDateTime, LocalDateTime endDateTime, String shop, List<String> skus, List<String> countries) {
|
||||||
|
return platformOrderMap.fetchUninvoicedOrdersWithSkusInCountry(startDateTime, endDateTime, shop, skus, countries);
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public List<String> fetchUninvoicedOrdersWithSkusNotInCountry(LocalDateTime startDateTime, LocalDateTime endDateTime, String shop, List<String> skus, List<String> countries) {
|
||||||
|
return platformOrderMap.fetchUninvoicedOrdersWithSkusNotInCountry(startDateTime, endDateTime, shop, skus, countries);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<String> findReadyAbnormalOrders(List<String> skus, List<String> shops) {
|
||||||
|
return platformOrderMap.findReadyAbnormalOrders(skus, shops);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<String> findReadyAbnormalOrdersWithSkus(List<String> skus) {
|
||||||
|
return platformOrderMap.findReadyAbnormalOrdersWithSkus(skus);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,17 @@
|
||||||
|
<#include "../components/header.ftl">
|
||||||
|
<tr>
|
||||||
|
<td style="padding:35px 0;">Cher Collègue</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td style="padding:0 0 35px 0;">Voici la liste des commandes dont le status a été mis à jour à "Normal" :</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td style="padding:10px 0;">Nombre de commandes :<b> ${count}</b><br/>
|
||||||
|
<ul>
|
||||||
|
<#list orderIds as orderId>
|
||||||
|
<li>${orderId}</li>
|
||||||
|
</#list>
|
||||||
|
</ul>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<#include "../components/footer.ftl">
|
Loading…
Reference in New Issue