我正在使用第 3 方库 - 如何使用 Single<> 或 RxJava Observable 包装他们的网络调用?

I'm using a 3rd party library - How do I wrap their network call with a Single<> or RxJava Observable?

我正在尝试使用第三方 SDK 实现 MVVM,该 SDK 可以查询钱包余额。 (他们没有 API 端点只有他们的 SDK,所以没有改造库使用)

在我的 MainRepository class 中,我正在使用他们的一种方法来发出请求和 return 钱包余额。

public Request<BigInteger> getWalletBalance(String walletAddress) {
        return thirdPartyService.getBalance(new Address(walletAddress));
}

在我的 MainViewModel class 中,我正在使用他们的 SDK

发出请求
public void getWalletBalance(String address) {
        mainRepository.getWalletBalance(address).execute(new Callback<BigInteger>() {
            @Override
            public void onSuccess(BigInteger result) {
                walletBalanceLiveData.postValue(String.valueOf(result));

            }

            @Override
            public void onFailure(Exception exception) {
                balanceErrorLiveData.postValue("Failed to get wallet balance");
            }
        });
    }

问题是,他们的方法 .execute() 是 运行 在 Android UI 线程上导致应用程序在进行查询时冻结。

如果我使用的是 RxJava,我可以做这样的事情(在我的 ViewModel 中)...

mainRepository.getWalletBalance(address)
                .subscribeOn(Schedulers.newThread())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new SingleObserver<BigInteger>() {
                    @Override
                    public void onSubscribe(@NonNull Disposable d) {

                    }

                    @Override
                    public void onSuccess(@NonNull BigInteger result) {
                        
                    }

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

但这行不通,因为 return 在我上面的 MainRepository 方法中输入 return 是 Request<BigInteger>.

所以我的问题是,是否可以用 RxJava class 包装 Request<BigInteger> 以便我可以用这个第三方库干净地实现 RxJava 请求?

或者我可以做一个更好或更简单的解决方案,以便在后台线程上发出请求并return在 ViewModel 中处理结果?

这可能不是世界上最干净的解决方案,但它可以工作。 让 execute 函数阻塞 Singles return 因为我们知道它已经正常阻塞了。

Single.fromCallable(()->{
        BigInteger bigIntResult = null;
           //You can take advantage of execute's blocking behavior by 
           // letting it block the callable's return.
        mainRepository.getWalletBalance(address).execute(new Callback<BigInteger>() {
            @Override
            public void onSuccess(BigInteger result) {
                bigIntResult = result;
            }
            @Override
            public void onFailure(Exception exception) {
                  throw exception;
            }
        }
        return bigIntResult;
})
            .subscribeOn(Schedulers.newThread())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(new SingleObserver<BigInteger>() {
                @Override
                public void onSubscribe(@NonNull Disposable d) {
                     // grab the disposable
                }
                @Override
                public void onSuccess(@NonNull BigInteger result) {
                     // Here is the callable's return
                     walletBalanceLiveData.postValue(String.valueOf(result));
                }

                @Override
                public void onError(@NonNull Throwable e) {
                     balanceErrorLiveData.postValue("Failed to get wallet balance");
                }
            }
});