我在我的Android应用程序中使用RXJava2,我有一个奇怪的场景。 我想执行未知数量的作业(由用户确定),但我希望它们仅在某个值发生变化后才启动。
我的具体要求是使用Socket进行服务器通信, 流程如下:
如何使用RXJava2实现这一目标?
先谢谢。
答案 0 :(得分:3)
您可以使用UnicastSubject
作为队列部分并执行一些flatMap
- 一旦建立连接就ping:
UnicastSubject<String> userRequests = new UnicastSubject.create();
Single.fromCallable(() -> new Socket("server", port))
.subscribeOn(Schedulers.io())
.flatMapObservable(socket -> {
InputStream in = socket.getInputStream();
OutputStream out = socket.getOutputStream();
byte[] responseBuffer = new byte[4096];
return userRequests
.observeOn(Schedulers.io())
.map(request -> {
out.write(request.getBytes());
int n = in.read(responseBuffer);
if (n >= 0) {
return new String(responseBuffer, 0, n);
}
throw new IOException("Socket closed while waiting for response");
})
.doFinally(() -> socket.close());
});
由于您正在处理Socket级别,因此您有责任确定要写入的请求的正确编码以及要读取的响应的正确解码(即,响应的长度(以字节为单位)特定的要求)。
答案 1 :(得分:0)
我相信你需要FlowableTransformers.valve()
,RxJava2Extensions。
它应该像这样工作
PublishSubject<String> jobs = PublishSubject.create().toSerialized();
BehaviorSubject<Boolean> isConnected = BehaviorSubject.createDefault(false);
CompositeDisposable disposables = new CompositeDisposable();
public void connect() {
disposables.add(socketService.subscribe((success) -> {
isConnected = true;
}));
}
public void addJob(String job) {
jobs.onNext(job);
}
public void executeQueuedTasks() {
disposables.add(jobs
.toFlowable(BackpressureStrategy.BUFFER)
.compose(FlowableTransformers.valve(isConnected))
.subscribeWith(new DisposableObserver<>() {
...
})
);
}
public void destroy() {
disposables.clear();
}
}
但上面的UnicastSubject
样本更有可能发挥作用,我把它写在了我的头顶。