Hello,
It's the first time writing to keycloak mailing list (I hope this is the correct one?)
so excuse if I forget to provide some information or any other mistakes ..
Sorry for the text wall.
Shortly what I try to do (maybe I got something completely wrong):
I create a backend (node.js Bearer Only) which shall offer an REST api. Partially it is
used via a frontend (keycloak-clients) or directly by some devices.
In general I try to create an application with a lot of CRUD. User Management is done in
keycloak and only I forward these requests to the admin REST Api. Other stuff like the
devices ... I store in a separate database.
So the backend is the abstraction layer for frontend and other use-cases.
So far so good, but for the beginning it was enough to check weather the request comes
from an authenticated person or not, so all handled via keycloak.protect() The Token from
the authenticated person was passed
But now I'd want to offer different authorization level (can differ due to reasons of
multitenancy, why I want to solve this via policies and co in admin-console inside the
client configuariton) because the normal user shall have access to only some routes and
the management shall have full access to the api, but of course don't need the
keycloak admin access.
So I enabled the service account for my backend client and gave this one the realm-admin
role so the client has access to everything and I can handle the authorization inside the
backend client it self (using policies, permissions, .. inside the admin-console).
(Just in case no one gets what I'm talking about. Fixing [1] should help me fixing my
issue I guess)
Setup
- node.js application using express
- registered as single client in keycloak admin-console (confidential, but config inside
the code is bearer-only)
- Keycloak is running in a docker-container (version 4.5)
- all services are running in a docker-compose network and are behind a reverse proxy for
common uri
- enabled Authorization in client and changed the default policy to Negative to always
deny => to see if it is enforced)
My Problem
I don't understand how to use the policies, permissions and Co I created in the
admin-console inside the backend it self. How do I enforce that these are used?
I tried to check different examples and documentation, but could get it working.
The last thing I found was that the entitlement api was removed, but a policy-enforcer was
added to the nodejs adapter. In the documentation for the policy-enforcer [2] I
couldn't find a documentation of the middleware (keycloak.enforcer({}) [3][4]).
My Code
*****
app.js
const express = require('express');
const app = express();
const Keycloak = require('keycloak-connect');
const session = require('express-session');
const routes = require('./routes/index');
const kcConfig = {
'realm': 'master',
'bearer-only': true,
'auth-server-url': `https://DOMAIN/auth<https://domain/auth>`,
'ssl-required': 'all',
'resource': 'fm-backend',
'credentials': {
secret: 'SOME_SECRET',
},
'confidential-port': 0,
'policy-enforcer': { //tried with an without
this, changed nothing
'enforcement-mode': 'ENFORCING',
},
};
const memoryStore = new session.MemoryStore();
const keycloak = new Keycloak({ memoryStore }, kcConfig);
app.use(keycloak.middleware({ logout: '/api/logout', protected:
'/api/gates' }));
// used before, worked for well for authentication
app.use('/api', keycloak.protect(), routes);
// now unfortunately I don't understand how to use keycloak.enforcer() middleware
app.use('/api', keycloak.enforcer({WHAT_COMES_HERE}), routes);
module.exports = app;
*****
[1]
https://stackoverflow.com/questions/53722033/how-to-enable-policy-enforci...
[2]
https://keycloak-docs.github.io/deploy-docs/dev/master/authorization_serv...
[3]
https://github.com/keycloak/keycloak-documentation/blob/master/securing_a...
[4]
https://github.com/keycloak/keycloak-nodejs-connect/blob/master/example/i...
Any Help is appreciated :)
With kind regards
Lasse