简短的问题:
使用使用页面大小加载新页面和BoundaryCallback类的API,从Architecture组件处理Paging库上的数据库+网络的正确方法是什么?
研究和解释
目前,BoundaryCallback在用于体系结构组件的分页库中使用的类接收列表中元素的实例作为参数,而没有该元素所在的实际上下文.它发生在onItemAtFrontLoaded和onItemAtEndLoaded.
我的Api应该接收页面和页面大小以加载下一个数据块.作为分页列表构建器的一部分添加的边界回调应该告诉您何时根据预取距离和页面大小加载下一页数据.
由于API需要的页码和页面提供的尺寸,我看不到的方式发送到API只是通过接收从列表中提供的元素之一onItemAtFrontLoaded和onItemAtEndLoaded.检查此链接中的google示例,他们使用最后一个元素的名称来获取下一个元素,但这不适合具有页面+大小的Api.
他们还有另一个只使用网络的例子PagedKeyedDatasource,但没有关于如何将它与数据库和BoundaryCallback混合的样本或线索.
编辑:到目前为止我找到的解决方案只是将最后加载的页面存储在共享首选项上,但这听起来像是一个肮脏的技巧.
有关官方输入,请参阅 https://github.com/googlesamples/android-architecture-components/issues/252#issuecomment-392119468.
android android-room android-livedata android-architecture-components android-paging
我正在使用Android Paging Library,如下所述:https: //developer.android.com/topic/libraries/architecture/paging.html
但我也有一个EditText用于按名称搜索用户.
如何过滤分页库中的结果以仅显示匹配的用户?
大家好,我使用 Android Jetpack Paging 库 3,我正在创建一个实现网络 + 数据库场景的新闻应用程序,我正在关注 google 的 Codelab https://codelabs.developers.google.com/codelabs/android-paging,我几乎就像在 Codelab 中一样,我几乎匹配了示例中显示的所有操作https://github.com/android/architecture-components-samples/tree/main/PagingWithNetworkSample。
它几乎按其应有的方式工作......但我的后端响应是页面键控的,我的意思是响应带有新闻列表和下一页网址,远程中介获取数据,填充数据库,设置存储库,设置视图模型。 ..
问题是:当recyclerview加载数据时,会发生以下情况:recyclerview闪烁、项目跳转、被删除、再次添加等等。我不知道为什么 recyclerview 或其 itemanimator 的行为如此,看起来如此丑陋和故障。更重要的是,当我滚动到列表末尾时,会获取新项目,并且再次发生故障和跳跃效果。
如果您能帮助我,我将非常感激,我已经坐了三天了,提前非常感谢您。这是我的代码片段:
@Entity(tableName = "blogs")
data class Blog(
@PrimaryKey(autoGenerate = true)
val databaseid:Int,
@field:SerializedName("id")
val id: Int,
@field:SerializedName("title")
val title: String,
@field:SerializedName("image")
val image: String,
@field:SerializedName("date")
val date: String,
@field:SerializedName("share_link")
val shareLink: String,
@field:SerializedName("status")
val status: Int,
@field:SerializedName("url")
val url: String
) {
var categoryId: Int? = null
var tagId: Int? = null
 }
