{"record":{"id":"070113ecd0dea072","repo":"uber-go/zap","slug":"may-not-contain-q","errorCode":null,"errorMessage":"may not contain %q","messagePattern":"may not contain %q","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"sink.go","lineNumber":177,"sourceCode":"}\n\nfunc normalizeScheme(s string) (string, error) {\n\t// https://tools.ietf.org/html/rfc3986#section-3.1\n\ts = strings.ToLower(s)\n\tif first := s[0]; 'a' > first || 'z' < first {\n\t\treturn \"\", errors.New(\"must start with a letter\")\n\t}\n\tfor i := 1; i < len(s); i++ { // iterate over bytes, not runes\n\t\tc := s[i]\n\t\tswitch {\n\t\tcase 'a' <= c && c <= 'z':\n\t\t\tcontinue\n\t\tcase '0' <= c && c <= '9':\n\t\t\tcontinue\n\t\tcase c == '.' || c == '+' || c == '-':\n\t\t\tcontinue\n\t\t}\n\t\treturn \"\", fmt.Errorf(\"may not contain %q\", c)\n\t}\n\treturn s, nil\n}\n","sourceCodeStart":159,"sourceCodeEnd":181,"githubUrl":"https://github.com/uber-go/zap/blob/bbd4ecbd8760678fdbac94c93d9aca8069c83b2f/sink.go#L159-L181","documentation":"normalizeScheme validates a URL scheme used when registering a custom sink via RegisterSink. A scheme may only contain ASCII letters, digits, '.', '+', and '-'. If any other character is found, the sink is rejected with this error naming the offending character.","triggerScenarios":"Calling zap.RegisterSink with a scheme containing illegal characters, e.g. RegisterSink(\"my sink\", factory) or RegisterSink(\"s3+bucket!\", ...) — any scheme character outside [A-Za-z0-9.+-] triggers it.","commonSituations":"Typos or spaces in scheme names, copy-pasted scheme strings with uppercase-delimiting characters like '_' (which is NOT allowed), dynamically built scheme names from user input or config values.","solutions":["Remove or replace the illegal character in the scheme passed to RegisterSink (use letters, digits, '.', '+', '-' only).","Use '_' alternatives such as '-' for multi-word schemes, e.g. \"my-sink\" instead of \"my_sink\".","Validate/normalize the scheme string (strings.TrimSpace, regexp ^[A-Za-z0-9.+-]+$) before calling RegisterSink."],"exampleFix":"// before\nerr := zap.RegisterSink(\"my_sink\", factory)\n// after\nerr := zap.RegisterSink(\"my-sink\", factory)","handlingStrategy":"validation","validationCode":"var schemeRe = regexp.MustCompile(`^[A-Za-z0-9.+-]+$`)\nif !schemeRe.MatchString(scheme) {\n    return fmt.Errorf(\"invalid sink scheme %q\", scheme)\n}\nerr := zap.RegisterSink(scheme, factory)","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Use only [A-Za-z0-9.+-] characters in scheme names; prefer '-' over '_'.","Trim whitespace from scheme strings built from config or user input.","Add a unit test registering every sink scheme your application uses."],"tags":["sink","validation","register-sink"],"backgroundTag":"invalid-url-scheme","analyzedSha":"bbd4ecbd8760678fdbac94c93d9aca8069c83b2f","analyzedAt":"2026-08-31T13:01:40.228Z","schemaVersion":2},"datasetVersion":"2026-09-01T08:17:40.651Z"}