Java Http介面加簽、驗簽操作方法_java

來源:互聯網
上載者:User

1、業務背景

最近接觸了一些電商業務,發現在處理電商業務介面時,比如淘寶、支付類介面,介面雙方為了確保資料參數在傳輸過程中未經過篡改,都需要對介面資料進行加簽,然後在介面伺服器端對介面參數進行驗簽,確保兩個簽名是一樣的,驗簽通過之後再進行商務邏輯處理。我們這裡主要介紹一下處理思路,至於簽名演算法我不做過多介紹,網上一大堆。

2、處理思路

雙方約定好,參數按特定順序排列,比如按首字母的順序排列,如url:http://xxx/xxx.do?a=wersd&b=sd2354&c=4&signature=XXXXXXXXXXXX(signature為傳入的簽名),等你拿到入參後,將參數串a=wersd&b=sd2354&c=4按你們約定的簽名規則,自己用md5加簽一次,然後和入參的signature值對比,以確認調用者是否合法,這就是介面簽名驗證的思路。

3、執行個體練習

介面雙方經過溝通,對介面達成如下共識:

1、注意事項,主要指介面的的協議、傳入參數類型、簽名演算法、檔案格式等說明

2、下面是一個電商業務介面的真實案例,雙方約定好了介面URL、業務參數、固定參數、簽名以及返回資料格式

