aclify
Description
This module provides a Node Access Control Lists implementation inspired by Zend_ACL and node_acl package.
When you develop a web site or application you will soon notice that sessions are not enough to protect all the available resources. Avoiding that malicious users access other users content proves a much more complicated task than anticipated. ACL can solve this problem in a flexible and elegant way.
Create roles and assign roles to users. Sometimes it may even be useful to create one role per user, to get the finest granularity possible, while in other situations you will give the asterisk permission for admin kind of functionality.
Install
$ npm install aclify --save
Features
- Users
- Roles
- Hierarchies
- Resources
- Express middleware for protecting resources.
- Robust implementation with good unit test coverage.
Documentation
- addUserRoles
- removeUserRoles
- removeUser
- userRoles
- roleUsers
- hasRole
- addRoleParents
- removeRoleParents
- removeRole
- removeResource
- allow
- removeAllow
- allowedPermissions
- isAllowed
- areAnyRolesAllowed
- whatResources
- middleware
- store
Stores
Aclify offers several possibilities to store your data:
- Memory
- Redis
- MongoDB
- Sequelize (mysql, mssql, sqlite or postgresql)
Examples
Create your acl module by requiring it and instantiating it with a valid store instance:
From import
// Using Redis storeacl = RedisClient prefix: 'acl_'; // Or Using the Memory storeacl = ; // Or Using the MongoDB storeacl = db prefix: 'acl_'; // Or Using a Sequelize store (mysql, mssql, sqlite or postgresql)acl = db prefix: 'acl_';
From require
const aclify = ; // Using Redis storeacl = RedisClient prefix: 'acl_'; // Or Using the Memory storeacl = ; // Or Using the MongoDB storeacl = db prefix: 'acl_'; // Or Using a Sequelize store (mysql, mssql, sqlite or postgresql)acl = db prefix: 'acl_';
All the following functions return a promise or optionally take a callback with an err parameter as last parameter. We omit them in the examples for simplicity.
Create roles implicitly by giving them permissions:
// guest is allowed to view blogsacl // allow function accepts arrays as any parameteracl
Users are likewise created implicitly by assigning them roles:
acl
Hierarchies of roles can be created by assigning parents to roles:
acl
Note that the order in which you call all the functions is irrelevant (you can add parents first and assign permissions to roles later)
acl
Use the wildcard to give all permissions:
acl
Sometimes is necessary to set permissions on many different roles and resources. This would lead to unnecessary nested callbacks for handling errors. Instead use the following:
acl
You can check if a user has permissions to access a given resource with isAllowed:
acl
Of course arrays are also accepted in this function:
acl
Note that all permissions must be fulfilled in order to get true.
Sometimes is necessary to know what permissions a given user has over certain resources:
acl
It will return an array of resource:[permissions] like this:
'blogs' : 'get' 'delete' 'forums':'get' 'put'
Finally, we provide a middleware for Express for easy protection of resources.
acl
We can protect a resource like this:
app
The middleware will protect the resource named by req.url, pick the user from req.session.userId and check the permission for req.method, so the above would be equivalent to something like this:
acl
The middleware accepts 3 optional arguments, that are useful in some situations. For example, sometimes we cannot consider the whole url as the resource:
app
In this case the resource will be just the three first components of the url (without the ending slash).
It is also possible to add a custom userId or check for other permissions than the method:
app
Methods
addUserRoles( userId, roles, function(err) )
Adds roles to a given user id.
Arguments
userId String|Number User id roles String|Array to add to the user id callback Function Callback called when finished
removeUser( userId, function(err) )
Remove user.
Arguments
userId String|Number User id callback Function Callback called when finished
removeUserRoles( userId, roles, function(err) )
Remove roles from a given user.
Arguments
userId String|Number User id roles String|Array to remove to the user id callback Function Callback called when finished
userRoles( userId, function(err, roles) )
Return all the roles from a given user.
Arguments
userId String|Number User id callback Function Callback called when finished
roleUsers( rolename, function(err, users) )
Return all users who has a given role.
Arguments
rolename String|Number User id callback Function Callback called when finished
hasRole( userId, rolename, function(err, hasRole) )
Return boolean whether user has the role
Arguments
userId String|Number User id rolename String|Number role name callback Function Callback called when finished
addRoleParents( role, parents, function(err) )
Adds a parent or parent list to role.
Arguments
role String Child role parents String|Array Parent to be added callback Function Callback called when finished
removeRoleParents( role, parents, function(err) )
Removes a parent or parent list from role.
If parents
is not specified, removes all parents.
Arguments
role String Child role parents String|Array Parent to be removed optional callback Function Callback called when finished optional
removeRole( role, function(err) )
Removes a role from the system.
Arguments
role String Role to be removed callback Function Callback called when finished
### removeResource( resource, function(err) )
Removes a resource from the system
Arguments
resource String Resource to be removed callback Function Callback called when finished
allow( roles, resources, permissions, function(err) )
Adds the given permissions to the given roles over the given resources.
Arguments
roles String|Array to add permissions to resources String|Array to add permisisons to permissions String|Array to add to the roles over the resources callback Function Callback called when finished
allow( permissionsArray, function(err) )
Arguments
permissionsArray Array Array with objects expressing what permissions to give roles:String|Array allows:resources:String|Array permissions:String|Array callback Function Callback called when finished
removeAllow( role, resources, permissions, function(err) )
Remove permissions from the given roles owned by the given role.
Note: we loose atomicity when removing empty role_resources.
Arguments
role String resources String|Array permissions String|Array callback Function
allowedPermissions( userId, resources, function(err, obj) )
Returns all the allowable permissions a given user have to access the given resources.
It returns an array of objects where every object maps a resource name to a list of permissions for that resource.
Arguments
userId String|Number User id resources String|Array to ask permissions for callback Function Callback called when finished
isAllowed( userId, resource, permissions, function(err, allowed) )
Checks if the given user is allowed to access the resource for the given permissions (note: it must fulfill all the permissions).
Arguments
userId String|Number User id resource String resource to ask permissions for permissions String|Array asked permissions callback Function Callback called with the result
areAnyRolesAllowed( roles, resource, permissions, function(err, allowed) )
Returns true if any of the given roles have the right permissions.
Arguments
roles String|Array to check the permissions for resource String resource to ask permissions for permissions String|Array asked permissions callback Function Callback called with the result
whatResources(role, function(err, {resourceName: [permissions]})
Returns what resources a given role has permissions over.
Arguments
role String|Array Roles callback Function Callback called with the result
whatResources(role, permissions, function(err, resources) )
Returns what resources a role has the given permissions over.
Arguments
role String|Array Roles permissions String|Array Permissions callback Function Callback called with the result
middleware( [numPathComponents, userId, permissions] )
Middleware for express.
To create a custom getter for userId, pass a function(req, res) which returns the userId when called (must not be async).
Arguments
numPathComponents Number number of components in the url to be considered part of the resource name userId String|Number|Function the user id for the acl permissions String|Array the to check for defaults to reqmethod
Creates a new Redis store using Redis client client
.
Tests
$ npm run docker:run:test
Scripts
Run using npm run