{"id":"5683829ed6a994d3","repo":"gofiber/fiber","slug":"fiber-keyauth-scope-contains-invalid-token","errorCode":null,"errorMessage":"fiber: keyauth scope contains invalid token","messagePattern":"fiber: keyauth scope contains invalid token","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"middleware/keyauth/config.go","lineNumber":156,"sourceCode":"\t}\n\tif cfg.ErrorDescription != \"\" && cfg.Error == \"\" {\n\t\tpanic(\"fiber: keyauth error_description requires error\")\n\t}\n\tif cfg.ErrorURI != \"\" {\n\t\tif cfg.Error == \"\" {\n\t\t\tpanic(\"fiber: keyauth error_uri requires error\")\n\t\t}\n\t\tif u, err := url.Parse(cfg.ErrorURI); err != nil || !u.IsAbs() {\n\t\t\tpanic(\"fiber: keyauth error_uri must be absolute\")\n\t\t}\n\t}\n\tif cfg.Error == ErrorInsufficientScope {\n\t\tif cfg.Scope == \"\" {\n\t\t\tpanic(\"fiber: keyauth insufficient_scope requires scope\")\n\t\t}\n\t\tfor scope := range strings.SplitSeq(cfg.Scope, \" \") {\n\t\t\tif scope == \"\" || !isScopeToken(scope) {\n\t\t\t\tpanic(\"fiber: keyauth scope contains invalid token\")\n\t\t\t}\n\t\t}\n\t} else if cfg.Scope != \"\" {\n\t\tpanic(\"fiber: keyauth scope requires insufficient_scope error\")\n\t}\n\n\treturn cfg\n}\n\nfunc isScopeToken(s string) bool {\n\tfor i := 0; i < len(s); i++ {\n\t\tc := s[i]\n\t\tif c < 0x21 || c > 0x7e || c == '\"' || c == '\\\\' {\n\t\t\treturn false\n\t\t}\n\t}\n\treturn s != \"\"\n}","sourceCodeStart":138,"sourceCodeEnd":174,"githubUrl":"https://github.com/gofiber/fiber/blob/9a4c7e57fe0b080a04235d28a4b0d2b4b353d58c/middleware/keyauth/config.go#L138-L174","documentation":"When Error is insufficient_scope, keyauth splits Config.Scope on spaces and validates each token with isScopeToken, which rejects empty strings and any character outside the printable ASCII range 0x21-0x7e or containing double-quote/backslash. A token failing that check panics in configDefault().","triggerScenarios":"Setting Config.Scope to a value with a double space (producing an empty token), a trailing space, a tab/newline separator, or characters like \\\\\" or \\\\. Any of these produce at least one invalid scope token that triggers the panic.","commonSituations":"Building scope from a comma-separated list instead of space-separated (e.g. \"read,write\"). Accidental trailing whitespace from trimming failures. Including quotes or backslashes from JSON-unescaped values. Copying scopes that contain Unicode characters.","solutions":["Use single spaces as the only delimiter and ensure no leading/trailing/duplicate spaces.","Strip any comma separators or quotes before assigning to Scope.","Validate each token against the isScopeToken rule (printable ASCII 0x21-0x7e, no quotes/backslashes) before constructing the middleware."],"exampleFix":"// before\napp.Use(keyauth.New(keyauth.Config{\n    Validator: validateKey,\n    Error:     keyauth.ErrorInsufficientScope,\n    Scope:     \"read, write\",\n}))\n// after\napp.Use(keyauth.New(keyauth.Config{\n    Validator: validateKey,\n    Error:     keyauth.ErrorInsufficientScope,\n    Scope:     \"read write\",\n}))","handlingStrategy":"validation","validationCode":"for _, tok := range strings.Split(cfg.Scope, \" \") {\n    if tok == \"\" {\n        log.Fatalf(\"keyauth: empty scope token in %q (check double/trailing spaces)\", cfg.Scope)\n    }\n    for i := 0; i < len(tok); i++ {\n        c := tok[i]\n        if c < 0x21 || c > 0x7e || c == '\"' || c == '\\\\' {\n            log.Fatalf(\"keyauth: invalid char in scope token %q\", tok)\n        }\n    }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Build scope strings by joining a []string with a single space rather than concatenating by hand.","Avoid comma separators; RFC 6750 scopes are space-delimited."],"tags":["keyauth","config","auth","rfc6750","scope","validation","panic"],"analyzedSha":"9a4c7e57fe0b080a04235d28a4b0d2b4b353d58c","analyzedAt":"2026-08-04T21:44:03.395Z","schemaVersion":2}