前言
在這之前,筆者釋出了兩篇移動app支付相關博文,得到一些關注,但是由於博文中程式碼零碎,有些讀者私信博主,以及加筆者qq諮詢相關問題。考慮到這些,筆者把之前專案中的支付相關程式碼從業務中剝離出來,重構,形成了現在的EasyPay。
EasyPay專案地址:github.com/xiong-it/Ea…,歡迎star & fork
本文原創作者:MichaelX,部落格連結:blog.csdn.net/xiong_it 轉載請註明來源,謝謝合作!
本篇文章已授權微信公眾號 guolin_blog(郭霖)獨家釋出.複製程式碼
EasyPay是什麼
EasyPay旨在幫助Android開發者快速整合接入移動支付SDK,其中包括主流的微信APP支付,支付寶APP支付,銀聯支付(開發中)。
為什麼要用EasyPay
EasyPay和微信支付等移動支付SDK的區別
EasyPay是一個開源的聚合支付可定製化框架,目前已整合微信APP支付,支付寶APP支付SDK。銀聯支付(開發中)。
Android開發者只需要簡單呼叫EasyPay的幾行程式碼,即可調起支付客戶端,完成支付流程,得到支付結果。
EasyPay宗旨:簡單,易用,可擴充套件。
EasyPay和其他第三方聚合支付的區別
第三方聚合支付,如知名的Ping++,需要同時接入其Server端SDK和Client端SDK,使接入企業面臨風險:
1、資訊洩露風險
2、支付整合服務商提供服務跟不上商戶業務發展需要的風險
3、支付整合服務商系統穩定性、安全性的風險
4、資金安全風險
---知乎:《使用第三方支付整合有何風險,例如 Beecloud 或者 Ping++?》
此外,天下沒有免費的午餐,第三方聚合支付平臺一般需要收取5%~15%左右的手續費等各種服務費用,使得接入企業收益受損。
而使用開源的EasyPay,程式碼透明,與Server端無關,Android開發者只需要根據自己需求對EasyPay進行個性化定製,即可打造一個支付平臺齊全的無風險支付框架。但是客觀的講,這同時也是EasyPay的短板,它只簡化了APP端開發者的呼叫工作,Server端工作人員仍需要按照移動支付第三方平臺的SDK文件進行開發。
如果覺得EasyPay對你有幫助,你付出的僅僅是一個點贊,或者一個star或者fork,如果不滿意,請幫忙提issue指出,而不是5%-15%左右的手續費等各種服務費用。
通過閱讀EasyPay原始碼,你可以知道移動支付的流程是怎樣的:
APP->APP伺服器->支付平臺後臺伺服器->APP伺服器->APP->支付客戶端->APP複製程式碼
通過擴充套件EasyPay,你可以較快的搭建一個私有的功能完善的支付框架。
EasyPay怎麼用
使用者場景:
APP使用者選擇一個價格為666元的商品:"皮皮蝦",商品描述:"此商品屬性過於強大,難以調教,一般人切勿輕易購買,吼吼!",然後使用者進入收款臺,選擇了微信支付。
好勒,皮皮蝦,我們們走!此處省略:皮皮蝦,我們們走.jpg
PayParams params = new PayParams.Builder(this)
.wechatAppID("your_wechat_appid")// 僅當支付方式選擇微信支付時需要此引數
.payWay(PayWay.WechatPay)
.goodsPrice(66600)// 單位為:分
.goodsName("皮皮蝦")
.goodsIntroduction("此商品屬性過於強大,難以調教,一般人切勿輕易購買,吼吼!")
.httpType(HttpType.Get)
.httpClientType(NetworkClientType.Retrofit)
.requestBaseUrl("http://blog.csdn.net/")// 此處替換為為你的app伺服器host主機地址
.build();
EasyPay.newInstance(params).requestPayInfo(new OnPayInfoRequestListener() {
@Override
public void onPayInfoRequetStart() {
// TODO 在此處做一些loading操作,progressbar.show();
}
@Override
public void onPayInfoRequstSuccess() {
// TODO 可以將loading狀態去掉了。請求預支付資訊成功,開始跳轉到客戶端支付。
}
@Override
public void onPayInfoRequestFailure() {
// / TODO 可以將loading狀態去掉了。獲取預支付資訊失敗,會同時得到一個支付失敗的回撥。
}
}).toPay(new OnPayResultListener() {
@Override
public void onPaySuccess(PayWay payWay) {
// 支付成功
}
@Override
public void onPayCancel(PayWay payWay) {
// 支付流程被使用者中途取消
}
@Override
public void onPayFailure(PayWay payWay, int errCode) {
// 支付失敗,errCode碼詳見來源部落格或者github專案主頁的README文件
}
});複製程式碼
開發者呼叫步驟:
- 通過建造者模式建立支付引數PayParams例項並傳入EasyPay的建立方法中
- 傳入支付結果回撥介面例項得到支付結果回撥
假如你的app中每個商品有id,請求伺服器時可以用商品id代替價格,讓伺服器自己去查詢價格,防止客戶端中的商品價格被惡意修改。
開發者需要做什麼
上一節是開發者在Activity/Fragment之類的View層呼叫程式碼,除此之外,開發者還需要做一些少量的額外的工作。
需要匯入EasyPay/library原始碼依賴並修改app客戶端相關檔案
- 下載EasyPay原始碼到本地
- 在Android Studio中開啟你的app專案
- Android Studio左上角File->New->Import Module->... 選擇library目錄匯入,app會自動依賴library這個module
- 複製
EasyPay/sample
下wxapi
包到你的包路徑下,假如你的包名:com.app.payclient
,那麼wxapi包應該放在payclient包下面 - 按照
EasyPay/sample
的AndroidMenifest.xml
檔案修改你的清單檔案 - 按照
EasyPay/sample
的proguard-rules.pro
修改你的混淆檔案
需要修改伺服器請求路徑和請求欄位和返回的json解析
由於筆者並不知道你的伺服器地址和請求路徑及欄位和返回json格式,所以你只需要動動小手修改EasyPay/library
中網路請求和解析*部分程式碼即可.
假如你的支付api介面文件如下:
host:api.yourhost.com/
路徑:pay/
請求方式為:Http,get
請求需要的引數欄位為:
假設你想使用的網路框架是Retrofit2。那麼network/NetwrokClientInterf
的實現類RetrofitClient需要做如下修改:
由於Retrofit請求一般需要藉助一個xxService類,那麼實際修改的是xxService類,以EasyPay原始碼中的network/PrePayInfoService
為例,它需要修改成如下:
public interface PrePayInfoService {
@GET("pay/")
Call<ResponseBody> getPrePayInfo(@Query("pay_way")String payWay, @Query("price") String GoddsPrice, @Query("goods_name") String goodsName, @Query(("goods_introduction")) String goodsIntroduce);
/*@POST("pay/")
Call<ResponseBody> postPrePayInfo(@Query("pay_way")String payWay, @Query("price") String GoddsPrice, @Query("goods_name") String goodsName, @Query(("goods_introduction")) String goodsIntroduce);*/
}
// (如需更多欄位請自行新增引數)複製程式碼
當網路連線使用其他框架時,需要在NetworkClientInterf對應的實現類中修改路徑及請求引數欄位。
假如當前使用者使用了微信支付,當伺服器返回的資料格式如下時:
假如json的格式如下:
以你們server端人員給出的實際json欄位來修改pay/PrePayInfo
。
當為其他支付方式時,也需要在對應的PayStragetyInterf支付實現策略類中修改解析。
library原始碼中需要修改的地方都打上了TODO
標籤,匯入Android Studio後,如下圖方式檢視:
開發者能做什麼
EasyPay目前實現了微信,支付寶app支付,如果你覺得支付邏輯程式碼不OK?完全可以通過實現PayStragetyInterf來完全重寫一個自己的微信,支付寶支付策略。
EasyPay支援的平臺(微信,支付寶,銀聯)不在你的需求範圍內?可以通過實現PayStragetyInterf來擴充套件一種支付方式。
EasyPay支援的網路框架(HttpUrlConnection,OkHttp3(前兩者嚴格意義上不屬於框架),Volley,Retrofit2)用的不順手?那就自己擼一個NetworkClientInterf介面的實現類來實現自己的網路請求客戶端。
其他,還是不夠滿足你的需求,歡迎提出issue,或者加入一起開發,完善該repo,打造一個更加優秀的EasyPay。
本文原創作者:MichaelX,部落格地址:blog.csdn.net/xiong_it.轉載…
歡迎光臨:MichaelX's Blog
後記
EasyPay算筆者的第一個正式的開源專案吧,受益於開源社群,也希望為開源奉獻一點力量,幫助一些開發者快速打造一個無風險的功能完備的支付框架。
EasyPay專案地址
附錄
移動支付開發博文
微信支付:Android App支付系列(一):微信支付接入詳細指南
支付寶:Android App支付系列(二):支付寶SDK接入詳細指南
移動支付的流程
- APP將商品資訊post給APP伺服器
- APP伺服器攜帶商品資訊和一些其他資訊請求支付平臺伺服器,獲取預支付訂單資訊
- APP伺服器得到預支付訂單資訊並返給APP
- APP解析預支付訂單資訊
- APP利用解析後的預支付資訊調起支付客戶端(微信,支付寶,等)
- 支付客戶端將支付結果返給APP
- APP向使用者展示支付結果
EasyPay的回撥errCode錯誤碼列表
通用errCode | 意義 |
---|---|
1 | 當前網路無連線(尚未進入支付階段) |
2 | 請求APP伺服器超時(尚未進入支付階段) |
-1 | 支付失敗-原因未知,需要開發者手動排查 |
微信errCode | 一般不會碰到 |
-3 | 微信接收支付請求失敗 |
-4 | 微信支付認證失敗,拒絕支付交易 |
-5 | 微信版本低,不支援交易 |
-6 | 微信拒絕了支付交易 |
-7 | 未安裝微信客戶端,交易失敗 |
支付寶errCode | 一般不會碰到 |
8000 | 支付結果待確認,生成了交易訂單,但是未支付。 |
6002 | 網路差導致支付失敗 |
6004 | 支付結果未知 |
6005 | 支付失敗,原因未知 |