问题
I want to secure my routes using Keycloak which is an open source identity and access management. I have tried to follow their documentation but I was not able to make it work.
Here is my app.js file:
const express = require( 'express' );
const routePlaces = require( './routes/placesRoutes' );
const Keycloak = require( 'keycloak-connect' );
const session = require( 'express-session' );
const memoryStrore = new session.MemoryStore();
let kcConfig = {
clientId = 'parking-app',
bearerOnly: true,
serverUrl: 'localhost:8080/auth',
realm: 'FlexParking',
reamlPublicKey: 'MIIBIjANBg…'
}
var keycloak = new KeyCloak( {store: memoryStore}, kcConfig );
app.use( keycloak.middleware({
// here I think I have to place my routes
}));
app.use( '/places, routePlaces );
module.exports = app;
The server is created in a server.js
file and all the endpoints are working perfectly before trying to use Keycloak.
Here is my routePlaces.js
file:
'use strict';
const express = require( 'express' );
const place = require( '../controllers/placesController' );
router.route( '/gps' ).get( place.get_place_by_gps );
router.route( '/street' ).get( place.get_place_by_street );
module.exports = router;
And here is my placesController.js
:
'use strict';
exports.get_place_by_gps = ( req, res, next ) => {
res.send( ' GET places by the GPS position' );
}
exports.get_place_by_street = ( req, res, next ) => {
res.send( ' GET places by the street name' );
}
I want my route ('/places/gps') to be protected using keycloak.connect('...')
and the route '/places/street' to be used without any protection. How to configure the Keycloak middleware to do that?
app.use( keycloak.middleware({
// here i think i have to place my routes
}));
How can the route be protected like this:
router.route( '/gps' ).get( place.get_place_by_gps, keycloak.connect('user'));
回答1:
> app.use(keycloak.middleware({
>
> // here i think i have to place my routes
>
> }));
It is incorrect. You have to pass the options
there.
app.use(keycloak.middleware({
logout: logoutUrl,
admin: '/'
}));
How has to be my route that i want to protect:
router.route('/gps').get(place.get_place_by_gps,keycloak.connect('user'); something as above?
keycloak.middleware()
Doesn't do any protection itself. It just tries to get grant
data from the request and put it in the special object request.kauth.grant
.
Also it does some additional things, like check for logout request.
To protect a resource you need to add keycloak.protect()
app.get('/gps', keycloak.protect(), handler);
To not protect a resource just don't add anything
app.get('/street', handler);
This is a more complex example from keycloak-nodejs-example, it uses a custom middleware
middleware(logoutUrl) {
// Return the Keycloak middleware.
//
// Specifies that the user-accessible application URL to
// logout should be mounted at /logout
//
// Specifies that Keycloak console callbacks should target the
// root URL. Various permutations, such as /k_logout will ultimately
// be appended to the admin URL.
let result = this.keyCloak.middleware({
logout: logoutUrl,
admin: '/'
});
result.push(this.createSecurityMiddleware());
return result;
}
createSecurityMiddleware() {
return (req, res, next) => {
if (this.permissions.isNotProtectedUrl(req)) {
return next();
}
const permission = this.permissions.findPermission(req);
if (!permission) {
console.log('Can not find a permission for: %s %s', req.method, req.originalUrl);
return this.keyCloak.accessDenied(req, res);
}
this.protectAndCheckPermission(req, res, next, permission.resource, permission.scope);
};
}
app.use(keyCloak.middleware('/logout'));
Sources
https://github.com/v-ladynev/keycloak-nodejs-example/blob/master/lib/keyCloakService.js#L69
https://github.com/v-ladynev/keycloak-nodejs-example/blob/master/app.js#L60
Also you can refer for a more complex protection schema, using (resource, scope) in the keycloak-nodejs-example
来源:https://stackoverflow.com/questions/53684255/use-keycloak-protect-with-express-router