{"record":{"id":"8a387a4c2dea44da","repo":"inancgumus/learngo","slug":"line-d-s","errorCode":null,"errorMessage":"line #%d: %s","messagePattern":"line #(.+?): (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"logparser/testing/report/parser.go","lineNumber":37,"sourceCode":"\tlerr    error    // the last error occurred\n}\n\n// New returns a new parsing state.\nfunc New() *Parser {\n\treturn &Parser{summary: newSummary()}\n}\n\n// Parse parses a log line and adds it to the summary.\nfunc (p *Parser) Parse(line string) {\n\t// if there was an error do not continue\n\tif p.lerr != nil {\n\t\treturn\n\t}\n\n\t// chain the parser's error to the result's\n\tres, err := parse(line)\n\tif p.lines++; err != nil {\n\t\tp.lerr = fmt.Errorf(\"line #%d: %s\", p.lines, err)\n\t\treturn\n\t}\n\n\tp.summary.update(res)\n}\n\n// Summarize summarizes the parsing results.\n// Only use it after the parsing is done.\nfunc (p *Parser) Summarize() *Summary {\n\treturn p.summary\n}\n\n// Err returns the last error encountered\nfunc (p *Parser) Err() error {\n\treturn p.lerr\n}\n","sourceCodeStart":19,"sourceCodeEnd":54,"githubUrl":"https://github.com/inancgumus/learngo/blob/3c475a78e54336c6255e925ff66b8ef4da6a2ae7/logparser/testing/report/parser.go#L19-L54","documentation":"The report parser's Parse method parses each line via parse(line) and, on failure, records the error in p.lerr prefixed with the 1-based line counter p.lines ('line #%d: %s') and returns, stopping further parsing. The stored error is reported after the whole file has been streamed.","triggerScenarios":"Calling Parse with a line whose field count != 3 (error 33) or whose numeric fields fail field.atoi (error 34); the wrapped message identifies the offending line number.","commonSituations":"Log lines missing the visits or time-spent column, negative visit counts, non-numeric numbers ('12,000'), or headers/blank lines accidentally fed to the parser.","solutions":["Fix or remove the line indicated by 'line #N' in the error","Validate lines before Parse (3 whitespace-separated fields, non-negative integers)","Decide on a policy: fail-fast (current) vs. collecting all bad lines and reporting a summary"],"exampleFix":"// before\nif p.lines++; err != nil {\n    p.lerr = fmt.Errorf(\"line #%d: %s\", p.lines, err)\n    return\n}\n// after\nif p.lines++; err != nil {\n    p.skipped++\n    p.lerr = fmt.Errorf(\"line #%d: %s\", p.lines, err) // keep last; continue parsing\n    return\n}","handlingStrategy":"validation","validationCode":"for i, line := range lines {\n    if len(strings.Fields(line)) != 3 {\n        log.Printf(\"line %d malformed, skipping\", i+1)\n        continue\n    }\n    p.Parse(line)\n}","typeGuard":"func isReportLine(line string) bool {\n    fs := strings.Fields(line)\n    if len(fs) != 3 { return false }\n    v, err1 := strconv.Atoi(fs[1]); t, err2 := strconv.Atoi(fs[2])\n    return err1 == nil && err2 == nil && v >= 0 && t >= 0\n}","tryCatchPattern":"if p.lerr != nil {\n    log.Fatalf(\"parsing stopped: %v\", p.lerr) // p.lerr already contains 'line #N: ...'\n}","preventionTips":["Validate each line (3 fields, non-negative ints) before Parse","Decide fail-fast vs. skip-and-report policy up front","Check p.lerr after the parse loop and surface it to the user","Keep a rejected-lines list for post-run inspection"],"tags":["go","parsing","report"],"backgroundTag":"log-line-parse-error","analyzedSha":"3c475a78e54336c6255e925ff66b8ef4da6a2ae7","analyzedAt":"2026-09-02T10:14:38.492Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-09T16:17:10.729Z"}