Skip to content

Commit 4da0d8c

Browse files
committed
test(json-api-server-e2e): add ACL atomic operation tests for admin and moderator scenarios
1 parent 14e822f commit 4da0d8c

File tree

1 file changed

+125
-0
lines changed

1 file changed

+125
-0
lines changed
Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
import { faker } from '@faker-js/faker';
2+
import {
3+
ArticleAcl,
4+
ArticleStatus,
5+
ArticleVisibility,
6+
ContextTestAcl,
7+
UserRole,
8+
UsersAcl,
9+
} from '@nestjs-json-api/microorm-database';
10+
import { JsonSdkPromise } from '@klerick/json-api-nestjs-sdk';
11+
import { creatSdk } from '../utils/run-application';
12+
import { AbilityBuilder } from '../utils/acl/acl';
13+
import { CheckFieldAndInclude } from '../utils/acl/data-test';
14+
import { AxiosError } from 'axios';
15+
16+
17+
const getArticleData = () => ({
18+
title: faker.lorem.sentence(),
19+
content: faker.lorem.paragraphs(8),
20+
coAuthorIds: [],
21+
status: ArticleStatus.PUBLISHED,
22+
visibility: ArticleVisibility.PUBLIC,
23+
metadata: {
24+
readTime: faker.number.int({ min: 5, max: 30 }),
25+
featured: true,
26+
premium: false,
27+
},
28+
publishedAt: faker.date.past(),
29+
expiresAt: null,
30+
});
31+
32+
describe('ACL atomic operation:', () => {
33+
let contextTestAcl = new ContextTestAcl();
34+
let usersAcl: UsersAcl[];
35+
let articleAcl: ArticleAcl[];
36+
contextTestAcl.aclRules = { rules: [] };
37+
contextTestAcl.context = {};
38+
let jsonSdk: JsonSdkPromise;
39+
beforeEach(async () => {
40+
jsonSdk = creatSdk();
41+
contextTestAcl = await jsonSdk.jonApiSdkService.postOne(contextTestAcl);
42+
usersAcl = await jsonSdk.jonApiSdkService.getAll(UsersAcl, {
43+
include: ['profile'],
44+
});
45+
articleAcl = await jsonSdk.jonApiSdkService.getAll(ArticleAcl, {
46+
include: ['author', 'editor'],
47+
});
48+
});
49+
afterEach(async () => {
50+
await jsonSdk.jonApiSdkService.deleteOne(contextTestAcl);
51+
});
52+
53+
describe('Without conditional: admin', () => {
54+
let bobUser: UsersAcl;
55+
beforeEach(async () => {
56+
const adminUser = usersAcl.find((user) => user.login === 'admin');
57+
if (!adminUser) throw new Error('Admin user not found');
58+
59+
const posibleBobUser = usersAcl.find((user) => user.login === 'bob');
60+
if (!posibleBobUser) throw new Error('Bob user not found');
61+
bobUser = posibleBobUser;
62+
63+
contextTestAcl.context = { currentUser: adminUser };
64+
65+
contextTestAcl.aclRules.rules = new AbilityBuilder(
66+
CheckFieldAndInclude
67+
).permissionsFor(UserRole.admin).rules as any;
68+
await jsonSdk.jonApiSdkService.patchOne(contextTestAcl);
69+
});
70+
71+
it('create one publish article with moderator author', async () => {
72+
const articleForCreate = Object.assign(
73+
new ArticleAcl(),
74+
getArticleData(),
75+
);
76+
articleForCreate.author = bobUser;
77+
78+
const [articleForUpdate] = await jsonSdk.atomicFactory().postOne(articleForCreate).run();
79+
articleForUpdate.title = 'new title'
80+
await jsonSdk.atomicFactory().patchOne(articleForUpdate).deleteOne(articleForUpdate).run();
81+
});
82+
});
83+
84+
describe('With conditional but with fields: moderator', () => {
85+
86+
let bobUser: UsersAcl;
87+
let moderatorUser: UsersAcl;
88+
beforeEach(async () => {
89+
const posibleModeratorUser = usersAcl.find(
90+
(user) => user.login === 'moderator'
91+
);
92+
if (!posibleModeratorUser) throw new Error('Sheila user not found');
93+
moderatorUser = posibleModeratorUser;
94+
const posibleBobUser = usersAcl.find((user) => user.login === 'bob');
95+
if (!posibleBobUser) throw new Error('Bob user not found');
96+
bobUser = posibleBobUser;
97+
98+
contextTestAcl.context = { currentUser: moderatorUser };
99+
100+
contextTestAcl.aclRules.rules = new AbilityBuilder(
101+
CheckFieldAndInclude
102+
).permissionsFor(UserRole.moderator).rules as any;
103+
await jsonSdk.jonApiSdkService.patchOne(contextTestAcl);
104+
});
105+
106+
it('allow create and patch but delete not allow', async () => {
107+
const articleForCreate = Object.assign(
108+
new ArticleAcl(),
109+
getArticleData()
110+
);
111+
articleForCreate.author = moderatorUser;
112+
articleForCreate.status = ArticleStatus.DRAFT;
113+
try {
114+
const [articleForUpdate] = await jsonSdk.atomicFactory().postOne(articleForCreate).run();
115+
articleForUpdate.status = ArticleStatus.REVIEW;
116+
await jsonSdk.atomicFactory().patchOne(articleForUpdate).deleteOne(articleForUpdate).run();
117+
} catch (e) {
118+
expect(e).toBeInstanceOf(AxiosError);
119+
expect((e as AxiosError).response?.status).toBe(403);
120+
expect(((e as AxiosError).response?.data as {error: string})['error']).toContain('deleteOne on ArticleAcl');
121+
}
122+
})
123+
124+
})
125+
});

0 commit comments

Comments
 (0)