微信公众号开发(三)快递信息查询

1.快递查询API

这里使用的是阿里云全国快递物流查询-快递查询接口:https://market.aliyun.com/products/56928004/cmapi021863.html

该接口支持只通过快递运单号查询物流信息, 不需要在额外设置参数. 该种方式95%能自动识别, 填写查询速度会更快, 已经满足一般开发的需求, 并能极大方便开发者的使用.

请求参数说明

返回结果说明

官方提供的示例代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
public static void main(String[] args) {
String host = "https://wuliu.market.alicloudapi.com";
String path = "/kdi";
String method = "GET";
System.out.println("请先替换成自己的AppCode");
String appcode = "833509fd73fe1124838xxxxxxxx"; // !!!替换填写自己的AppCode 在买家中心查看
Map<String, String> headers = new HashMap<String, String>();
headers.put("Authorization", "APPCODE " + appcode); //格式为:Authorization:APPCODE 83359fd73fe11248385f570e3c139xxx
Map<String, String> querys = new HashMap<String, String>();
querys.put("no", "462587770684");// !!! 请求参数
querys.put("type", "zto");// !!! 请求参数
//JDK 1.8示例代码请在这里下载: http://code.fegine.com/Tools.zip
try {
/**
* 重要提示如下:
* HttpUtils请从
* https://github.com/aliyun/api-gateway-demo-sign-java/blob/master/src/main/java/com/aliyun/api/gateway/demo/util/HttpUtils.java
* 或者直接下载:
* http://code.fegine.com/HttpUtils.zip
* 下载
*
* 相应的依赖请参照
* https://github.com/aliyun/api-gateway-demo-sign-java/blob/master/pom.xml
* 相关jar包(非pom)直接下载:
* http://code.fegine.com/aliyun-jar.zip
*/
HttpResponse response = HttpUtils.doGet(host, path, method, headers, querys);
//System.out.println(response.toString());如不输出json, 请打开这行代码,打印调试头部状态码。
//状态码: 200 正常;400 URL无效;401 appCode错误; 403 次数用完; 500 API网管错误
//获取response的body
System.out.println(EntityUtils.toString(response.getEntity())); //输出json
} catch (Exception e) {
e.printStackTrace();
}
}

正常返回示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
{
"status": "0",/* status 0:正常查询 201:快递单号错误 203:快递公司不存在 204:快递公司识别失败 205:没有信息 207:该单号被限制,错误单号 */
"msg": "ok",
"result": {
"number": "780098068058",
"type": "zto",
"list": [{
"time": "2018-03-09 11:59:26",
"status": "【石家庄市】快件已在【长安三部】 签收,签收人: 本人,感谢使用中通快递,期待再次为您服务!"
}, {
"time": "2018-03-09 09:03:10",
"status": "【石家庄市】 快件已到达 【长安三部】(0311-85344265),业务员 容晓光(13081105270) 正在第1次派件, 请保持电话畅通,并耐心等待"
}, {
"time": "2018-03-08 23:43:44",
"status": "【石家庄市】 快件离开 【石家庄】 发往 【长安三部】"
}, {
"time": "2018-03-08 21:00:44",
"status": "【石家庄市】 快件到达 【石家庄】"
}, {
"time": "2018-03-07 01:38:45",
"status": "【广州市】 快件离开 【广州中心】 发往 【石家庄】"
}, {
"time": "2018-03-07 01:36:53",
"status": "【广州市】 快件到达 【广州中心】"
}, {
"time": "2018-03-07 00:40:57",
"status": "【广州市】 快件离开 【广州花都】 发往 【石家庄中转】"
}, {
"time": "2018-03-07 00:01:55",
"status": "【广州市】 【广州花都】(020-37738523) 的 马溪 (18998345739) 已揽收"
}],
"deliverystatus": "3", /* 0:快递收件(揽件)1.在途中 2.正在派件 3.已签收 4.派送失败 5.疑难件 6.退件签收 */
"issign": "1", /* 1.是否签收 */
"expName": "中通快递", /* 快递公司名称 */
"expSite": "www.zto.com", /* 快递公司官网 */
"expPhone": "95311", /* 快递公司电话 */
"courier": "容晓光", /* 快递员 或 快递站(没有则为空)*/
"courierPhone":"13081105270", /* 快递员电话 (没有则为空) */
"updateTime":"2019-08-27 13:56:19", /* 快递轨迹信息最新时间 */
"takeTime":"2天20小时14分", /* 发货到收货消耗时长 (截止最新轨迹) */
"logo":"http://img3.fegine.com/express/zto.jpg" /* 快递公司LOGO */
}
}

失败返回示例:

