user4383363
user4383363

Reputation:

How to access the value of a key inside a key in a JSON response in android fetched with Retrofit2?

I'm accessing a WordPress API to fetch the posts using Retrofit2, then when I try to assign the values to the views in my adapter:

inner class MainActivityViewHolder(view: View) : RecyclerView.ViewHolder(view) {
    fun bind(post: Post) {
        with(post) {
            itemView.tv_post_title.text = title
            itemView.tv_post_date.text = date
            itemView.tv_post_content.text = content
        }
    }
}

The Retrofit's GET returns an Observable, and thus, the following error in onErrorResumeNext is shown when it tries to assign:

java.lang.IllegalStateException: Expected a string but was BEGIN_OBJECT at line 1 column 373 path $[0].title

This is because title key has a rendered key within it:

{  
  id:497,
  date:"2018-04-08T03:34:12",
  [...]
  title:{  
    rendered:"Lorem ipsum dolor sit amet"
  }
}

The same applies to content and excerpt. How do I access these rendereds keys? I tried something like

val title: JsonElement = JsonParser().parse(post.title)

but the same error persists.

Upvotes: 0

Views: 454

Answers (1)

Amolpskamble
Amolpskamble

Reputation: 978

This happening because json parser is not able to parse the title object.

java.lang.IllegalStateException: Expected a string but was BEGIN_OBJECT at line 1 column 373 path $[0].title

To avoid this runtime error, click here to create java pojo for expected json and then use it as return type in your retrofit api.

Try using following java pojo for your json which is created using above mentioned tool.

Post.kt

data class Post(
    @PrimaryKey(autoGenerate = true)
    @SerializedName("id")
    val id: Int,

    @SerializedName("title")
    @Embedded
    val title: Title,

    @SerializedName("excerpt")
    @Embedded
    val excerpt: Excerpt,

    @SerializedName("content")
    @Embedded
    val content: Content,

    @SerializedName("date")
    val date: String,

    @SerializedName("modified")
    val modified: String
)

Content.kt

class Content {
    @SerializedName("rendered")
    var content: String? = null
}

Title.kt

class Title {
    @SerializedName("rendered")
    var title: String? = null
}

Excerpt.kt

class Excerpt {
    @SerializedName("rendered")
    var excerpt: String? = null
}

Import following dependency for Gson

import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;

@SerializedName: Give the ability to map JSON key with java member variable with a different name than JSON key. Check this question

Upvotes: 1

Related Questions