Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

GSON throwing "Expected BEGIN_OBJECT but was BEGIN_ARRAY"?

Tags:

java

android

gson

I'm trying to parse a JSON string like this one

[    {       "updated_at":"2012-03-02 21:06:01",       "fetched_at":"2012-03-02 21:28:37.728840",       "description":null,       "language":null,       "title":"JOHN",       "url":"http://rus.JOHN.JOHN/rss.php",       "icon_url":null,       "logo_url":null,       "id":"4f4791da203d0c2d76000035",       "modified":"2012-03-02 23:28:58.840076"    },    {       "updated_at":"2012-03-02 14:07:44",       "fetched_at":"2012-03-02 21:28:37.033108",       "description":null,       "language":null,       "title":"PETER",       "url":"http://PETER.PETER.lv/rss.php",       "icon_url":null,       "logo_url":null,       "id":"4f476f61203d0c2d89000253",       "modified":"2012-03-02 23:28:57.928001"    } ] 

into a list of objects.

List<ChannelSearchEnum> lcs = (List<ChannelSearchEnum>) new Gson().fromJson( jstring , ChannelSearchEnum.class); 

Here's an object class I'm using.

import com.google.gson.annotations.SerializedName;  public class ChannelSearchEnum {    @SerializedName("updated_at") private String updated_at;  @SerializedName("fetched_at") private String fetched_at;  @SerializedName("description") private String description;  @SerializedName("language") private String language;  @SerializedName("title") private String title;  @SerializedName("url") private String url;  @SerializedName("icon_url") private String icon_url;  @SerializedName("logo_url") private String logo_url;  @SerializedName("id") private String id;  @SerializedName("modified") private String modified;  public final String get_Updated_at() {     return this.updated_at; }  public final String get_Fetched_at() {     return this.fetched_at; }  public final String get_Description() {     return this.description; }  public final String get_Language() {     return this.language; }  public final String get_Title() {     return this.title; }  public final String get_Url() {     return this.url; }  public final String get_Icon_url() {     return this.icon_url; }  public final String get_Logo_url() {     return this.logo_url; }  public final String get_Id() {     return this.id; }  public final String get_Modified() {     return this.modified; }          } 

But it throws me with

com.google.gson.JsonSyntaxException: java.lang.IllegalStateException: Expected BEGIN_OBJECT but was BEGIN_ARRAY at line 1 column 2 

Any ideas how should I fix it?

like image 504
Roger Travis Avatar asked Mar 07 '12 09:03

Roger Travis


People also ask

What is Begin_array?

begin_array means the json response is an array which will look something like this [{},{},..] begin_object means the json response is an object which will look something like this {....} gson is one cool library that will provide us with cool tips in the form of errors while handling json responses.

What does GSON toJson do?

Gson is the main actor class of Google Gson library. It provides functionalities to convert Java objects to matching JSON constructs and vice versa. Gson is first constructed using GsonBuilder and then toJson(Object) or fromJson(String, Class) methods are used to read/write JSON constructs.


2 Answers

The problem is you're telling Gson you have an object of your type. You don't. You have an array of objects of your type. You can't just try and cast the result like that and expect it to magically work ;)

The User guide for Gson Explains how to deal with this:

https://github.com/google/gson/blob/master/UserGuide.md

This will work:

ChannelSearchEnum[] enums = gson.fromJson(yourJson, ChannelSearchEnum[].class); 

But this is better:

Type collectionType = new TypeToken<Collection<ChannelSearchEnum>>(){}.getType(); Collection<ChannelSearchEnum> enums = gson.fromJson(yourJson, collectionType); 
like image 138
Brian Roach Avatar answered Sep 19 '22 11:09

Brian Roach


The problem is that you are asking for an object of type ChannelSearchEnum but what you actually have is an object of type List<ChannelSearchEnum>.

You can achieve this with:

Type collectionType = new TypeToken<List<ChannelSearchEnum>>(){}.getType(); List<ChannelSearchEnum> lcs = (List<ChannelSearchEnum>) new Gson()                .fromJson( jstring , collectionType); 
like image 36
Guillaume Polet Avatar answered Sep 22 '22 11:09

Guillaume Polet