支付宝开发流程:
1、在支付宝申请一个账号并开通开发者功能和移动支付的功能。
支付宝地址:https://auth.alipay.com/login/index.htm?goto=https%3A%2F%2Fopenhome.alipay.com%2Fdeveloper%2FisvApply.htm%3Fflag%3Daop
支付宝移动支付地址:https://b.alipay.com/order/productDetail.htm?productId=2014110308141993
2、上面步骤完成后下载支付宝集成文档和SDK。
3、
命令:
RSA密钥生成命令
生成RSA私钥
openssl>genrsa -out rsa_private_key.pem 1024
生成RSA公钥
openssl>rsa -in rsa_private_key.pem -pubout -out rsa_public_key.pem
将RSA私钥转换成PKCS8格式
openssl>pkcs8 -topk8 -inform PEM -in rsa_private_key.pem -outform PEM -nocrypt
打开openssl按照上面的命令生成个密钥rsa_private_key.pem 和 rsa_public_key.pem。
根据rsa_private_key.pem 和 rsa_public_key.pem生成pkcs8密钥。
4、然后把rsa_public_key.pem里的内容组装成一个字符串(去掉空格、换行、-----BEGIN PUBLIC KEY-----、-----END PUBLIC KEY-----),复制到支付宝网站上生成支付宝公钥。
5、在工程里的androidManifest.xml里添加申明
<activity
android:name="com.alipay.sdk.app.H5PayActivity"
android:configChanges="orientation|keyboardHidden|navigation"
android:exported="false"
android:screenOrientation="behind"
android:windowSoftInputMode="adjustResize|stateHidden" >
</activity>
<activity
android:name="com.alipay.sdk.pay.demo.PayDemoActivity"
android:icon="@drawable/msp_icon"
android:label="@string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
6、把alipaySDK-20150602.jar拷贝到lib下,把alipay下的Base64.java和PayResult.java SignUtils,java拷贝到工程项目里。
7、首先获得订单信息getOrderInfo(),然后对订单用pkcs8密钥做RSA签名sign(getOrderInfo()),
生成订单数据String payInfo = getOrderInfo() + "&sign=\"" + sign(getOrderInfo()) + "\"&"
+ getSignType(); //getSignType为获取订单的签名方式,默认为"sign_type=\"RSA\""。
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;
}
//对订单进行签名
public String sign(String content) {
return SignUtils.sign(content, RSA_PRIVATE);
}
8、在新线程中调用支付接口
Runnable payRunnable = new Runnable() {
@Override
public void run() {
// 构造PayTask 对象
PayTask alipay = new PayTask(this);
// 调用支付接口,获取支付结果
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();
private Handler mHandler = new Handler() {
public void handleMessage(Message msg) {
switch (msg.what) {
case SDK_PAY_FLAG: {
PayResult payResult = new PayResult((String) msg.obj);
// 支付宝返回此次支付结果及加签,建议对支付宝签名信息拿签约时支付宝提供的公钥做验签
String resultInfo = payResult.getResult();
String resultStatus = payResult.getResultStatus();
// 判断resultStatus 为“9000”则代表支付成功,具体状态码代表含义可参考接口文档
if (TextUtils.equals(resultStatus, "9000")) {
Toast.makeText(this, "支付成功",
Toast.LENGTH_SHORT).show();
} else {
// 判断resultStatus 为非“9000”则代表可能支付失败
// “8000”代表支付结果因为支付渠道原因或者系统原因还在等待支付结果确认,最终交易是否成功以服务端异步通知为准(小概率状态)
if (TextUtils.equals(resultStatus, "8000")) {
Toast.makeText(this, "支付结果确认中",
Toast.LENGTH_SHORT).show();
} else {
// 其他值就可以判断为支付失败,包括用户主动取消支付,或者系统返回的错误
Toast.makeText(this, "支付失败",
Toast.LENGTH_SHORT).show();
}
}
break;
}
case SDK_CHECK_FLAG: {
Toast.makeText(this, "检查结果为:" + msg.obj,
Toast.LENGTH_SHORT).show();
break;
}
default:
break;
}
};
};