Как управлять контролем доступа с помощью ролей, чтобы пользователь Basi c не мог обновлять учетную запись, которая не принадлежит - PullRequest
1 голос
/ 13 февраля 2020

В моем NodeJS API я реализовал роли, используя этот npm pkg accesscontrol, и также использовал JWT для части токена. Моя проблема в том, что я не могу ограничить роль пользователя basi c для обновления учетной записи, которая не является его / ее собственной. Чего я хотел бы добиться, так это того, что Admin может делать все, что он хочет, но другие роли, такие как basi c, ограничены. В моем случае я хочу, чтобы пользователь с ролью basi c мог обновлять только свою учетную запись, но не другую, но теперь не работающую.

В моем Почтальоне я вызываю конечную точку обновления токеном роли basei c и пытаюсь обновить идентификатор пользователя, который не связан с токеном. То, что я должен увидеть, это сообщение, которое говорит You don't have enough permission to perform this action, но вместо этого я могу обновить.

Роли, которые я использовал, это PKG AccessControl

// Access controls roles
const AccessControl = require("accesscontrol");

let grantsObject = {
    admin: {
        user: {
            "create:any": ["*"],
            "read:any": ["*"],
            "update:any": ["*"],
            "delete:any": ["*"]
        }
    },
    basic: {
        user: {
            "create:own": ["*"],
            "read:own": ["*"],
            "update:own": ["*"],
            "delete:own": ["*"],
        }
    }
};

// Init
const accessCtrl = new AccessControl();

// Roles access
// Here adding the access rules and to what we give access to a specific role
// Basic, Moderator, Admin
// Admin => Read/Write full powers
// Moderator => Read access everywhere
// Basic => Read/write own information
exports.roles = (() => {
    accessCtrl.setGrants(grantsObject);

    return accessCtrl;
})();

Мой route

// PUT update user
router.put(
    "/:userId",
    Auth.allowIfLoggedin,
    Auth.grantAccess("updateOwn", "user"),
    UserCtrl.updateUser
);

Используется промежуточное ПО:

/ Allowing access to right role permission
const grantAccess = (action, resource) => {
    return async (req, res, next) => {
        try {
            console.log(req.user.role);
            // Permission to perform the specified action of the provided resource
            const permission = Roles.roles.can(req.user.role)[action](resource);
            // No permission => 401
            if (!permission.granted) {
                throw new ErrorHandlers.ErrorHandler(
                    401,
                    "You don't have enough permission to perform this action"
                );
            }
            next();
        } catch (error) {
            next(error);
        }
    };
};

// Allow if user logged in
const allowIfLoggedin = async (req, res, next) => {
    try {
        console.log("LOCALS", JSON.stringify(res.locals));
        const user = res.locals.loggedInUser;
        if (!user)
            throw new ErrorHandlers.ErrorHandler(
                401,
                "You need to be logged in to perform this operation"
            );
        // User
        req.user = user;
        next();
    } catch (error) {
        next(error);
    }
};

module.exports = { grantAccess, allowIfLoggedin };

Контроллер

// UPDATE user
    async updateUser(req, res, next) {
        try {
            // Check empty req.body
            if (Object.keys(req.body).length === 0) {
                throw new ErrorHandlers.ErrorHandler(500, "Nothing to update");
            }
            // Body to update
            const update = req.body;
            // UserId to update
            const userId = req.params.userId;
            // Finding the user to update
            await User.findByIdAndUpdate(userId, update);
            // Updated user
            const user = await User.findById(userId);
            // Response
            res.status(200).json({
                user: user,
                message: "User has been updated"
            });
        } catch (error) {
            next(error);
        }
    },
...