You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android Studio中使用Retrofit重复查询结果不一致问题

问题:Google Books API多次查询结果不一致

我开发了一款图书搜索应用,通过Retrofit调用Google Books API获取数据,但多次执行q=domani查询时,返回的结果(缩略图列表)有时会不一致。

相关代码

ViewModel查询逻辑

fun getPhotos(query: String) {
    viewModelScope.launch {
        fetchUiState = FetchUiState.Loading
        fetchUiState = try {
            var thumbnails = bookRepository.getBooks(query)
                .items.map { it.volumeInfo.imageLinks?.thumbnail }
            thumbnails=thumbnails.filterNotNull()
            Log.d("getPhotos", "${thumbnails.size} Thumbnails: $thumbnails")

            FetchUiState.Success(thumbnails)
        } catch (e: HttpException) {
            Log.e("getPhotos", "HTTP exception occurred", e)
            FetchUiState.Error
        } catch (e: IOException) {
            Log.e("getPhotos", "Network or IO exception occurred", e)
            FetchUiState.Error
        } catch (e: Exception) {
            Log.e("getPhotos", "Unexpected exception occurred", e)
            FetchUiState.Error
        }
    }
}

Retrofit配置

interface BookApiService{
@GET("volumes")suspend fun getBooks(@Query("q") query: String): QueryResult
}

interface AppContainer {
val bookRepository: BookRepository
}
class DefaultAppContainer : AppContainer {

private val json = Json {
    ignoreUnknownKeys = true
}
private val baseUrl="https://www.googleapis.com/books/v1/"
private val retrofit: Retrofit = Retrofit.Builder()
    .addConverterFactory(json.asConverterFactory("application/json".toMediaType()))
    .baseUrl(baseUrl)
    .build()

private  val retrofitService: BookApiService by lazy {
    retrofit.create(BookApiService::class.java)
}
override val bookRepository: BookRepository by lazy {
    NetWorkBookRepository(retrofitService)
}

}

数据模型

@Serializable
data class QueryResult(
val items: List<BookInfo>
)

@Serializable
data class BookInfo(
val id: String,
val volumeInfo: VolumeInfo
)

@Serializable
data class VolumeInfo(
val imageLinks: ImageLinks? = null,
)

@Serializable
data class ImageLinks(
val thumbnail: String
)

日志表现

两次相同查询返回的缩略图数量不同,比如一次返回3个,一次返回2个,列表内容也存在差异。


原因分析

  1. Google Books API的动态特性:该API的搜索结果会根据内容更新、用户区域、服务器负载等因素动态调整,默认无固定排序或分页约束,导致多次请求结果不同。
  2. 缺少分页与排序参数:当前请求仅传入q参数,未指定maxResults(返回结果数量)、startIndex(起始位置)和orderBy(排序方式),API会返回默认的可变结果集。
  3. 无本地缓存:每次请求直接调用远程API,没有缓存机制,无法保证相同查询的结果一致性。

解决方案

1. 固定API请求参数

修改BookApiService,添加分页和排序参数,确保每次请求的结果范围一致:

interface BookApiService{
    @GET("volumes")
    suspend fun getBooks(
        @Query("q") query: String,
        @Query("maxResults") maxResults: Int = 10, // 固定返回数量
        @Query("startIndex") startIndex: Int = 0, // 固定起始位置
        @Query("orderBy") orderBy: String = "relevance" // 固定排序方式
    ): QueryResult
}

2. 实现本地缓存

使用Room或其他缓存库,对相同查询的结果进行缓存,优先读取缓存数据:

  • 创建缓存实体类映射查询结果
  • 在NetWorkBookRepository中,先检查缓存是否存在对应查询结果,存在则返回缓存,否则请求API并更新缓存

3. 验证结果一致性

如果需要追踪结果变化,可记录每次返回的BookInfo.id列表,对比差异,确认是API返回变化还是本地处理逻辑问题。


内容的提问来源于stack exchange,提问作者Trần Thanh Vinh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 14:13:15