{"record":{"id":"a5d3a160a204714c","repo":"apache/cassandra","slug":"only-superusers-can-create-a-role-with-superuser-s","errorCode":null,"errorMessage":"Only superusers can create a role with superuser status","messagePattern":"Only superusers can create a role with superuser status","errorType":"validation","errorClass":"UnauthorizedException","httpStatus":null,"severity":"error","filePath":"src/java/org/apache/cassandra/cql3/statements/CreateRoleStatement.java","lineNumber":73,"sourceCode":"    {\n        if (options.isGeneratedName())\n            this.role = RoleResource.GENERATED_ROLE;\n        else\n            this.role = RoleResource.role(name.getName());\n\n        this.opts = options;\n        this.dcPermissions = dcPermissions;\n        this.cidrPermissions = cidrPermissions;\n        this.ifNotExists = ifNotExists;\n    }\n\n    public void authorize(ClientState state) throws UnauthorizedException\n    {\n        super.checkPermission(state, Permission.CREATE, RoleResource.root());\n        if (opts.getSuperuser().isPresent())\n        {\n            if (opts.getSuperuser().get() && !state.getUser().isSuper())\n                throw new UnauthorizedException(\"Only superusers can create a role with superuser status\");\n        }\n    }\n\n    public void validate(ClientState state) throws RequestValidationException\n    {\n        opts.validate();\n        if (role.getRoleName().isEmpty())\n            throw new InvalidRequestException(\"Role name can't be an empty string\");\n\n        if (dcPermissions != null)\n        {\n            dcPermissions.validate();\n        }\n\n        if (cidrPermissions != null)\n        {\n            cidrPermissions.validate();\n        }","sourceCodeStart":55,"sourceCodeEnd":91,"githubUrl":"https://github.com/apache/cassandra/blob/88fd0f6a0eaed8943f05ac9e8f947882b8ddc8f1/src/java/org/apache/cassandra/cql3/statements/CreateRoleStatement.java#L55-L91","documentation":"CreateRoleStatement.authorize enforces that only superusers may set the SUPERUSER option when creating a role. If a non-superuser authenticated user issues CREATE ROLE ... WITH SUPERUSER = true, Cassandra throws UnauthorizedException to prevent privilege escalation.","triggerScenarios":"A logged-in non-superuser executes CREATE ROLE foo WITH SUPERUSER = true (or LOGIN/SUPERUSER options implying superuser status).","commonSituations":"Operators granting role-creation rights via a custom role manager but forgetting Cassandra still reserves SUPERUSER creation for superusers; automation running with a provisioned non-super account attempting to bootstrap admin roles; post-upgrade from systems without this check.","solutions":["Run the CREATE ROLE statement as a superuser account.","Remove the SUPERUSER = true option and have a superuser alter the role afterward.","Grant the necessary permissions properly: create the role without SUPERUSER, then have a superuser execute ALTER ROLE foo WITH SUPERUSER = true."],"exampleFix":"// before (as non-superuser)\nCREATE ROLE admin WITH SUPERUSER = true AND LOGIN = true;\n// after (as superuser, or two-step)\nCREATE ROLE admin WITH LOGIN = true;\n-- then, connected as a superuser:\nALTER ROLE admin WITH SUPERUSER = true;","handlingStrategy":"validation","validationCode":"// client-side pre-check\nboolean wantsSuperuser = createCql.contains(\"SUPERUSER = true\");\nif (wantsSuperuser && !currentUserIsSuperuser(session)) throw new IllegalStateException(\"requires superuser connection\");","typeGuard":null,"tryCatchPattern":"try { session.execute(createRoleCql); } catch (UnauthorizedException e) { if (e.getMessage().contains(\"Only superusers can create a role with superuser status\")) { /* retry via superuser connection or two-step create+alter */ } else throw e; }","preventionTips":["Use a superuser connection for any statement setting SUPERUSER = true","Create roles without SUPERUSER and have a superuser ALTER them afterward","Keep provisioning automation credentials' privilege level in sync with the operations they perform"],"tags":["authz","roles","permission-denied"],"backgroundTag":"permission-denied","analyzedSha":"88fd0f6a0eaed8943f05ac9e8f947882b8ddc8f1","analyzedAt":"2026-09-10T07:29:22.284Z","contentChangedAt":"2026-09-10T07:29:22.284Z","schemaVersion":2},"datasetVersion":"2026-09-17T15:17:12.973Z"}