IAM (Identity Access Management) plays the role of a wrapper around express middlewares, IAM is a declarative way to make application routes, they also make it easy to make role-based privileges in your app.
In the /todo
folder create a new folder called iam
and under /iam
create a new file called main.server.iam.js
The folder structure so far should be looking like this:
modules└── todo├── bootstraps│ └── main.server.bootstrap.js└── iam└── main.server.iam.js
To declare a new route, you can use the provided snippet to automatically generate it, in your text editor on the main.server.iam.js
if you're using vscode text editor type iam
and then press TAB
.
What IAM does is export an object with some properties:
Prefix: the API endpoint routes prefix
Routes: an array where we declare our API routes each route is an object where we can specify the
path
and the http methods to execute on that route
Our first route will have a GET
request to list out our todos.
modules/todo/iam/main.server.iam.js
1/**2 * @type { IAM.default }3 */4module.exports = {5 prefix: "/todo",6 routes: [7 {8 path: "/",9 methods: {10 get: {11 iam: "modules:todo:main:list",12 title: "List todo",13 groups: [],14 parents: ["modules:todo", "modules:todo:main"],15 description: "List available todo",16 middlewares: [(req, res) => res.json({ message: "Hello, world" })],17 },18 },19 },20 ],21};
To test out our app so far we will be using a popular http client called Postman
Open up postman and make a GET
request to http://localhost:<port-number>/api/v1/todo
at First we'd get a response with a message saying "User is not signed in", Because by default to call our API we must be logged in but to make it simple for this tutorial, all we need to do now is to make the API public by simply going to /config/lib/acl.js
and add the iam string to the guest array like the following:
config/lib/acl.js
1/**2 * Guest role3 * @type {Array}4 */5const guest = ["vendor:users:public", "modules:todo:main"];67/**8 * User role9 * @type {Array}10 */1112const user = [13 /**14 * Users IAMs15 */16 "vendor:users:user",17 "vendor:users:auth",18];19/**20 * Admin role21 * @type {Array}22 */23const admin = [24 ...user,25 /**26 * Admin IAMs27 */28 "vendor:users:admin",29 "vendor:users:roles",30];31/**32 * All roles33 */34module.exports = [35 {36 name: "guest",37 protected: true,38 title: "Guest role",39 description:40 "Role given for any unauthenticated user, or users who don't have any role.",41 iams: guest,42 },43 {44 name: "user",45 protected: true,46 iams: user,47 title: "User role",48 description: "The default role.",49 },50 {51 name: "admin",52 protected: true,53 iams: admin,54 title: "Admin role",55 description: "Given to advanced users.",56 },57];
Now let's save and test our app again, it should work as intended now
We will discuss Roles and IAM in details the next section
Now let's make the rest of the routes necessary for our CRUD
Edit this page on GitHubmodules/todo/iam/main.server.iam.js
1/**2 * @type { IAM.default }3 */4module.exports = {5 prefix: '/todo',6 routes: [7 {8 path: '/',9 methods: {10 get: {11 iam: 'modules:todo:main:list',12 title: 'List todo',13 groups: [],14 parents: ['modules:todo', 'modules:todo:main'],15 description: 'List available todo',16 middlewares: [(req, res) => res.json({ message: 'Hello, world' })],17 },1819 post: {20 iam: 'modules:todo:main:create',21 title: 'Create new task',22 groups: [],23 parents: ['modules:todo', 'modules:todo:main'],24 description: 'Create new task',25 middlewares: [(req, res) => res.status(201).json({ message: 'Todo Created' })],26 },27 },28 },29 {30 path: '/:taskId',31 methods: {32 get: {33 iam: 'modules:todo:main:one:get',34 title: 'Get task',35 groups: [],36 parents: ['modules:todo', 'modules:todo:main'],37 description: 'Get specific task',38 middlewares: [(req, res) => res.json({ message: 'got one task' })],39 },40 put: {41 iam: 'modules:todo:main:one:update',42 title: 'Update task',43 groups: [],44 parents: ['modules:todo', 'modules:todo:main'],45 description: 'Modify task',46 middlewares: [(req, res) => res.json({ message: 'Updated one task' })],47 },48 delete: {49 iam: 'modules:todo:main:one:remove',50 title: 'Remove task',51 groups: [],52 parents: ['modules:todo', 'modules:todo:main'],53 description: 'Remove an existing task',54 middlewares: [(req, res) => res.json({ message: 'deleted one task' })],55 },56 },57 },58 ],59};