当一个app的基础功能需要提供给其他app使用的时候,例如我们平常使用美团点外卖和滴滴进行打车时,最后订单结算的时候进行支付,这个时候弹出支付方式中基本会包含支付宝和微信支付这两种方式,这个过程其实涉及美团、滴滴与支付宝或者微信进行通信的过程,美团需要把商品信息(订单号、金额)传递给支付宝,那是如何传递的呢?本文会对此过程进行一个大概的梳理。
如上图所示,一个进程无法和另一个进程直接通信,在android中,每个应用,都分配一个独立的进行,进程之间的通信是基于Binder驱动来实现的,体现在应用层是通过android接口下定义语言AIDL(android interace defeniton language)通过代理来处理的。
下面通过demo具体来演示如何通过AIDL来实现两个app间的通信。
一:服务端(支付宝端)
1.创建AIDL文件
在android studio中src/main目录下,右键创建AIDL文件,创建好文件之后,点击菜单栏Budil中的make project,在app/build/generated下会产品aidl文件夹。
IAliPayNeiXian接口类详情如下:
同时aidl文件的内容如下:
备注:aidl传递的数据类型,8中基本类型可直接传递,自定义bean类需要实现Parcel接口。
2.创建一个供第三方(美团 滴滴)调用的PayService
2.1 其中Service中的onBind()方法中返回的IBinder即为IAliPayNeiXian接口中继承Binder和实现了IAliPayNeiXian的Stub类,详情如下:
1public IBinder onBind(Intent intent) {
2 Log.i(TAG,"返回支付宝服务代理");
3 return new AliPayProxy();
4}
2.2 再来看看具体的AliPayProxy
1//该类实现了IAliPayNeiXian接口,并继承了Binder
2private class AliPayProxy extends IAliPayNeiXian.Stub{
3 @Override
4 public void pay(String account, double monkey) throws RemoteException {
5 //调用支付宝中的pay方法
6 go2Pay(account,monkey);
7 }
8}
2.3 接着去真正的执行支付宝中扣除商品金额的方法
1/**
2 * 在支付宝中实际的对某个帐号进行具体金额的支付
3 * @param account
4 * @param monkey
5 */
6private void go2Pay(String account, double monkey) {
7 //TODO对帐号扣除具体金额的操作
8 Log.i(TAG,"帐号:" + account + ",支付了" + monkey + "金额");
9}
3. PayService需在清单文件中设置action给第三方进行隐式调用
1
2
3
4
5
二:客户端(美团 滴滴等)处理
1.拷贝服务端的AIDL文件,且相应的包名要一致
2.绑定服务,拿到支付宝PayService中的AliPayProxy(IAliPayNeiXian.Stub)
1/**
2 * 绑定支付宝的服务,拿到支付宝服务中的代理IAliPayNeiXian
3 * @param view
4 */
5public void bindService(View view){
6 //隐式调用其他app的组件
7 Intent intent = new Intent();
8 intent.setAction("com.example.alipaydemo");
9 intent.setPackage("com.example.alipaydemo");
10 myConnection = new MyConnection();
11 bindService(intent, myConnection, Service.BIND_AUTO_CREATE);
12}
其中myConnection的具体类如下,在绑定服务连接的回调方法中通过IAliPayNeiXian.Stub.asInterface(IBinder)拿到支付宝PayService中的IAliPayNeiXian,进而通过该proxy,把商品金额等信息传递过去:
1private IAliPayNeiXian proxy;
2class MyConnection implements ServiceConnection{
3
4 /**
5 * 服务连接的回调方法中,会拿到支付宝app中的IAliPayNeiXian
6 * @param name
7 * @param service
8 */
9 @Override
10 public void onServiceConnected(ComponentName name, IBinder service) {
11 proxy = IAliPayNeiXian.Stub.asInterface(service);
12 Log.i(TAG,"美团绑定支付宝服务,拿到了支付宝支付的代理:IAliPayNeiXian");
13 }
14
15 @Override
16 public void onServiceDisconnected(ComponentName name) {
17
18 }
19}
3.美团客户端发起具体商品金额支付
1/**
2 *美团页面发起商品支付宝支付
3 * @param view
4 */
5public void callAliPay(View view){
6 try {
7 proxy.pay("wangkaibing",99.9f);
8 } catch (RemoteException e) {
9 Log.i(TAG,"RemoteException is caught");
10 }
11}
现在我们具体来运行下代码,在美团客户端进行对支付宝PayService的绑定,日志如下:
进行具体商品金额的支付,日志如下:
上面的梳理只是把Android中app进程间通信应用层做个分析,希望自己后面有机会把涉及底层Binder驱动的原理也能够梳理出来。