{"record":{"id":"66c53391fadb44f0","repo":"coollabsio/coolify","slug":"you-do-not-have-permission-to-create-tokens-with-r","errorCode":null,"errorMessage":"You do not have permission to create tokens with root permissions.","messagePattern":"You do not have permission to create tokens with root permissions\\.","errorType":"exception","errorClass":"Exception","httpStatus":null,"severity":"error","filePath":"app/Livewire/Security/ApiTokens.php","lineNumber":119,"sourceCode":"            $this->permissions = ['deploy'];\n        } else {\n            if (count($this->permissions) == 0) {\n                $this->permissions = ['read'];\n            }\n        }\n        sort($this->permissions);\n    }\n\n    public function addNewToken()\n    {\n        try {\n            $this->authorize('create', PersonalAccessToken::class);\n\n            // Re-evaluate policies fresh against the current authenticated user.\n            // Never trust $this->canUse* booleans — they come from the Livewire\n            // snapshot which can be replayed from another user's session.\n            if (in_array('root', $this->permissions, true) && ! auth()->user()->can('useRootPermissions', PersonalAccessToken::class)) {\n                throw new \\Exception('You do not have permission to create tokens with root permissions.');\n            }\n\n            if (array_intersect(['write', 'write:sensitive'], $this->permissions) && ! auth()->user()->can('useWritePermissions', PersonalAccessToken::class)) {\n                throw new \\Exception('You do not have permission to create tokens with write permissions.');\n            }\n\n            if (in_array('deploy', $this->permissions, true) && ! auth()->user()->can('useDeployPermissions', PersonalAccessToken::class)) {\n                throw new \\Exception('You do not have permission to create tokens with deploy permissions.');\n            }\n\n            if (in_array('read:sensitive', $this->permissions, true) && ! auth()->user()->can('useSensitivePermissions', PersonalAccessToken::class)) {\n                throw new \\Exception('You do not have permission to create tokens with read:sensitive permissions.');\n            }\n\n            $this->validate([\n                'description' => 'required|min:3|max:255',\n                'expiresInDays' => 'nullable|integer|in:7,30,60,90,365',\n            ]);","sourceCodeStart":101,"sourceCodeEnd":137,"githubUrl":"https://github.com/coollabsio/coolify/blob/70b9acc42467278373e00de77abb40684e25b395/app/Livewire/Security/ApiTokens.php#L101-L137","documentation":"addNewToken() on the API tokens screen re-authorizes requested abilities server-side: if 'root' appears in the submitted permissions array but the current user fails the useRootPermissions gate, token creation aborts. The component deliberately ignores the cached $canUse* booleans because Livewire snapshots can be replayed from another session - the policy is evaluated fresh against auth()->user().","triggerScenarios":"A non-root team member (or a user who lost root standing) submitting a token creation with the 'root' permission ticked; a tampered Livewire request injecting 'root' into the permissions array; a page rendered before a role/subscription downgrade.","commonSituations":"Team role changes after the tokens page was loaded; attempts to self-elevate via browser devtools; cloud instances where root abilities depend on the team's root status.","solutions":["Untick the root permission and create the token with ordinary abilities (read, and others you are allowed)","Have the instance/team root (or owner) create the root-scoped token instead","Reload the API tokens page so the permission checkboxes reflect your current gates before submitting","If you believe you should have the ability, verify your team role and the PersonalAccessTokenPolicy::useRootPermissions conditions"],"exampleFix":"// blade: before\n<input type=\"checkbox\" value=\"root\" wire:model=\"permissions\">\n\n// blade: after\n<input type=\"checkbox\" value=\"root\" wire:model=\"permissions\"\n    @if(!auth()->user()->can('useRootPermissions', \\App\\Models\\PersonalAccessToken::class)) disabled @endif>","handlingStrategy":"validation","validationCode":"use App\\Models\\PersonalAccessToken;\n\nif (in_array('root', $permissions, true)\n    && ! auth()->user()->can('useRootPermissions', PersonalAccessToken::class)) {\n    unset($permissions[array_search('root', $permissions, true)]);\n    // or block submission in the UI\n}","typeGuard":null,"tryCatchPattern":"Keep the try/catch in addNewToken(); catch \\Exception and dispatch('error', $e->getMessage()). Never precompute ability booleans into the snapshot - always re-evaluate gates server-side at submit time.","preventionTips":["Disable permission checkboxes the user cannot use: auth()->user()->can(...)","Have owners mint root tokens; members request tokens without privileged abilities","Reload the tokens page after any role change before submitting"],"tags":["api-token","authorization","sanctum","permissions","livewire"],"backgroundTag":"authorization-denied","analyzedSha":"70b9acc42467278373e00de77abb40684e25b395","analyzedAt":"2026-08-17T01:41:01.313Z","schemaVersion":2},"datasetVersion":"2026-08-17T04:17:16.089Z"}