集成支付宝支付
ONE Goal ,ONE Passion!
第一步:正式准备阶段.
服务端.
负责生成订单及签名,及接受支付异步通知。
客户端
负责使用服务端传来的订单信息调用支付宝支付接口,及根据SDK同步返回的支付结果展示结果页。
注意: 私钥必须放在服务端,签名过程必须放在服务端。
第二步,开始接入的准备工作.
解压接口压缩文件(文件名是WS_MOBILE_PAY_SDK_BASE.zip),找到安卓的压缩文件(文件名是支付宝钱包支付开发包标准版(Android).zip)。
标准开发包以jar包方式提供给商户应用工程集成,打开alipay-sdk-common文件夹获取alipaySDK-20150602.jar,后8位数字标识发布日期,商户可根据日期时间判断SDK版本的新旧。
1, 将alipaySDK-20150602.jar包放入商户应用工程的libs目录下,如下图。
2,进入商户应用工程的Java Build Path,将libs目录下的alipaySDK-20150602.jar导入,如下图。
3,选中Order and Export,勾选alipaySDK-20150602.jar,如下图。
修改Manifest
在商户应用工程的AndroidManifest.xml文件里面添加声明:
<code class="hljs xml has-numbering" style="display: block; padding: 0px; background: transparent; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal;"><span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"><<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">activity </span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:name</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"你的支付界面(即PayDemoActivity )"</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:configChanges</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"orientation|keyboardHidden|navigation"</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:exported</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"false"</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:screenOrientation</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"behind"</span> ></span> <span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"></<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">activity</span>></span></code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; background-color: rgb(238, 238, 238); top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right;"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; background-color: rgb(238, 238, 238); top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right;"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li></ul>
权限声明:
<code class="hljs xml has-numbering" style="display: block; padding: 0px; background: transparent; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal;"><span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"><<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">uses-permission</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:name</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"android.permission.INTERNET"</span> /></span> <span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"><<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">uses-permission</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:name</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"android.permission.ACCESS_NETWORK_STATE"</span> /></span> <span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"><<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">uses-permission</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:name</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"android.permission.ACCESS_WIFI_STATE"</span> /></span> <span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"><<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">uses-permission</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:name</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"android.permission.READ_PHONE_STATE"</span> /></span> <span class="hljs-tag" style="color: rgb(0, 102, 102); box-sizing: border-box;"><<span class="hljs-title" style="box-sizing: border-box; color: rgb(0, 0, 136);">uses-permission</span> <span class="hljs-attribute" style="box-sizing: border-box; color: rgb(102, 0, 102);">android:name</span>=<span class="hljs-value" style="box-sizing: border-box; color: rgb(0, 136, 0);">"android.permission.WRITE_EXTERNAL_STORAGE"</span> /></span></code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; background-color: rgb(238, 238, 238); top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right;"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li></ul><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; background-color: rgb(238, 238, 238); top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right;"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li></ul>
第3步 :支付接口调用
需要在新线程中调用支付接口。(可参考alipay_demo实现)
获取PayTask支付对象调用支付(支付或者授权的行为需要在独立的非ui线程中执行)
alipay.pay(payInfo, true)方法中payInfo一些参数含义:
参数 | 意义 |
---|---|
orderInfo | 订单信息—getOrderInfo(“测试的商品”, “该测试商品的详细描述”, “0.01”)返回的数据 |
sign | 后台给我们的签名(后台就是拿着订单信息进行签名) |
getSignType() | “sign_type=\”RSA\”” (固定值) |
我们的支付activity
<code class="hljs java has-numbering" style="display: block; padding: 0px; background: transparent; color: inherit; box-sizing: border-box; font-family: "Source Code Pro", monospace;font-size:undefined; white-space: pre; border-radius: 0px; word-wrap: normal;"><span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-class" style="box-sizing: border-box;"><span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">class</span> <span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">PayDemoActivity</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">extends</span> <span class="hljs-title" style="box-sizing: border-box; color: rgb(102, 0, 102);">FragmentActivity</span> {</span> <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 商户PID</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> String PARTNER = <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"这些字段我们不写在代码中,而是由服务器处理"</span>; <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 商户收款账号</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> String SELLER = <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"这些字段我们不写在代码中,而是由服务器处理"</span>; <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 商户私钥,pkcs8格式</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> String RSA_PRIVATE = <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"这些字段我们不写在代码中,而是由服务器处理"</span>; <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 支付宝公钥</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">static</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> String RSA_PUBLIC = <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"这些字段我们不写在代码中,而是由服务器处理"</span>; <span class="hljs-annotation" style="color: rgb(155, 133, 157); box-sizing: border-box;">@Override</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">protected</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span> <span class="hljs-title" style="box-sizing: border-box;">onCreate</span>(Bundle savedInstanceState) { <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">super</span>.onCreate(savedInstanceState); setContentView(R.layout.<span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"你的布局"</span>); } <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/** * 点击--调用SDK支付 * sign是从后台获得的,因为签名过程涉及一些秘钥之类的,最好不要暴 * 露在代码中,因此我们让后台对数据处理生成签名后直接给我们. */</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span> <span class="hljs-title" style="box-sizing: border-box;">pay</span>(View v) { <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">try</span> { <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/** * 我们仅需对sign 做URL编码 */</span> sign = URLEncoder.encode(sign, <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"UTF-8"</span>); } <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">catch</span> (UnsupportedEncodingException e) { e.printStackTrace(); } <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">//完整的符合支付宝参数规范的订单信息</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">final</span> String payInfo = orderInfo + <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"&sign=\""</span> + sign + <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"\"&"</span> + getSignType(); Runnable payRunnable = <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">new</span> Runnable() { <span class="hljs-annotation" style="color: rgb(155, 133, 157); box-sizing: border-box;">@Override</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">public</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">void</span> <span class="hljs-title" style="box-sizing: border-box;">run</span>() { <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 构造PayTask 对象</span> PayTask alipay = <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">new</span> PayTask(PayDemoActivity.<span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">this</span>); <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 调用支付接口,获取支付结果</span> String result = alipay.pay(payInfo, <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">true</span>); <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// result中已经有支付结果了,不过为了安全性.我们一般去查询自己公司服务器接口,从而得到支付结果.然后再做处理</span> } }; <span class="hljs-comment" style="color: rgb(136, 0, 0); box-sizing: border-box;">// 必须异步调用</span> Thread payThread = <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">new</span> Thread(payRunnable); payThread.start(); } <span class="hljs-javadoc" style="color: rgb(136, 0, 0); box-sizing: border-box;">/** * get the sign type we use. 获取签名方式 * */</span> <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">private</span> String <span class="hljs-title" style="box-sizing: border-box;">getSignType</span>() { <span class="hljs-keyword" style="color: rgb(0, 0, 136); box-sizing: border-box;">return</span> <span class="hljs-string" style="color: rgb(0, 136, 0); box-sizing: border-box;">"sign_type=\"RSA\""</span>; } }</code><ul class="pre-numbering" style="box-sizing: border-box; position: absolute; width: 50px; background-color: rgb(238, 238, 238); top: 0px; left: 0px; margin: 0px; padding: 6px 0px 40px; border-right: 1px solid rgb(221, 221, 221); list-style: none; text-align: right;"><li style="box-sizing: border-box; padding: 0px 5px;">1</li><li style="box-sizing: border-box; padding: 0px 5px;">2</li><li style="box-sizing: border-box; padding: 0px 5px;">3</li><li style="box-sizing: border-box; padding: 0px 5px;">4</li><li style="box-sizing: border-box; padding: 0px 5px;">5</li><li style="box-sizing: border-box; padding: 0px 5px;">6</li><li style="box-sizing: border-box; padding: 0px 5px;">7</li><li style="box-sizing: border-box; padding: 0px 5px;">8</li><li style="box-sizing: border-box; padding: 0px 5px;">9</li><li style="box-sizing