1

我正在使用 Kotlin、OkHttp、RxJava2 开发一个 Android 应用程序。

我正在尝试进行自动搜索。

当用户输入一个字符时,搜索它。

override fun search(subject: PublishSubject<String>) {
    disposable.add(
            subject.debounce(1000, TimeUnit.MILLISECONDS)
                    .filter { it.isNotEmpty() }
                    .distinctUntilChanged()
                    .switchMap { keyword ->
                        search(keyword)
                    }
                    .subscribeOn(Schedulers.io())
                    .observeOn(AndroidSchedulers.mainThread())
                    .subscribe({ response ->
                        // using the response
                    }, {
                        it.printStackTrace()
                    })
    )
}

和搜索功能:

    fun search(keyword: String): Observable<String> {
        val request = Request.Builder()
            .url(url)
            .post(RequestBody.create(contentType, xmlBody(keyword)))
            .build()

        return Observable.fromCallable {
            val response = OkHttpClient().newCall(request).execute()
            response.body()?.string()
        }
    }

我喜欢“改造”,但就我而言,我应该使用 XML。我尝试将 Retrofit 与 SimpleXMLConverter 一起使用,但它不适合这个项目。所以我正在使用“OkHttp”。但是上面的代码抛出“InterruptedIOException”。

第一次通话没问题。但是在处理第一个请求时收到下一个搜索请求时会发生异常。

我应该如何解决这个问题?

我认为,switchMap 应该取消先前的请求,但事实并非如此。

4

1 回答 1

2

您设置了错误的调度程序。

你需要:

override fun search(subject: PublishSubject<String>) {
disposable.add(
        subject.debounce(1000, TimeUnit.MILLISECONDS)
                .filter { it.isNotEmpty() }
                .distinctUntilChanged()
                .switchMap { keyword ->
                    search(keyword).subscribeOn(Schedulers.io())
                }

                .observeOn(AndroidSchedulers.mainThread())
                .subscribe({ response ->
                    // using the response
                }, {
                    it.printStackTrace()
                })
)

}

注意后台调度器需要直接在search Completable中设置,而不是在链后switchmap。这是在主链以外的一条链上执行搜索,否则整个链都会被阻塞,swichmap看起来没有任何效果,因为它只有在自然完成后才会取消搜索。

于 2020-04-06T16:02:41.867 回答