@truedat/auth 8.14.1 → 8.14.2

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 (65) hide show
  1. package/package.json +4 -4
  2. package/src/groups/components/EditGroup.js +64 -20
  3. package/src/groups/components/Group.js +39 -41
  4. package/src/groups/components/GroupCard.js +51 -54
  5. package/src/groups/components/GroupCards.js +60 -25
  6. package/src/groups/components/GroupDeleteModal.js +98 -0
  7. package/src/groups/components/GroupDropdown.js +92 -0
  8. package/src/groups/components/GroupForm.js +165 -84
  9. package/src/groups/components/GroupFormModal.js +137 -0
  10. package/src/groups/components/GroupInfoModal.js +114 -0
  11. package/src/groups/components/GroupMemberPicker.js +364 -0
  12. package/src/groups/components/GroupRouteModal.js +46 -0
  13. package/src/groups/components/GroupUsers.js +31 -14
  14. package/src/groups/components/GroupUsersTable.js +136 -83
  15. package/src/groups/components/NewGroup.js +38 -10
  16. package/src/groups/components/__tests__/EditGroup.spec.js +105 -0
  17. package/src/groups/components/__tests__/Group.spec.js +29 -47
  18. package/src/groups/components/__tests__/GroupCard.spec.js +8 -20
  19. package/src/groups/components/__tests__/GroupDropdown.spec.js +27 -0
  20. package/src/groups/components/__tests__/GroupForm.spec.js +32 -5
  21. package/src/groups/components/__tests__/GroupMemberPicker.spec.js +378 -0
  22. package/src/groups/components/__tests__/GroupModals.spec.js +210 -0
  23. package/src/groups/components/__tests__/GroupUsers.spec.js +17 -2
  24. package/src/groups/components/__tests__/GroupUsersTable.spec.js +34 -2
  25. package/src/groups/components/__tests__/__snapshots__/Group.spec.js.snap +1 -0
  26. package/src/groups/components/__tests__/__snapshots__/GroupCard.spec.js.snap +32 -30
  27. package/src/groups/components/__tests__/__snapshots__/GroupCards.spec.js.snap +90 -77
  28. package/src/groups/components/__tests__/__snapshots__/GroupUsers.spec.js.snap +75 -11
  29. package/src/groups/components/__tests__/__snapshots__/GroupUsersTable.spec.js.snap +70 -13
  30. package/src/groups/components/index.js +0 -4
  31. package/src/groups/hooks/__tests__/useGroupOperation.spec.js +167 -0
  32. package/src/groups/hooks/__tests__/useGroups.spec.js +90 -0
  33. package/src/groups/hooks/useGroupOperation.js +83 -0
  34. package/src/groups/hooks/useGroups.js +64 -0
  35. package/src/groups/reducers/index.js +0 -4
  36. package/src/groups/routines.js +0 -7
  37. package/src/groups/sagas/index.js +2 -24
  38. package/src/hooks/useRoles.js +6 -3
  39. package/src/styles/Groups.less +1009 -0
  40. package/src/users/components/AdminUserRoutes.js +1 -14
  41. package/src/users/components/GroupUserCrumbs.js +7 -12
  42. package/src/users/components/UserRoutes.js +12 -35
  43. package/src/users/components/UsersAndGroups.js +3 -6
  44. package/src/users/components/__tests__/GroupUserCrumbs.spec.js +26 -30
  45. package/src/users/components/__tests__/UserRoutes.spec.js +4 -6
  46. package/src/users/components/__tests__/UsersAndGroups.spec.js +5 -7
  47. package/src/users/components/__tests__/__snapshots__/UserRoutes.spec.js.snap +9 -55
  48. package/src/groups/components/GroupLoader.js +0 -27
  49. package/src/groups/components/GroupsLoader.js +0 -30
  50. package/src/groups/components/__tests__/GroupLoader.spec.js +0 -71
  51. package/src/groups/components/__tests__/__snapshots__/GroupLoader.spec.js.snap +0 -11
  52. package/src/groups/reducers/__tests__/groupRedirect.spec.js +0 -51
  53. package/src/groups/reducers/__tests__/groupUsers.spec.js +0 -60
  54. package/src/groups/reducers/group.js +0 -56
  55. package/src/groups/reducers/groupRedirect.js +0 -20
  56. package/src/groups/reducers/groupUsers.js +0 -16
  57. package/src/groups/reducers/groups.js +0 -29
  58. package/src/groups/sagas/__tests__/deleteGroup.spec.js +0 -93
  59. package/src/groups/sagas/__tests__/deleteGroupUser.spec.js +0 -80
  60. package/src/groups/sagas/createGroup.js +0 -27
  61. package/src/groups/sagas/deleteGroup.js +0 -31
  62. package/src/groups/sagas/deleteGroupUser.js +0 -35
  63. package/src/groups/sagas/fetchGroup.js +0 -30
  64. package/src/groups/sagas/fetchGroups.js +0 -26
  65. package/src/groups/sagas/updateGroup.js +0 -28
