有用 AAC 的旁友吗,有个 LiveData 的问题想请教 - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
ukyoo
V2EX    Android

有用 AAC 的旁友吗,有个 LiveData 的问题想请教

  •  
  •   ukyoo 2019-07-30 18:15:04 +08:00 12990 次点击
    这是一个创建于 2265 天前的主题,其中的信息可能已经有所发展或是发生改变。
    假设我当前使用 RxJava 的 Flowable 作为数据源, 我应当在 Repository 里就把 Flowable 转换成 LiveData 返回, 还是在 ViewModel 的 Flowable.subscribe( )里调用 LiveData#setValue()呢, 哪个更合适呢.
    如果是 Repository 返回, 那 ViewModel 里的 val LiveData 又无法指向新的 LiveData 对象,如果用 Transformations.switchMapsourceLiveData)处理又不是每次都能有输入参数来给你观察的,比如我点击 N 次.

    如果是后者,感觉加工 LiveData 的过程又不应该交给 ViewModel 来处理.
    7 条回复    2019-10-18 13:36:58 +08:00
    2bab
        1
    2bab  
       2019-08-02 09:12:31 +08:00
    后者,因为:

    1. LiveData 就是真实值的包装,长期可观察的对象,确实如你所言我觉得不可以也不应该不断指向新的对象;
    2. LiveData 是和 Android Framework 本身有关联的(或者说和 LifeCycle Framework ),而 Repository 层面其实是更加底层、通用层面,可以不做关心,这也是你为什么用更重量级更通用的 Rx Framework 在这一层来处理逻辑和数据的原因吧,故放在 ViewModel 挺合理,楼主可以说一下为什么感觉不合理~
    ukyoo
        2
    ukyoo  
    OP
       2019-08-02 09:42:25 +08:00
    @2bab Hi, 这么做不是不可以.我是这么想的, 既然已经用了 Repository,在 ViewModel 只是应该调用 Repo 来直接获取加工好的数据, ViewModel 应该只负责向 View 层提供 LiveData.
    参考官方的 arch_browse_sample 里, 成功失败的状态和数据都是在 Repo 里包装的,ViewModel 里直接通过 Repo 获取 LiveData. 但是官方的例子大量使用了 Transformations.flatMap(sourceLiveData), 在实际开发中不可能一直有 sourceLivedata 来观测, 比如我只是点击一下这时候是没有输入参数的,这时就不能借助 flatMap..所以我在 arch_sample 下提了个 issue:
    https://github.com/googlesamples/android-architecture-components/issues/686

    别的帖子里大佬的思路: 把 ViewModel 里 LiveData 的引用传递给 Repo
    https://i.loli.net/2019/07/30/5d40467b25b8b95582.png
    2bab
        3
    2bab  
       2019-08-02 10:34:34 +08:00
    @ukyoo 我觉得你说的很具体了,那可以讨论一下几个具体的点:

    1. ",在 ViewModel 只是应该调用 Repo 来直接获取加工好的数据":这点可以这样考虑,比如同样一个购物车信息的 Repo 可以被多个地方调用(甚至是同一个 Repo 的同一个 API ),但展示出来的方式可能略有不同,所以你可能会分别在 ViewModel 内做一些针对不同 UI 元素的数据后置处理(比如把给每个标题加上 1234 的顺序索引),我觉得 Repo 不需要承担 100% 的源数据处理工作,更多的是做好偏下层的通用性处理,ViewModel 可以有一点点真正对 "View" 的 "Model" 的处理;
    2. "把 ViewModel 里 LiveData 的引用传递给 Repo":正如前面讨论的,LiveData 更多是要在 ViewModel 和 View 这边去发挥作用,而 Repo 本身是可以被更多地方使用,例如几个 Repo 之间可以互相调用,也即现在比较普遍的模块化框架下几个模块之间的功能互相 invoke,这种情况下我们并不需要 LiveData,而是使用如题所说的 Rx,如果要做这个方案,那么就得把大量的 Repo 里的 API 提供两套接口,一套没有 LiveData 一套有,不过也不能说不是一种解法吧。
    ukyoo
        4
    ukyoo  
    OP
       2019-08-02 19:21:35 +08:00
    @2bab 嗯哈怎么写都可以...只是想看看官方的最佳实践, "advanced" browseSample 还是不够
    colaman
        5
    colaman  
       2019-08-08 10:22:46 +08:00
    livedata 实际上更应该是对于结果 /状态的发射,而不是像我们以前的一个 rxjava 流一样做各种变换操作,官方有 livedata 和 Observable 的转换方法,但是实际上不适用于 RxJava,如果是用原本的 Retrofit+Rxjava 的 方式来写,确实更应该在数据变换完之后用 livedata 发射出去,只是这样看起来有点多余。如果用 kotlin 协程来写的话就显得比较简洁有效了
    ukyoo
        6
    ukyoo  
    OP
       2019-08-08 11:24:25 +08:00
    @colaman LiveDataReactiveStreams 没法处理 rxjava 的 onError, 这个不满足我现在的需求. 我没用过协程,请问协程怎么处理异常啊, 用 CoroutineExceptionHandler 吗?
    colaman
        7
    colaman  
       2019-10-18 13:36:58 +08:00
    @ukyoo 协程按照官方的处理是 try catch 这种最基础的写法,但是可以自己封装一下代码块或者 CoroutineExceptionHandler 都是可以的,看自己喜欢哪种思路。
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     978 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 24ms UTC 23:18 PVG 07:18 LAX 16:18 JFK 19:18
    Do have faith in what you're doing.
    ubao snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86