Android Kotlin Retrofit + Rxjava rest调用未返回请求的数据

时间:2019-05-02 14:43:16

标签: android kotlin retrofit rx-java2 moshi

我有一个用Kotlin编写的Android应用程序,该应用程序从API获取数据,现在它只是一个本地托管的JSON文件。当我尝试获取数据时,收到以下错误:我的清单人员未初始化,因此人员== null并且未接收到数据。我不确定自己做错了什么以及如何解决。

模型

data class Person (
  @Json(name = "personId")
  val personId: Int,

  @Json(name = "personName")
  val name: String,

  @Json(name = "personAge")
  val age: Int,

  @Json(name = "isFemale")
  val isFemale: Boolean,
)

JSON响应

{
  "persons": [{
      "personId": 1,
      "personName": "Bert",
      "personAge": 19,
      "isFemale": "false",
    }
  ]
}

ApiClient

class ApiClient {
    companion object {

        private const val BASE_URL = "http://10.0.2.2:3000/"

        fun getClient(): Retrofit {
            val moshi = Moshi.Builder()
                .add(customDateAdapter)
                .build()

            return Builder()
                .baseUrl(BASE_URL)
                .addConverterFactory(MoshiConverterFactory.create(moshi))
                .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
                .build()
        }
    }
}

翻新http方法

interface ApiInterface {

    @GET("persons")
    fun getPersons(): Observable<List<Person>>
}

最后是通话

class PersonActivity: AppCompatActivity(){
  private lateinit var jsonAPI: ApiInterface
  private lateinit var persons: List<Person>

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

    val retrofit = ApiClient.getClient()
    jsonAPI = retrofit.create(ApiInterface::class.java)
    jsonAPI.getPersons()
            .subscribeOn(Schedulers.io())
            .unsubscribeOn(Schedulers.computation())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe({ persons = it })
  }
}

预期:从JSON文件到人员列表的数据,而不是NULL。

2 个答案:

答案 0 :(得分:0)

您的moshi适配器期望直接使用person对象,但它们嵌套在“人” Json数组中。

您应该添加以下其他模型

data class Persons (
    @Json(name="persons")
    val persons : List<Person>
)

还更改界面以返回新对象。

interface ApiInterface {
    @GET("persons")
    fun getPersons(): Observable<Persons>
}

还需要将订阅更改为

.subscribe({ persons = it.persons })

答案 1 :(得分:0)

我认为可能是两个问题之一。

如果您正在使用moshi反射,则gradle中将具有类似以下的依赖项:

//Moshi Core
implementation "com.squareup.moshi:moshi:1.8.0"

//Moshi Reflection
implementation "com.squareup.moshi:moshi-kotlin:1.8.0"

在这种情况下,您将需要使用KotlinJsonAdapterFactory:

  val moshi = Moshi.Builder()
        .add(customDateAdapter)
        .add(KotlinJsonAdapterFactory())
        .build()

如果您使用的是代码生成器,则需要以下代码:

apply plugin: 'kotlin-kapt'
...
//Moshi Core Artifact
implementation "com.squareup.moshi:moshi:1.8.0"

//Moshi Codegen
kapt "com.squareup.moshi:moshi-kotlin-codegen:1.8.0"

此外,您要反序列化的每个类都应带有注释 @JsonClass(generateAdapter = true)(因此是Person和Persons类)