How to handle a NumberFormatException with Gson in deserialization a JSON response

后端 未结 7 617
情深已故
情深已故 2020-12-01 03:45

I\'m reading a JSON response with Gson, which returns somtimes a NumberFormatException because an expected int value is set to an empty string. Now

相关标签:
7条回答
  • 2020-12-01 04:17

    As stated in another comment, as of GSON 2.3.1 you can register type adapters for primitive types, here is a type adapter that handles int and Integer types, and gracefully defaults to 0 (or null) for strings, booleans and nulls. This will continue to parse strings that have numbers in them like "runtime" : "5".

    public static final TypeAdapter<Number> UNRELIABLE_INTEGER = new TypeAdapter<Number>() {
        @Override
        public Number read(JsonReader in) throws IOException {
            JsonToken jsonToken = in.peek();
            switch (jsonToken) {
                case NUMBER:
                case STRING:
                    String s = in.nextString();
                    try {
                        return Integer.parseInt(s);
                    } catch (NumberFormatException ignored) {
                    }
                    try {
                        return (int)Double.parseDouble(s);
                    } catch (NumberFormatException ignored) {
                    }
                    return null;
                case NULL:
                    in.nextNull();
                    return null;
                case BOOLEAN:
                    in.nextBoolean();
                    return null;
                default:
                    throw new JsonSyntaxException("Expecting number, got: " + jsonToken);
            }
        }
        @Override
        public void write(JsonWriter out, Number value) throws IOException {
            out.value(value);
        }
    };
    public static final TypeAdapterFactory UNRELIABLE_INTEGER_FACTORY = TypeAdapters.newFactory(int.class, Integer.class, UNRELIABLE_INTEGER);
    

    You can register it with the following code

    Gson gson = new GsonBuilder()
                .registerTypeAdapterFactory(UNRELIABLE_INTEGER_FACTORY)
                .create();
    

    Note that the normal JsonReader.nextInt() that this replaces attempts to call parseInt and parseDouble on the token, so this will replicate internal logic for parsing integers.

    0 讨论(0)
提交回复
热议问题