# Setting Up Roles and Permissions in Keycloak

Roles and permissions in Keycloak define what users and applications are allowed to do. Roles can be assigned to users, groups, or clients, and are embedded into access tokens to enforce authorization. This guide explains how to define and manage roles via the Admin Console, REST API, and CLI, with best practices and common issues.

## **Creating Roles via Keycloak Admin Console**

This is the easiest way to create and manage roles visually.

#### **Access the Admin Console**

Log in to:

```
http://<your-keycloak-domain>/admin/
```

Choose the appropriate realm.

#### **Create Realm Roles**

1. <span class="s1">Go to </span>**Roles &gt; Add Role**
2. Enter:
    
    
    - <span class="s1">**Role Name**</span><span class="s2">: e.g., </span>admin<span class="s2">, </span>viewer<span class="s2">, </span>editor
    - <span class="s1">**Description**</span>: Optional but recommended
3. Click <span class="s1">**Save**</span>

[![image.png](https://docs.elest.io/uploads/images/gallery/2025-06/scaled-1680-/dvYimage.png)](https://docs.elest.io/uploads/images/gallery/2025-06/dvYimage.png)

#### **Create Client Roles**

1. <span class="s1">Go to </span>**Clients &gt; \[client-name\] &gt; Roles &gt; Create Role**
2. Fill in the <span class="s1">**Role Name**</span> and optional <span class="s1">**Description**</span>
3. Save the role

[![image.png](https://docs.elest.io/uploads/images/gallery/2025-06/scaled-1680-/cQIimage.png)](https://docs.elest.io/uploads/images/gallery/2025-06/cQIimage.png)

#### **Assign Roles to Users**

1. <span class="s1">Go to </span>**Users &gt; \[username\] &gt; Role Mappings**
2. In <span class="s1">**Available Roles**</span>, choose from:
    
    
    - Realm roles (top-left dropdown)
    - Client roles (select client under “Client Roles”)
3. <span class="s1">Click </span>**Add selected**

[![image.png](https://docs.elest.io/uploads/images/gallery/2025-06/scaled-1680-/j8timage.png)](https://docs.elest.io/uploads/images/gallery/2025-06/j8timage.png)

## **Creating Roles via Keycloak REST API**

#### **Get Access Token**

```bash
curl -X POST "https://<keycloak-domain>/realms/master/protocol/openid-connect/token" \
  -H "Content-Type: application/x-www-form-urlencoded" \
  -d "username=admin" \
  -d "password=admin-password" \
  -d "grant_type=password" \
  -d "client_id=admin-cli"
```

<span class="s1">Save the </span>access\_token<span class="s1">.</span>

#### **Create Realm Role**

```bash
curl -X POST "https://<keycloak-domain>/admin/realms/<realm>/roles" \
  -H "Authorization: Bearer <access_token>" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "viewer",
    "description": "Read-only access"
  }'
```

#### **Create Client Role**

```bash
curl -X POST "https://<keycloak-domain>/admin/realms/<realm>/clients/<client-id>/roles" \
  -H "Authorization: Bearer <access_token>" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "api-user",
    "description": "API access for clients"
  }'
```

To get the client ID:

```bash
curl -H "Authorization: Bearer <access_token>" \
  "https://<keycloak-domain>/admin/realms/<realm>/clients"
```

## **Creating Roles via Docker CLI** 

**Access the Container**

```
docker exec -it keycloak bash
```

**Create Roles via CLI**

```bash
/opt/keycloak/bin/kcadm.sh config credentials \
  --server http://localhost:8080 --realm master \
  --user admin --password admin

/opt/keycloak/bin/kcadm.sh create roles -r <realm> \
  -s name=auditor -s description="Can view reports"
```

To create client roles:

```bash
/opt/keycloak/bin/kcadm.sh create clients/<client-id>/roles -r <realm> \
  -s name=external-api -s description="Role for external apps"
```

## **Required Permissions for Managing Roles**

To manage roles, users need:

- <span class="s1">manage-realm</span> role for realm roles
- <span class="s1">manage-clients</span> role for client-specific roles

To assign via Admin Console:

```
Users > [admin-user] > Role Mappings > Realm Roles > Add 'manage-realm' or 'manage-clients'
```

## **Best Practices for Roles and Permissions**

- **Use Fine-Grained Role Names:** <span class="s2">Use names like </span>invoice\_viewer<span class="s2">, </span>invoice\_editor<span class="s2">, or </span>admin\_dashboard<span class="s2"> for clarity.</span>
- **Use Groups to Assign Roles in Bulk:** Create groups such as <span class="s3">managers</span>, <span class="s3">sales</span>, or <span class="s3">auditors</span>, then assign roles to groups.
- **Map Roles to Access Tokens:** Use <span class="s4">**Client &gt; Mappers**</span> to include role names in the <span class="s3">access\_token</span> or <span class="s3">id\_token</span>.
- **Prefer Client Roles for Application Permissions:** Client roles are scoped to individual apps and help separate responsibilities.
- **Use Composite Roles Sparingly:** Composite roles combine multiple roles into one but may add complexity if overused.

## **Common Issues and Troubleshooting**

<table border="1" id="bkmrk-issue-possible-cause" style="border-collapse: collapse; border-color: rgb(0, 0, 0);"><thead><tr><th style="border-color: rgb(0, 0, 0);">**Issue**

</th><th style="border-color: rgb(0, 0, 0);">**Possible Cause**

</th><th style="border-color: rgb(0, 0, 0);">**Solution**

</th></tr></thead><tbody><tr><td style="border-color: rgb(0, 0, 0);">Role doesn’t appear in token

</td><td style="border-color: rgb(0, 0, 0);">Missing protocol mapper

</td><td style="border-color: rgb(0, 0, 0);">Add a role mapper in <span class="s1">**Client &gt; Mappers**</span>

</td></tr><tr><td style="border-color: rgb(0, 0, 0);">User not authorized despite role assignment

</td><td style="border-color: rgb(0, 0, 0);">Role not assigned to the correct client/realm

</td><td style="border-color: rgb(0, 0, 0);">Verify if the role is client-scoped or realm-wide

</td></tr><tr><td style="border-color: rgb(0, 0, 0);"><span class="s1">403 Forbidden</span> despite valid login

</td><td style="border-color: rgb(0, 0, 0);">Role not embedded in access token

</td><td style="border-color: rgb(0, 0, 0);">Ensure token includes required roles via protocol mappers

</td></tr><tr><td style="border-color: rgb(0, 0, 0);">REST API: <span class="s1">409 Conflict</span> when creating role

</td><td style="border-color: rgb(0, 0, 0);">Role with same name already exists

</td><td style="border-color: rgb(0, 0, 0);">Use a unique name or update existing role

</td></tr><tr><td style="border-color: rgb(0, 0, 0);">Cannot assign role to user

</td><td style="border-color: rgb(0, 0, 0);">User lacks <span class="s1">manage-users</span> privilege

</td><td style="border-color: rgb(0, 0, 0);">Ensure admin has role assignment rights

</td></tr></tbody></table>