@strapi/plugin-users-permissions 4.0.0-next.1 → 4.0.0-next.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (74) hide show
  1. package/admin/src/index.js +31 -28
  2. package/admin/src/pages/AdvancedSettings/index.js +14 -2
  3. package/admin/src/pages/AdvancedSettings/utils/form.js +2 -2
  4. package/admin/src/pages/EmailTemplates/index.js +8 -1
  5. package/admin/src/pages/Providers/index.js +8 -1
  6. package/admin/src/pages/Roles/CreatePage/index.js +1 -1
  7. package/admin/src/pages/Roles/EditPage/index.js +2 -2
  8. package/admin/src/pages/Roles/ListPage/index.js +1 -1
  9. package/admin/src/pages/Roles/index.js +14 -8
  10. package/admin/src/permissions.js +12 -14
  11. package/admin/src/translations/en.json +4 -0
  12. package/admin/src/translations/zh-Hans.json +26 -7
  13. package/documentation/1.0.0/overrides/users-permissions-Role.json +6 -6
  14. package/package.json +8 -6
  15. package/{config/functions/bootstrap.js → server/bootstrap/index.js} +9 -18
  16. package/{config → server/bootstrap}/users-permissions-actions.js +0 -0
  17. package/server/config.js +23 -0
  18. package/server/content-types/index.js +11 -0
  19. package/server/content-types/permission/index.js +31 -0
  20. package/server/content-types/role/index.js +48 -0
  21. package/server/content-types/user/index.js +72 -0
  22. package/{models/User.config.js → server/content-types/user/schema-config.js} +0 -0
  23. package/{controllers → server/controllers}/auth.js +63 -77
  24. package/server/controllers/index.js +15 -0
  25. package/server/controllers/permissions.js +26 -0
  26. package/server/controllers/role.js +77 -0
  27. package/server/controllers/settings.js +84 -0
  28. package/{controllers → server/controllers}/user/admin.js +26 -42
  29. package/{controllers → server/controllers}/user/api.js +11 -27
  30. package/{controllers → server/controllers}/user.js +2 -18
  31. package/{controllers → server/controllers}/validation/email-template.js +0 -0
  32. package/server/index.js +21 -0
  33. package/server/policies/index.js +7 -0
  34. package/{config → server}/policies/rateLimit.js +4 -8
  35. package/server/register.js +7 -0
  36. package/server/routes/admin/index.js +10 -0
  37. package/server/routes/admin/permissions.js +20 -0
  38. package/server/routes/admin/role.js +79 -0
  39. package/server/routes/admin/settings.js +95 -0
  40. package/server/routes/content-api/auth.js +73 -0
  41. package/server/routes/content-api/index.js +11 -0
  42. package/server/routes/content-api/permissions.js +9 -0
  43. package/server/routes/content-api/role.js +29 -0
  44. package/server/routes/content-api/user.js +61 -0
  45. package/server/routes/index.js +6 -0
  46. package/{config → server}/schema.graphql.js +96 -63
  47. package/server/services/index.js +15 -0
  48. package/{services → server/services}/jwt.js +12 -14
  49. package/server/services/providers.js +592 -0
  50. package/server/services/role.js +182 -0
  51. package/{services → server/services}/user.js +31 -34
  52. package/server/services/users-permissions.js +222 -0
  53. package/server/strategies/users-permissions.js +122 -0
  54. package/{utils → server/utils}/index.d.ts +6 -1
  55. package/server/utils/index.js +9 -0
  56. package/strapi-server.js +3 -0
  57. package/config/layout.js +0 -10
  58. package/config/policies/isAuthenticated.js +0 -9
  59. package/config/policies/permissions.js +0 -94
  60. package/config/request.json +0 -6
  61. package/config/routes.json +0 -381
  62. package/config/security.json +0 -5
  63. package/controllers/users-permissions.js +0 -271
  64. package/middlewares/users-permissions/defaults.json +0 -5
  65. package/middlewares/users-permissions/index.js +0 -40
  66. package/models/Permission.js +0 -7
  67. package/models/Permission.settings.json +0 -45
  68. package/models/Role.js +0 -7
  69. package/models/Role.settings.json +0 -43
  70. package/models/User.js +0 -7
  71. package/models/User.settings.json +0 -63
  72. package/services/providers.js +0 -598
  73. package/services/users-permissions.js +0 -430
  74. package/utils/index.js +0 -11