@@ -1,60 +0,0 @@
1
- import { clearGroup, deleteGroupUser, fetchGroup } from "../../routines";
2
- import { groupUsers, initialState } from "../groupUsers";
3
-
4
- const fooState = { foo: "bar" };
5
-
6
- describe("reducers: groupUsers", () => {
7
- it("should provide the initial state", () => {
8
- expect(groupUsers(undefined, {})).toBe(initialState);
9
- });
10
-
11
- it("should handle the fetchGroup action", () => {
12
- const users = [
13
- {
14
- id: 1,
15
- user_name: "user_name1",
16
- full_name: "user name 1",
17
- email: "email1@test.com",
18
- },
19
- {
20
- id: 2,
21
- user_name: "user_name2",
22
- full_name: "user name 2",
23
- email: "email2@test.com",
24
- },
25
- ];
26
-
27
- expect(
28
- groupUsers(fooState, {
29
- type: fetchGroup.SUCCESS,
30
- payload: { data: { users } },
31
- }),
32
- ).toBe(users);
33
- });
34
-
35
- it("should handle the clearGroup action", () => {
36
- expect(groupUsers(fooState, { type: clearGroup.TRIGGER })).toEqual([]);
37
- });
38
-
39
- it("should handle the deleteGroupUser action", () => {
40
- const users = [
41
- {
42
- id: 2,
43
- user_name: "user_name2",
44
- full_name: "user name 2",
45
- email: "email2@test.com",
46
- },
47
- ];
48
-
49
- expect(
50
- groupUsers(fooState, {
51
- type: deleteGroupUser.SUCCESS,
52
- payload: { data: { users } },
53
- }),
54
- ).toBe(users);
55
- });
56
-
57
- it("should ignore unknown actions", () => {
58
- expect(groupUsers(fooState, { type: "FOO" })).toBe(fooState);
59
- });
60
- });
@@ -1,56 +0,0 @@
1
- import _ from "lodash/fp";
2
- import { clearGroup, fetchGroup, updateGroup, createGroup } from "../routines";
3
-
4
- const initialState = {};
5
-
6
- const pickFields = _.pick(["id", "name", "description", "alias"]);
7
-
8
- const group = (state = initialState, { type, payload }) => {
9
- switch (type) {
10
- case clearGroup.TRIGGER:
11
- return initialState;
12
- case fetchGroup.TRIGGER:
13
- return initialState;
14
- case fetchGroup.SUCCESS:
15
- return pickFields(payload.data);
16
- case updateGroup.SUCCESS:
17
- return pickFields(payload.data);
18
- default:
19
- return state;
20
- }
21
- };
22
-
23
- const groupLoading = (state = false, { type }) => {
24
- switch (type) {
25
- case fetchGroup.TRIGGER:
26
- return true;
27
- case fetchGroup.FULFILL:
28
- return false;
29
- default:
30
- return state;
31
- }
32
- };
33
-
34
- const groupCreating = (state = false, { type }) => {
35
- switch (type) {
36
- case createGroup.TRIGGER:
37
- return true;
38
- case createGroup.FULFILL:
39
- return false;
40
- default:
41
- return state;
42
- }
43
- };
44
-
45
- const groupUpdating = (state = false, { type }) => {
46
- switch (type) {
47
- case updateGroup.TRIGGER:
48
- return true;
49
- case updateGroup.FULFILL:
50
- return false;
51
- default:
52
- return state;
53
- }
54
- };
55
-
56
- export { group, groupLoading, groupCreating, groupUpdating };
@@ -1,20 +0,0 @@
1
- import { clearRedirect } from "@truedat/core/routines";
2
- import { GROUPS } from "@truedat/core/routes";
3
- import { createGroup, deleteGroup, updateGroup } from "../routines";
4
-
5
- const initialState = "";
6
-
7
- export const groupRedirect = (state = initialState, { type }) => {
8
- switch (type) {
9
- case clearRedirect.TRIGGER:
10
- return initialState;
11
- case createGroup.SUCCESS:
12
- return GROUPS;
13
- case updateGroup.SUCCESS:
14
- return GROUPS;
15
- case deleteGroup.SUCCESS:
16
- return GROUPS;
17
- default:
18
- return state;
19
- }
20
- };
@@ -1,16 +0,0 @@
1
- import _ from "lodash/fp";
2
- import { clearGroup, deleteGroupUser, fetchGroup } from "../routines";
3
-
4
- export const initialState = [];
5
-
6
- export const groupUsers = (state = initialState, { type, payload }) => {
7
- switch (type) {
8
- case fetchGroup.SUCCESS:
9
- case deleteGroupUser.SUCCESS:
10
- return _.pathOr([], "data.users")(payload);
11
- case clearGroup.TRIGGER:
12
- return initialState;
13
- default:
14
- return state;
15
- }
16
- };
@@ -1,29 +0,0 @@
1
- import _ from "lodash/fp";
2
- import { fetchGroups } from "../routines";
3
-
4
- const initialState = [];
5
-
6
- const caseInsensitiveName = ({ name }) => _.lowerCase(name);
7
-
8
- const groups = (state = initialState, { type, payload }) => {
9
- switch (type) {
10
- case fetchGroups.SUCCESS:
11
- const collection = _.prop("data")(payload);
12
- return _.sortBy(caseInsensitiveName)(collection);
13
- default:
14
- return state;
15
- }
16
- };
17
-
18
- const groupsLoading = (state = false, { type }) => {
19
- switch (type) {
20
- case fetchGroups.TRIGGER:
21
- return true;
22
- case fetchGroups.FULFILL:
23
- return false;
24
- default:
25
- return state;
26
- }
27
- };
28
-
29
- export { groups, groupsLoading };
@@ -1,93 +0,0 @@
1
- import { compile } from "path-to-regexp";
2
- import { testSaga } from "redux-saga-test-plan";
3
- import { apiJsonDelete, JSON_OPTS } from "@truedat/core/services/api";
4
- import { deleteGroupRequestSaga, deleteGroupSaga } from "../deleteGroup";
5
- import { deleteGroup, fetchGroups } from "../../routines";
6
- import { API_GROUP } from "../../api";
7
-
8
- describe("sagas: deleteGroupRequestSaga", () => {
9
- it("should invoke deleteGroupSaga on deleteGroup.TRIGGER", () => {
10
- expect(() => {
11
- testSaga(deleteGroupRequestSaga)
12
- .next()
13
- .takeLatest(deleteGroup.TRIGGER, deleteGroupSaga)
14
- .finish()
15
- .isDone();
16
- }).not.toThrow();
17
- });
18
-
19
- it("should throw exception if an unhandled action is received", () => {
20
- expect(() => {
21
- testSaga(deleteGroupRequestSaga)
22
- .next()
23
- .takeLatest("FOO", deleteGroupRequestSaga);
24
- }).toThrow();
25
- });
26
- });
27
-
28
- describe("sagas: deleteGroupSaga", () => {
29
- const payload = { id: "1", name: "group-1" };
30
- const url = compile(API_GROUP)({ id: `${payload.id}` });
31
-
32
- it("should put a success action and fetchGroups when a response is returned", () => {
33
- expect(() => {
34
- testSaga(deleteGroupSaga, { payload })
35
- .next()
36
- .put(deleteGroup.request())
37
- .next()
38
- .call(apiJsonDelete, url, JSON_OPTS)
39
- .next({ data: payload })
40
- .put(deleteGroup.success(payload))
41
- .next()
42
- .put(fetchGroups())
43
- .next()
44
- .put(deleteGroup.fulfill())
45
- .next()
46
- .isDone();
47
- }).not.toThrow();
48
- });
49
-
50
- it("should put a failure action when the call returns an error response", () => {
51
- const error = {
52
- response: { status: 500, data: { message: "Request failed" } },
53
- };
54
-
55
- expect(() => {
56
- testSaga(deleteGroupSaga, { payload })
57
- .next()
58
- .put(deleteGroup.request())
59
- .next()
60
- .call(apiJsonDelete, url, JSON_OPTS)
61
- .throw(error)
62
- .put(
63
- deleteGroup.failure({
64
- status: 500,
65
- data: { message: "Request failed" },
66
- }),
67
- )
68
- .next()
69
- .put(deleteGroup.fulfill())
70
- .next()
71
- .isDone();
72
- }).not.toThrow();
73
- });
74
-
75
- it("should put a failure action when the call returns an error message", () => {
76
- const message = "Request failed";
77
- const error = { message };
78
-
79
- expect(() => {
80
- testSaga(deleteGroupSaga, { payload })
81
- .next()
82
- .put(deleteGroup.request())
83
- .next()
84
- .call(apiJsonDelete, url, JSON_OPTS)
85
- .throw(error)
86
- .put(deleteGroup.failure(message))
87
- .next()
88
- .put(deleteGroup.fulfill())
89
- .next()
90
- .isDone();
91
- }).not.toThrow();
92
- });
93
- });
@@ -1,80 +0,0 @@
1
- import _ from "lodash/fp";
2
- import { compile } from "path-to-regexp";
3
- import { testSaga } from "redux-saga-test-plan";
4
- import { apiJsonPut, JSON_OPTS } from "@truedat/core/services/api";
5
- import {
6
- deleteGroupUserSaga,
7
- deleteGroupUserRequestSaga,
8
- } from "../deleteGroupUser";
9
- import { deleteGroupUser } from "../../routines";
10
- import { API_GROUP } from "../../api";
11
-
12
- describe("sagas: deleteGroupUserRequestSaga", () => {
13
- it("should invoke deleteGroupUserSaga on deleteGroupUser.TRIGGER", () => {
14
- expect(() => {
15
- testSaga(deleteGroupUserRequestSaga)
16
- .next()
17
- .takeLatest(deleteGroupUser.TRIGGER, deleteGroupUserSaga)
18
- .finish()
19
- .isDone();
20
- }).not.toThrow();
21
- });
22
-
23
- it("should throw exception if an unhandled action is received", () => {
24
- expect(() => {
25
- testSaga(deleteGroupUserRequestSaga)
26
- .next()
27
- .takeLatest("FOO", deleteGroupUserRequestSaga);
28
- }).toThrow();
29
- });
30
- });
31
-
32
- describe("sagas: deleteGroupUserSaga", () => {
33
- const group = { id: "1", name: "g1" };
34
- const user = { id: "2" };
35
- const groupUsers = [{ id: "2" }, { id: "3" }, { id: "4" }, { id: "5" }];
36
- const payload = { group, user, groupUsers };
37
-
38
- const url = compile(API_GROUP)({ id: `${group.id}` });
39
- const meta = { group_id: group.id };
40
- const updatedGroup = {
41
- ...group,
42
- user_ids: _.map("id")(_.differenceBy("id", groupUsers, [user])),
43
- };
44
- const requestData = { group: updatedGroup };
45
-
46
- it("should put a success action when a response is returned", () => {
47
- expect(() => {
48
- testSaga(deleteGroupUserSaga, { payload })
49
- .next()
50
- .put({ meta, ...deleteGroupUser.request() })
51
- .next()
52
- .call(apiJsonPut, url, requestData, JSON_OPTS)
53
- .next({ data: payload })
54
- .put({ meta, ...deleteGroupUser.success(payload) })
55
- .next()
56
- .put(deleteGroupUser.fulfill())
57
- .next()
58
- .isDone();
59
- }).not.toThrow();
60
- });
61
-
62
- it("should put a failure action when the call returns an error", () => {
63
- const message = "Request failed";
64
- const error = { message };
65
-
66
- expect(() => {
67
- testSaga(deleteGroupUserSaga, { payload })
68
- .next()
69
- .put({ meta, ...deleteGroupUser.request() })
70
- .next()
71
- .call(apiJsonPut, url, requestData, JSON_OPTS)
72
- .throw(error)
73
- .put(deleteGroupUser.failure(message))
74
- .next()
75
- .put(deleteGroupUser.fulfill())
76
- .next()
77
- .isDone();
78
- }).not.toThrow();
79
- });
80
- });
@@ -1,27 +0,0 @@
1
- import { call, put, takeLatest } from "redux-saga/effects";
2
- import { apiJsonPost, JSON_OPTS } from "@truedat/core/services/api";
3
- import { createGroup } from "../routines";
4
- import { API_GROUPS } from "../api";
5
-
6
- export function* createGroupSaga({ payload: group }) {
7
- try {
8
- const url = API_GROUPS;
9
- const requestData = { group };
10
- yield put(createGroup.request());
11
- const { data } = yield call(apiJsonPost, url, requestData, JSON_OPTS);
12
- yield put(createGroup.success(data));
13
- } catch (error) {
14
- if (error.response) {
15
- const { status, data } = error.response;
16
- yield put(createGroup.failure({ status, data }));
17
- } else {
18
- yield put(createGroup.failure(error.message));
19
- }
20
- } finally {
21
- yield put(createGroup.fulfill());
22
- }
23
- }
24
-
25
- export function* createGroupRequestSaga() {
26
- yield takeLatest(createGroup.TRIGGER, createGroupSaga);
27
- }
@@ -1,31 +0,0 @@
1
- import { compile } from "path-to-regexp";
2
- import { call, put, takeLatest } from "redux-saga/effects";
3
- import { apiJsonDelete, JSON_OPTS } from "@truedat/core/services/api";
4
- import { deleteGroup, fetchGroups } from "../routines";
5
- import { API_GROUP } from "../api";
6
-
7
- const toApiPath = compile(API_GROUP);
8
-
9
- export function* deleteGroupSaga({ payload }) {
10
- try {
11
- const group = payload;
12
- const url = toApiPath({ id: `${group.id}` });
13
- yield put(deleteGroup.request());
14
- const { data } = yield call(apiJsonDelete, url, JSON_OPTS);
15
- yield put(deleteGroup.success(data));
16
- yield put(fetchGroups());
17
- } catch (error) {
18
- if (error.response) {
19
- const { status, data } = error.response;
20
- yield put(deleteGroup.failure({ status, data }));
21
- } else {
22
- yield put(deleteGroup.failure(error.message));
23
- }
24
- } finally {
25
- yield put(deleteGroup.fulfill());
26
- }
27
- }
28
-
29
- export function* deleteGroupRequestSaga() {
30
- yield takeLatest(deleteGroup.TRIGGER, deleteGroupSaga);
31
- }
@@ -1,35 +0,0 @@
1
- import _ from "lodash/fp";
2
- import { compile } from "path-to-regexp";
3
- import { call, put, takeLatest } from "redux-saga/effects";
4
- import { apiJsonPut, JSON_OPTS } from "@truedat/core/services/api";
5
- import { deleteGroupUser } from "../routines";
6
- import { API_GROUP } from "../api";
7
-
8
- export function* deleteGroupUserSaga({ payload }) {
9
- try {
10
- const { group, user, groupUsers } = payload;
11
- const updatedGroup = {
12
- ...group,
13
- user_ids: _.map("id")(_.differenceBy("id", groupUsers, [user])),
14
- };
15
- const url = compile(API_GROUP)({ id: `${group.id}` });
16
- const requestData = { group: updatedGroup };
17
- const meta = { group_id: group.id };
18
- yield put({ meta, ...deleteGroupUser.request() });
19
- const { data } = yield call(apiJsonPut, url, requestData, JSON_OPTS);
20
- yield put({ meta, ...deleteGroupUser.success(data) });
21
- } catch (error) {
22
- if (error.response) {
23
- const { status, data } = error.response;
24
- yield put(deleteGroupUser.failure({ status, data }));
25
- } else {
26
- yield put(deleteGroupUser.failure(error.message));
27
- }
28
- } finally {
29
- yield put(deleteGroupUser.fulfill());
30
- }
31
- }
32
-
33
- export function* deleteGroupUserRequestSaga() {
34
- yield takeLatest(deleteGroupUser.TRIGGER, deleteGroupUserSaga);
35
- }
@@ -1,30 +0,0 @@
1
- import { compile } from "path-to-regexp";
2
- import { call, put, takeLatest } from "redux-saga/effects";
3
- import { apiJson, JSON_OPTS } from "@truedat/core/services/api";
4
- import { fetchGroup } from "../routines";
5
- import { API_GROUP } from "../api";
6
-
7
- const toApiPath = compile(API_GROUP);
8
-
9
- export function* fetchGroupSaga({ payload }) {
10
- try {
11
- const { id } = payload;
12
- const url = toApiPath({ id: `${id}` });
13
- yield put(fetchGroup.request());
14
- const { data } = yield call(apiJson, url, JSON_OPTS);
15
- yield put(fetchGroup.success(data));
16
- } catch (error) {
17
- if (error.response) {
18
- const { status, data } = error.response;
19
- yield put(fetchGroup.failure({ status, data }));
20
- } else {
21
- yield put(fetchGroup.failure(error.message));
22
- }
23
- } finally {
24
- yield put(fetchGroup.fulfill());
25
- }
26
- }
27
-
28
- export function* fetchGroupRequestSaga() {
29
- yield takeLatest(fetchGroup.TRIGGER, fetchGroupSaga);
30
- }
@@ -1,26 +0,0 @@
1
- import { call, put, takeLatest } from "redux-saga/effects";
2
- import { apiJson, JSON_OPTS } from "@truedat/core/services/api";
3
- import { fetchGroups } from "../routines";
4
- import { API_GROUPS } from "../api";
5
-
6
- export function* fetchGroupsSaga() {
7
- try {
8
- const url = API_GROUPS;
9
- yield put(fetchGroups.request());
10
- const { data } = yield call(apiJson, url, JSON_OPTS);
11
- yield put(fetchGroups.success(data));
12
- } catch (error) {
13
- if (error.response) {
14
- const { status, data } = error.response;
15
- yield put(fetchGroups.failure({ status, data }));
16
- } else {
17
- yield put(fetchGroups.failure(error.message));
18
- }
19
- } finally {
20
- yield put(fetchGroups.fulfill());
21
- }
22
- }
23
-
24
- export function* fetchGroupsRequestSaga() {
25
- yield takeLatest(fetchGroups.TRIGGER, fetchGroupsSaga);
26
- }
@@ -1,28 +0,0 @@
1
- import { compile } from "path-to-regexp";
2
- import { call, put, takeLatest } from "redux-saga/effects";
3
- import { apiJsonPut, JSON_OPTS } from "@truedat/core/services/api";
4
- import { updateGroup } from "../routines";
5
- import { API_GROUP } from "../api";
6
-
7
- export function* updateGroupSaga({ payload: group }) {
8
- try {
9
- const url = compile(API_GROUP)({ id: `${group.id}` });
10
- const requestData = { group };
11
- yield put(updateGroup.request());
12
- const { data } = yield call(apiJsonPut, url, requestData, JSON_OPTS);
13
- yield put(updateGroup.success(data));
14
- } catch (error) {
15
- if (error.response) {
16
- const { status, data } = error.response;
17
- yield put(updateGroup.failure({ status, data }));
18
- } else {
19
- yield put(updateGroup.failure(error.message));
20
- }
21
- } finally {
22
- yield put(updateGroup.fulfill());
23
- }
24
- }
25
-
26
- export function* updateGroupRequestSaga() {
27
- yield takeLatest(updateGroup.TRIGGER, updateGroupSaga);
28
- }