From c8f20e6d5549be4a12a706f42db69c26369d35f0 Mon Sep 17 00:00:00 2001 From: Joshi <3040996759@qq.com> Date: Wed, 23 Jul 2025 11:46:55 +0800 Subject: [PATCH] =?UTF-8?q?=E5=A4=87=E6=B3=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../com/ruoyi/oa/utils/StoRouteQueryUtil.java | 107 +++++++++++++++++ .../com/ruoyi/oa/utils/YdRouteQueryUtil.java | 69 +++++++++++ .../com/ruoyi/oa/utils/YtRouteQueryUtil.java | 110 ++++++++++++++++++ .../com/ruoyi/oa/utils/ZtoRouteQueryUtil.java | 105 +++++++++++++++++ 4 files changed, 391 insertions(+) create mode 100644 ruoyi-oa/src/main/java/com/ruoyi/oa/utils/StoRouteQueryUtil.java create mode 100644 ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YdRouteQueryUtil.java create mode 100644 ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YtRouteQueryUtil.java create mode 100644 ruoyi-oa/src/main/java/com/ruoyi/oa/utils/ZtoRouteQueryUtil.java diff --git a/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/StoRouteQueryUtil.java b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/StoRouteQueryUtil.java new file mode 100644 index 0000000..ee21a25 --- /dev/null +++ b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/StoRouteQueryUtil.java @@ -0,0 +1,107 @@ +package com.ruoyi.oa.utils; + +import com.alibaba.fastjson2.JSON; +import com.alibaba.fastjson2.JSONObject; +import com.ruoyi.oa.domain.vo.OaExpressVo; +import org.apache.commons.codec.binary.Base64; +import org.apache.commons.codec.digest.DigestUtils; +import java.io.BufferedReader; +import java.io.InputStreamReader; +import java.io.OutputStream; +import java.net.HttpURLConnection; +import java.net.URL; +import java.nio.charset.StandardCharsets; + +public class StoRouteQueryUtil { + // 请填写你自己的key/secret + private static final String APP_KEY = ""; + private static final String APP_SECRET = ""; + private static final String API_URL = "https://open.sto.cn/openapi/traceQuery"; // 申通轨迹查询接口 + + /** + * 查询申通轨迹 + * @param mailNo 运单号 + * @return 查询结果JSON + */ + public static String queryRoute(String mailNo) { + try { + // 构造请求参数,具体参数请参考申通官方文档 + JSONObject params = new JSONObject(); + params.put("appKey", APP_KEY); + params.put("timestamp", System.currentTimeMillis()); + params.put("sign", ""); // 签名算法见官方文档 + params.put("method", "sto.trace.query.common"); + params.put("format", "json"); + params.put("billNo", mailNo); + // 其他参数可根据实际需求补充 + + String jsonParams = params.toJSONString(); + URL url = new URL(API_URL); + HttpURLConnection conn = (HttpURLConnection) url.openConnection(); + conn.setDoOutput(true); + conn.setDoInput(true); + conn.setUseCaches(false); + conn.setRequestMethod("POST"); + conn.setRequestProperty("Content-Type", "application/json;charset=UTF-8"); + OutputStream out = conn.getOutputStream(); + out.write(jsonParams.getBytes(StandardCharsets.UTF_8)); + out.flush(); + out.close(); + StringBuilder sbResult = new StringBuilder(); + if (200 == conn.getResponseCode()) { + BufferedReader responseReader = new BufferedReader(new InputStreamReader(conn.getInputStream(), "UTF-8")); + String readLine; + while ((readLine = responseReader.readLine()) != null) { + sbResult.append(readLine).append("\n"); + } + responseReader.close(); + } + return sbResult.toString(); + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + /** + * 解析申通返回数据,转为OaExpressVo + */ + public static OaExpressVo parseData(String result) { + if (result == null || result.isEmpty()) return null; + try { + JSONObject json = JSON.parseObject(result); + // 具体字段请根据申通返回格式调整 + JSONObject data = json.getJSONObject("data"); + if (data == null) return null; + OaExpressVo vo = new OaExpressVo(); + vo.setExpressCode(data.getString("billNo")); + vo.setLastStatus(data.getString("status")); + vo.setLastUpdateTime(data.getDate("updateTime")); + // 你可以根据实际返回内容补充更多字段 + return vo; + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + // 申通签名算法 body+appSecret,MD5后Base64 + public static String sign(String body, String secret) { + String text = body + secret; + byte[] md5 = DigestUtils.md5(text); + return Base64.encodeBase64String(md5); + } + + // main方法测试 + public static void main(String[] args) { + String mailNo = "测试单号"; + String body = "{\"orderNo\":\"" + mailNo + "\"}"; + String secret = "你的密钥"; + String sign = sign(body, secret); + System.out.println("申通签名:" + sign); + String result = queryRoute(mailNo); // 你可以根据实际参数完善queryRoute + System.out.println("申通原始返回:" + result); + OaExpressVo vo = parseData(result); + System.out.println("解析后:" + vo); + } +} \ No newline at end of file diff --git a/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YdRouteQueryUtil.java b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YdRouteQueryUtil.java new file mode 100644 index 0000000..925464e --- /dev/null +++ b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YdRouteQueryUtil.java @@ -0,0 +1,69 @@ +package com.ruoyi.oa.utils; + +import com.yundasys.OpenApiHttpUtils; +import com.alibaba.fastjson2.JSON; +import com.alibaba.fastjson2.JSONObject; +import com.ruoyi.oa.domain.vo.OaExpressVo; +import java.security.MessageDigest; + +public class YdRouteQueryUtil { + // 请根据实际环境切换key/secret + private static final String APP_KEY = "004160"; // 生产环境 + private static final String APP_SECRET = "ac9ee46d749e44b98e7a9e38f3c8f8f3"; // 生产环境 + private static final String API_URL = "https://u-openapi.yundasys.com/openapi/outer/logictis/query"; + + /** + * 查询韵达轨迹 + * @param mailNo 运单号 + * @return 查询结果JSON + */ + public static String queryRoute(String mailNo) { + String jsonParams = "{\"mailno\":\"" + mailNo + "\"}"; + return OpenApiHttpUtils.doPostJson(API_URL, jsonParams, APP_KEY, APP_SECRET); + } + + /** + * 解析韵达返回数据,转为OaExpressVo + */ + public static OaExpressVo parseData(String result) { + if (result == null || result.isEmpty()) return null; + try { + JSONObject json = JSON.parseObject(result); + // 具体字段请根据韵达返回格式调整 + JSONObject data = json.getJSONObject("data"); + if (data == null) return null; + OaExpressVo vo = new OaExpressVo(); + vo.setExpressCode(data.getString("mailNo")); + vo.setLastStatus(data.getString("status")); + vo.setLastUpdateTime(data.getDate("updateTime")); + // 你可以根据实际返回内容补充更多字段 + return vo; + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + // MD5签名算法(如需自定义签名,可用此方法) + public static String md5(String str, String charset) throws Exception { + MessageDigest md = MessageDigest.getInstance("MD5"); + md.update(str.getBytes(charset)); + byte[] result = md.digest(); + StringBuilder sb = new StringBuilder(32); + for (byte b : result) { + int val = b & 0xff; + if (val <= 0xf) sb.append("0"); + sb.append(Integer.toHexString(val)); + } + return sb.toString().toLowerCase(); + } + + // main方法测试 + public static void main(String[] args) { + String mailNo = "测试单号"; + String result = queryRoute(mailNo); + System.out.println("韵达原始返回:" + result); + OaExpressVo vo = parseData(result); + System.out.println("解析后:" + vo); + } +} \ No newline at end of file diff --git a/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YtRouteQueryUtil.java b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YtRouteQueryUtil.java new file mode 100644 index 0000000..7bd69e7 --- /dev/null +++ b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/YtRouteQueryUtil.java @@ -0,0 +1,110 @@ +package com.ruoyi.oa.utils; + +import com.alibaba.fastjson2.JSON; +import com.alibaba.fastjson2.JSONObject; +import com.ruoyi.oa.domain.vo.OaExpressVo; +import org.apache.commons.codec.binary.Base64; +import org.apache.commons.codec.digest.DigestUtils; +import java.io.BufferedReader; +import java.io.InputStreamReader; +import java.io.OutputStream; +import java.net.HttpURLConnection; +import java.net.URL; +import java.nio.charset.StandardCharsets; + +public class YtRouteQueryUtil { + // 请填写你自己的key/secret + private static final String APP_KEY = ""; + private static final String APP_SECRET = ""; + private static final String API_URL = "https://openapi.yto.net.cn/openApi/queryTrack"; // 圆通轨迹查询接口 + + /** + * 查询圆通轨迹 + * @param mailNo 运单号 + * @return 查询结果JSON + */ + public static String queryRoute(String mailNo) { + try { + // 构造请求参数,具体参数请参考圆通官方文档 + JSONObject params = new JSONObject(); + params.put("app_key", APP_KEY); + params.put("timestamp", System.currentTimeMillis()); + params.put("sign", ""); // 签名算法见官方文档 + params.put("method", "yto.marketing.waybill.trace.get"); + params.put("format", "json"); + params.put("user_id", ""); // 用户ID(如有) + params.put("waybill_no", mailNo); + // 其他参数可根据实际需求补充 + + String jsonParams = params.toJSONString(); + URL url = new URL(API_URL); + HttpURLConnection conn = (HttpURLConnection) url.openConnection(); + conn.setDoOutput(true); + conn.setDoInput(true); + conn.setUseCaches(false); + conn.setRequestMethod("POST"); + conn.setRequestProperty("Content-Type", "application/json;charset=UTF-8"); + OutputStream out = conn.getOutputStream(); + out.write(jsonParams.getBytes(StandardCharsets.UTF_8)); + out.flush(); + out.close(); + StringBuilder sbResult = new StringBuilder(); + if (200 == conn.getResponseCode()) { + BufferedReader responseReader = new BufferedReader(new InputStreamReader(conn.getInputStream(), "UTF-8")); + String readLine; + while ((readLine = responseReader.readLine()) != null) { + sbResult.append(readLine).append("\n"); + } + responseReader.close(); + } + return sbResult.toString(); + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + /** + * 解析圆通返回数据,转为OaExpressVo + */ + public static OaExpressVo parseData(String result) { + if (result == null || result.isEmpty()) return null; + try { + JSONObject json = JSON.parseObject(result); + // 具体字段请根据圆通返回格式调整 + JSONObject data = json.getJSONObject("data"); + if (data == null) return null; + OaExpressVo vo = new OaExpressVo(); + vo.setExpressCode(data.getString("mailNo")); + vo.setLastStatus(data.getString("status")); + vo.setLastUpdateTime(data.getDate("updateTime")); + // 你可以根据实际返回内容补充更多字段 + return vo; + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + // 圆通签名算法 param+method+v+secret,MD5后Base64 + public static String sign(String param, String method, String v, String secret) { + String data = param + method + v; + byte[] md5 = DigestUtils.md5(data + secret); + return Base64.encodeBase64String(md5); + } + + // main方法测试 + public static void main(String[] args) { + String mailNo = "测试单号"; + String param = "{\"NUMBER\":\"" + mailNo + "\"}"; + String method = "yto.marketing.waybill.trace.get"; // 请根据实际接口填写 + String v = "1.01"; // 请根据实际接口填写 + String secret = "你的密钥"; + String sign = sign(param, method, v, secret); + System.out.println("圆通签名:" + sign); + String result = queryRoute(mailNo); // 你可以根据实际参数完善queryRoute + System.out.println("圆通原始返回:" + result); + OaExpressVo vo = parseData(result); + System.out.println("解析后:" + vo); + } +} \ No newline at end of file diff --git a/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/ZtoRouteQueryUtil.java b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/ZtoRouteQueryUtil.java new file mode 100644 index 0000000..09a54ff --- /dev/null +++ b/ruoyi-oa/src/main/java/com/ruoyi/oa/utils/ZtoRouteQueryUtil.java @@ -0,0 +1,105 @@ +package com.ruoyi.oa.utils; + +import com.alibaba.fastjson2.JSON; +import com.alibaba.fastjson2.JSONObject; +import com.ruoyi.oa.domain.vo.OaExpressVo; +import org.apache.commons.codec.binary.Base64; +import org.apache.commons.codec.digest.DigestUtils; +import java.io.BufferedReader; +import java.io.InputStreamReader; +import java.io.OutputStream; +import java.net.HttpURLConnection; +import java.net.URL; +import java.nio.charset.StandardCharsets; + +public class ZtoRouteQueryUtil { + // 请填写你自己的key/secret + private static final String APP_KEY = ""; + private static final String APP_SECRET = ""; + private static final String API_URL = "https://japi.zto.com/traceInterfaceNewTraces"; // 中通轨迹查询接口 + + /** + * 查询中通轨迹 + * @param mailNo 运单号 + * @return 查询结果JSON + */ + public static String queryRoute(String mailNo) { + try { + // 构造请求参数,具体参数请参考中通官方文档 + JSONObject params = new JSONObject(); + params.put("company_id", APP_KEY); + params.put("msg_type", "NEW_TRACES"); + params.put("data", "[{\"billCode\":\"" + mailNo + "\"}]"); + params.put("data_digest", ""); // 签名算法见官方文档 + // 其他参数可根据实际需求补充 + + String jsonParams = params.toJSONString(); + URL url = new URL(API_URL); + HttpURLConnection conn = (HttpURLConnection) url.openConnection(); + conn.setDoOutput(true); + conn.setDoInput(true); + conn.setUseCaches(false); + conn.setRequestMethod("POST"); + conn.setRequestProperty("Content-Type", "application/json;charset=UTF-8"); + OutputStream out = conn.getOutputStream(); + out.write(jsonParams.getBytes(StandardCharsets.UTF_8)); + out.flush(); + out.close(); + StringBuilder sbResult = new StringBuilder(); + if (200 == conn.getResponseCode()) { + BufferedReader responseReader = new BufferedReader(new InputStreamReader(conn.getInputStream(), "UTF-8")); + String readLine; + while ((readLine = responseReader.readLine()) != null) { + sbResult.append(readLine).append("\n"); + } + responseReader.close(); + } + return sbResult.toString(); + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + /** + * 解析中通返回数据,转为OaExpressVo + */ + public static OaExpressVo parseData(String result) { + if (result == null || result.isEmpty()) return null; + try { + JSONObject json = JSON.parseObject(result); + // 具体字段请根据中通返回格式调整 + JSONObject data = json.getJSONObject("data"); + if (data == null) return null; + OaExpressVo vo = new OaExpressVo(); + vo.setExpressCode(data.getString("billCode")); + vo.setLastStatus(data.getString("status")); + vo.setLastUpdateTime(data.getDate("updateTime")); + // 你可以根据实际返回内容补充更多字段 + return vo; + } catch (Exception e) { + e.printStackTrace(); + return null; + } + } + + // 中通签名算法 body+appSecret,MD5后Base64 + public static String sign(String body, String secret) { + String text = body + secret; + byte[] md5 = DigestUtils.md5(text); + return Base64.encodeBase64String(md5); + } + + // main方法测试 + public static void main(String[] args) { + String mailNo = "测试单号"; + String body = "{\"billCode\":\"" + mailNo + "\"}"; + String secret = "你的密钥"; + String sign = sign(body, secret); + System.out.println("中通签名:" + sign); + String result = queryRoute(mailNo); // 你可以根据实际参数完善queryRoute + System.out.println("中通原始返回:" + result); + OaExpressVo vo = parseData(result); + System.out.println("解析后:" + vo); + } +} \ No newline at end of file