qzyf / google-gson

Automatically exported from code.google.com/p/google-gson
0 stars 0 forks source link

JsonPrimitive string to number is inconsistent and bad #453

Open GoogleCodeExporter opened 9 years ago

GoogleCodeExporter commented 9 years ago
What steps will reproduce the problem?

(0. run the attached test case)

1. use an long attribute with exponent like "dateCreated": 1.020204000000e+12
2. Object deserialization works with new Gson().fromJson(...)
3. When using GsonBuilder + custom JsonDeserializer it fails when deserializing 
on the given context (see Test case line 65 or below 
context.deserialize(jsonElement, Content.class))

    public TestObject deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
            throws JsonParseException {
        JsonObject jsonObject = json.getAsJsonObject();

        TestObject testObject = new TestObject();
        JsonArray jsonArray = jsonObject.getAsJsonArray("content");
        for (JsonElement jsonElement : jsonArray) {
            Content content = context.deserialize(jsonElement, Content.class);
            testObject.content.add(content);
        }
        return testObject;
    }

What is the expected output? What do you see instead?
- expected: successfully deserialize the value to 1020204000000 
- actual: com.google.gson.JsonSyntaxException: java.lang.NumberFormatException: 
For input string: "1.0202040"

What version of the product are you using? On what operating system?
- >= 2.0 (1.6. works)

Please provide any additional information below.
- see attached JUnit test case

Original issue reported on code.google.com by jenshadl...@googlemail.com on 22 Jun 2012 at 10:11

Attachments:

GoogleCodeExporter commented 9 years ago
Great bug. The distilled form looks like this:

  public void testDeserialize() {
    String number = "1.020204000000e+12";
    new Gson().fromJson(number, Long.class); // works
    new Gson().fromJson(new JsonPrimitive(number), Long.class); // fails
  }

The underlying problem is that we have two different ways to convert strings to 
longs. In JsonPrimitive we truncate the high order bits. This program prints 
two '1' characters:

    System.out.println(new JsonPrimitive("1").getAsNumber().longValue());
    System.out.println(new JsonPrimitive("18446744073709551617").getAsNumber().longValue());

We should be doing something more robust throughout JsonPrimitive.

Original comment by limpbizkit on 30 Jun 2012 at 3:06

GoogleCodeExporter commented 9 years ago

Original comment by limpbizkit on 30 Jun 2012 at 3:07

GoogleCodeExporter commented 9 years ago
Thanks for the distilled form and explanations. I'm looking forward for your 
fix, because this is a showstopper for us and prevents from upgrading from 
version 1.x to 2.x

Original comment by jenshadl...@googlemail.com on 1 Jul 2012 at 12:02

GoogleCodeExporter commented 9 years ago
Issue 462 has been merged into this issue.

Original comment by limpbizkit on 2 Sep 2012 at 9:39