{"record":{"id":"0caa9e97640c53f1","repo":"google/gson","slug":"expecting-number-got-jsontoken-at-path-pat","errorCode":null,"errorMessage":"Expecting number, got: ${jsonToken}; at path ${path}","messagePattern":"Expecting number, got: (.+?); at path (.+?)","errorType":"exception","errorClass":"JsonSyntaxException","httpStatus":null,"severity":"error","filePath":"gson/src/main/java/com/google/gson/internal/bind/NumberTypeAdapter.java","lineNumber":73,"sourceCode":"    if (toNumberStrategy == ToNumberPolicy.LAZILY_PARSED_NUMBER) {\n      return LAZILY_PARSED_NUMBER_FACTORY;\n    } else {\n      return newFactory(toNumberStrategy);\n    }\n  }\n\n  @Override\n  public Number read(JsonReader in) throws IOException {\n    JsonToken jsonToken = in.peek();\n    switch (jsonToken) {\n      case NULL:\n        in.nextNull();\n        return null;\n      case NUMBER:\n      case STRING:\n        return toNumberStrategy.readNumber(in);\n      default:\n        throw new JsonSyntaxException(\n            \"Expecting number, got: \" + jsonToken + \"; at path \" + in.getPath());\n    }\n  }\n\n  @Override\n  public void write(JsonWriter out, Number value) throws IOException {\n    out.value(value);\n  }\n}\n","sourceCodeStart":55,"sourceCodeEnd":83,"githubUrl":"https://github.com/google/gson/blob/310ac341f2f92a454b229bf21f70d2d18b2b6db7/gson/src/main/java/com/google/gson/internal/bind/NumberTypeAdapter.java#L55-L83","documentation":"NumberTypeAdapter handles fields/variables typed as Number. Its read() accepts only NULL, NUMBER, or STRING (numeric) tokens; any other token (BOOLEAN, BEGIN_OBJECT, BEGIN_ARRAY, NAME, END_*) is a type mismatch and Gson throws JsonSyntaxException with the offending token and the reader path. This guards against silently coercing incompatible JSON into a numeric Java field.","triggerScenarios":"Deserializing JSON where a Number-typed field receives a boolean, object, or array; e.g. {\"count\": true} mapped to a Number field, or {\"amount\": {}} where a number was expected.","commonSituations":"Schema drift where a numeric field arrives as a different JSON type; weakly-typed Object payloads later narrowed to Number; producer bugs emitting the wrong value type.","solutions":["Fix the source data to send a numeric JSON value for Number-typed fields","Register a custom TypeAdapter<Number> that coerces or nulls incompatible tokens","Deserialize the field as Object and post-process, or use a more permissive target type"],"exampleFix":"// before - boolean where Number expected\n{\"count\": true}\n\n// after - numeric value\n{\"count\": 1}","handlingStrategy":"type-guard","validationCode":"// Inspect the token before binding a Number field\nJsonReader reader = ...;\nJsonToken t = reader.peek();\nif (t == JsonToken.NUMBER || t == JsonToken.STRING || t == JsonToken.NULL) {\n    Number n = gson.fromJson(reader, Number.class);\n} else {\n    // schema drift: handle, default, or skip\n    reader.skipValue();\n}","typeGuard":"// Narrow a JsonElement to a numeric value before binding\nstatic boolean isNumeric(JsonElement e) {\n    return e != null && e.isJsonPrimitive() && e.getAsJsonPrimitive().isNumber();\n}","tryCatchPattern":"try {\n  Number n = gson.fromJson(json, Number.class);\n} catch (com.google.gson.JsonSyntaxException e) {\n  // 'Expecting number, got: <token>': source sent a non-numeric; coerce or skip\n}","preventionTips":["Validate the JSON token type for Number fields before deserialization","Register a custom TypeAdapter<Number> to coerce or null invalid tokens","Pin down producer schemas so numeric fields never carry other types"],"tags":["json","deserialization","type-mismatch","numeric"],"backgroundTag":null,"analyzedSha":"310ac341f2f92a454b229bf21f70d2d18b2b6db7","analyzedAt":"2026-08-10T02:58:47.455Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}