Rule with class and conditions doesn't work
See original GitHub issueFirst at all, sorry if I forgot something.
Describe the bug When I define rules using a class name in typescript, in that rules where there are some condition always return false.
To Reproduce
I have these classes User
and Post
enum Role {
ADMIN = 'admin',
USER = 'user'
}
class User {
id: number;
login: string;
role: Role;
}
class Post {
title: string;
text: string;
authrorId: number;
}
I define the rules in a static class method called createForUser
as follow:
enum Action {
MANAGE = 'manage',
CREATE = 'create',
READ = 'read',
UPDATE = 'update',
DELETE = 'delete'
}
type Subjects = typeof Post | typeof User | Post | User | 'all';
type AppAbility = Ability<[Action, Subjects}>;
class CaslAbilityFactory {
static createForUser(user: User) {
cosnt { can, cannot, build } = new AbilityBuilder<AppAbility>(Ability as AbilityClass<AppAbility>);
if (user.role === Role.ADMIN) {
can(Action.MANAGE, 'all');
} else {
can(Action.READ, Post);
cannot(Action.DELETE, Post);
}
can(Action.UPDATE, Post, { authorId: user.id });
return build();
}
}
When I check the ability of READ a post, with a user with Role USER, it works as expected. The problem is when I check to update a post as follow:
const user: User = new User();
user.id = 1;
user.login = 'user01';
user.role = Role.USER;
const post: Post = new Post();
post.title = "Dummy post";
post.text = "Something interesting";
post.authorId = user.id;
const ability = CaslAbilityFactory.createForUser(user);
console.log(ability.can(Action.READ, Post)); // ---> Prints true and expected true.
console.log(ability.can(Action.UPDATE, post)); // ---> Prints false, but expected true
But if we add 'Post'
to the type Subjects
and change Post
for 'Post'
as following:
type Subjects = typeof Post | typeof User | Post | User | 'Post' | 'all';
class CaslAbilityFactory {
...
can(Action.UPDATE, 'Post', { authorId: user.id });
...
return build();
}
console.log(ability.can(Action.READ, Post)); // ---> Prints true and expected true.
console.log(ability.can(Action.UPDATE, post)); // ---> Now prints true and expected true
I tried too of downgrade @casl/ability
to version 4.1.6 and the first code (using Post
in the rule specification) works as expected.
Interactive example Here is a link to the interactive example in codesandobx. https://codesandbox.io/s/casl-bug-3txfo?file=/src/index.ts
CASL Version
@casl/ability
- 5.1.1
Environment:
node
- 12.18.4
typescript
- 4.1.3
Issue Analytics
- State:
- Created 3 years ago
- Comments:21 (9 by maintainers)
Top GitHub Comments
Casl subjects still be as you have it. Check how I handle this here: https://github.com/davidgpgr94/nestjs-blog-api/blob/master/src/posts/controllers/posts.controller.ts#L81 https://github.com/davidgpgr94/nestjs-blog-api/blob/master/src/casl/casl-ability.factory.ts#L13
Hello there! Have similar problem discussed above. Can’t find a solution. Kindly ask you to help with it. Here is a link to the description: https://stackoverflow.com/questions/70584146/nest-js-authorization-with-casl-doesnt-work-as-expected