{"record":{"id":"54c34bf641ab05be","repo":"antonmedv/fx","slug":"invalid-character-q-in-number","errorCode":null,"errorMessage":"Invalid character %q in number","messagePattern":"Invalid character %q in number","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/jsonx/json.go","lineNumber":267,"sourceCode":"\treturn str\n}\n\nfunc (p *JsonParser) parseMinus() *Node {\n\tstart := p.end - 1\n\tp.next()\n\tswitch p.char {\n\tcase '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':\n\t\treturn p.parseNumber(start)\n\t}\n\tif !p.strict {\n\t\tswitch p.char {\n\t\tcase 'n', 'N':\n\t\t\treturn p.parseNan(start)\n\t\tcase 'i', 'I':\n\t\t\treturn p.parseInfinity(start)\n\t\t}\n\t}\n\tpanic(fmt.Sprintf(\"Invalid character %q in number\", p.char))\n}\n\nfunc (p *JsonParser) parseNumber(start int) *Node {\n\tnum := &Node{\n\t\tKind:       Number,\n\t\tDepth:      p.depth,\n\t\tLineNumber: p.lineNumberPlusPlus(),\n\t}\n\n\t// Leading zero\n\tif p.char == '0' {\n\t\tp.next()\n\t} else {\n\t\tfor utils.IsDigit(p.char) {\n\t\t\tp.next()\n\t\t}\n\t}\n","sourceCodeStart":249,"sourceCodeEnd":285,"githubUrl":"https://github.com/antonmedv/fx/blob/4f31cd3a0c5d66f1b4290a2719bab14a5cee8ebe/internal/jsonx/json.go#L249-L285","documentation":"parseMinus consumed a leading '-' but the next character is neither a digit nor (in non-strict mode) n/N (NaN) or i/I (Infinity). A negative number must be followed by a digit, so the parser panics reporting the offending character.","triggerScenarios":"Parse on inputs like `-,`, `-}`, `- abc`, `\"key\": -` , or `-NaN`/`-Infinity` while strict mode is enabled (the lenient branch is skipped when p.strict is true).","commonSituations":"Hand-edited numeric fields left as bare '-', JavaScript payloads with -Infinity parsed in strict mode, template rendering producing `\"timeout\": -` when a variable was empty, CSV/JSON converters emitting placeholder minus signs.","solutions":["Replace the bare '-' with a valid negative number (e.g. -1) or null","If the intent was -Infinity or -NaN, disable strict mode so parseMinus accepts n/N and i/I","Validate numeric fields before serialization so empty values become null instead of '-'","Locate the exact position via the %q character in the message and repair that line"],"exampleFix":"// before\n{\"delta\": -}\n// after\n{\"delta\": -1}  // or null; or use -Infinity with strict=false","handlingStrategy":"validation","validationCode":"// Reject bare '-' before parsing\nfor _, m := range bareMinus.FindAllString(string(b), -1) { // regexp: `(-)([^0-9]|$)`\n\t_ = m\n\treturn errors.New(\"minus sign not followed by digit or -Infinity\")\n}","typeGuard":null,"tryCatchPattern":"defer func() {\n\tif r := recover(); r != nil {\n\t\tif msg, ok := r.(string); ok && strings.Contains(msg, \"in number\") {\n\t\t\terr = fmt.Errorf(\"malformed negative number: %s\", msg)\n\t\t}\n\t}\n}()","preventionTips":["Validate numeric fields at serialization time (never emit bare '-')","Map unknown numerics to null instead of placeholders","Use -Infinity only with strict=false and document it","Sanitize templated numbers so empty variables become null"],"tags":["json","number","syntax-error","strict-mode"],"backgroundTag":"invalid-json-number","analyzedSha":"4f31cd3a0c5d66f1b4290a2719bab14a5cee8ebe","analyzedAt":"2026-09-02T02:17:47.344Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-09T06:17:21.866Z"}