介面調用時,介面調用方代碼如下(僅供參考):
package com.pcmall;import java.io.BufferedReader;import java.io.DataOutputStream;import java.io.IOException;import java.io.InputStreamReader;import java.io.UnsupportedEncodingException;import java.net.HttpURLConnection;import java.net.URL;import java.net.URLEncoder;import java.security.MessageDigest;import java.security.NoSuchAlgorithmException;import java.util.ArrayList;import java.util.Collections;import java.util.Iterator;import java.util.List;import java.util.Map;import java.util.TreeMap;public class APITest {  static String TEST_URL = "待定";  static String TEST_KEY = "待定";  static String TEST_SEC = "待定";    public static void main(String[] args) throws UnsupportedEncodingException, NoSuchAlgorithmException {    String result = getResult(TEST_URL, getReqParam());    System.out.print(result);  }  private static String getReqParam() throws UnsupportedEncodingException, NoSuchAlgorithmException {  TreeMap<String, String> req = new TreeMap<String, String>();    req.put("a", TEST_KEY);    req.put("f", "json");    req.put("l", "zh_CN");    req.put("m", "zhongan.repair.query");    req.put("v", "1.0");    req.put("i", "" + System.currentTimeMillis() / 1000);    req.put("params", "{\"assignNo\":\"TEST018\"}");    req.put("s", sign(req, null, TEST_SEC));        StringBuilder param = new StringBuilder();    for (Iterator<Map.Entry<String, String>> it = req.entrySet().iterator(); it.hasNext();) {      Map.Entry<String, String> e = it.next();      param.append("&").append(e.getKey()).append("=").append(URLEncoder.encode(e.getValue(), "UTF-8"));    }        return param.toString().substring(1);  }    private static String sign(Map<String, String> paramValues, List<String> ignoreParamNames, String secret) throws NoSuchAlgorithmException, UnsupportedEncodingException {    StringBuilder sb = new StringBuilder();    List<String> paramNames = new ArrayList<String>(paramValues.size());    paramNames.addAll(paramValues.keySet());    if (ignoreParamNames != null && ignoreParamNames.size() > 0) {      for (String ignoreParamName : ignoreParamNames) {        paramNames.remove(ignoreParamName);      }    }    Collections.sort(paramNames);        sb.append(secret);    for (String paramName : paramNames) {      sb.append(paramName).append(paramValues.get(paramName));    }    sb.append(secret);    MessageDigest md = MessageDigest.getInstance("SHA-1");    return byte2hex(md.digest(sb.toString().getBytes("UTF-8")));  }    private static String byte2hex(byte[] bytes) {    StringBuilder sign = new StringBuilder();    for (int i = 0; i < bytes.length; i++) {      String hex = Integer.toHexString(bytes[i] & 0xFF);      if (hex.length() == 1) {        sign.append("0");      }      sign.append(hex.toUpperCase());    }    return sign.toString();  }    private static String getResult(String urlStr, String content) {    URL url = null;    HttpURLConnection connection = null;    try {      url = new URL(urlStr);      connection = (HttpURLConnection) url.openConnection();      connection.setDoOutput(true);      connection.setDoInput(true);      connection.setRequestMethod("POST");      connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded;charset=UTF-8");      connection.setUseCaches(false);      connection.connect();            DataOutputStream out = new DataOutputStream(connection.getOutputStream());      out.write(content.getBytes("UTF-8"));      out.flush();      out.close();            BufferedReader reader = new BufferedReader(new InputStreamReader(connection.getInputStream(), "UTF-8"));      StringBuffer buffer = new StringBuffer();      String line = "";      while ((line = reader.readLine()) != null) {        buffer.append(line);      }      reader.close();      return buffer.toString();    } catch (IOException e) {      e.printStackTrace();    } finally {      if (connection != null) {        connection.disconnect();      }    }        return null;  }    }

伺服器端代碼如下(僅供參考):

@RequestMapping("/repairTakeOrder")@ResponseBodypublic ResponseVO repairTakeOrder(@RequestBody String jsonStr) {logger.info("repairTakeOrder入參:" + jsonStr);ResponseVO responseVO = null;try {RepairOrder repairOrder = JackJsonUtil.toBean(jsonStr,RepairOrder.class);TreeMap<String, String> paramsMap = new TreeMap<String, String>();paramsMap.put("gsxx01", repairOrder.getGsxx01());paramsMap.put("orderType", repairOrder.getOrderType().toString());paramsMap.put("serviceNo", repairOrder.getServiceNo());paramsMap.put("vipCard", repairOrder.getVipCard());paramsMap.put("customerName", repairOrder.getCustomerName());paramsMap.put("customerPhone", repairOrder.getCustomerPhone());paramsMap.put("customerTel", repairOrder.getCustomerTel());paramsMap.put("province", repairOrder.getProvince());paramsMap.put("city", repairOrder.getCity());paramsMap.put("county", repairOrder.getCounty());paramsMap.put("address", repairOrder.getAddress());paramsMap.put("salerCode", repairOrder.getSalerCode());paramsMap.put("salerName", repairOrder.getSalerName());paramsMap.put("storeCode", repairOrder.getStoreCode());paramsMap.put("storeName", repairOrder.getStoreName());paramsMap.put("site", repairOrder.getSite());paramsMap.put("siteDesp", repairOrder.getSiteDesp());paramsMap.put("engineerCode", repairOrder.getEngineerCode());paramsMap.put("engineerName", repairOrder.getEngineerName());if (repairOrder.getServiceDate() != null) {paramsMap.put("serviceDate",DateUtils.formatDate(repairOrder.getServiceDate()));}if (repairOrder.getSalePrice() != null) {paramsMap.put("salePrice", repairOrder.getSalePrice().toString());}paramsMap.put("profitCenter", repairOrder.getProfitCenter());paramsMap.put("costCenter", repairOrder.getCostCenter());paramsMap.put("gsxx02", repairOrder.getGsxx02());paramsMap.put("returnReason", repairOrder.getReturnReason());if (repairOrder.getOriOrder() != null) {paramsMap.put("oriOrder", repairOrder.getOriOrder().toString());}if (repairOrder.getOriServiceNo() != null) {paramsMap.put("oriServiceNo", repairOrder.getOriServiceNo());}// 拼接簽名原串(a=1&b=2)String paramSrc = RequestUtils.getParamSrc(paramsMap);logger.info("簽名原串:" + paramSrc);//進行驗簽操作if (SignUtils.verifymd5(paramSrc, repairOrder.getSign())) {//處理商務邏輯responseVO=erpServiceImpl.repairTakeOrder(repairOrder);} else {responseVO = new ResponseVO();responseVO.setSuccess(false);responseVO.setErrorMsg("驗簽失敗");}} catch (Exception e) {logger.error("", e);responseVO = new ResponseVO();responseVO.setSuccess(false);responseVO.setErrorMsg(StringUtils.isNotBlank(e.getMessage()) ? e.getMessage() : "後台異常");}return responseVO;}

以上這篇Java Http介面加簽、驗簽操作方法就是小編分享給大家的全部內容了,希望能給大家一個參考,也希望大家多多支援雲棲社區。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.