Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

No support for fields whose types are type parameters #168

Closed
GoogleCodeExporter opened this issue Mar 17, 2015 · 10 comments
Closed

No support for fields whose types are type parameters #168

GoogleCodeExporter opened this issue Mar 17, 2015 · 10 comments

Comments

@GoogleCodeExporter
Copy link

Assume you have the following 2 classes:
class Entity<IDT,NameT>{
    IDT id;
    NameT name;

    public Entity(IDT id, NameT name) {
        super();
        this.id = id;
        this.name = name;
    }
    public IDT getId() {
        return id;
    }
    public NameT getName() {
        return name;
    }
}

class Employee extends Entity<Integer,String>{
    double age; 
    private int tag;

    public Employee() {
        super(0,null);
    }
    public Employee(int id, String name, double age) {
        super(id,name);
        this.age = age;
    }

    public double getAge() {
        return age;
    }

    void setTag(int tag){
        this.tag = tag;
    }   
}

when trying to use 
  new GsonBuilder().create().toJson(new Employee(1,"Mary",10)); it throws 

java.lang.UnsupportedOperationException: Expecting parameterized type, got
class test.gson.Employee.
 Are you missing the use of TypeToken idiom?
 See
http://sites.google.com/site/gson/gson-user-guide#TOC-Serializing-and-Deserializ
ing-Gener

ok, then I try the generic one using 
new GsonBuilder().create().toJson(new Employee(1,"Mary",10),new
TypeToken<Employee>(){}.getType()); Gson will only show id/name field, all
other field in Employee class is ignored. any solution? 

I've refered <a
href="http://code.google.com/p/google-gson/source/browse/trunk/gson/src/test/jav
a/com/google/gson/functional/ParameterizedTypesTest.java">,
but didn't help.

please help to solve the problem. thanks!

Original issue reported on code.google.com by hnjch...@gmail.com on 26 Oct 2009 at 8:49

@GoogleCodeExporter
Copy link
Author

by the way, I tried this under both 1.3/1.4 beta, both threw the same exception

Original comment by hnjch...@gmail.com on 26 Oct 2009 at 8:51

@GoogleCodeExporter
Copy link
Author

I am having the same issue as well.

I am using the 1.4 version on Ubuntu.

Is there any solution for this?  

Original comment by ekaqu1...@gmail.com on 14 Mar 2010 at 6:03

@GoogleCodeExporter
Copy link
Author

Pls refer to the gson's guide for generic class:

Serializing and Deserializing Generic Types
When you call toJson(obj), Gson calls obj.getClass() to get information on the 
fields
to serialize. Similarly, you can typically pass MyClass.class object in the
fromJson(json, MyClass.class) method. This works fine if the object is a 
non-generic
type. However, if the object is of a generic type, then the Generic type 
information
is lost because of Java Type Erasure. Here is an example illustrating the point:

List<String> myStrings = new List<String>();
gson.toJson(myStrings); // Will cause a runtime exception

gson.fromJson(json, myStrings.getClass());

The above call results in a runtime exception because Gson invokes
myStrings.getClass() to get its class information, but this method returns a raw
class, List.class. This means that Gson has no way of knowing that this is a 
list of
Strings, and not plain objects.

You can solve this problem by specifying the correct parameterized type for your
generic type. You can do this by using the TypeToken class.
Type listType = new TypeToken<List<String>>() {}.getType();
gson.toJson(myStrings, listType);

gson.fromJson(json, listType);

The idiom used to get listType actually defines an anonymous local inner class
containing a method getType() that returns the fully parameterized type. 

Original comment by pvthang...@gmail.com on 22 Apr 2010 at 3:38

@GoogleCodeExporter
Copy link
Author

The core problem is that GSON isn't tracking that the type of 'IDT' will be 
'Integer' for Employee instances.

Original comment by limpbizkit on 1 Nov 2010 at 11:10

  • Changed title: No support for fields whose types are type parameters

@GoogleCodeExporter
Copy link
Author

I've attached a patch that uses type mojo stolen from Guice. In general I think 
it's a big leap forward because it'll give GSON better support for type 
parameters in fields and type arguments of fields. In particular, this should 
work:
  class Foo<K, V> {
    K k1;
    Map<K, V> map;
    List<V> list;
  }

More interestingly, these should also work:
  class WackyHashMap<V, K> extends HashMap<K, V> {...}
  class SecondArgCollection<A, B> implements Collection<B> {...}

I'd prefer not to commit this change in time for GSON 1.6 because this change 
is destabilizing. It's a large change and we can build upon it by using 
TypeToken internally everywhere instead of TypeInfo.

Original comment by limpbizkit on 2 Nov 2010 at 8:08

  • Changed state: Started

Attachments:

@GoogleCodeExporter
Copy link
Author

Original comment by inder123 on 3 Nov 2010 at 1:47

  • Added labels: Milestone-Release1.7

@GoogleCodeExporter
Copy link
Author

The attached patch resolves merge conflicts.

Original comment by limpbizkit on 3 Nov 2010 at 3:12

Attachments:

@GoogleCodeExporter
Copy link
Author

Issue 241 has been merged into this issue.

Original comment by limpbizkit on 3 Nov 2010 at 3:16

@GoogleCodeExporter
Copy link
Author

Issue 40 has been merged into this issue.

Original comment by limpbizkit on 3 Nov 2010 at 3:20

@GoogleCodeExporter
Copy link
Author

This issue was closed by revision r707.

Original comment by limpbizkit on 19 Jan 2011 at 10:24

  • Changed state: Fixed

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant