{"record":{"id":"e64072d14b2fbf87","repo":"hashicorp/nomad","slug":"selector-is-invalid-v","errorCode":null,"errorMessage":"selector is invalid: %v","messagePattern":"selector is invalid: (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"nomad/structs/acl.go","lineNumber":2116,"sourceCode":"\t\tmErr.Errors = append(mErr.Errors, errors.New(\"bind type is missing\"))\n\tcase ACLBindingRuleBindTypeRole, ACLBindingRuleBindTypePolicy:\n\t\tif a.BindName == \"\" {\n\t\t\tmErr.Errors = append(mErr.Errors, errors.New(\"bind name is missing\"))\n\t\t}\n\tcase ACLBindingRuleBindTypeManagement:\n\t\tif a.BindName != \"\" {\n\t\t\tmErr.Errors = append(mErr.Errors, errors.New(\"bind name should be empty\"))\n\t\t}\n\tdefault:\n\t\tmErr.Errors = append(mErr.Errors, fmt.Errorf(\"unsupported bind type: %q\", a.BindType))\n\t}\n\n\t// If there is a selector configured, ensure that go-bexpr can parse this.\n\t// Otherwise, the user will get an ambiguous failure when attempting to\n\t// login.\n\tif a.Selector != \"\" {\n\t\tif _, err := bexpr.CreateEvaluator(a.Selector, nil); err != nil {\n\t\t\tmErr.Errors = append(mErr.Errors, fmt.Errorf(\"selector is invalid: %v\", err))\n\t\t}\n\t}\n\n\treturn mErr.ErrorOrNil()\n}\n\n// Merge merges binding rule a with b. It sets all required empty fields of rule\n// a to corresponding values of rule b, except for \"ID\" which must be provided.\nfunc (a *ACLBindingRule) Merge(b *ACLBindingRule) {\n\ta.BindName = helper.Merge(a.BindName, b.BindName)\n\ta.BindType = helper.Merge(a.BindType, b.BindType)\n\ta.AuthMethod = helper.Merge(a.AuthMethod, b.AuthMethod)\n}\n\n// SetHash is used to compute and set the hash of the ACL binding rule. This\n// should be called every and each time a user specified field on the method is\n// changed before updating the Nomad state store.\nfunc (a *ACLBindingRule) SetHash() []byte {","sourceCodeStart":2098,"sourceCodeEnd":2134,"githubUrl":"https://github.com/hashicorp/nomad/blob/482b49bf1aec006f089bcfc7e632d8f6ac303e5e/nomad/structs/acl.go#L2098-L2134","documentation":"When an ACL binding rule declares a Selector, Nomad compiles it with go-bexpr at validation time; if bexpr.CreateEvaluator cannot parse the expression, the rule would ambiguously fail at login, so validation wraps the parse error as \"selector is invalid\". The wrapped %v contains the exact bexpr syntax problem.","triggerScenarios":"Creating/updating a binding rule with a Selector expression that go-bexpr cannot parse - unbalanced parentheses, invalid operators, unknown comparison syntax, or referencing fields with malformed identifiers.","commonSituations":"Hand-written boolean selectors with syntax mistakes; using quote/escaping incorrectly around values; migrating selectors from other systems with different expression languages; testing selectors that work in one IdP claim shape but are syntactically invalid.","solutions":["Read the wrapped bexpr error to locate the offending token/position and fix the expression syntax.","Test the selector with go-bexpr or a minimal Nomad API call before submitting.","Simplify the expression (split into multiple rules) if it is complex.","Ensure string values are properly quoted and parentheses balanced."],"exampleFix":"// before\nselector = \" ENG in list(value.roles) \"\n\n// after\nselector = \"\"\"\"eng\" in list(value.roles)\"\"\"","handlingStrategy":"validation","validationCode":"if rule.Selector != \"\" {\n    if _, err := bexpr.CreateEvaluator(rule.Selector, nil); err != nil {\n        return fmt.Errorf(\"selector syntax invalid: %w\", err)\n    }\n}","typeGuard":null,"tryCatchPattern":"if err := client.ACLBindingRules().Upsert(rule); err != nil && strings.Contains(err.Error(), \"selector is invalid\") {\n    // parse out the nested bexpr error and re-prompt the operator to fix the expression\n    return fmt.Errorf(\"fix binding rule selector: %w\", err)\n}","preventionTips":["Pre-test selectors with bexpr.CreateEvaluator in unit tests.","Keep selector expressions simple; split complex logic across rules.","Quote string values properly and balance parentheses."],"tags":["nomad","acl","binding-rule","selector","bexpr","validation"],"backgroundTag":"invalid-selector-expression","analyzedSha":"482b49bf1aec006f089bcfc7e632d8f6ac303e5e","analyzedAt":"2026-09-04T07:54:14.808Z","contentChangedAt":"2026-09-04T07:54:14.808Z","schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}