【问题标题】:How to parse JSON data using retrofit and rx?如何使用改造和 rx 解析 JSON 数据?
【发布时间】:2018-10-30 01:23:20
【问题描述】:

我正在尝试使用改造和 rx 从 JSON 获取数据。我关注了this tutorial。但是那个教程中的 JSON 和我的有点不同。所以我只是改变了如何解析它。但是,如果我得到 JSON,因为我不知道我如何知道 JSON 是否已经被调用,并且在应用程序中它没有显示任何内容。

如果有人知道它是如何工作的以及如何进行解析,请指导我。

这是我要在片段中解析 JSON 数据的代码。

override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
    rv__list_posts?.layoutManager = LinearLayoutManager(this.requireContext())

    val retrofit = Retrofit.Builder().addConverterFactory(GsonConverterFactory.create(GsonBuilder().create()))
            .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
            .baseUrl("https://www.thesportsdb.com/").build()

    val postsApi = retrofit.create(INetworkAPI::class.java)

    var response = postsApi.getAllPosts()

    response.observeOn(AndroidSchedulers.mainThread()).subscribeOn(IoScheduler()).subscribe {
        rv__list_posts.adapter = MainAdapter(listOf(it), this.requireContext())
    }
}

这是我的界面:

interface INetworkAPI {
  @GET("api/v1/json/1/eventslast.php?id=133602")
  fun getAllPosts(): Observable<Team>
}

这是适配器:

class MainAdapter(val postList: List<Team>, val context: Context) :
  RecyclerView.Adapter<MainAdapter.ViewHolder>() {

  override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): 
  ViewHolder {
    return 
    ViewHolder(LayoutInflater.from(context).inflate(R.layout.item_layout,parent,false))
  }

  override fun getItemCount(): Int {
      return 10
  }

  override fun onBindViewHolder(holder: ViewHolder, position: Int) {
    holder.itemView.home_team.text = postList.get(position).homeTeam
    holder.itemView.home_score.text = postList.get(position).homeScore.toString()
    holder.itemView.away_team.text = postList.get(position).awayTeam
    holder.itemView.away_score.text = postList.get(position).awayScore.toString()
  }
  class ViewHolder(view: View) : RecyclerView.ViewHolder(view)
}

感谢您的帮助。

【问题讨论】:

  • 可以加Team类吗?
  • 完成。我添加了它

标签: android kotlin rx-java retrofit2 reactivex


【解决方案1】:

您的 API 响应具有以下结构:

你需要做更复杂的模型。比如你可以做TeamResponse类:

data class TeamResponse(var results: List<Team>)

并将INetworkAPI 更改为:

interface INetworkAPI {
  @GET("api/v1/json/1/eventslast.php?id=133602")
  fun getAllPosts(): Observable<TeamResponse>
}

然后在你的片段中:

response
   .observeOn(AndroidSchedulers.mainThread())
   .subscribeOn(IoScheduler())
   .subscribe {
      rv__list_posts.adapter = MainAdapter(it.results, this.requireContext())
   }

编辑: 您可以在 LogCat 中查看所有 api 交互(您将可以看到请求和响应)。为它添加依赖:

 implementation "com.squareup.okhttp3:logging-interceptor:3.9.1"

然后改变改造建造者:

val retrofit = Retrofit.Builder().addConverterFactory(GsonConverterFactory.create(GsonBuilder().create()))
        .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
        .baseUrl("https://www.thesportsdb.com/")
        .client(getClient())
        .build()

getClient()代码:

private fun getClient(): OkHttpClient {
    val clientBuilder = OkHttpClient.Builder();
    if (BuildConfig.DEBUG) {
        val loggingInterceptor = HttpLoggingInterceptor();
        loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
        clientBuilder.addInterceptor(loggingInterceptor);
    }
    return clientBuilder.build();
}

并将所有 Int 字段从 Team 模型更改为字符串(所有这些都是字符串作为响应)。

【讨论】:

  • (listOf(it.results) 中说需要List&lt;Team&gt; 所以我在没有listOf() 的情况下更改它
  • 我编辑了答案。将 getClient 更改为 Kotlin 并删除 listOf()
  • 它说像这样的错误java.lang.IllegalArgumentException: Parameter specified as non-null is null: method kotlin.jvm.internal.Intrinsics.checkParameterIsNotNull, parameter postList at com.mqa.android.footballmatchschedule.MainAdapter.&lt;init&gt;(MainAdapter.kt:19) at com.mqa.android.footballmatchschedule.LastActivity$onCreateView$2.accept(LastActivity.kt:93) at com.mqa.android.footballmatchschedule.LastActivity$onCreateView$2.accept(LastActivity.kt:37)
  • 检查 LogCat 中的响应。得到正确的答复?
  • 结果好像是null
猜你喜欢
  • 2017-07-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-08-23
  • 1970-01-01
  • 2020-02-29
  • 1970-01-01
  • 2023-03-23
相关资源
最近更新 更多