简体   繁体   English

Android rxjava2 Flowable与CompositeDisposable

[英]Android rxjava2 Flowable with compositedisposable

I have a problem with Flowables and adding them to the compositeDisposables. 我在Flowables上遇到了问题,并将它们添加到CompositeDisposables中。 I want to switch from an Observable to a Flowable as the operation might emit 1000 or more values. 我想从Observable切换到Flowable,因为该操作可能会发出1000个或更多值。 Im somewhat unexperienced with rxjava2 so please forgive me if that question is stupid :) 我对rxjava2不太了解,所以如果这个问题很愚蠢,请原谅我:)

So far I used the observable like this: 到目前为止,我使用了如下所示的可观察对象:

 public Observable<String> uploadPictureRx(String path)
    {
        return Observable.create(new ObservableOnSubscribe<String>()
        {
            @Override
            public void subscribe(ObservableEmitter<String> e) throws Exception
            {
                Uri file = Uri.fromFile(new File(path));
                String segment = file.getLastPathSegment();
                UploadTask uploadTask = reference.child("SomeChild").child(segment).putFile(file);


                uploadTask.addOnFailureListener(new OnFailureListener()
                {
                    @Override
                    public void onFailure(@NonNull Exception exception)
                    {
                        e.onError(exception);
                    }
                }).addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>()
                {
                    @Override
                    public void onSuccess(UploadTask.TaskSnapshot taskSnapshot)
                    {                           
                        //noinspection VisibleForTests
                        downloadUrl = taskSnapshot.getDownloadUrl();
                        String url = downloadUrl.getPath();
                        e.onNext(url);
                        e.onComplete();
                    }
                }).addOnProgressListener(new OnProgressListener<UploadTask.TaskSnapshot>()
                {
                    @Override
                    public void onProgress(UploadTask.TaskSnapshot taskSnapshot)
                    {
                        //noinspection VisibleForTests
                        long bytes = taskSnapshot.getBytesTransferred();
                        String bytesS = String.valueOf(bytes);
                        e.onNext(bytesS);
                    }
                });
            }
        });
    }

and called the method like this: 然后调用这样的方法:

private void uploadPicToFireBaseStorage(String path)
    {
        compositeDisposable.add(storageService.uploadPictureRx(path)
                .subscribeOn(Schedulers.io())
                .observeOn(mainScheduler)
                .subscribeWith(new DisposableObserver<String>()
                {

                    @Override
                    public void onNext(String s)
                    {
                        String ss = s;
                        System.out.println(ss);
                    }

                    @Override
                    public void onError(Throwable e)
                    {
                        e.printStackTrace();
                    }

                    @Override
                    public void onComplete()
                    {
                        view.displayToast("Picture Upload completed");
                    }
                })
        );
    }

This works fine! 这样很好! However when I try to do the same with a Flowable instead of observable it wont compile: 但是,当我尝试使用Flowable而不是Observable进行相同操作时,它将无法编译:

public Flowable<String> uploadPictureRx(String path)
    {
        return Flowable.create(new FlowableOnSubscribe<String>()
        {

            @Override
            public void subscribe(FlowableEmitter<String> e) throws Exception
            {
                Uri file = Uri.fromFile(new File(path));
                String segment = file.getLastPathSegment();
                UploadTask uploadTask = reference.child("somechild").child(segment).putFile(file);    

                uploadTask.addOnFailureListener(new OnFailureListener()
                {
                    @Override
                    public void onFailure(@NonNull Exception exception)
                    {
                        e.onError(exception);
                    }
                }).addOnSuccessListener(new OnSuccessListener<UploadTask.TaskSnapshot>()
                {
                    @Override
                    public void onSuccess(UploadTask.TaskSnapshot taskSnapshot)
                    {                           
                        //noinspection VisibleForTests
                        downloadUrl = taskSnapshot.getDownloadUrl();
                        String url = downloadUrl.getPath();
                        e.onNext(url);
                        e.onComplete();
                    }
                }).addOnProgressListener(new OnProgressListener<UploadTask.TaskSnapshot>()
                {
                    @Override
                    public void onProgress(UploadTask.TaskSnapshot taskSnapshot)
                    {
                        //noinspection VisibleForTests
                        long bytes = taskSnapshot.getBytesTransferred();
                        String bytesS = String.valueOf(bytes);
                        e.onNext(bytesS);
                    }
                });
            }
        }, BackpressureStrategy.BUFFER);

    }

