1、目的
实现不同进程间的通信。可以将客户端的数据通过Message传递到服务端,同时服务端的数据也可以通过Message返回到客户端。
2、原理
不同进程间的通信通过Messenger为服务端创建接口,客户端就可以Message发送给服务端,交给服务端的Handler进行处理消息;当然客户端也可以定义Messenger,方便服务端将处理完的消息返回给客户端。
在单一线程中创建包含所有请求的队列,采用串行的方式来处理客户端发送来的消息。
局限性:不能处理大量并发请求。因为所有的请求都是串行执行
3、使用过程
(1)客户端发送message到服务端
创建一个类继承于Service
(a)服务器实现一个Handler,来接收客户端的消息
private class MessengerHandler extends Handler{
@Override
public void handleMessage(Message msg) {
Log.d("MessService","Message is from client");
}
}
(b)通过上面创建的Handler来创建Messenger对象
private Messenger messenger = new Messenger(new MessengerHandler());
(c)将上述的Messenger创建IBinder,通过onBinder返回给客户端
@Override
public IBinder onBind(Intent intent) {
return messenger.getBinder();
}
在Acitivity中实现bind该service
(e)客户端bind该service
private ServiceConnection messConnect = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
isBinderService = true;
servermessenger = new Messenger(service);
Log.d("MessService","bind success");
Message msg = Message.obtain();
msg.what = 1;
msg.arg1 = 2;
try {
servermessenger.send(msg);
} catch (RemoteException e) {
e.printStackTrace();
}
}
@Override
public void onServiceDisconnected(ComponentName name) {
isBinderService = false;
servermessenger = null;
}
};
private void startMessService(){
if (isBinderService){
return;
}
isBinderService= bindService(new Intent(MainActivity.this, MessService.class),messConnect,Context.BIND_AUTO_CREATE);
}
(f)在AndroidMenifest文件中注册该服务,这里将该Service放到另外一个进程中
<service android:name=".service.MessService"
android:process=".messservice">
</service>
上述几步就可以实现了将Message发送到服务端,打印日志如下:
10-30 14:30:57.261 6094-6094/com.j1 D/MessService: bind success
10-30 14:30:57.262 6137-6137/? D/MessService: Message is from client
(2)服务端回调message到客户端
在Activity中
(a)在客户端中定义自己的Messenger
private Messenger clientMessenger = new Messenger(new Handler(){
@Override
public void handleMessage(Message msg) {
Log.d("MessService","get msg from server"+msg.what+", "+msg.arg1);
}
});
(b)将该定义的Messenger和发送给服务端的Message绑定到一起,可以在服务端接收到Message的时候,获得该Messenger,方便服务器回传Message。
在上面的(e)中创建的Message中绑定该Messenger
//。。。。省略代码
Message msg = Message.obtain();
msg.what = 1;
msg.arg1 = 2;
msg.replyTo = clientMessenger;
//。。。。省略代码
在自定义的Service中
(c)在服务端需要返回Message的地方获取(a)创建的Messenger来回传消息。我们暂时先放到Handler
@Override
public void handleMessage(Message msg) {
//。。。。省略代码
Messenger clientMessenger = msg.replyTo;
try {
clientMessenger.send(msg);
} catch (RemoteException e) {
e.printStackTrace();
}
//。。。。省略代码
}
上述几步就可以完成,服务端将Message返回给客户端,打印日志如下:
10-30 15:16:12.290 7944-7944/com.j1 D/MessService: get msg from server
4、总结
(1)Messenger对AIDL进行封装,可以实现基于消息的跨进程通信。
(2)客户端和服务端都可以Messenger来传递消息,通过msg.repayTo = clientMessenger来将客户端的Messenger传递给服务端。
(3)