在Grpc Android Java中使用双向流时如何检测(物理)断开连接
我使用了在Grpc Android Java中使用双向流时如何检测(物理)断开连接,java,android,grpc,grpc-java,Java,Android,Grpc,Grpc Java,我使用了双向流概念,即Grpc使用异步存根 下面是我的代码 @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); btnOnline = (Button) findViewById(R.id.btnOnline); btnOffline = (
双向流
概念,即Grpc
使用异步存根
下面是我的代码
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btnOnline = (Button) findViewById(R.id.btnOnline);
btnOffline = (Button) findViewById(R.id.btnOffline);
btnAcceptRide = (Button) findViewById(R.id.btnAcceptRide);
btnCancelRide = (Button) findViewById(R.id.btnCancelRide);
txtCode = (EditText) findViewById(R.id.txtCode);
txtReply = (TextView) findViewById(R.id.txtReply);
ClientConnState = 0;
btnOnline.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
new GrpcTask().execute();
}
});
private class GrpcTask extends AsyncTask<Void, Void, String> {
private String mHost;
private String mMessage;
private int mPort;
private ManagedChannel mChannel;
@Override
protected void onPreExecute() {
mHost = "localhost";
mPort = 8080;
mChannel = ManagedChannelBuilder.forAddress("192.168.0.102", 50049)
.usePlaintext(true)
.build();
blockingStub = bidirectionalserviceGrpc.newBlockingStub(mChannel);
asyncStub = bidirectionalserviceGrpc.newStub(mChannel);
}
@Override
protected String doInBackground(Void... nothing) {
try {
final CountDownLatch countDownLatch = new CountDownLatch(1);
requestStreamObserver = asyncStub.requestRide(new StreamObserver<Bidirectional.RideReply>() {
@Override
public void onNext(Bidirectional.RideReply value) {
if (countDownLatch.getCount() > 0) {
countDownLatch.countDown();
}
}
@Override
public void onError(Throwable t) {
countDownLatch.countDown();
}
@Override
public void onCompleted() {
countDownLatch.countDown();
}
});
Bidirectional.RideRequest rideRequest = Bidirectional.RideRequest.newBuilder()
.setRequestid(1)
.setDrivercode(txtCode.getText().toString())
.build();
requestStreamObserver.onNext(rideRequest);
if (!countDownLatch.await(15, TimeUnit.SECONDS)) {
throw new RuntimeException(
"Could not finish rpc within 1 minute, the server is likely down");
}
return "completed";
} catch (Exception e) {
StringWriter sw = new StringWriter();
PrintWriter pw = new PrintWriter(sw);
e.printStackTrace(pw);
pw.flush();
return "Failed... : " + System.lineSeparator() + sw;
}
}
@Override
protected void onPostExecute(String result) {
Log.e(logger.getName(), result);
}
}
final Handler handler = new Handler() {
@Override
public void handleMessage(Message msg) {
// Write Logic here
super.handleMessage(msg);
}
};
@覆盖
创建时受保护的void(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btnOnline=(按钮)findViewById(R.id.btnOnline);
btnOffline=(按钮)findViewById(R.id.btnOffline);
btnAcceptRide=(按钮)findViewById(R.id.btnAcceptRide);
btnCancelRide=(按钮)findViewById(R.id.btnCancelRide);
txtCode=(EditText)findViewById(R.id.txtCode);
txtReply=(TextView)findViewById(R.id.txtReply);
ClientConnState=0;
btnOnline.setOnClickListener(新视图.OnClickListener(){
@凌驾
公共void onClick(视图){
新建GrpcTask().execute();
}
});
私有类GrpcTask扩展了AsyncTask{
私有字符串mHost;
私有字符串消息;
私人进口;
专用管理频道mcchannel;
@凌驾
受保护的void onPreExecute(){
mHost=“localhost”;
mPort=8080;
McChannel=ManagedChannel Builder.forAddress(“192.168.0.102”,50049)
.usePlaintext(真)
.build();
blockingStub=双向服务GRPC.新blockingStub(MCChannel);
asyncStub=双向服务GRPC.newStub(MCChannel);
}
@凌驾
受保护的字符串doInBackground(无效…无){
试一试{
最终倒计时锁存器倒计时锁存器=新倒计时锁存器(1);
requestStreamObserver=asyncStub.requestRide(新的StreamObserver(){
@凌驾
public void onNext(双向.RideReply值){
如果(countDownLatch.getCount()>0){
countdownlock.countDown();
}
}
@凌驾
公共作废登记员(可丢弃的t){
countdownlock.countDown();
}
@凌驾
未完成的公共无效(){
countdownlock.countDown();
}
});
双向.RideRequest RideRequest=双向.RideRequest.newBuilder()
.setRequestid(1)
.setDrivercode(txtCode.getText().toString())
.build();
requestStreamObserver.onNext(rideRequest);
如果(!countDownLatch.Wait(15,时间单位秒)){
抛出新的运行时异常(
“无法在1分钟内完成rpc,服务器可能已关闭”);
}
返回“已完成”;
}捕获(例外e){
StringWriter sw=新的StringWriter();
PrintWriter pw=新的PrintWriter(sw);
e、 printStackTrace(pw);
pw.flush();
返回“Failed…”“+System.lineSeparator()+sw;
}
}
@凌驾
受保护的void onPostExecute(字符串结果){
Log.e(logger.getName(),result);
}
}
最终处理程序=新处理程序(){
@凌驾
公共无效handleMessage(消息消息消息){
//在这里写逻辑
超级handleMessage(msg);
}
};
现在一切都正常了。我可以使用已建立的流对服务器/客户端进行ping/pong。但当我关闭服务器并从客户端发出流请求时,它会无限期地等待。我希望它抛出OnError()
事件,但它不会
有人能帮我解决这个问题吗?根据服务器的运行方式和客户端的操作,TCP可能不会发现连接中断。您应该在
ManagedChannel Builder
上启用keepAliveTime()
。Javadoc应该让您开始使用,如果您感兴趣,它会提供更多信息
您可能还希望启用idleTimeout()