1
2
3
4
5
6
7
8
9
{
"status": "205", /* status状态码见产品详情 */
"msg": "没有信息",
"result": {
"number": "1111ADECD1234",
"type": "AUTO",
"list": []
}
}

错误码定义:

错误码 错误信息 描述
201 快递单号错误 status:快递单号错误
203 快递公司不存在 status:快递公司不存在
204 快递公司识别失败 status:快递公司识别失败
205 没有信息 status:没有信息
207 该单号被限制,错误单号 status:该单号被限制,错误单号;一个单号对应多个快递公司,请求须指定快递公司
0 正常 status:正常查询

2.核心代码

工具类:

  1. HttpUtils(官方提供)

    下载地址 http://code.fegine.com/HttpUtils.zip

  2. TextUtil 用于判断输入发送的消息是否为英文字母+数字或纯数字(即符合快递运单号基本规则)

    1
    2
    3
    4
    5
    6
    7
    public class TextUtil {
    public static boolean DecText(String text){
    Pattern p=Pattern.compile("^[A-Za-z0-9]+$"); //正则表达式
    Matcher matcher = p.matcher(text);
    return matcher.matches();
    }
    }
  3. ExpressUtil 调用API查询物流信息

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    public class ExpressUtil {
    public static String QueryExpress(String num) throws Exception {
    String host = "https://wuliu.market.alicloudapi.com";
    String path = "/kdi";
    String method = "GET";
    String appcode = "06a9e928218141bxxxxxxx"; // !!!替换填写自己的AppCode 在买家中心查看
    Map<String, String> headers = new HashMap<String, String>();
    headers.put("Authorization", "APPCODE " + appcode); //格式为:Authorization:APPCODE 83359fd73fe11248385f570e3c139xxx
    Map<String, String> querys = new HashMap<String, String>();
    querys.put("no", num);// !!! 请求参数
    HttpResponse response = HttpUtils.doGet(host, path, method, headers, querys);
    //System.out.println(response.toString());
    //获取response的body
    String str = EntityUtils.toString(response.getEntity());//输出json
    JSONObject jsonObject = JSONObject.parseObject(str);
    // 获取到key为result的值
    String result = jsonObject.getString("result");
    jsonObject = JSONObject.parseObject(result);
    // 获取到key为list的值
    String list = jsonObject.getString("list");
    return list;
    }
    }

    此时返回的数据为:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    [{
    "time": "2020-02-29 19:45:12",
    "status": "快件由【浙江嘉善公司】发往【下一站浙江嘉兴转运中心】,扫描员【何海桃】"
    }, {
    "time": "2020-02-29 19:45:12",
    "status": "快件在【浙江嘉善公司】进行装车,扫描员【何海桃】,车签号【】"
    }, {
    "time": "2020-02-29 19:42:13",
    "status": "快件由【浙江嘉善公司】发往【下一站浙江嘉兴转运中心】,扫描员【何德文】"
    }, {
    "time": "2020-02-29 19:42:13",
    "status": "快件在【浙江嘉善公司】进行装包,扫描员【何德文】,袋号【9005261902881】"
    }, {
    "time": "2020-02-29 19:41:07",
    "status": "快件由【浙江嘉善公司】发往【下一站浙江嘉兴转运中心】,扫描员【何德文】"
    }, {
    "time": "2020-02-29 19:29:40",
    "status": "【浙江嘉善公司】的【公司称重()】已收件,扫描员【公司出港1】"
    }, {
    "time": "2020-02-29 18:32:52",
    "status": "快件由【浙江嘉善公司】发往【下一站浙江嘉兴转运中心】,扫描员【何德文】"
    }]

MsgService

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
if (TextUtil.DecText(content)==true){
String str = ExpressUtil.QueryExpress(content);
List<HashMap> r = JSON.parseArray(str, HashMap.class);
StringBuilder stringBuilder = new StringBuilder();
for (int i = r.size() - 1; i >= 0; i--) {
System.out.println(r.get(i).get("time") + ":" + r.get(i).get("status"));
String string = r.get(i).get("time") + ":" + r.get(i).get("status");
if (i == 0) {
stringBuilder.append(string);
} else {
stringBuilder.append(string).append("\n");
}
}
System.out.println(stringBuilder);
//文本消息
TextMessage text = new TextMessage();
text.setContent(stringBuilder+"");
text.setToUserName(fromUserName);
text.setFromUserName(toUserName);
text.setCreateTime(LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
text.setMsgType(MessageUtil.RESP_MESSAGE_TYPE_TEXT);
respMessage = MessageUtil.textMessageToXml(text);
}

3.功能测试

请作者喝瓶肥宅快乐水