You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

805 lines
30 KiB

  1. package com.simple.utils;
  2. import com.alibaba.fastjson.JSON;
  3. import com.alibaba.fastjson.JSONArray;
  4. import com.alibaba.fastjson.JSONObject;
  5. import okhttp3.*;
  6. import org.apache.commons.lang3.StringUtils;
  7. import org.slf4j.Logger;
  8. import org.slf4j.LoggerFactory;
  9. import java.io.IOException;
  10. import java.math.BigDecimal;
  11. import java.security.MessageDigest;
  12. import java.time.LocalDateTime;
  13. import java.time.format.DateTimeFormatter;
  14. /**
  15. * @Title: OpenapiCaller
  16. * @Package: cn.etcp.openplatform.service
  17. * @Description: ETCP开放平台接口调用示例
  18. * @author: zhiyong.fan
  19. * @date: 2018/3/8 17:41
  20. * @version: V1.0
  21. */
  22. public class ETCPUtil {
  23. private static final Logger logger = LoggerFactory.getLogger(ETCPUtil.class);
  24. /**
  25. * 域名地址
  26. */
  27. private static final String domain = "http://mapi.test.etcp.cn";
  28. //
  29. private static final String appId = "FMLK";
  30. private static final int payType = 5;
  31. /**
  32. * 商户号 测试时请换成ETCP开放平台为商户平台分配的商户号
  33. */
  34. private static final String merchantNo = "C7AEAF80BA8C44ADB42F3DB3CBC7D18A";
  35. /**
  36. * 商户密钥 测试时请换成ETCP开放平台为商户平台分配的商户密钥
  37. */
  38. private static final String merchantKey = "C292FFC7DCFB46AFB02792CD43F6DCC7";
  39. /**
  40. * 接口服务版本号
  41. */
  42. private static final String version = "1.0.0";
  43. /**
  44. * 6.1. 联合登录
  45. */
  46. private static final String userSigninUrl = "/merchant/open/{version}/openapi/usersigin";
  47. /**
  48. * 7.1. 车牌绑定
  49. */
  50. private static final String bindCarUrl = "/merchant/open/{version}/openapi/bindcar";
  51. /**
  52. * 7.2. 车牌解绑
  53. */
  54. private static final String unbindCarUrl = "/merchant/open/{version}/openapi/unbindcar";
  55. /**
  56. * 7.3. 车牌认证
  57. */
  58. private static final String carAuthUrl = "/merchant/open/{version}/openapi/carauth";
  59. /**
  60. * 7.4. 车牌找回
  61. */
  62. private static final String carRetrieveUrl = "/merchant/open/{version}/openapi/carretrieve";
  63. /**
  64. * 7.5. 已绑车辆信息查询
  65. */
  66. private static final String carNumUrl = "/merchant/open/{version}/openapi/carnum";
  67. /**
  68. * 8.1. 停车费查询
  69. */
  70. private static final String orderUnpayUrl = "/merchant/open/{version}/openapi/orderunpay";
  71. /**
  72. * 8.2. 优惠券查询
  73. */
  74. private static final String couponListUrl = "/merchant/open/{version}/openapi/couponlist";
  75. /**
  76. * 8.3. 历史停车查询
  77. */
  78. private static final String orderHistoryUrl = "/merchant/open/{version}/openapi/orderhistory";
  79. /**
  80. * 9.1. 主动支付(ETCP 收款)
  81. */
  82. private static final String orderpayUrl = "/merchant/open/{version}/openapi/orderpay";
  83. /**
  84. * 9.2. 主动支付(商户平台收款)
  85. */
  86. private static final String orderPaidUrl = "/merchant/open/{version}/openapi/orderpaid";
  87. /**
  88. * 10.1. 签约地址获取
  89. */
  90. private static final String signUrl = "/merchant/open/{version}/withhold/sign";
  91. /**
  92. * 10.2. 签约状态查询
  93. */
  94. private static final String statusUrl = "/merchant/open/{version}/withhold/status";
  95. /**
  96. * 11.1. 车场信息查询
  97. */
  98. private static final String parkingInfoUrl = "/merchant/open/{version}/openapi/surroundingparking";
  99. /**
  100. * 11.2. 车场状态查询
  101. */
  102. private static final String parkingStatusUrl = "/merchant/open/{version}/openapi/parkingstatus";
  103. /**
  104. * 12.1. 坏账查询
  105. */
  106. private static final String getDebtUrl = "/merchant/open/{version}/openapi/getdebt";
  107. /**
  108. * 12.2. 坏账清缴
  109. */
  110. private static final String repayDebtUrl = "/merchant/open/{version}/openapi/repaydebt";
  111. /**
  112. * 13.1. 商家优免券模板查询
  113. */
  114. private static final String bCouponListUrl = "/merchant/open/{version}/openapi/b/coupon/list";
  115. /**
  116. * 13.2. 商家优免券发放
  117. */
  118. private static final String bCouponRecordUrl = "/merchant/open/{version}/openapi/b/coupon/record";
  119. /**
  120. * 14.1. 车辆进出场模拟接口
  121. */
  122. private static final String bCarSimulationUrl = "/merchant/open/{version}/openapi/car/simulation";
  123. private final OkHttpClient client = new OkHttpClient();
  124. private DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyyMMddHHmmss");
  125. /** 错误码
  126. * 0 成功
  127. * 1 失败
  128. * 2 服务器异常
  129. * 3 时间戳超时
  130. * 4 签名校验非法
  131. * 5 没有找到商户密钥
  132. * 6 参数错误
  133. * 7 更新订单失败
  134. * 8 生产订单失败
  135. * 20100 操作失败
  136. * 20101 无效 token
  137. * 20102 缺少必要参数
  138. * 20106 参数错误
  139. * 20201 手机号错误
  140. * 20202 获取验证码失败
  141. * 20203 手机验证码错误
  142. * 20206 支付金额与应付金额不匹配
  143. * 20207 60s 内只能发送一次验证码
  144. * 20208 APP 未有该权限
  145. * 20209 优惠金额与应付金额不匹配
  146. * 20301 签约失败
  147. * 20302 签约成功
  148. * 20401 无效车架号
  149. * 20407 车辆信息不匹配
  150. * 20408 操作失败,请稍后重试
  151. * 20501 操作失败,请稍后重试
  152. * 20602 returnUrl 为空
  153. * 20603 未查询到费用
  154. * 20604 请先清偿坏账
  155. * 20605 synId 错误
  156. * 20606 待支付费用为 0,无需支付
  157. * 20607 支付链接失效
  158. * 20608 查费失败
  159. * 20701 appId 错误
  160. * 20801 未绑定该车辆
  161. * 20802 该车辆已被他人绑定
  162. * 20803 绑定数量超限
  163. * 20804 30 天内最多绑定 4 辆不同的车
  164. * 20805 在场车辆不可解绑
  165. * 20901 车辆不在场
  166. * 20902 车场不支持电子支付
  167. * 20903 没有车场查费权限
  168. * 20904 用户未绑定该查费车牌
  169. * 20905 查询费用异常
  170. * 20906 用户不存在
  171. * 20907 商户未配置查费车场
  172. * 20908 长租车,费用为 0
  173. * 20909 车牌错误
  174. * 21001 查询失败
  175. * 21002 请稍后再试
  176. * 21003 未查询到坏账
  177. * 21004 错误支付类型
  178. * 21101 签约号已存在
  179. */
  180. public static void main(String[] args) {
  181. ETCPUtil caller = new ETCPUtil();
  182. String ret = "";
  183. JSONObject objret = null;
  184. String etcpToken = "44529274-7a31-4fb5-a35d-91d5b0be8641";
  185. String carNumber = "京D12345";
  186. String parkId = "Wj7YdvqyiYM=";
  187. String businessId = "testasfsfsd";
  188. //caller.carSimulation(appId, merchantNo, merchantKey, version, carNumber);
  189. caller.getBCouponList(domain, merchantNo, merchantKey, version, parkId, businessId);
  190. // 联合登录测试
  191. /*ret = caller.userSignin(appId, merchantNo, merchantKey, version, "13910154397");
  192. objret = JSON.parseObject(ret);
  193. if (objret.getIntValue("code") != 0)
  194. return;
  195. etcpToken = objret.getJSONObject("data").getString("token");
  196. System.out.println(etcpToken);
  197. // 绑定车牌查询
  198. ret = caller.carNum(merchantNo, merchantKey, version, etcpToken);
  199. System.out.println(ret);
  200. objret = JSON.parseObject(ret);
  201. if (objret.getIntValue("code") != 0)
  202. return;
  203. JSONObject data = objret.getJSONObject("data");
  204. if (data.getIntValue("number") <= 0) {
  205. // 车牌绑定测试
  206. ret = caller.bindCar(etcpToken, carNumber, null, merchantNo, merchantKey, version);
  207. objret = JSON.parseObject(ret);
  208. if (objret.getIntValue("code") != 0)
  209. return;
  210. }
  211. JSONArray carArry = data.getJSONArray("carList");
  212. carNumber = JSON.toJSONString(carArry.get(0));
  213. carNumber = carNumber.substring(1, carNumber.length() -1);
  214. System.out.println(carNumber);
  215. // 停车费查询
  216. ret = caller.orderUnpay(appId, merchantNo, merchantKey, version, etcpToken, carNumber);
  217. System.out.println(ret);
  218. objret = JSON.parseObject(ret);
  219. if (objret.getIntValue("code") != 0)
  220. return;
  221. JSONArray payArr = objret.getJSONArray("data");
  222. JSONObject payObj = payArr.getJSONObject(0);
  223. String orderId = payObj.getString("orderId");
  224. // 微信h5支付
  225. ret = caller.orderPay(merchantNo, merchantKey, version, etcpToken, orderId, "http://test.cn", null);
  226. System.out.println(ret);
  227. */
  228. // 车牌解绑测试
  229. //caller.unbindCar(merchantNo, merchantKey, version, etcpToken, carNumber);
  230. //String orderId = "867C6F2F-4F3A-4767-890E-BA7F53F9C601";
  231. //caller.orderPay(etcpToken, 5, orderId, "test.cn", null);
  232. // 支付完成通知测试
  233. /*caller.orderPaid(etcpToken, "51C3E00A-4F87-43FB-A71B-C1287ED956CB",
  234. "201803120000001", BigDecimal.valueOf(8.85), "2018-03-12 11:58:31",
  235. "FSED9JvxgAU6XJUd8YRF5f7OuzyQ/lGJch0h8dVVkNaHUpPISCLBshnn0AIoEdIdi2aQMOrrcmdVz2Smy+UbQ8pXl95Mv50aPNnUgaDlxSDqHQ8iOD6FT5XV7ikozZ0800CJKDkvQrmCZS2O21G+xg==",
  236. "ETCP");*/
  237. }
  238. public static int getPayType() {
  239. return payType;
  240. }
  241. /**
  242. * 6.1. 联合登录
  243. *
  244. * @param appId appId(非空)
  245. * @param merchantNo merchantNo(非空)
  246. * @param merchantKey merchantKey(非空)
  247. * @param version version(非空)
  248. * @param mobilePhone 手机号(非空)
  249. * @return 联合登录响应信息
  250. * {
  251. * "code": 0,
  252. * "data": {
  253. * "token": "0b59582d-ea6f-4bf1-a570-e803cc24ebe0"
  254. * },
  255. * "message": "ok"
  256. * }
  257. */
  258. public String userSignin(String baseUrl, String appId, String merchantNo, String merchantKey, String version,
  259. String mobilePhone) {
  260. JSONObject jsonObject = new JSONObject();
  261. jsonObject.put("appId", appId);
  262. jsonObject.put("mobilePhone", mobilePhone);
  263. String data = jsonObject.toJSONString();
  264. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  265. String sign = genSign(data, merchantKey, timeStamp);
  266. return doPost(baseUrl + userSigninUrl.replaceAll("\\{version}", version), data, sign,
  267. timeStamp, merchantNo);
  268. }
  269. /**
  270. * 7.1. 车牌绑定
  271. *
  272. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  273. * @param plateNumber 车牌号(非空)
  274. * @param plateColor 车牌颜色(可空)
  275. * @return 绑牌响应信息
  276. * {
  277. * "code": 0,
  278. * "message": "ok"
  279. * }
  280. */
  281. public String bindCar(String baseUrl, String merchantNo, String merchantKey, String version,
  282. String etcpToken,
  283. String plateNumber, String plateColor) {
  284. JSONObject jsonObject = new JSONObject();
  285. jsonObject.put("token", etcpToken);
  286. jsonObject.put("plateNumber", plateNumber);
  287. if ("1".equals(plateColor) || "2".equals(plateColor) || "3".equals(plateColor)
  288. || "4".equals(plateColor)) {
  289. jsonObject.put("plateColor", plateColor);
  290. }
  291. String data = jsonObject.toJSONString();
  292. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  293. String sign = genSign(data, merchantKey, timeStamp);
  294. return doPost(baseUrl + bindCarUrl.replaceAll("\\{version}", version),
  295. data, sign, timeStamp, merchantNo);
  296. }
  297. /**
  298. * 7.2. 车牌解绑
  299. *
  300. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  301. * @param plateNumber 车牌号(非空)
  302. * @return 车牌解绑响应信息
  303. * {
  304. * "code": 0,
  305. * "message": "ok"
  306. * }
  307. */
  308. public String unbindCar(String baseUrl, String merchantNo, String merchantKey, String version,
  309. String etcpToken,
  310. String plateNumber) {
  311. JSONObject jsonObject = new JSONObject();
  312. jsonObject.put("token", etcpToken);
  313. jsonObject.put("plateNumber", plateNumber);
  314. String data = jsonObject.toJSONString();
  315. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  316. String sign = genSign(data, merchantKey, timeStamp);
  317. return doPost(baseUrl + unbindCarUrl.replaceAll("\\{version}", version),
  318. data, sign, timeStamp, merchantNo);
  319. }
  320. /**
  321. * 7.3. 车牌认证
  322. *
  323. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  324. * @param carFrameNum 车架号(非空)
  325. * @param plateNumber 车牌号(非空)
  326. * @param carEngineNum 发动机号(非空)
  327. * @return 车牌解绑响应信息
  328. * {
  329. * "code": 0,
  330. * "message": "ok"
  331. * }
  332. */
  333. public String carAuth(String baseUrl, String merchantNo, String merchantKey, String version,
  334. String etcpToken,
  335. String carFrameNum, String plateNumber, String carEngineNum
  336. ) {
  337. JSONObject jsonObject = new JSONObject();
  338. jsonObject.put("token", etcpToken);
  339. jsonObject.put("carFrameNum", carFrameNum);
  340. jsonObject.put("plateNumber", plateNumber);
  341. jsonObject.put("carEngineNum", carEngineNum);
  342. String data = jsonObject.toJSONString();
  343. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  344. String sign = genSign(data, merchantKey, timeStamp);
  345. return doPost(baseUrl + carAuthUrl.replaceAll("\\{version}", version),
  346. data, sign, timeStamp, merchantNo);
  347. }
  348. /**
  349. * 7.4. 车牌找回
  350. *
  351. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  352. * @param carFrameNum 车架号(非空)
  353. * @param plateNumber 车牌号(非空)
  354. * @param carEngineNum 发机号(非空)
  355. * @param plateColor 车牌颜色(1 蓝 2 黑 3 黄 4 白)
  356. * @return 车牌找回响应信息
  357. * {
  358. * "code": 0,
  359. * "message": "ok"
  360. * }
  361. */
  362. public String carRetrieve(String baseUrl, String merchantNo, String merchantKey, String version,
  363. String etcpToken,
  364. String carFrameNum, String plateNumber, String carEngineNum, String plateColor ) {
  365. JSONObject jsonObject = new JSONObject();
  366. jsonObject.put("token", etcpToken);
  367. jsonObject.put("carFrameNum", carFrameNum);
  368. jsonObject.put("plateNumber", plateNumber);
  369. jsonObject.put("carEngineNum", carEngineNum);
  370. if (!StringUtils.isBlank(plateColor))
  371. jsonObject.put("plateColor", plateColor);
  372. String data = jsonObject.toJSONString();
  373. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  374. String sign = genSign(data, merchantKey, timeStamp);
  375. return doPost(baseUrl + carRetrieveUrl.replaceAll("\\{version}", version),
  376. data, sign, timeStamp, merchantNo);
  377. }
  378. /**
  379. * 7.5. 已绑车辆信息查询
  380. *
  381. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  382. * @return 已绑车辆信息查询响应信息
  383. * {
  384. * "code": 0,
  385. * "msg": "ok",
  386. * "data": {
  387. * "number": 3,
  388. * "carList": [
  389. * "晋 BMZ105",
  390. * "云 C12345"
  391. * ]
  392. * }
  393. * }
  394. */
  395. public String carNum(String baseUrl, String merchantNo, String merchantKey, String version,
  396. String etcpToken) {
  397. JSONObject jsonObject = new JSONObject();
  398. jsonObject.put("token", etcpToken);
  399. String data = jsonObject.toJSONString();
  400. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  401. String sign = genSign(data, merchantKey, timeStamp);
  402. return doGet(baseUrl + carNumUrl.replaceAll("\\{version}", version),
  403. data, sign, timeStamp, merchantNo);
  404. }
  405. /**
  406. * 8.1. 停车费查询
  407. *
  408. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  409. * @param plateNumber 车牌号(非空)
  410. * @param appId appId(可空)
  411. * @return 停车费查询响应信息
  412. */
  413. public String orderUnpay(String baseUrl,
  414. String appId, String merchantNo, String merchantKey, String version,
  415. String etcpToken,
  416. String plateNumber) {
  417. JSONObject jsonObject = new JSONObject();
  418. jsonObject.put("token", etcpToken);
  419. jsonObject.put("plateNumber", plateNumber);
  420. if (appId != null && appId.length() > 0) {
  421. jsonObject.put("appId", appId);
  422. }
  423. String data = jsonObject.toJSONString();
  424. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  425. String sign = genSign(data, merchantKey, timeStamp);
  426. return doGet(baseUrl + orderUnpayUrl.replaceAll("\\{version}", version),
  427. data, sign, timeStamp, merchantNo);
  428. }
  429. /**
  430. * 8.2. 优惠券查询
  431. *
  432. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  433. * @param lastCode 上一分页代码(可空)
  434. * @param pageSize 1-200 之间的分页每页数量(非空)
  435. * @return 停车费查询响应信息
  436. */
  437. public String couponList(String baseUrl,
  438. String merchantNo, String merchantKey, String version,
  439. String etcpToken,
  440. String lastCode, String pageSize) {
  441. JSONObject jsonObject = new JSONObject();
  442. jsonObject.put("token", etcpToken);
  443. if (!StringUtils.isBlank(lastCode))
  444. jsonObject.put("lastCode", lastCode);
  445. jsonObject.put("pageSize", pageSize);
  446. String data = jsonObject.toJSONString();
  447. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  448. String sign = genSign(data, merchantKey, timeStamp);
  449. return doGet(baseUrl + couponListUrl.replaceAll("\\{version}", version),
  450. data, sign, timeStamp, merchantNo);
  451. }
  452. /**
  453. * 8.3.历史停车查询
  454. *
  455. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin}) (非空)
  456. * @return 停车费查询响应信息
  457. */
  458. public String orderHistory(String baseUrl,
  459. String merchantNo, String merchantKey, String version,
  460. String etcpToken) {
  461. JSONObject jsonObject = new JSONObject();
  462. jsonObject.put("token", etcpToken);
  463. String data = jsonObject.toJSONString();
  464. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  465. String sign = genSign(data, merchantKey, timeStamp);
  466. return doGet(baseUrl + orderHistoryUrl.replaceAll("\\{version}", version),
  467. data, sign, timeStamp, merchantNo);
  468. }
  469. /**
  470. * 9.1. 主动支付(ETCP 收款)
  471. *
  472. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin})(非空)
  473. * @param orderId 停车记录ID ({@link ETCPUtil#orderUnpay})(非空)
  474. * @param returnUrl 外部支付流水号(商户平台生成)(非空)
  475. * @param couponCode 支付金额 ({@link ETCPUtil#orderUnpay})(非空)
  476. * @return
  477. */
  478. public String orderPay(String baseUrl,
  479. String merchantNo, String merchantKey, String version,
  480. String etcpToken, String orderId,
  481. String returnUrl, String couponCode) {
  482. // payType 支付方式(1 微信公众号内支付 2 支付宝 H5 支付 3 微信二维码 4 支付宝二维码 5 微信 H5)(非空)
  483. int payType = 5;
  484. JSONObject jsonObject = new JSONObject();
  485. jsonObject.put("token", etcpToken);
  486. jsonObject.put("payType", payType);
  487. jsonObject.put("synId", orderId);
  488. jsonObject.put("returnUrl", returnUrl);
  489. if (couponCode != null && couponCode.length() > 0) {
  490. jsonObject.put("couponCode", couponCode);
  491. }
  492. String data = jsonObject.toJSONString();
  493. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  494. String sign = genSign(data, merchantKey, timeStamp);
  495. return doPost(baseUrl + orderpayUrl.replaceAll("\\{version}", version),
  496. data, sign, timeStamp, merchantNo);
  497. }
  498. /**
  499. * 9.2. 主动支付(商户平台收款)
  500. *
  501. * @param etcpToken 商户平台调用联合接口获取的token({@link ETCPUtil#userSignin})(非空)
  502. * @param orderId 停车记录ID ({@link ETCPUtil#orderUnpay})(非空)
  503. * @param externalOrderId 外部支付流水号(商户平台生成)(非空)
  504. * @param payment 支付金额 ({@link ETCPUtil#orderUnpay})(非空)
  505. * @param payTime 支付时间, 格式:yyyy-MM-dd HH:mm:ss(非空)
  506. * @param verificationInfo 验证信息串 ({@link ETCPUtil#orderUnpay})(非空)
  507. * @param appId appId(可空)
  508. * @return
  509. */
  510. public String orderPaid(String baseUrl,
  511. String appId, String merchantNo, String merchantKey, String version,
  512. String etcpToken,
  513. String orderId, String externalOrderId,
  514. BigDecimal payment, String payTime, String verificationInfo) {
  515. JSONObject jsonObject = new JSONObject();
  516. jsonObject.put("token", etcpToken);
  517. jsonObject.put("orderId", orderId);
  518. jsonObject.put("externalOrderId", externalOrderId);
  519. jsonObject.put("payment", payment);
  520. jsonObject.put("payTime", payTime);
  521. jsonObject.put("verificationInfo", verificationInfo);
  522. if (appId != null && appId.length() > 0) {
  523. jsonObject.put("appId", appId);
  524. }
  525. String data = jsonObject.toJSONString();
  526. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  527. String sign = genSign(data, merchantKey, timeStamp);
  528. return doPost(baseUrl + orderPaidUrl.replaceAll("\\{version}", version),
  529. data, sign, timeStamp, merchantNo);
  530. }
  531. /**
  532. * 11.2. 车场状态查询
  533. *
  534. * @param parkingId 车场ID(非空)
  535. * @return 车场状态查询响应信息
  536. */
  537. public String parkingStatusUrl(String baseUrl,
  538. String merchantNo, String merchantKey, String version,
  539. String parkingId) {
  540. JSONObject jsonObject = new JSONObject();
  541. jsonObject.put("parkingId", parkingId);
  542. String data = jsonObject.toJSONString();
  543. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  544. String sign = genSign(data, merchantKey, timeStamp);
  545. return doPost(baseUrl + parkingStatusUrl.replaceAll("\\{version}", version),
  546. data, sign, timeStamp, merchantNo);
  547. }
  548. /**
  549. * 12.1. 坏账查询
  550. *
  551. * @param etcpToken
  552. * @return 车场状态查询响应信息
  553. */
  554. public String getDebt(String baseUrl,
  555. String appId, String merchantNo, String merchantKey, String version,
  556. String etcpToken, String carNumber) {
  557. JSONObject jsonObject = new JSONObject();
  558. jsonObject.put("token", etcpToken);
  559. jsonObject.put("appId", appId);
  560. jsonObject.put("plateNumber", carNumber);
  561. String data = jsonObject.toJSONString();
  562. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  563. String sign = genSign(data, merchantKey, timeStamp);
  564. return doPost(baseUrl + parkingStatusUrl.replaceAll("\\{version}", version),
  565. data, sign, timeStamp, merchantNo);
  566. }
  567. /**
  568. * 12.2. 坏账清缴
  569. *
  570. * @param etcpToken
  571. * @param
  572. * @param returnUrl
  573. * @return 车场状态查询响应信息
  574. */
  575. public String repayDebt(String baseUrl,
  576. String merchantNo, String merchantKey, String version,
  577. String etcpToken, String returnUrl) {
  578. // payType(1:支付宝 2:微信H5)
  579. int payType = 2;
  580. JSONObject jsonObject = new JSONObject();
  581. jsonObject.put("token", etcpToken);
  582. jsonObject.put("payType", payType);
  583. jsonObject.put("returnUrl", returnUrl);
  584. String data = jsonObject.toJSONString();
  585. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  586. String sign = genSign(data, merchantKey, timeStamp);
  587. return doPost(baseUrl + parkingStatusUrl.replaceAll("\\{version}", version),
  588. data, sign, timeStamp, merchantNo);
  589. }
  590. /**
  591. * 13.1. 商家优免券模板查询
  592. *
  593. * @return 商家优免券模板查询结果
  594. */
  595. public String getBCouponList(String baseUrl,
  596. String merchantNo, String merchantKey, String version,
  597. String parkId, String businessId) {
  598. JSONObject jsonObject = new JSONObject();
  599. jsonObject.put("parkId", parkId);
  600. jsonObject.put("businessId", businessId);
  601. String data = jsonObject.toJSONString();
  602. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  603. String sign = genSign(data, merchantKey, timeStamp);
  604. return doPost(baseUrl + bCouponListUrl.replaceAll("\\{version}", version),
  605. data, sign, timeStamp, merchantNo);
  606. }
  607. /**
  608. * 13.2. 商家优免券发放
  609. *
  610. * @param etcpToken
  611. * @return 商家优免券发放结果
  612. */
  613. public String bCouponRecord(String baseUrl,
  614. String merchantNo, String merchantKey, String version,
  615. String etcpToken,
  616. String parkId, String businessId, String carNumber, String couponFreeId) {
  617. JSONObject jsonObject = new JSONObject();
  618. jsonObject.put("token", etcpToken);
  619. jsonObject.put("parkId", parkId);
  620. jsonObject.put("businessId", businessId);
  621. jsonObject.put("vehicleNo", carNumber);
  622. jsonObject.put("couponFreeId", couponFreeId);
  623. String data = jsonObject.toJSONString();
  624. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  625. String sign = genSign(data, merchantKey, timeStamp);
  626. return doPost(baseUrl + bCouponRecordUrl.replaceAll("\\{version}", version),
  627. data, sign, timeStamp, merchantNo);
  628. }
  629. /**
  630. * 14.1. 车辆进出场模拟接口
  631. *
  632. * @param appId, plateNumber
  633. * @return 车场状态查询响应信息
  634. */
  635. public String carSimulation(String baseUrl,
  636. String appId, String merchantNo, String merchantKey, String version,
  637. String plateNumber) {
  638. JSONObject jsonObject = new JSONObject();
  639. jsonObject.put("appId", appId);
  640. jsonObject.put("plateNumber", plateNumber);
  641. String data = jsonObject.toJSONString();
  642. String timeStamp = dateTimeFormatter.format(LocalDateTime.now());
  643. String sign = genSign(data, merchantKey, timeStamp);
  644. return doPost(baseUrl + bCarSimulationUrl.replaceAll("\\{version}", version),
  645. data, sign, timeStamp, merchantNo);
  646. }
  647. private String doPost(String url, String data, String sign, String timeStamp, String merchantNo) {
  648. logger.info("请求url地址:{}, 请求参数为:data={}, sign={}, time_stamp={}, merchant_no={}", url, data,
  649. sign, timeStamp, merchantNo);
  650. RequestBody body = new FormBody.Builder().add("data", data).add("sign", sign)
  651. .add("time_stamp", timeStamp).add("merchant_no", merchantNo).build();
  652. Request request = new Request.Builder().url(url).post(body).build();
  653. try (Response response = client.newCall(request).execute()) {
  654. String responseStr = response.body().string();
  655. logger.info("post接口响应信息为:{}", responseStr);
  656. return responseStr;
  657. } catch (IOException e) {
  658. e.printStackTrace();
  659. }
  660. return null;
  661. }
  662. private String doGet(String sourceUrl, String data, String sign, String timeStamp, String merchantNo) {
  663. logger.info("请求url地址:{}, 请求参数为:data={}, sign={}, time_stamp={}, merchant_no={}", sourceUrl,
  664. data, sign, timeStamp, merchantNo);
  665. HttpUrl url = HttpUrl.parse(sourceUrl).newBuilder().addQueryParameter("data", data)
  666. .addQueryParameter("sign", sign).addQueryParameter("time_stamp", timeStamp)
  667. .addQueryParameter("merchant_no", merchantNo).build();
  668. Request request = new Request.Builder().url(url).build();
  669. try (Response response = client.newCall(request).execute()) {
  670. String responseStr = response.body().string();
  671. logger.info("get请求接口响应信息为:{}", responseStr);
  672. return responseStr;
  673. } catch (IOException e) {
  674. e.printStackTrace();
  675. }
  676. return null;
  677. }
  678. // 签名
  679. private String genSign(String param, String merchantKey, String time) {
  680. String preparedString = new StringBuilder(param).append(merchantKey).append(time).toString();
  681. return md5Encode(preparedString.replaceAll("[ \r\t\n]", ""));
  682. }
  683. private String md5Encode(String content) {
  684. StringBuilder sb = new StringBuilder();
  685. try {
  686. if (content == null || content.length() == 0) {
  687. return null;
  688. }
  689. MessageDigest digestInstance = MessageDigest.getInstance("MD5");
  690. digestInstance.update(content.getBytes("UTF-8"));
  691. byte[] md = digestInstance.digest();
  692. for (int i = 0; i < md.length; ++i) {
  693. int val = md[i] & 0xff;
  694. if (val < 16) {
  695. sb.append("0");
  696. }
  697. sb.append(Integer.toHexString(val));
  698. }
  699. } catch (Exception ex) {
  700. }
  701. return sb.toString().toUpperCase();
  702. }
  703. }