繁体   English   中英

即使没有附加观察者,如何触发LiveData SwitchMap

[英]How to trigger LiveData SwitchMap even if there is no observer attached

问题:

在其结果必须具有活动的观察者之前,switchMap转换不会触发。 我正在尝试触发switchMap转换,即使没有观察者也是如此。 谁能建议我如何实现此功能? 下面有一些代码描述了当前的情况。

繁殖方法:

在ProfileViewModel中,UI可以观察两个不同的LiveData

  • profileLiveData :观察配置文件数据
  • profileApiStateLiveData :观察从后端获取配置文件数据的Http调用的状态

ProfileViewModel.java

public class ProfileViewModel extends AndroidViewModel {

    private MutableLiveData<Boolean> getProfileCommand = new MutableLiveData<>();

    public ProfileViewModel(@NonNull Application application) {
        super(application);
        profileLiveData = Transformations.switchMap(getProfileCommand, forceUpdate -> UserRepository.getInstance().getProfile(forceUpdate));
        profileApiStateLiveData = UserRepository.getInstance().getProfileApiRequestStatus();
    }

    public void loadProfile(boolean forceUpdate) {
        getProfileCommand.postValue(forceUpdate);
    }

    // Profile Data : Observable Field
    private LiveData<Profile> profileLiveData;
    public LiveData<Profile> getProfileLiveData() {
        if(profileLiveData == null) profileLiveData = new MutableLiveData<>();
        return profileLiveData;
    }

    // Profile Http Call's State : Observable Field
    private LiveData<ApiRequest>  profileApiStateLiveData;
    public LiveData<ApiRequest>  getProfileApiStateLiveData() {
        if(profileApiStateLiveData == null) profileApiStateLiveData = new MutableLiveData<>();
        return profileApiStateLiveData;
    }
}

现在,UI可以观察Profile Data和Http Call状态的变化。 因此,如果UI要下载并在UI上显示Profile,则UI负责观察profileLiveDataprofileApiStateLiveData ,然后调用ViewModel的方法loadProfile(true);。

// Observes Profile Data
mProfileViewModel.getProfileLiveData().observe(this, profileData -> {
    // Use profile data here
});

// Observes State of Profile Http Call
mProfileViewModel.getProfileApiStateLiveData().observe(this, profileHttpCallState -> {
    // show/hide progress based on http call state
});

// start downloading profile data
mProfileViewModel.loadProfile(true);

我们在这里可以看到方法loadProfile将触发switchMap转换并启动Http调用。 请注意,发生switchMap触发是因为UI观察到的结果LiveData是profileLiveData

这种情况下工作正常。 但是,如果某个Activity只想发起Http调用并且只想观察profileApiStateLiveData而不是profileLiveData ,则switchMap触发器将永远不会发生,这是因为没有活动的LiveLive结果LiveData profileLiveData观察者。

    /**** Do not observe Profile Data, because here we only need to observe Http Call State  ***/

    /**** Only Observe State of Profile Http Call  ***/
    mProfileViewModel.getProfileApiStateLiveData().observe(this, profileHttpCallState -> {
        // show/hide progress based on http call state
    });

    /**** start downloading profile data ***/
    mProfileViewModel.loadProfile(true);

    /**** The above line does not trigger the switchMap Transformation. ***/

我有一个丑陋的解决方案,其中我必须在UI中为profileLiveData添加不必要的空白观察者。 但这很容易出错,因为其他开发人员可能会忘记为profileLiveData添加此不必要的空白观察者,并且即使他们调用方法loadProfile(true) ,他们也不知道为何未获取概要文件数据的任何线索。

这里非常感谢Rx专家的帮助:-)

感谢@ arka-prava-basu,这个问题已得到很好的回答。 profileLiveData已从Transformation中分离出来,现在可以直接从Room Database中获取。 和动作

(UserRepository.getInstance()。getProfile(forceUpdate))

此转换执行的操作现在已转移到loadProfile方法。 下面是重构的代码。

ProfileViewModel.java

public class ProfileViewModel extends AndroidViewModel {

   public ProfileViewModel(@NonNull Application application) {
        super(application);
        profileLiveData = UserRepository.getInstance().getMemberInfo();
        profileApiStateLiveData = UserRepository.getInstance().getProfileApiRequestStatus();
    }

    public void loadProfile(boolean forceDownload) {
        if(forceDownload) {
            UserRepository.getInstance().initiateProfileDownloading();
        }
    }

    // Profile Data : Observable Field
    private LiveData<Profile> profileLiveData;
    public LiveData<Profile> getProfileLiveData() {
        return profileLiveData;
    }

    // Profile Http Call's State : Observable Field
    private LiveData<ApiRequest>  profileApiStateLiveData;
    public LiveData<ApiRequest>  getProfileApiStateLiveData() {
        return profileApiStateLiveData;
    }
}

暂无
暂无

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

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