The Error is: Inferred type 'E' for type parameter 'E' is not within its bound; 错误是:类型参数'E'的推断类型'E'不在其范围内; should implement 'org.reactivestreams.Subscriber 应该实现'org.reactivestreams.Subscriber

My guess is, that Flowable does not implement Disposable and thats why it wont compile. 我的猜测是,Flowable没有实现Disposable,这就是为什么它无法编译。 I have no clue if thats true or not, just my best guess so far. 我不知道那是否是正确的,只是到目前为止我的最佳猜测。 Or do I have to change subscribeWith() to subscribe()? 还是我必须将subscribeWith()更改为subscribe()? I dont know what the impact of that change would be. 我不知道这种改变会带来什么影响。

Anyway suggestions how to make this work and get this Flowable into my compositedisposable is really appreciated. 无论如何,关于如何使这项工作有效并使该Flowable进入我的CompositeDisposable的建议,我们深表感谢。

Thanks guys! 多谢你们!

Edit: 编辑:

Tried to change the DisposableObserver into a Subscriber. 试图将DisposableObserver更改为订户。 But this results in the following Error: Compiler Error 但这会导致以下错误: 编译器错误

Flowables use Subscription instead of Disposable for the reason of Backpressure. 由于背压的原因,可流动物料使用“订购”而不是“一次性”。 Basically use Subscription.request() method to tell observable how many items I want for that moment. 基本上使用Subscription.request()方法告诉那一刻我想要多少个项目。

Change your code: 更改您的代码:

private void uploadPicToFireBaseStorage(String path)
{
    compositeDisposable.add(storageService.uploadPictureRx(path)
            .subscribeOn(Schedulers.io())
            .observeOn(mainScheduler)
            .subscribeWith(new DisposableObserver<String>()
            {

                @Override
                public void onNext(String s)
                {
                    String ss = s;
                    System.out.println(ss);
                }

                @Override
                public void onError(Throwable e)
                {
                    e.printStackTrace();
                }

                @Override
                public void onComplete()
                {
                    view.displayToast("Picture Upload completed");
                }
            })
    );
}

into 进入

private void uploadPicToFireBaseStorage(String path)
{
    compositeDisposable.add(storageService.uploadPictureRx(path)
            .subscribeOn(Schedulers.io())
            .observeOn(mainScheduler)
            .subscribeWith(new ResourceSubscriber<String>()
            {
                @Override
                public void onNext(String s)
                {
                    String ss = s;
                    System.out.println(ss);
                }

                @Override
                public void onError(Throwable e)
                {
                    e.printStackTrace();
                }

                @Override
                public void onComplete()
                {
                    view.displayToast("Picture Upload completed");
                }
            })
    );
}

Flowable works according to pub-sub pattern , ie publisher - subscriber pattern Flowable作品根据发布-订阅模式 ,即发行商-用户模式

whereas , 而,

Observable works according to observer pattern 根据观察者模式 Observable作品

In pub-sub pattern there is middle event channel which holds the data released by the publisher and then the event channel emits the data and the subscriber gets the data in onNext(...) . pub-sub模式中,有一个中间事件通道,该通道保存发布者publisher的数据,然后event channel 发出数据,而subscriberonNext(...)获取数据。

Whereas, In observer pattern the observable directly emits the data or throws the data directly to the observer . 而在观察者模式中, observable直接发出数据或将数据直接抛出给observer This might create back-pressure.(cause it emits the whole data in one go.) 这可能会产生反压(因为它会一次性发出整个数据。)

So use ( Flowable ) 所以用( Flowable

 .subscribeWith(new ResourceSubscriber<>) // in case of flowable

Or, 要么,

 .subscribeWith(new DisposableSubscriber<>) 

whereas in case of ( observable ) use 而在( observable )使用的情况下

  .subscribeWith(new ResourceObserver<>)  

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM