參考資料:html
https://b.alipay.com/order/productDetail.htm?productId=2013080604609654android
https://b.alipay.com/order/productDetail.htm?productId=2013080604609654&tabId=4#ps-tabinfo-hashweb
--- 網頁支付服務器
http://wappaygw.alipay.com/service/rest.htm? req_data= <direct_trade_create_req> <subject>12121212</subject> <out_trade_no>12121021</out_trade_no> <total_fee>1</total_fee> <seller_account_name>che12121</seller_account_name> <notify_url>http://www.alipay.com/waptest0504/servlet/NotifyReceiver</notify_url> <out_user>outID123</out_user> <merchant_url>http://www.alipay.com</merchant_url> <pay_expire>10</pay_expire> </direct_trade_create_req> &service=alipay.wap.trade.create.direct &sec_id=0001&partner=12112 &req_id=11121212 &sign=bDfw5%2Bctc3pxzl7emPxqOod4EiPu3BkE0 Um54g4whHT22CwLbOn1gzyE%2BU5SIleGPke2rNQ%3D &format=xml &v=2.0
網頁支付拿這服務器返回的地址,經過webview直接請求就能夠app
public class AlipayWebActivity extends Activity { private WebView mWebView; private ProgressDialog mProgressDialog; private static final String TAG = "AlipayWebActivity"; protected static final int PAY_SUCCESS = 20; protected static final int LOAD_FINISH_CODE = 40; private static final int DEFAULT_CODE = 50; private ImageView quitImageView; public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.web); FactoryUtil.getInstance().addActivity(this); quitImageView = (ImageView) findViewById(R.id.iv_quit); mWebView = (WebView) findViewById(R.id.webview); mWebView.setBackgroundColor(0); initial(); quitImageView.setOnClickListener(new MyOnClickListener()); } @SuppressLint({ "SetJavaScriptEnabled", "HandlerLeak" }) @TargetApi(Build.VERSION_CODES.HONEYCOMB) private void initial() { String url = getIntent().getStringExtra("url"); LogUtil.i(TAG, url); WebSettings webSettings = mWebView.getSettings(); mWebView.requestFocus(); webSettings.setJavaScriptEnabled(true); mWebView.setFocusable(true); webSettings.setBuiltInZoomControls(true); mWebView.setScrollBarStyle(0); if (MobileUtil.getMobileVersion()>11) { mWebView.setLayerType(View.LAYER_TYPE_SOFTWARE, null); } mWebView.setWebChromeClient(new WebChromeClient() { public void onProgressChanged(WebView view, int newProgress) { LogUtil.i(TAG, "newProgress: " + newProgress); if (newProgress == 100 && mProgressDialog!=null) { mProgressDialog.dismiss(); } super.onProgressChanged(view, newProgress); } }); mWebView.setWebViewClient(new WebViewClient() { public boolean shouldOverrideUrlLoading(WebView view, String url) { LogUtil.i(TAG, "URL : " + url); LogUtil.i(TAG, "URL : " + url.contains("&cmd=success&")); loadUrl(view, url); return true;//中止在當前界面 } public void onPageFinished(WebView view, String url) { LogUtil.i(TAG, "onPageFinished" + url); //trade_status : TRADE_FINISHED,成功以後處理
super.onPageFinished(view, url); } public void onPageStarted(WebView view, String url, Bitmap favicon) { super.onPageStarted(view, url, favicon); LogUtil.i(TAG, "onPageStarted" + url); } }); loadUrl(mWebView, url); } @SuppressLint("HandlerLeak") private Handler mUihandler = new Handler() { public void handleMessage(Message msg) { switch (msg.what) { case PAY_SUCCESS: clearCache(); FactoryUtil.getInstance().exit(); break; case LOAD_FINISH_CODE: if (mProgressDialog != null && mProgressDialog.isShowing()) { mProgressDialog.dismiss(); } break; case DEFAULT_CODE: showProgressDialog(AlipayWebActivity.this, R.string.dialog_loading); } super.handleMessage(msg); } }; private void loadUrl(final WebView webView, final String url) { mUihandler.sendEmptyMessage(DEFAULT_CODE); webView.loadUrl(url); } public boolean onKeyDown(int keyCode, KeyEvent event) { LogUtil.i(TAG, "can goback:" + mWebView.canGoBack()); if (keyCode == KeyEvent.KEYCODE_BACK && mWebView.canGoBack()) { mWebView.goBack(); return true; } else if (keyCode == KeyEvent.KEYCODE_BACK) { onBackPressed(); return true; } return super.onKeyDown(keyCode, event); } public void showProgressDialog(Context context, int message) { if (mProgressDialog == null) { mProgressDialog = new ProgressDialog(context); mProgressDialog.setMessage(context.getText(message)); mProgressDialog.show(); } } private void clearCache() { mWebView.clearCache(true); mWebView.loadDataWithBaseURL(null, "", "text/html", "utf-8", null); finish(); } private class MyOnClickListener implements OnClickListener{ @Override public void onClick(View v) { int id = v.getId(); if (id==R.id.iv_quit) { finish(); } } } }
--- 快捷支付
一、公鑰,密鑰,簽名在服務器端完成,比放在客戶端安全。
二、報4000 4100通常就是參數出現錯誤,仔細比對,若是參數都沒問題,頗有多是sign也就是簽名沒有經過。簽名以後不能對已經簽名的字符串作任何修改,由於支付寶須要解密的。
三、若是報服務器繁忙,而後打印出參數非法的警告信息時, KeyFactory.getInstance("RSA", "BC") 能夠解決。
四、sign簽名要utf-8格式。
ide
/* * Copyright (C) 2010 The MobileSecurePay Project * All right reserved. * author: shiqun.shi@alipay.com */ package com.ztgame.dudu.payment.alipay; import android.app.Activity; import android.content.DialogInterface; import android.os.Handler; import android.os.Message; import android.widget.Toast; import com.alipay.android.app.sdk.AliPay; import com.ztgame.dudu.payment.R; import com.ztgame.dudu.payment.ui.FactoryUtil; import com.ztgame.dudu.payment.util.BaseDialogUtil; import com.ztgame.dudu.payment.util.LogUtil; public class AlipayUtil { private static String TAG = "AlipayUtil"; private Activity activity; private String order; private static final int RQF_PAY = 1; private static final int RQF_LOGIN = 2; public AlipayUtil(Activity activity, String order) { this.activity = activity; this.order = order; LogUtil.i(TAG, activity.toString() + " " + activity.getMainLooper().toString()); } public void pay() { // 根據訂單信息開始進行支付 try { new Thread() { public void run() { AliPay alipay = new AliPay(activity, mHandler); String result = alipay.pay(order); Message msg = new Message(); msg.what = RQF_PAY; msg.obj = result; mHandler.sendMessage(msg); } }.start(); } catch (Exception ex) { Toast.makeText(activity, R.string.pay_fail,Toast.LENGTH_SHORT).show(); activity.finish(); } } Handler mHandler = new Handler() { public void handleMessage(android.os.Message msg) { Result result = new Result((String) msg.obj); switch (msg.what) { case RQF_PAY: case RQF_LOGIN: { try { String ret = result.getResult(); result.parseResult(); LogUtil.i(TAG, ret); LogUtil.i(TAG, "1: " + result.isSignOk + " 2: " + result.memo + " 3: " + result.resultStatus); // 先驗籤通知 // 1: false 2: 3: 操做成功(9000) // 驗籤失敗 if (result.isSignOk) { Toast.makeText(activity, R.string.check_sign_fail, Toast.LENGTH_SHORT).show(); } else {// 驗籤成功。驗籤成功後再判斷交易狀態碼 if ("操做成功(9000)".equals(result.resultStatus)) {// 判斷交易狀態碼,只有9000表示交易成功
//成功以後執行
}); } else { Toast.makeText(activity, "支付失敗。交易狀態碼:" + result.resultStatus, Toast.LENGTH_SHORT).show(); } } } catch (Exception e) { e.printStackTrace(); Toast.makeText(activity, R.string.pay_fail, Toast.LENGTH_SHORT).show(); } } break; default: break; } }; }; }
剩下的文檔裏面都有,只須要處理的是支付成功與失敗的邏輯。oop
提交到支付寶的訂單快捷支付:ui
partner="2088511"&out_trade_no="2014410490790001211"&subject="支付0.01元"&body="支付0.01元"&total_fee="0.01" ¬ify_url="http%3A%2F%2F122.32.196.157%3A90%2Freeonse%2Falipaydut"&service="mobile.securitypay.pay"&_input_charset="utf-8"&payment_type="1"&seller_id="2008354621302100"&show_url="m.alipay.cm" &it_b_pay="30m"&sign="MPZ8lamKUDgidaIn2KwX%2B6GX4o3BSheEUI2xg3aJa1b%2B1M6VXP%2BaMA3szSBPyl7UYm%2Fdhz8KVuFn5Du057R2lUNQ%2B2nSb3qSXZ6rZcNQ2rCrZ84Kiy3MWFBqlt%2Buq%2FufaCOnGEQyo18NXnm6OGDazSMppQP9cr434ILLguhcntM%3D" &sign_type="RSA"