如何在 Kotlin Android 上使用 Retrofit2、RxJava2 读取 JSON 文件

问题描述

我最近开始学习反应式编程。我可以使用 Retrofit2 读取 API JSON 文件,但我不知道如何使用 RxJava2 使用响应式编程来做到这一点。如果你有链接或现成的代码,将不胜感激。 我自己试图实现这个任务,但它不起作用。我根据这个链接做了一切 - https://www.learn2crack.com/2017/11/retrofit-and-rxjava-in-kotlin.html,但是当我在订阅调用响应函数时,没有任何作用。例如,我尝试显示它,但没有显示

MainActivity 类


package com.example.json_rxjava

import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.util.Log
import android.widget.Toast
import com.example.json_rxjava.MODEL.JsonModel
import com.example.json_rxjava.NETWORK.RequestInterface
import io.reactivex.android.schedulers.AndroidSchedulers
import io.reactivex.disposables.Compositedisposable
import io.reactivex.schedulers.Schedulers
import retrofit2.Retrofit
import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory
import retrofit2.converter.gson.GsonConverterFactory

class MainActivity : AppCompatActivity() {
    private val BASE_URL = "https://learn2crack-json.herokuapp.com/"
    private var mCompositedisposable: Compositedisposable? = null
    private var mJsonModelDataList: ArrayList<JsonModel>? = null

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        loadJSON()
    }

    private fun loadJSON() {
        val requestInterface = Retrofit.Builder()
            .baseUrl(BASE_URL)
            .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
            .addConverterFactory(GsonConverterFactory.create())
            .build().create(RequestInterface::class.java)

        mCompositedisposable?.add( requestInterface.getData()
            .observeOn(AndroidSchedulers.mainThread())
            .subscribeOn(Schedulers.io())
            .subscribe(this::handleResponse)
        )
    }

    private fun handleError(error: Throwable) {
        Log.e("ERROR: ",error.localizedMessage)
    }

    private fun handleResponse(jsonModel: List<JsonModel>) {
        Log.e("LOG TEST","THIS IS RESPONSE")
        mJsonModelDataList = ArrayList(jsonModel)
        for(i in 0..mJsonModelDataList!!.size-1) {
            Log.e("LOG: ",mJsonModelDataList?.get(i)?.name.toString())
        }
    }

    override fun onDestroy() {
        super.onDestroy()
        mCompositedisposable?.clear()
    }
}

请求接口


package com.example.json_rxjava.NETWORK

import com.example.json_rxjava.MODEL.JsonModel
import io.reactivex.Observable
import retrofit2.http.GET

interface RequestInterface {
    @GET("api/android")
    fun getData(): Observable<List<JsonModel>>
}

JsonModel


package com.example.json_rxjava.MODEL

data class JsonModel(
    val version: String,val name: String,val apiLevel: String
)

在 build.gradle 中添加了以下依赖项:


//RxJava and Retrofit
implementation 'com.squareup.retrofit2:retrofit:2.3.0'
implementation 'com.squareup.retrofit2:converter-gson:2.3.0'
implementation 'com.squareup.retrofit2:adapter-rxjava2:2.3.0'
implementation 'io.reactivex.rxjava2:rxjava:2.1.6'
implementation 'io.reactivex.rxjava2:rxandroid:2.0.1'

在 AndroidManifest 中添加

<uses-permission android:name="android.permission.INTERNET"/>

程序输出


D/NetworkSecurityConfig: Using Network Security Config from resource network_security_config debugBuild: true
D/: HostConnection::get() New Host Connection established 0xa3fc0140,tid 8411
D/: HostConnection::get() New Host Connection established 0xa3fc0500,tid 8460
I/Openglrenderer: Initialized EGL,version 1.4
D/Openglrenderer: Swap behavior 1
W/Openglrenderer: Failed to choose config with EGL_SWAP_BEHAVIOR_PRESERVED,retrying without...
D/Openglrenderer: Swap behavior 0
D/EGL_emulation: eglCreateContext: 0xaed85360: maj 2 min 0 rcv 2
D/EGL_emulation: eglMakeCurrent: 0xaed85360: ver 2 0 (tinfo 0xaed831f0)
D/EGL_emulation: eglMakeCurrent: 0xaed85360: ver 2 0 (tinfo 0xaed831f0)
D/EGL_emulation: eglMakeCurrent: 0xaed85360: ver 2 0 (tinfo 0xaed831f0)

请告诉我,如果您知道问题出在哪里,或者您有关于如何在 Kotlin 中使用 Retrofit2 和 RxJava2 读取 API JSON 的链接或现成代码,请丢弃它。

解决方法

什么都没发生的原因是你忘记初始化mCompositeDisposable。因此,无论何时执行 mCompositeDisposable?.,都会跳过该代码,因为 mCompositeDisposable 是 null

要修复它,请将声明替换为

private val mCompositeDisposable: CompositeDisposable = CompositeDisposable()