順豐電子面單SDK呼叫總結-java
一、獲得順豐電子面單SDK
https://qiao.sf-express.com/index.html 豐橋系統中,文件中心->SDK使用說明->運單自助列印SDK
支援的開發環境: Java sdk 支援1.8及以上
二、啟動SDK本地服務:
1.windows環境:
①將csim_waybill_print_service_V1.0.3.jar和RUN-SF-PRINTER.bat置於同一目錄下,雙擊RUN-SF-PRINTER.bat檔案即可開啟本地運單列印服務。(這種情況也有可能開啟不成功,建議使用下面命令的方式)
②java -jar path [port]
例:(不填寫埠,則預設為4040)
2.linux環境:
①linux下安裝jdk1.8,執行命令:yum -y install java
②建立資料夾sf-service將csim_waybill_print_service_V1.0.3.jar放在資料夾中
③執行命令:chmod 777 csim_waybill_print_service_V1.0.3.jar 進行授權
④linux下進入sf-service檔案,執行命令:nohup java -jar csim_waybill_print_service_V1.0.3.jar &
(注:nohup <程式名> &:命令在Unix/Linux中,普通程序用“&”符號放到後臺執行,則控制檯logout後,程序仍然繼續執行,起到守護程序的作用,使用nohup命令後,原程式的的標準輸出被自動改向到當前目錄下的nohup.out檔案,起到了log的作用)。
3.驗證伺服器執行情況:
瀏覽器:http://localhost:4040/servertest.html(4040為啟動埠),顯示“OK!”則表示啟動成功
4.Linux系統下需安裝黑體字型!!!
①檢視安裝了哪些中文字型,命令:fc-list :lang=zh(如果命令不存在,則yum安裝fontconfig
②cd /usr/share/fonts(沒有目錄則建立,命令:mkdir /usr/share/fonts)
③將順豐sdk裡帶的黑體字型放到該資料夾下
⑤建立字型快取
mkfontscal (如果命令不存在,則yum安裝mkfontscale,命令:yum install mkfontscale)
mkfontdir (如果命令不存在,則yum安裝mkfontscale,命令:yum install mkfontdir)
fc-cache -fv
⑥讓字型生效
source /etc/profile
fc-match (檢視設定是否生效)
三、專案中引用順豐jar包
方法一:將sf-csim-printer-api-1.0.3.jar包放在專案lib目錄下,並add as library(使用maven的不建議這樣做)
方法二:將sf-csim-printer-api-1.0.3.jar包放到maven私服上,並在專案中引用依賴
<dependency>
<groupId>sf-csim</groupId>
<artifactId>printer-api</artifactId>
<version>1.0.3</version>
</dependency>
四、呼叫demo
1.使用210面單,使用SDK中生成圖片url和呼叫印表機url
/** * 呼叫印表機 彈出視窗 可選擇份數 適用於單張列印【三聯單】 */ private static String printUrl = "http://localhost:4040/sf/waybill/print?type=V3.0_poster_100mm210mm&output=print"; /** * 直接輸出圖片的BASE64編碼字串 可以使用html標籤直接轉換成圖片【三聯單】 */ private static String imageUrl = "http://localhost:4040/sf/waybill/print?type=V3.0_poster_100mm210mm&output=image";
2.列印電子面單方法
(注:列印url方法無需接返回的byte[],自動會調起印表機)@Override public byte[] sfPrintWaybill(Map<String, Object> params, Integer printType) throws Exception { logger.info("進入順豐列印快遞面單介面:params={},printType={}", JSONObject.toJSONString(params),printType); //1.根據業務需求確定請求地址 String reqURL = ""; if (printType == 1){ reqURL = imageUrl; } else if (printType == 2){ reqURL = printUrl; } //2.電子面單頂部是否需要logo true:需要logo false:不需要logo boolean topLogo = false; if(reqURL.contains("V2.0")&&topLogo){ reqURL=reqURL.replace("V2.0", "V2.1"); } if(reqURL.contains("V3.0")&&topLogo){ reqURL=reqURL.replace("V3.0", "V3.1"); } //3.構建WaybillDtoList List<WaybillDto> waybillDtoList = bulidWaybillDto(params); HttpURLConnection httpConn = buildHttpConn(reqURL); ObjectMapper objectMapper = new ObjectMapper(); StringWriter stringWriter = new StringWriter(); objectMapper.writeValue(stringWriter,waybillDtoList); httpConn.getOutputStream().write(stringWriter.toString().getBytes()); httpConn.getOutputStream().flush(); httpConn.getOutputStream().close(); InputStream in = httpConn.getInputStream(); BufferedReader in2=new BufferedReader(new InputStreamReader(in)); String y=""; String strImg=""; while((y=in2.readLine())!=null){ strImg=y.substring(y.indexOf("[")+1,y.length()-"]".length()-1); if(strImg.startsWith("\"")){ strImg=strImg.substring(1,strImg.length()); } if(strImg.endsWith("\"")){ strImg=strImg.substring(0,strImg.length()-1); } } //將換行全部替換成空 strImg=strImg.replace("\\n", ""); byte[] bytes = (new Base64()).decode(strImg); return bytes; }
3.構建WaybillDtoList
private List<WaybillDto> bulidWaybillDto(Map<String, Object> params) throws Exception{ List<WaybillDto> waybillDtoList = new ArrayList<>(); WaybillDto dto = new WaybillDto(); //對應clientCode dto.setAppId(clientCode); //對應checkWord dto.setAppKey(checkword); //快遞單號 String mailNo = (String) params.get("mailNo"); dto.setMailNo(mailNo); //收件人資訊 String receiverProvince = (String) params.get("receiverProvince"); String receiverCity = (String) params.get("receiverCity"); String receiverCounty = (String) params.get("receiverCounty"); String receiverAddress = (String) params.get("receiverAddress"); String receiverMobile = (String) params.get("receiverMobile"); String receiverName = (String) params.get("receiverName"); dto.setConsignerProvince(receiverProvince); dto.setConsignerCity(receiverCity); dto.setConsignerCounty(receiverCounty); dto.setConsignerAddress(receiverAddress); //詳細地址建議最多38個字,欄位過長可能影響列印效果 dto.setConsignerCompany(d_company); dto.setConsignerMobile(receiverMobile); dto.setConsignerName(receiverName); //寄件人資訊 dto.setDeliverProvince(j_province); dto.setDeliverCity(j_city); dto.setDeliverCounty(j_county); dto.setDeliverCompany(j_company); dto.setDeliverAddress(j_address);//詳細地址建議最多38個字,欄位過長可能影響列印效果 dto.setDeliverName(j_contact); dto.setDeliverMobile(j_tel); //原寄地程式碼(下訂單介面順豐會返回,需要儲存) String originCode = (String) params.get("originCode"); dto.setZipCode(originCode); //目的地程式碼(下訂單介面順豐會返回,需要儲存) String destCode = (String) params.get("destCode"); dto.setDestCode(destCode); //快遞型別 //1 :標準快遞 2.順豐特惠 3: 電商特惠 5:順豐次晨 6:順豐即日 7.電商速配 15:生鮮速配 dto.setExpressType(1); //陸運E標示 //業務型別為“電商特惠、順豐特惠、電商專配、陸運件”則必須列印E標識,用以提示中轉場分揀為陸運 dto.setElectric("E"); // 1-寄付 2-到付 3-第三方支付 dto.setPayMethod(1); //加密項 //加密寄件人及收件人名稱 dto.setEncryptCustName(true); //加密寄件人及收件人聯絡手機 dto.setEncryptMobile(true); //物品資訊 String orderNo = (String) params.get("orderNo"); List<CargoInfoDto> cargoInfoList = new ArrayList<>(); List<OrderDetailOutputDto> orderDetailList = (List<OrderDetailOutputDto>) params.get("orderDetailList"); for (OrderDetailOutputDto orderDetail : orderDetailList){ CargoInfoDto cargo = new CargoInfoDto(); cargo.setCargo(orderDetail.getCommodityName()); cargo.setCargoCount(orderDetail.getNum()); cargo.setCargoUnit("雙"); cargo.setSku(orderDetail.getSkuNo()); cargo.setRemark(orderNo); cargoInfoList.add(cargo); } dto.setCargoInfoDtoList(cargoInfoList); waybillDtoList.add(dto); logger.info("生成電子運單請求引數: "+ MyJsonUtil.object2json(dto)); return waybillDtoList;
4.構建Http連線
private HttpURLConnection buildHttpConn(String reqURL) throws Exception{ /**注意 需要使用對應業務場景的url **/ URL myURL = new URL(reqURL); HttpURLConnection httpConn = (HttpURLConnection) myURL.openConnection(); httpConn.setDoOutput(true); httpConn.setDoInput(true); httpConn.setUseCaches(false); httpConn.setRequestMethod("POST"); httpConn.setRequestProperty("Content-Type", "application/json;charset=utf-8"); httpConn.setConnectTimeout(10000); httpConn.setReadTimeout(2 * 5000); return httpConn; }
五、controller層呼叫及前端
//預覽列印快遞單 byte[] imageByte = orderBackgroundApi.printWaybill(order,orderDeatilList, orderAddressList.get(0),orderConsignList.get(0),printType); return JSONObject.toJSONString(imageByte);
controller層呼叫api,並返回byte陣列給前端,前端頁面中使用<img>標籤,並使用src="data:image/png;base64,"方式來展示二進位制圖片(需要對二進位制陣列進行base64編碼,順豐介面返回給我們的已經是經過base64編碼的字串)
function printWaybill(orderId,orderNo) { layer.load(2); $.ajax({ url:"/order/printWaybill.sc", type:"post", data:{orderId:orderId,orderNo:orderNo,printType:1}, dataType:"json", success:function (data) { layer.closeAll(); layer.open({ type:1, title: '預覽', closeBtn:1, area:['850px','600px'], content:'<img src="data:image/png;base64,'+data+'" style="width:850px;"/>', btn: ['列印'], yes:function (index, layero) { $.ajax({ url: "/order/printWaybill.sc", type: "post", data: {orderId: orderId, orderNo: orderNo, printType:2}, dataType: "json", success:function (data) { mmGrid.load(); } }); } }); } }) }