@@ -1,430 +0,0 @@
1
- 'use strict';
2
-
3
- const _ = require('lodash');
4
- const request = require('request');
5
- const { getService } = require('../utils');
6
-
7
- const DEFAULT_PERMISSIONS = [
8
- { action: 'admincallback', controller: 'auth', type: 'users-permissions', roleType: 'public' },
9
- { action: 'adminregister', controller: 'auth', type: 'users-permissions', roleType: 'public' },
10
- { action: 'callback', controller: 'auth', type: 'users-permissions', roleType: 'public' },
11
- { action: 'connect', controller: 'auth', type: 'users-permissions', roleType: null },
12
- { action: 'forgotpassword', controller: 'auth', type: 'users-permissions', roleType: 'public' },
13
- { action: 'register', controller: 'auth', type: 'users-permissions', roleType: 'public' },
14
- {
15
- action: 'emailconfirmation',
16
- controller: 'auth',
17
- type: 'users-permissions',
18
- roleType: 'public',
19
- },
20
- { action: 'resetpassword', controller: 'auth', type: 'users-permissions', roleType: 'public' },
21
- { action: 'init', controller: 'userspermissions', type: null, roleType: null },
22
- { action: 'me', controller: 'user', type: 'users-permissions', roleType: null },
23
- { action: 'autoreload', controller: null, type: null, roleType: null },
24
- ];
25
-
26
- const isPermissionEnabled = (permission, role) =>
27
- DEFAULT_PERMISSIONS.some(
28
- defaultPerm =>
29
- (defaultPerm.action === null || permission.action === defaultPerm.action) &&
30
- (defaultPerm.controller === null || permission.controller === defaultPerm.controller) &&
31
- (defaultPerm.type === null || permission.type === defaultPerm.type) &&
32
- (defaultPerm.roleType === null || role.type === defaultPerm.roleType)
33
- );
34
-
35
- module.exports = {
36
- async createRole(params) {
37
- if (!params.type) {
38
- params.type = _.snakeCase(_.deburr(_.toLower(params.name)));
39
- }
40
-
41
- const role = await strapi
42
- .query('plugins::users-permissions.role')
43
- .create({ data: _.omit(params, ['users', 'permissions']) });
44
-
45
- const arrayOfPromises = Object.keys(params.permissions || {}).reduce((acc, type) => {
46
- Object.keys(params.permissions[type].controllers).forEach(controller => {
47
- Object.keys(params.permissions[type].controllers[controller]).forEach(action => {
48
- acc.push(
49
- strapi.query('plugins::users-permissions.permission').create({
50
- data: {
51
- role: role.id,
52
- type,
53
- controller,
54
- action: action.toLowerCase(),
55
- ...params.permissions[type].controllers[controller][action],
56
- },
57
- })
58
- );
59
- });
60
- });
61
-
62
- return acc;
63
- }, []);
64
-
65
- // Use Content Manager business logic to handle relation.
66
- if (params.users && params.users.length > 0)
67
- arrayOfPromises.push(
68
- strapi.query('plugins::users-permissions.role').update({
69
- where: {
70
- id: role.id,
71
- },
72
- data: { users: params.users },
73
- })
74
- );
75
-
76
- return await Promise.all(arrayOfPromises);
77
- },
78
-
79
- async deleteRole(roleID, publicRoleID) {
80
- const role = await strapi
81
- .query('plugins::users-permissions.role')
82
- .findOne({ where: { id: roleID }, populate: ['users', 'permissions'] });
83
-
84
- if (!role) {
85
- throw new Error('Cannot find this role');
86
- }
87
-
88
- // Move users to guest role.
89
- const arrayOfPromises = role.users.reduce((acc, user) => {
90
- acc.push(
91
- strapi.query('plugins::users-permissions.user').update({
92
- where: {
93
- id: user.id,
94
- },
95
- data: {
96
- role: publicRoleID,
97
- },
98
- })
99
- );
100
-
101
- return acc;
102
- }, []);
103
-
104
- // Remove permissions related to this role.
105
- role.permissions.forEach(permission => {
106
- arrayOfPromises.push(
107
- strapi.query('plugins::users-permissions.permission').delete({
108
- where: { id: permission.id },
109
- })
110
- );
111
- });
112
-
113
- // Delete the role.
114
- arrayOfPromises.push(
115
- strapi.query('plugins::users-permissions.role').delete({ where: { id: roleID } })
116
- );
117
-
118
- return await Promise.all(arrayOfPromises);
119
- },
120
-
121
- getPlugins(lang = 'en') {
122
- return new Promise(resolve => {
123
- request(
124
- {
125
- uri: `https://marketplace.strapi.io/plugins?lang=${lang}`,
126
- json: true,
127
- timeout: 3000,
128
- headers: {
129
- 'cache-control': 'max-age=3600',
130
- },
131
- },
132
- (err, response, body) => {
133
- if (err || response.statusCode !== 200) {
134
- return resolve([]);
135
- }
136
-
137
- resolve(body);
138
- }
139
- );
140
- });
141
- },
142
-
143
- getActions() {
144
- const generateActions = data =>
145
- Object.keys(data).reduce((acc, key) => {
146
- if (_.isFunction(data[key])) {
147
- acc[key] = { enabled: false, policy: '' };
148
- }
149
-
150
- return acc;
151
- }, {});
152
-
153
- const appControllers = Object.keys(strapi.api || {})
154
- .filter(key => !!strapi.api[key].controllers)
155
- .reduce(
156
- (acc, key) => {
157
- Object.keys(strapi.api[key].controllers).forEach(controller => {
158
- acc.controllers[controller] = generateActions(strapi.api[key].controllers[controller]);
159
- });
160
-
161
- return acc;
162
- },
163
- { controllers: {} }
164
- );
165
-
166
- const pluginsPermissions = Object.keys(strapi.plugins).reduce((acc, key) => {
167
- const initialState = {
168
- controllers: {},
169
- };
170
-
171
- acc[key] = Object.keys(strapi.plugins[key].controllers).reduce((obj, k) => {
172
- obj.controllers[k] = generateActions(strapi.plugins[key].controllers[k]);
173
-
174
- return obj;
175
- }, initialState);
176
-
177
- return acc;
178
- }, {});
179
-
180
- const permissions = {
181
- application: {
182
- controllers: appControllers.controllers,
183
- },
184
- };
185
-
186
- return _.merge(permissions, pluginsPermissions);
187
- },
188
-
189
- async getRole(roleID, plugins) {
190
- const role = await strapi
191
- .query('plugins::users-permissions.role')
192
- .findOne({ where: { id: roleID }, populate: ['permissions'] });
193
-
194
- if (!role) {
195
- throw new Error('Cannot find this role');
196
- }
197
-
198
- // Group by `type`.
199
- const permissions = role.permissions.reduce((acc, permission) => {
200
- _.set(acc, `${permission.type}.controllers.${permission.controller}.${permission.action}`, {
201
- enabled: _.toNumber(permission.enabled) == true,
202
- policy: permission.policy,
203
- });
204
-
205
- if (permission.type !== 'application' && !acc[permission.type].information) {
206
- acc[permission.type].information =
207
- plugins.find(plugin => plugin.id === permission.type) || {};
208
- }
209
-
210
- return acc;
211
- }, {});
212
-
213
- return {
214
- ...role,
215
- permissions,
216
- };
217
- },
218
-
219
- async getRoles() {
220
- const roles = await strapi
221
- .query('plugins::users-permissions.role')
222
- .findMany({ sort: ['name'] });
223
-
224
- for (let i = 0; i < roles.length; ++i) {
225
- roles[i].nb_users = await strapi
226
- .query('plugins::users-permissions.user')
227
- .count({ where: { role: { id: roles[i].id } } });
228
- }
229
-
230
- return roles;
231
- },
232
-
233
- async getRoutes() {
234
- const routes = Object.keys(strapi.api || {}).reduce((acc, current) => {
235
- return acc.concat(_.get(strapi.api[current].config, 'routes', []));
236
- }, []);
237
- const clonedPlugins = _.cloneDeep(strapi.plugins);
238
- const pluginsRoutes = Object.keys(clonedPlugins || {}).reduce((acc, current) => {
239
- const routes = _.get(clonedPlugins, [current, 'config', 'routes'], []).reduce((acc, curr) => {
240
- const prefix = curr.config.prefix;
241
- const path = prefix !== undefined ? `${prefix}${curr.path}` : `/${current}${curr.path}`;
242
- _.set(curr, 'path', path);
243
-
244
- return acc.concat(curr);
245
- }, []);
246
-
247
- acc[current] = routes;
248
-
249
- return acc;
250
- }, {});
251
-
252
- return _.merge({ application: routes }, pluginsRoutes);
253
- },
254
-
255
- async updatePermissions() {
256
- const roles = await strapi.query('plugins::users-permissions.role').findMany();
257
-
258
- const rolesMap = _.groupBy(roles, 'id');
259
-
260
- const dbPermissions = await strapi
261
- .query('plugins::users-permissions.permission')
262
- .findMany({ populate: ['role'] });
263
-
264
- let permissionsFoundInDB = dbPermissions.map(permission => {
265
- const { type, controller, action, role } = permission;
266
- return `${type}.${controller}.${action}.${role.id}`;
267
- });
268
-
269
- permissionsFoundInDB = _.uniq(permissionsFoundInDB);
270
-
271
- // Aggregate first level actions.
272
- const appActions = Object.keys(strapi.api || {}).reduce((acc, api) => {
273
- Object.keys(_.get(strapi.api[api], 'controllers', {})).forEach(controller => {
274
- const actions = Object.keys(strapi.api[api].controllers[controller])
275
- .filter(action => _.isFunction(strapi.api[api].controllers[controller][action]))
276
- .map(action => `application.${controller}.${action.toLowerCase()}`);
277
-
278
- acc = acc.concat(actions);
279
- });
280
-
281
- return acc;
282
- }, []);
283
-
284
- // Aggregate plugins' actions.
285
- const pluginsActions = Object.keys(strapi.plugins).reduce((acc, plugin) => {
286
- Object.keys(strapi.plugins[plugin].controllers).forEach(controller => {
287
- const actions = Object.keys(strapi.plugins[plugin].controllers[controller])
288
- .filter(action => _.isFunction(strapi.plugins[plugin].controllers[controller][action]))
289
- .map(action => `${plugin}.${controller}.${action.toLowerCase()}`);
290
-
291
- acc = acc.concat(actions);
292
- });
293
-
294
- return acc;
295
- }, []);
296
-
297
- const actionsFoundInFiles = appActions.concat(pluginsActions);
298
-
299
- const permissionsFoundInFiles = [];
300
-
301
- for (const role of roles) {
302
- actionsFoundInFiles.forEach(action => {
303
- permissionsFoundInFiles.push(`${action}.${role.id}`);
304
- });
305
- }
306
-
307
- // Compare to know if actions have been added or removed from controllers.
308
- if (!_.isEqual(permissionsFoundInDB.sort(), permissionsFoundInFiles.sort())) {
309
- const splitted = str => {
310
- const [type, controller, action, roleId] = str.split('.');
311
-
312
- return { type, controller, action, roleId };
313
- };
314
-
315
- // We have to know the difference to add or remove the permissions entries in the database.
316
- const toRemove = _.difference(permissionsFoundInDB, permissionsFoundInFiles).map(splitted);
317
- const toAdd = _.difference(permissionsFoundInFiles, permissionsFoundInDB).map(splitted);
318
-
319
- const query = strapi.query('plugins::users-permissions.permission');
320
-
321
- // Execute request to update entries in database for each role.
322
- await Promise.all(
323
- toAdd.map(permission =>
324
- query.create({
325
- data: {
326
- type: permission.type,
327
- controller: permission.controller,
328
- action: permission.action,
329
- enabled: isPermissionEnabled(permission, rolesMap[permission.roleId]),
330
- policy: '',
331
- role: permission.roleId,
332
- },
333
- })
334
- )
335
- );
336
-
337
- await Promise.all(
338
- toRemove.map(permission => {
339
- const { type, controller, action, roleId } = permission;
340
- return query.delete({ where: { type, controller, action, role: { id: roleId } } });
341
- })
342
- );
343
- }
344
- },
345
-
346
- async initialize() {
347
- const roleCount = await strapi.query('plugins::users-permissions.role').count();
348
-
349
- if (roleCount === 0) {
350
- await strapi.query('plugins::users-permissions.role').create({
351
- data: {
352
- name: 'Authenticated',
353
- description: 'Default role given to authenticated user.',
354
- type: 'authenticated',
355
- },
356
- });
357
-
358
- await strapi.query('plugins::users-permissions.role').create({
359
- data: {
360
- name: 'Public',
361
- description: 'Default role given to unauthenticated user.',
362
- type: 'public',
363
- },
364
- });
365
- }
366
-
367
- return getService('users-permissions').updatePermissions();
368
- },
369
-
370
- async updateRole(roleID, body) {
371
- const [role, authenticated] = await Promise.all([
372
- this.getRole(roleID, []),
373
- strapi.query('plugins::users-permissions.role').findOne({ where: { type: 'authenticated' } }),
374
- ]);
375
-
376
- await strapi.query('plugins::users-permissions.role').update({
377
- where: { id: roleID },
378
- data: _.pick(body, ['name', 'description']),
379
- });
380
-
381
- await Promise.all(
382
- Object.keys(body.permissions || {}).reduce((acc, type) => {
383
- Object.keys(body.permissions[type].controllers).forEach(controller => {
384
- Object.keys(body.permissions[type].controllers[controller]).forEach(action => {
385
- const bodyAction = body.permissions[type].controllers[controller][action];
386
- const currentAction = _.get(
387
- role.permissions,
388
- `${type}.controllers.${controller}.${action}`,
389
- {}
390
- );
391
-
392
- if (!_.isEqual(bodyAction, currentAction)) {
393
- acc.push(
394
- strapi.query('plugins::users-permissions.permission').update({
395
- where: {
396
- role: roleID,
397
- type,
398
- controller,
399
- action: action.toLowerCase(),
400
- },
401
- data: bodyAction,
402
- })
403
- );
404
- }
405
- });
406
- });
407
-
408
- return acc;
409
- }, [])
410
- );
411
-
412
- // Add user to this role.
413
- const newUsers = _.differenceBy(body.users, role.users, 'id');
414
- await Promise.all(newUsers.map(user => this.updateUserRole(user, roleID)));
415
-
416
- const oldUsers = _.differenceBy(role.users, body.users, 'id');
417
- await Promise.all(oldUsers.map(user => this.updateUserRole(user, authenticated.id)));
418
- },
419
-
420
- async updateUserRole(user, role) {
421
- return strapi
422
- .query('plugins::users-permissions.user')
423
- .update({ where: { id: user.id }, data: { role } });
424
- },
425
-
426
- template(layout, data) {
427
- const compiledObject = _.template(layout);
428
- return compiledObject(data);
429
- },
430
- };
package/utils/index.js DELETED
@@ -1,11 +0,0 @@
1
- 'use strict';
2
-
3
- const { prop } = require('lodash/fp');
4
-
5
- const getService = name => {
6
- return prop(`users-permissions.services.${name}`, strapi.plugins);
7
- };
8
-
9
- module.exports = {
10
- getService,
11
- };