这是 DAO
@Insert(onConflict …android android-architecture-components android-paging android-paging-library android-paging-3
Android Architecture Component 现在引入了Paging Library,这很棒。
根据官方的 demoDataSource.Factory现在支持map和mapByPage方法,这意味着我们可以将项目转换为一个DataSource。
但是DataSource并且DataSource.Factory应该在模型层,而不是Presenter/View 层。然而,很多时候我们想要在我们的 Adapter(对于 RecyclerView 或 ListView)中转换数据,很明显,这是 Presentor/View 层逻辑。现在,一个 Adapter 持有一个 的实例PagedList,但PageList不能支持这些操作,这有点尴尬。此外,有时我们还想向PagedList.
所以这是一个功能请求:
支持项目转换 PagedList
支持项目添加/删除到/从 PagedList
欢迎任何讨论。
paging android android-architecture-components android-paging
我从 Paging 2 迁移到 Paging 3 库,现在我使用它PagingSource从服务器加载数据页面。但我很难理解getRefreshKey必须在那里重写的方法。我找到了一些代码示例,如何根据用于获取后续页面的密钥来实现它,但我仍然不明白。基于这些示例,我编写了以下代码:
override fun getRefreshKey(state: PagingState<Pair<String, String>, User>): Pair<String, String>? {
    return state.anchorPosition?.let { anchorPosition ->
        state.closestPageToPosition(anchorPosition)?.prevKey
    }
}
但如果我使它始终返回 null,它不会改变任何事情:
override fun getRefreshKey(state: PagingState<Pair<String, String>, User>): Pair<String, String>? = null
那么我为什么不能选择最简单的解决方案呢?还是有我没有看到的用例?
我试图为新的 Paging 3 库模仿 Google 的 codelab,当我尝试让 Room DAO 方法返回 a 时遇到以下错误PagingSource:
D:\Programming\Android\something\app\build\tmp\kapt3\stubs\debug\com\someapp\something\data\db\UsersDao.java:38: error: Not sure how to convert a Cursor to this method's return type (androidx.paging.PagingSource<java.lang.Integer,com.someapp.something.data.db.GithubUser>).
    public abstract androidx.paging.PagingSource<java.lang.Integer, com.someapp.something.data.db.GithubUser> getUserByUserName(@org.jetbrains.annotations.NotNull()
    
^D:\Programming\Android\something\app\build\tmp\kapt3\stubs\debug\com\someapp\something\data\db\UsersDao.java:43: error: Not sure how to convert a Cursor to this method's return type (androidx.paging.PagingSource<java.lang.Integer,com.someapp.something.data.db.GithubUser>).
public abstract androidx.paging.PagingSource<java.lang.Integer, com.someapp.something.data.db.GithubUser> getUserByNote(@org.jetbrains.annotations.NotNull()
这是我的UsersDao.kt:
@Dao
interface UsersDao {
    @Insert
    fun insert(user: GithubUser): Completable
    @Insert
    fun insert(userList: List<GithubUser>): Completable
    @Query("DELETE FROM userDb")
    fun clearDb(): Completable
    @Query("SELECT * FROM …android rx-java2 android-room android-paging android-paging-library
我正在尝试Android架构组件中的分页库,但我怀疑将它集成到基于干净架构的项目中.
一般来说我有3个模块:
为了引入分页,我不得不将PagedList<T>类视为域类.(IMO不是一个可怕的想法,因为最终是一个列表,数据源是抽象的)
所以在域层我可以有一个像以下的repostiory:
interface ItemRepository {
    fun getItems():PagedList<Item>
}
然后在数据模块中创建如下的实现:
class ItemRepositoryImpl: ItemRepositoy(private val factory:ItemDataSourceFavtory) {
    fun getItems():PagedList<Item> {
  val pageConfigurations = PagedList.Config.Builder()
            .setPageSize(10)
            .setInitialLoadSizeHint(15)
            .setPrefetchDistance(5)
            .setEnablePlaceholders(false)
            .build()
    return RxPagedListBuilder(locationDataSourceFactory, pageConfigurations)
            .setInitialLoadKey(1)
            .buildObservable()
}
到现在为止还挺好.我的疑问是,当我们需要变换域模型为表示层(比方说我的项目需要意识到,如果被检查显示的图标检查),通常我会我的域模型映射到演示文稿一个.
我知道DataSourceFactoryhas map和mapByPage方法,但工厂驻留在数据层.我的Viewmodel使用来自模型层的数据,在这种情况下,这将是一个数据PagedList,据我所知,分页列表不支持映射.
那么在这种情况下适当的做法是什么呢?
android clean-architecture android-architecture-components android-jetpack android-paging
我正在使用分页库从 api 检索数据并将它们显示在列表中
为此,我在我的存储库中创建了该方法:
fun getArticleList(query: String): Flow<PagingData<ArticleHeaderData>>
在我的视图模型中,我创建了如下所示的搜索方法:
override fun search(query: String) {
    val lastResult = articleFlow
    if (query == lastQuery && lastResult != null)
        return
    lastQuery = query
    searchJob?.cancel()
    searchJob = launch {
        val newResult: Flow<PagingData<ArticleList>> = repo.getArticleList(query)
            .map {
                it.insertSeparators { //code to add separators }.cachedIn(this)
        articleFlow = newResult
        newResult.collectLatest {
            articleList.postValue(it)
        }
    }
}
为了测试我的视图模型,我使用测试方法PagingData.from来创建一个从我的模拟存储库返回的流,如下所示:
whenever(repo.getArticleList(query)).thenReturn(flowOf(PagingData.from(articles)))
然后我从 articleList LiveData 中检索实际的分页数据,如下所示:
val data = vm.articleList.value!!
这将返回一个PagingData<ArticleList>对象,我想验证它是否包含来自服务的数据(即articles,何时返回)
我发现这样做的唯一方法是创建以下扩展函数:
private val dcb = …我一直在与谷歌的拱库一起工作,但是让测试变得困难的一件事就是合作PagedList.
对于此示例,我使用存储库模式并从API或网络返回详细信息.
所以在ViewModel中我调用了这个接口方法:
override fun getFoos(): Observable<PagedList<Foo>>
然后,存储库将RxPagedListBuilder用于创建Observable类型为PagedList的类型:
 override fun getFoos(): Observable<PagedList<Foo>> =
            RxPagedListBuilder(database.fooDao().selectAll(), PAGED_LIST_CONFIG).buildObservable()
我希望能够通过这些返回a的方法设置返回测试PagedList<Foo>.类似的东西
when(repository.getFoos()).thenReturn(Observable.just(TEST_PAGED_LIST_OF_FOOS)
两个问题:
PagedList<Foo>?我的目标是以更加端到端的方式进行验证(例如确保在屏幕上显示正确的Foos列表).片段/活动/视图是PagedList<Foo>从ViewModel 观察的片段/活动/视图.
我有一个问题,紧接着onItemAtEndLoaded调用该方法后 onZeroItemsLoaded,行为应该只在我完成滚动时.你知道发生了什么吗?我可以提供我的GitHub回购.
android-paging ×10
android ×9
android-architecture-components ×5
android-room ×2
kotlin ×1
paging ×1
rx-java2 ×1
search ×1
unit-testing ×1