在近期,公司須要開發一個關於在線支付的模塊,因此須要用到第三方支付平臺java
轉載請註明出處:http://blog.csdn.net/ht_android/article/details/45307165android
通過一週多的時間對這兩種支付平臺的研究,完成功能後將經驗分享給你們,但願能幫助到有需求的朋友。express
首先是支付寶的開發資料方面: 接口申請url https://b.alipay.com/order/productDetail.htm?productId=2014110308141993api
API開發文檔 http://download.alipay.com/public/api/base/WS_MOBILE_PAY_SDK_BASE.zip服務器
申請流程 註冊支付寶帳號——進行實名認證——提交審覈資料——審覈經過app
備註:申請經過後會得到:合做者身份ID(PID),該ID在項目配置中須要用到dom
開發流程: 第一步: 下載API開發文檔後,便可獲取官方Demo,該Demo中須要將審覈經過後獲取的PID替換,而且輸入支付寶收款帳戶便可。這裏很是簡單,就不過多敘述。 第二步: 官方Api開發文檔中,存在一個openssl的文件夾,該文件夾主要是用於生成支付寶所須要用到的公鑰以及私鑰。打開該文件夾能夠看到詳細的生成方式,根據提示生成公鑰及私鑰,請注意,密鑰須要通過pkcs8二次加密。 第三步: 將生成的公鑰和私鑰配置到Demo中。 第四步(可省略): 爲了方便後期維護,建議將支付寶相關的方法及配置項抽取出來作爲單獨的一個類,後期須要使用直接調用便可。代碼以下:異步
package com.alipay.pay; import java.io.UnsupportedEncodingException; import java.net.URLEncoder; import java.text.DecimalFormat; import java.text.SimpleDateFormat; import java.util.Date; import java.util.Locale; import java.util.Random; import android.app.Activity; import android.os.Handler; import android.os.Message; import android.support.v4.app.FragmentActivity; import android.view.View; import android.widget.Toast; import com.alipay.sdk.app.PayTask; public class Alipay { // 商戶PID public static final String PARTNER = "******"; // 商戶收款帳號 public static final String SELLER = "***@alipay.com"; // 商戶私鑰,pkcs8格式 public static final String RSA_PRIVATE = "*****"; // 支付寶公鑰 public static final String RSA_PUBLIC = "******"; public static final int SDK_PAY_FLAG = 1; public static final int SDK_CHECK_FLAG = 2; private Handler mHandler; private Activity activity; private String orderNo; public Alipay(Handler handler, Activity activity) { mHandler = handler; this.activity = activity; } /** * call alipay sdk pay. 調用SDK支付 * */ public void pay(PayInfo payinfo) { // 訂單 DecimalFormat df = new DecimalFormat("0.00"); String orderInfo = getOrderInfo(payinfo.getName(), payinfo.getDesc() + " ", df.format(payinfo.getPrice() * payinfo.getRate())); // 對訂單作RSA 簽名 String sign = sign(orderInfo); try { // 僅需對sign 作URL編碼 sign = URLEncoder.encode(sign, "UTF-8"); } catch (UnsupportedEncodingException e) { e.printStackTrace(); } // 完整的符合支付寶參數規範的訂單信息 final String payInfo = orderInfo + "&sign=\"" + sign + "\"&" + getSignType(); Runnable payRunnable = new Runnable() { @Override public void run() { // 構造PayTask 對象 PayTask alipay = new PayTask(activity); // 調用支付接口,獲取支付結果 String result = alipay.pay(payInfo); Message msg = new Message(); msg.what = SDK_PAY_FLAG; msg.obj = result; mHandler.sendMessage(msg); } }; // 必須異步調用 Thread payThread = new Thread(payRunnable); payThread.start(); } /** * check whether the device has authentication alipay account. * 查詢終端設備是否存在支付寶認證帳戶 * */ public void check(View v) { Runnable checkRunnable = new Runnable() { @Override public void run() { // 構造PayTask 對象 PayTask payTask = new PayTask(activity); // 調用查詢接口,獲取查詢結果 boolean isExist = payTask.checkAccountIfExist(); Message msg = new Message(); msg.what = SDK_CHECK_FLAG; msg.obj = isExist; mHandler.sendMessage(msg); } }; Thread checkThread = new Thread(checkRunnable); checkThread.start(); } /** * get the sdk version. 獲取SDK版本號 * */ public void getSDKVersion() { PayTask payTask = new PayTask(activity); String version = payTask.getVersion(); Toast.makeText(activity, version, Toast.LENGTH_SHORT).show(); } /** * create the order info. 建立訂單信息 * */ public String getOrderInfo(String subject, String body, String price) { // 簽約合做者身份ID String orderInfo = "partner=" + "\"" + PARTNER + "\""; // 簽約賣家支付寶帳號 orderInfo += "&seller_id=" + "\"" + SELLER + "\""; // 商戶網站惟一訂單號 orderInfo += "&out_trade_no=" + "\"" + getOutTradeNo() + "\""; // 商品名稱 orderInfo += "&subject=" + "\"" + subject + "\""; // 商品詳情 orderInfo += "&body=" + "\"" + body + "\""; // 商品金額 orderInfo += "&total_fee=" + "\"" + price + "\""; // 服務器異步通知頁面路徑 orderInfo += "¬ify_url=" + "\"" + "http://notify.msp.hk/notify.htm" + "\""; // 服務接口名稱, 固定值 orderInfo += "&service=\"mobile.securitypay.pay\""; // 支付類型, 固定值 orderInfo += "&payment_type=\"1\""; // 參數編碼, 固定值 orderInfo += "&_input_charset=\"utf-8\""; // 設置未付款交易的超時時間 // 默認30分鐘,一旦超時,該筆交易就會自動被關閉。 // 取值範圍:1m~15d。 // m-分鐘,h-小時,d-天,1c-當天(不管交易什麼時候建立,都在0點關閉)。 // 該參數數值不接受小數點,如1.5h,可轉換爲90m。 orderInfo += "&it_b_pay=\"30m\""; // extern_token爲通過快登受權獲取到的alipay_open_id,帶上此參數用戶將使用受權的帳戶進行支付 // orderInfo += "&extern_token=" + "\"" + extern_token + "\""; // 支付寶處理完請求後,當前頁面跳轉到商戶指定頁面的路徑,可空 orderInfo += "&return_url=\"m.alipay.com\""; // 調用銀行卡支付,需配置此參數,參與簽名, 固定值 (須要簽約《無線銀行卡快捷支付》才能使用) // orderInfo += "&paymethod=\"expressGateway\""; return orderInfo; } /** * get the out_trade_no for an order. 生成商戶訂單號,該值在商戶端應保持惟一(可自定義格式規範) * */ public String getOutTradeNo() { SimpleDateFormat format = new SimpleDateFormat("MMddHHmmss", Locale.getDefault()); Date date = new Date(); String key = format.format(date); Random r = new Random(); key = key + r.nextInt(); key = key.substring(0, 15); String md5 = Constants.MD5(key); this.orderNo = md5; return md5; } /** * 獲取已經生產的訂單編號 * * @return */ public String getOrderNo() { return this.orderNo; } /** * sign the order info. 對訂單信息進行簽名 * * @param content * 待簽名訂單信息 */ public String sign(String content) { return SignUtils.sign(content, RSA_PRIVATE); } /** * get the sign type we use. 獲取簽名方式 * */ public String getSignType() { return "sign_type=\"RSA\""; } }
從上面代碼能夠看出,程序的主要運行流程是:經過開啓一個子線程去調用支付寶的支付功能,獲取到支付結果後,經過Handler通知UI線程,根據支付結果去顯示不一樣的。ide
到這裏基本上整個開發流程已經大體完成了,具體細節根據需求去修改便可。官方建議支付完成後,將獲取到的支付結果上傳到本身的服務器,經過官方提供的API進行驗證,建議添加該流程。網站