Java Async MongoDB驱动程序和RxJava2 Observables

时间:2018-11-02 15:25:36

标签: java mongodb observable rx-java2 asyncmongo

我正在研究RxJava2的反应式编程,我对它在MongoDB等异步数据库驱动程序中的用法有疑问。

如果我使用阻塞的MongoDB驱动程序来获取集合,则方法是这样的:

public class MyDao{
   ...
   public Document getFirstDocument(String collectionName){
      MongoCollection<Document> collection = database.getCollection(collectionName);
      return collection.find().first();
   }
}



public class MyService {
   ...
   public Observable<Document> getFirstOf(String collectionName){
       return Observable.just(myDao.getFirstDocument(collectionName)); 
   }
}

相反,使用MongoDB的异步驱动程序,我的读取操作返回类型为void(而不是Document或Future),其中包含回调方法,例如:

collection.find().first(
        (document, throwable) -> {
            myService.myCallback(document);
        }
);

那么,如何将可观察文档传递给MyService?

public class MyDao{
   ...
   public void getFirstDocument(String collectionName){
      MongoCollection<Document> collection = database.getCollection(collectionName);
      collection.find().first(
        (document, throwable) -> {
            //SOME SORT OF CALLBACK
        }
     );
   }
}



public class MyService {
   ...
   public Observable<Document> getFirstOf(String collectionName){
       return ??????? 
   }
}

1 个答案:

答案 0 :(得分:1)

中使用Observable.just()
public Observable<Document> getFirstOf(String collectionName){
    return Observable.just(myDao.getFirstDocument(collectionName)); 
}

它等于下一个代码

public Observable<Document> getFirstOf(String collectionName){
    Document doc = myDao.getFirstDocument(collectionName);
    return Observable.just(doc); 
}

您会注意到它不是async代码,并且对DB的请求是在调用线程上执行的。要制作该代码async,您需要像这样重写它

public Observable<Document> getFirstOf(String collectionName){
    return Observable.fromCallable(() -> myDao.getFirstDocument(collectionName)); 
}

如果您正在使用async MongoDB驱动程序并将其包装在Observable中,则可以用这种方式编写

public Observable<Document> getFirstDocument(String collectionName) {
    return Observable.create(emitter -> {
        MongoCollection<Document> collection = database.getCollection(collectionName);
        collection.find().first((document, throwable) -> {
            if(document != null) {
                emitter.onNext(document);
                emitter.onComplete();
            } else if(throwable != null) {
                emitter.onError(throwable);
            }
        });
    });
}