|
@@ -0,0 +1,212 @@
|
|
|
+package com.fjhx.victoriatourist.service.jd.impl;
|
|
|
+
|
|
|
+import cn.hutool.core.bean.BeanUtil;
|
|
|
+import cn.hutool.core.util.ObjectUtil;
|
|
|
+import com.alibaba.fastjson2.JSONObject;
|
|
|
+import com.fjhx.victoriatourist.entity.jd.po.JdOrder;
|
|
|
+import com.fjhx.victoriatourist.service.jd.JdApiService;
|
|
|
+import com.fjhx.victoriatourist.service.jd.JdOrderService;
|
|
|
+import com.jd.open.api.sdk.DefaultJdClient;
|
|
|
+import com.jd.open.api.sdk.JdClient;
|
|
|
+import com.jd.open.api.sdk.domain.supplier.PoQueryForJosWebService.response.getpurchaseorderlist.JOSOrderResultDto;
|
|
|
+import com.jd.open.api.sdk.domain.supplier.PoQueryForJosWebService.response.getpurchaseorderlist.PurchaseOrderDto;
|
|
|
+import com.jd.open.api.sdk.request.supplier.VcGetdetailbyorderidRequest;
|
|
|
+import com.jd.open.api.sdk.request.supplier.VcGetpurchaseorderlistRequest;
|
|
|
+import com.jd.open.api.sdk.response.supplier.VcGetdetailbyorderidResponse;
|
|
|
+import com.jd.open.api.sdk.response.supplier.VcGetpurchaseorderlistResponse;
|
|
|
+import com.ruoyi.framework.mybatis.holder.TenantHolder;
|
|
|
+import com.ruoyi.system.utils.ConfigUtil;
|
|
|
+import lombok.extern.slf4j.Slf4j;
|
|
|
+import org.apache.commons.io.IOUtils;
|
|
|
+import org.apache.http.HttpEntity;
|
|
|
+import org.apache.http.HttpResponse;
|
|
|
+import org.apache.http.client.HttpClient;
|
|
|
+import org.apache.http.client.config.RequestConfig;
|
|
|
+import org.apache.http.client.methods.HttpGet;
|
|
|
+import org.apache.http.client.methods.HttpRequestBase;
|
|
|
+import org.apache.http.impl.client.HttpClients;
|
|
|
+import org.springframework.beans.factory.annotation.Autowired;
|
|
|
+import org.springframework.stereotype.Service;
|
|
|
+
|
|
|
+import java.io.IOException;
|
|
|
+import java.nio.charset.StandardCharsets;
|
|
|
+import java.text.SimpleDateFormat;
|
|
|
+import java.util.ArrayList;
|
|
|
+import java.util.Calendar;
|
|
|
+import java.util.Date;
|
|
|
+import java.util.List;
|
|
|
+import java.util.stream.Collectors;
|
|
|
+
|
|
|
+@Slf4j
|
|
|
+@Service
|
|
|
+public class JdApiServiceImpl implements JdApiService {
|
|
|
+
|
|
|
+ private static final SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
|
|
|
+
|
|
|
+ private static final String appKey = "ECCD5CE82A501C7E0D8BB41C030C447D";
|
|
|
+ private static final String appSecret = "5b55c3f3eb874b0d8746ff28e7f91f64";
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ private JdOrderService jdOrderService;
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 获取AccessToken
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public void getAccessTokenByCode(String code) {
|
|
|
+ if (ObjectUtil.isEmpty(code)) {
|
|
|
+ log.error("获取AccessToken失败:code不能为空");
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ //获取AccessToken并存入数据库
|
|
|
+ String path = "https://open-oauth.jd.com/oauth2/access_token?app_key=%s&app_secret=%s&grant_type=authorization_code&code=%s";
|
|
|
+ path = String.format(path, appKey, appSecret, code);
|
|
|
+ try {
|
|
|
+ JSONObject responseJson = getJSON(new HttpGet(path));
|
|
|
+ if (ObjectUtil.isNotEmpty(responseJson.getString("access_token")) && ObjectUtil.isNotEmpty(responseJson.getString("refresh_token"))) {
|
|
|
+ log.info("成功获取AccessToken并保存" + responseJson);
|
|
|
+ ConfigUtil.set("jd_token_json", responseJson.toString());
|
|
|
+ } else {
|
|
|
+ log.error("获取AccessToken失败:" + responseJson);
|
|
|
+ }
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("获取AccessToken出错:" + e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 刷新Token
|
|
|
+ */
|
|
|
+ private void refreshToken() {
|
|
|
+ String jdTokenJsonStr = ConfigUtil.get("jd_token_json");
|
|
|
+ if (ObjectUtil.isEmpty(jdTokenJsonStr)) {
|
|
|
+ log.error("jd_token_json为空无法刷新Token请检查");
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ JSONObject jdTokenJson = JSONObject.parseObject(jdTokenJsonStr);
|
|
|
+ if (ObjectUtil.isEmpty(jdTokenJson.get("refresh_token"))) {
|
|
|
+ log.error("refresh_token为空无法刷新Token请检查");
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ String path = "https://open-oauth.jd.com/oauth2/refresh_token?app_key=%s&app_secret=%s&grant_type=refresh_token&refresh_token=%s";
|
|
|
+ path = String.format(path, appKey, appSecret, jdTokenJson.get("refresh_token"));
|
|
|
+ try {
|
|
|
+ JSONObject responseJson = getJSON(new HttpGet(path));
|
|
|
+ if (ObjectUtil.isNotEmpty(responseJson.getString("access_token")) && ObjectUtil.isNotEmpty(responseJson.getString("refresh_token"))) {
|
|
|
+ log.info("成功刷新AccessToken并保存" + responseJson);
|
|
|
+ ConfigUtil.set("jd_token_json", responseJson.toString());
|
|
|
+ } else {
|
|
|
+ log.error("刷新AccessToken失败:" + responseJson);
|
|
|
+ }
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("刷新AccessToken出错:" + e.getMessage(), e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+// @PostConstruct//项目启动时运行一次
|
|
|
+// @Scheduled(cron = "0 0/1 * * * ? ")// 每1分钟执行一次
|
|
|
+ void orderSync() throws Exception {
|
|
|
+
|
|
|
+// JSONObject jdTokenJson = JSONObject.parseObject(ConfigUtil.get("jd_token_json"));
|
|
|
+ JSONObject jdTokenJson = JSONObject.parseObject("{\"access_token\":\"eaea297f24944a1e9f88de4ef9f67605lyti\",\"expires_in\":86399,\"refresh_token\":\"d42c559aed09415aacd32df4c5712711yyzu\",\"scope\":\"snsapi_base\",\"open_id\":\"CqJo6jtBlMczlbw1LWVshD1Re_qBaw6BLQSYQWPPNKs\",\"uid\":\"0063800318\",\"time\":1699422692835,\"token_type\":\"bearer\",\"code\":0,\"xid\":\"o*AAQrc1AbQq2SNpnAmdEFbwM-ZGU3ZUdz2_M6Wu3p3d_-3U273S4pUQYjFXGrDJzp3YTAVN4R\"}");
|
|
|
+ if (ObjectUtil.isEmpty(jdTokenJson)) {
|
|
|
+ log.error("京东token详细为空请检查");
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ JdClient client = new DefaultJdClient("http://api.jd.com/routerjson", jdTokenJson.getString("access_token"), appKey, appSecret);
|
|
|
+
|
|
|
+ //获取开始同步的时间
|
|
|
+ Date startTime = sdf.parse("2023-11-01 00:00:00");
|
|
|
+ TenantHolder.setIgnore(true);//忽略租户
|
|
|
+ JdOrder lastJdOrder = jdOrderService.getOne(q -> q.isNotNull(JdOrder::getCreatedDate).orderByDesc(JdOrder::getCreatedDate));
|
|
|
+ TenantHolder.clear();
|
|
|
+ if (ObjectUtil.isNotEmpty(lastJdOrder)) {
|
|
|
+ //将最后一个下单时间减1个小时设置为开始时间
|
|
|
+ Calendar calendar = Calendar.getInstance();
|
|
|
+ calendar.setTime(lastJdOrder.getCreatedDate());
|
|
|
+ calendar.add(Calendar.HOUR_OF_DAY, -1);
|
|
|
+
|
|
|
+ startTime = calendar.getTime();
|
|
|
+ }
|
|
|
+
|
|
|
+ Date endTime = new Date();
|
|
|
+
|
|
|
+ Integer recordCount = getJdOrderInfo(1, 1, startTime, endTime, client).getRecordCount();
|
|
|
+
|
|
|
+ int pageSize = 50;
|
|
|
+ int pageCount = (recordCount + pageSize - 1) / pageSize;
|
|
|
+
|
|
|
+ List<PurchaseOrderDto> purchaseOrderList = new ArrayList<>();
|
|
|
+ //数据返回订单是倒序反过来按正顺保存
|
|
|
+ for (int i = pageCount; i > 0; i--) {
|
|
|
+ JOSOrderResultDto josOrderResultDto = getJdOrderInfo(i, pageSize, startTime, endTime, client);
|
|
|
+ purchaseOrderList.addAll(josOrderResultDto.getPurchaseOrderList());
|
|
|
+ }
|
|
|
+
|
|
|
+ //处理数据(过滤已存在的数据)
|
|
|
+ List<Long> jdOrderIds = purchaseOrderList.stream().map(PurchaseOrderDto::getOrderId).collect(Collectors.toList());
|
|
|
+ TenantHolder.setIgnore(true);//忽略租户
|
|
|
+ //获取已同步的京东订单id
|
|
|
+ List<Long> jdOrderIds1 = jdOrderService.listObject(JdOrder::getOrderId, q -> q.in(JdOrder::getOrderId, jdOrderIds));
|
|
|
+ TenantHolder.clear();
|
|
|
+
|
|
|
+ //过滤出未同步的数据
|
|
|
+ List<PurchaseOrderDto> purchaseOrderListFilter = purchaseOrderList.stream().filter(item -> !jdOrderIds1.contains(item.getOrderId())).collect(Collectors.toList());
|
|
|
+
|
|
|
+ //转为系统自己的实体类
|
|
|
+ List<JdOrder> jdOrderList = BeanUtil.copyToList(purchaseOrderListFilter, JdOrder.class);
|
|
|
+ //赋值租户id
|
|
|
+// jdOrderList.forEach(item->item.setTenantId("wdly"));
|
|
|
+ //将数据存储到库
|
|
|
+ TenantHolder.setIgnore(true);//忽略租户
|
|
|
+ jdOrderService.saveBatch(jdOrderList);
|
|
|
+ TenantHolder.clear();
|
|
|
+
|
|
|
+ //获取明细
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 获取京东订单信息分页
|
|
|
+ */
|
|
|
+ private JOSOrderResultDto getJdOrderInfo(Integer pageIndex, Integer pageSize, Date startTime, Date endTime, JdClient client) throws Exception {
|
|
|
+ VcGetpurchaseorderlistRequest request = new VcGetpurchaseorderlistRequest();
|
|
|
+ request.setCreatedDateStart(startTime);
|
|
|
+ request.setCreatedDateEnd(endTime);
|
|
|
+ request.setPageIndex(pageIndex);
|
|
|
+ request.setPageSize(pageSize);
|
|
|
+ VcGetpurchaseorderlistResponse response = client.execute(request);
|
|
|
+ return response.getJosOrderResultDto();
|
|
|
+ }
|
|
|
+
|
|
|
+ private static JSONObject getJSON(HttpRequestBase httpRequestBase) throws IOException {
|
|
|
+ HttpClient client = HttpClients.createDefault();
|
|
|
+ httpRequestBase.setConfig(RequestConfig.custom().setConnectTimeout(3000).build());
|
|
|
+ HttpResponse response = client.execute(httpRequestBase);
|
|
|
+ int statusCode = response.getStatusLine().getStatusCode();
|
|
|
+ HttpEntity entity = response.getEntity();
|
|
|
+ String responseStr = IOUtils.toString(entity.getContent(), StandardCharsets.UTF_8);
|
|
|
+ if (statusCode != 200) {
|
|
|
+ log.error("请求失败 {} {} {}", statusCode, httpRequestBase.getURI(), responseStr);
|
|
|
+ }
|
|
|
+ return JSONObject.parseObject(responseStr);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ public static void main(String[] args) throws Exception {
|
|
|
+ JSONObject jdTokenJson = JSONObject.parseObject("{\"access_token\":\"eaea297f24944a1e9f88de4ef9f67605lyti\",\"expires_in\":86399,\"refresh_token\":\"d42c559aed09415aacd32df4c5712711yyzu\",\"scope\":\"snsapi_base\",\"open_id\":\"CqJo6jtBlMczlbw1LWVshD1Re_qBaw6BLQSYQWPPNKs\",\"uid\":\"0063800318\",\"time\":1699422692835,\"token_type\":\"bearer\",\"code\":0,\"xid\":\"o*AAQrc1AbQq2SNpnAmdEFbwM-ZGU3ZUdz2_M6Wu3p3d_-3U273S4pUQYjFXGrDJzp3YTAVN4R\"}");
|
|
|
+ if (ObjectUtil.isEmpty(jdTokenJson)) {
|
|
|
+ log.error("京东token详细为空请检查");
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ JdClient client = new DefaultJdClient("http://api.jd.com/routerjson", jdTokenJson.getString("access_token"), appKey, appSecret);
|
|
|
+
|
|
|
+ VcGetdetailbyorderidRequest request=new VcGetdetailbyorderidRequest();
|
|
|
+ request.setOrderId(1526033586L);
|
|
|
+ request.setIsPage(false);
|
|
|
+ VcGetdetailbyorderidResponse response=client.execute(request);
|
|
|
+ System.out.println(JSONObject.toJSONString(response.getJosDetailResultDto()));
|
|
|
+ }
|
|
|
+}
|