@greatapps/common 1.1.44 → 1.1.48
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.
- package/dist/components/layouts/UsersSelectorPopover.mjs +92 -21
- package/dist/components/layouts/UsersSelectorPopover.mjs.map +1 -1
- package/dist/index.mjs +3 -0
- package/dist/index.mjs.map +1 -1
- package/dist/modules/accounts/actions/account-management.action.mjs +80 -29
- package/dist/modules/accounts/actions/account-management.action.mjs.map +1 -1
- package/dist/modules/projects/actions/add-project-user.action.mjs +9 -0
- package/dist/modules/projects/actions/add-project-user.action.mjs.map +1 -0
- package/dist/modules/projects/actions/list-available-users.action.mjs +9 -0
- package/dist/modules/projects/actions/list-available-users.action.mjs.map +1 -0
- package/dist/modules/projects/actions/list-project-users.action.mjs +9 -0
- package/dist/modules/projects/actions/list-project-users.action.mjs.map +1 -0
- package/dist/modules/projects/actions/remove-project-user.action.mjs +9 -0
- package/dist/modules/projects/actions/remove-project-user.action.mjs.map +1 -0
- package/dist/modules/projects/hooks/project-users.hook.mjs +70 -0
- package/dist/modules/projects/hooks/project-users.hook.mjs.map +1 -0
- package/dist/modules/projects/services/project-users.service.mjs +67 -0
- package/dist/modules/projects/services/project-users.service.mjs.map +1 -0
- package/dist/modules/projects/types.mjs +22 -0
- package/dist/modules/projects/types.mjs.map +1 -0
- package/dist/server.mjs +10 -0
- package/dist/server.mjs.map +1 -1
- package/package.json +1 -1
- package/src/components/layouts/UsersSelectorPopover.tsx +163 -63
- package/src/index.ts +2 -0
- package/src/modules/accounts/actions/account-management.action.ts +112 -48
- package/src/modules/accounts/types.ts +1 -0
- package/src/modules/projects/actions/add-project-user.action.ts +8 -0
- package/src/modules/projects/actions/list-available-users.action.ts +8 -0
- package/src/modules/projects/actions/list-project-users.action.ts +8 -0
- package/src/modules/projects/actions/remove-project-user.action.ts +8 -0
- package/src/modules/projects/hooks/project-users.hook.ts +81 -0
- package/src/modules/projects/services/project-users.service.ts +94 -0
- package/src/modules/projects/types.ts +28 -0
- package/src/server.ts +7 -0
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
"use server";
|
|
2
|
+
import { projectUsersService } from "../services/project-users.service";
|
|
3
|
+
async function removeProjectUserAction(params) {
|
|
4
|
+
return projectUsersService.removeFromProject(params);
|
|
5
|
+
}
|
|
6
|
+
export {
|
|
7
|
+
removeProjectUserAction
|
|
8
|
+
};
|
|
9
|
+
//# sourceMappingURL=remove-project-user.action.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../../src/modules/projects/actions/remove-project-user.action.ts"],"sourcesContent":["'use server';\r\n\r\nimport { projectUsersService } from '../services/project-users.service';\r\nimport type { AddRemoveProjectUsersParams } from '../types';\r\n\r\nexport async function removeProjectUserAction(params: AddRemoveProjectUsersParams): Promise<void> {\r\n return projectUsersService.removeFromProject(params);\r\n}\r\n"],"mappings":";AAEA,SAAS,2BAA2B;AAGpC,eAAsB,wBAAwB,QAAoD;AAChG,SAAO,oBAAoB,kBAAkB,MAAM;AACrD;","names":[]}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { useMemo } from "react";
|
|
3
|
+
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
|
|
4
|
+
import { addProjectUserAction } from "../actions/add-project-user.action";
|
|
5
|
+
import { listAvailableUsersAction } from "../actions/list-available-users.action";
|
|
6
|
+
import { listProjectUsersAction } from "../actions/list-project-users.action";
|
|
7
|
+
import { removeProjectUserAction } from "../actions/remove-project-user.action";
|
|
8
|
+
const DEFAULT_AVATAR = "/images/Logomark.png";
|
|
9
|
+
const projectUsersQueryKey = (id_project) => ["project-users", id_project];
|
|
10
|
+
function useProjectUsers(id_project) {
|
|
11
|
+
const queryClient = useQueryClient();
|
|
12
|
+
const { data: inProject = [], isLoading: isLoadingIn } = useQuery({
|
|
13
|
+
queryKey: [...projectUsersQueryKey(id_project), "in"],
|
|
14
|
+
queryFn: () => listProjectUsersAction(id_project),
|
|
15
|
+
enabled: !!id_project
|
|
16
|
+
});
|
|
17
|
+
const { data: notInProject = [], isLoading: isLoadingOut } = useQuery({
|
|
18
|
+
queryKey: [...projectUsersQueryKey(id_project), "out"],
|
|
19
|
+
queryFn: () => listAvailableUsersAction(id_project),
|
|
20
|
+
enabled: !!id_project
|
|
21
|
+
});
|
|
22
|
+
const invalidate = () => {
|
|
23
|
+
queryClient.invalidateQueries({ queryKey: projectUsersQueryKey(id_project) });
|
|
24
|
+
};
|
|
25
|
+
const addMutation = useMutation({
|
|
26
|
+
mutationFn: (user_id) => addProjectUserAction({ id_project, users: [user_id] }),
|
|
27
|
+
onSuccess: invalidate
|
|
28
|
+
});
|
|
29
|
+
const removeMutation = useMutation({
|
|
30
|
+
mutationFn: (user_id) => removeProjectUserAction({ id_project, users: [user_id] }),
|
|
31
|
+
onSuccess: invalidate
|
|
32
|
+
});
|
|
33
|
+
const users = useMemo(
|
|
34
|
+
() => [
|
|
35
|
+
...inProject.map((u) => ({
|
|
36
|
+
id: u.id_user,
|
|
37
|
+
name: u.name,
|
|
38
|
+
avatar: u.photo ?? DEFAULT_AVATAR,
|
|
39
|
+
checked: true
|
|
40
|
+
})),
|
|
41
|
+
...notInProject.map((u) => ({
|
|
42
|
+
id: u.id,
|
|
43
|
+
name: u.name,
|
|
44
|
+
avatar: u.photo ?? DEFAULT_AVATAR,
|
|
45
|
+
checked: false
|
|
46
|
+
}))
|
|
47
|
+
],
|
|
48
|
+
[inProject, notInProject]
|
|
49
|
+
);
|
|
50
|
+
const toggleUser = (id) => {
|
|
51
|
+
const user = users.find((u) => u.id === id);
|
|
52
|
+
if (!user) return;
|
|
53
|
+
if (user.checked) {
|
|
54
|
+
removeMutation.mutate(id);
|
|
55
|
+
} else {
|
|
56
|
+
addMutation.mutate(id);
|
|
57
|
+
}
|
|
58
|
+
};
|
|
59
|
+
return {
|
|
60
|
+
users,
|
|
61
|
+
isLoading: isLoadingIn || isLoadingOut,
|
|
62
|
+
userCount: inProject.length,
|
|
63
|
+
toggleUser
|
|
64
|
+
};
|
|
65
|
+
}
|
|
66
|
+
export {
|
|
67
|
+
projectUsersQueryKey,
|
|
68
|
+
useProjectUsers
|
|
69
|
+
};
|
|
70
|
+
//# sourceMappingURL=project-users.hook.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../../src/modules/projects/hooks/project-users.hook.ts"],"sourcesContent":["'use client';\r\n\r\nimport { useMemo } from 'react';\r\nimport { useMutation, useQuery, useQueryClient } from '@tanstack/react-query';\r\n\r\nimport type { UserSelectorItem } from '../../../components/layouts/UsersSelectorPopover';\r\nimport { addProjectUserAction } from '../actions/add-project-user.action';\r\nimport { listAvailableUsersAction } from '../actions/list-available-users.action';\r\nimport { listProjectUsersAction } from '../actions/list-project-users.action';\r\nimport { removeProjectUserAction } from '../actions/remove-project-user.action';\r\n\r\nconst DEFAULT_AVATAR = '/images/Logomark.png';\r\n\r\nexport const projectUsersQueryKey = (id_project: number) => ['project-users', id_project];\r\n\r\nexport function useProjectUsers(id_project: number) {\r\n const queryClient = useQueryClient();\r\n\r\n const { data: inProject = [], isLoading: isLoadingIn } = useQuery({\r\n queryKey: [...projectUsersQueryKey(id_project), 'in'],\r\n queryFn: () => listProjectUsersAction(id_project),\r\n enabled: !!id_project,\r\n });\r\n\r\n const { data: notInProject = [], isLoading: isLoadingOut } = useQuery({\r\n queryKey: [...projectUsersQueryKey(id_project), 'out'],\r\n queryFn: () => listAvailableUsersAction(id_project),\r\n enabled: !!id_project,\r\n });\r\n\r\n const invalidate = () => {\r\n queryClient.invalidateQueries({ queryKey: projectUsersQueryKey(id_project) });\r\n };\r\n\r\n const addMutation = useMutation({\r\n mutationFn: (user_id: number) =>\r\n addProjectUserAction({ id_project, users: [user_id] }),\r\n onSuccess: invalidate,\r\n });\r\n\r\n const removeMutation = useMutation({\r\n mutationFn: (user_id: number) =>\r\n removeProjectUserAction({ id_project, users: [user_id] }),\r\n onSuccess: invalidate,\r\n });\r\n\r\n const users: UserSelectorItem[] = useMemo(\r\n () => [\r\n ...inProject.map((u) => ({\r\n id: u.id_user,\r\n name: u.name,\r\n avatar: u.photo ?? DEFAULT_AVATAR,\r\n checked: true,\r\n })),\r\n ...notInProject.map((u) => ({\r\n id: u.id,\r\n name: u.name,\r\n avatar: u.photo ?? DEFAULT_AVATAR,\r\n checked: false,\r\n })),\r\n ],\r\n [inProject, notInProject]\r\n );\r\n\r\n const toggleUser = (id: number) => {\r\n const user = users.find((u) => u.id === id);\r\n if (!user) return;\r\n if (user.checked) {\r\n removeMutation.mutate(id);\r\n } else {\r\n addMutation.mutate(id);\r\n }\r\n };\r\n\r\n return {\r\n users,\r\n isLoading: isLoadingIn || isLoadingOut,\r\n userCount: inProject.length,\r\n toggleUser,\r\n };\r\n}\r\n"],"mappings":";AAEA,SAAS,eAAe;AACxB,SAAS,aAAa,UAAU,sBAAsB;AAGtD,SAAS,4BAA4B;AACrC,SAAS,gCAAgC;AACzC,SAAS,8BAA8B;AACvC,SAAS,+BAA+B;AAExC,MAAM,iBAAiB;AAEhB,MAAM,uBAAuB,CAAC,eAAuB,CAAC,iBAAiB,UAAU;AAEjF,SAAS,gBAAgB,YAAoB;AAClD,QAAM,cAAc,eAAe;AAEnC,QAAM,EAAE,MAAM,YAAY,CAAC,GAAG,WAAW,YAAY,IAAI,SAAS;AAAA,IAChE,UAAU,CAAC,GAAG,qBAAqB,UAAU,GAAG,IAAI;AAAA,IACpD,SAAS,MAAM,uBAAuB,UAAU;AAAA,IAChD,SAAS,CAAC,CAAC;AAAA,EACb,CAAC;AAED,QAAM,EAAE,MAAM,eAAe,CAAC,GAAG,WAAW,aAAa,IAAI,SAAS;AAAA,IACpE,UAAU,CAAC,GAAG,qBAAqB,UAAU,GAAG,KAAK;AAAA,IACrD,SAAS,MAAM,yBAAyB,UAAU;AAAA,IAClD,SAAS,CAAC,CAAC;AAAA,EACb,CAAC;AAED,QAAM,aAAa,MAAM;AACvB,gBAAY,kBAAkB,EAAE,UAAU,qBAAqB,UAAU,EAAE,CAAC;AAAA,EAC9E;AAEA,QAAM,cAAc,YAAY;AAAA,IAC9B,YAAY,CAAC,YACX,qBAAqB,EAAE,YAAY,OAAO,CAAC,OAAO,EAAE,CAAC;AAAA,IACvD,WAAW;AAAA,EACb,CAAC;AAED,QAAM,iBAAiB,YAAY;AAAA,IACjC,YAAY,CAAC,YACX,wBAAwB,EAAE,YAAY,OAAO,CAAC,OAAO,EAAE,CAAC;AAAA,IAC1D,WAAW;AAAA,EACb,CAAC;AAED,QAAM,QAA4B;AAAA,IAChC,MAAM;AAAA,MACJ,GAAG,UAAU,IAAI,CAAC,OAAO;AAAA,QACvB,IAAI,EAAE;AAAA,QACN,MAAM,EAAE;AAAA,QACR,QAAQ,EAAE,SAAS;AAAA,QACnB,SAAS;AAAA,MACX,EAAE;AAAA,MACF,GAAG,aAAa,IAAI,CAAC,OAAO;AAAA,QAC1B,IAAI,EAAE;AAAA,QACN,MAAM,EAAE;AAAA,QACR,QAAQ,EAAE,SAAS;AAAA,QACnB,SAAS;AAAA,MACX,EAAE;AAAA,IACJ;AAAA,IACA,CAAC,WAAW,YAAY;AAAA,EAC1B;AAEA,QAAM,aAAa,CAAC,OAAe;AACjC,UAAM,OAAO,MAAM,KAAK,CAAC,MAAM,EAAE,OAAO,EAAE;AAC1C,QAAI,CAAC,KAAM;AACX,QAAI,KAAK,SAAS;AAChB,qBAAe,OAAO,EAAE;AAAA,IAC1B,OAAO;AACL,kBAAY,OAAO,EAAE;AAAA,IACvB;AAAA,EACF;AAEA,SAAO;AAAA,IACL;AAAA,IACA,WAAW,eAAe;AAAA,IAC1B,WAAW,UAAU;AAAA,IACrB;AAAA,EACF;AACF;","names":[]}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import "server-only";
|
|
2
|
+
import { api } from "../../../infra/api/client";
|
|
3
|
+
import { ApiError } from "../../../infra/api/types";
|
|
4
|
+
import { getUserContext } from "../../auth/utils/get-user-context";
|
|
5
|
+
import {
|
|
6
|
+
AccountUserSchema,
|
|
7
|
+
ProjectUserSchema
|
|
8
|
+
} from "../types";
|
|
9
|
+
class ProjectUsersService {
|
|
10
|
+
async listInProject(id_project) {
|
|
11
|
+
const { id_account, id_user } = await getUserContext();
|
|
12
|
+
const url = `/account/${id_account}/user/${id_user}/projects/${id_project}/users`;
|
|
13
|
+
const response = await api.pages.get(url);
|
|
14
|
+
if (response.status === 0) {
|
|
15
|
+
throw new ApiError(
|
|
16
|
+
response.message || "Erro ao listar usu\xE1rios do projeto",
|
|
17
|
+
"LIST_PROJECT_USERS_FAILED",
|
|
18
|
+
400
|
|
19
|
+
);
|
|
20
|
+
}
|
|
21
|
+
return response.data.map((item) => ProjectUserSchema.parse(item));
|
|
22
|
+
}
|
|
23
|
+
async listNotInProject(id_project) {
|
|
24
|
+
const { id_account } = await getUserContext();
|
|
25
|
+
const url = `/accounts/${id_account}/users?notInProject=${id_project}`;
|
|
26
|
+
const response = await api.apps.get(url);
|
|
27
|
+
if (response.status === 0) {
|
|
28
|
+
throw new ApiError(
|
|
29
|
+
response.message || "Erro ao listar usu\xE1rios dispon\xEDveis",
|
|
30
|
+
"LIST_AVAILABLE_USERS_FAILED",
|
|
31
|
+
400
|
|
32
|
+
);
|
|
33
|
+
}
|
|
34
|
+
return response.data.map((item) => AccountUserSchema.parse(item));
|
|
35
|
+
}
|
|
36
|
+
async addToProject({ id_project, users }) {
|
|
37
|
+
const { id_account, id_user } = await getUserContext();
|
|
38
|
+
const url = `/account/${id_account}/user/${id_user}/projects/${id_project}/users`;
|
|
39
|
+
const response = await api.pages.post(url, { users });
|
|
40
|
+
if (response.status === 0) {
|
|
41
|
+
throw new ApiError(
|
|
42
|
+
response.message || "Erro ao adicionar usu\xE1rio ao projeto",
|
|
43
|
+
"ADD_PROJECT_USER_FAILED",
|
|
44
|
+
400
|
|
45
|
+
);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
async removeFromProject({ id_project, users }) {
|
|
49
|
+
const { id_account, id_user } = await getUserContext();
|
|
50
|
+
const url = `/account/${id_account}/user/${id_user}/projects/${id_project}/users`;
|
|
51
|
+
const response = await api.pages.delete(url, {
|
|
52
|
+
body: JSON.stringify({ users })
|
|
53
|
+
});
|
|
54
|
+
if (response.status === 0) {
|
|
55
|
+
throw new ApiError(
|
|
56
|
+
response.message || "Erro ao remover usu\xE1rio do projeto",
|
|
57
|
+
"REMOVE_PROJECT_USER_FAILED",
|
|
58
|
+
400
|
|
59
|
+
);
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
const projectUsersService = new ProjectUsersService();
|
|
64
|
+
export {
|
|
65
|
+
projectUsersService
|
|
66
|
+
};
|
|
67
|
+
//# sourceMappingURL=project-users.service.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../../src/modules/projects/services/project-users.service.ts"],"sourcesContent":["import 'server-only';\r\n\r\nimport { api } from '../../../infra/api/client';\r\nimport { ApiError } from '../../../infra/api/types';\r\nimport { getUserContext } from '../../auth/utils/get-user-context';\r\nimport {\r\n AccountUser,\r\n AccountUserSchema,\r\n AddRemoveProjectUsersParams,\r\n ProjectUser,\r\n ProjectUserSchema,\r\n} from '../types';\r\n\r\ninterface ApiListResponse<T> {\r\n data: T[];\r\n total: number;\r\n status: number;\r\n message?: string;\r\n}\r\n\r\ninterface ApiActionResponse {\r\n status: number;\r\n message?: string;\r\n}\r\n\r\nclass ProjectUsersService {\r\n async listInProject(id_project: number): Promise<ProjectUser[]> {\r\n const { id_account, id_user } = await getUserContext();\r\n const url = `/account/${id_account}/user/${id_user}/projects/${id_project}/users`;\r\n\r\n const response = await api.pages.get<ApiListResponse<ProjectUser>>(url);\r\n\r\n if (response.status === 0) {\r\n throw new ApiError(\r\n response.message || 'Erro ao listar usuários do projeto',\r\n 'LIST_PROJECT_USERS_FAILED',\r\n 400\r\n );\r\n }\r\n\r\n return response.data.map((item) => ProjectUserSchema.parse(item));\r\n }\r\n\r\n async listNotInProject(id_project: number): Promise<AccountUser[]> {\r\n const { id_account } = await getUserContext();\r\n const url = `/accounts/${id_account}/users?notInProject=${id_project}`;\r\n\r\n const response = await api.apps.get<ApiListResponse<AccountUser>>(url);\r\n\r\n if (response.status === 0) {\r\n throw new ApiError(\r\n response.message || 'Erro ao listar usuários disponíveis',\r\n 'LIST_AVAILABLE_USERS_FAILED',\r\n 400\r\n );\r\n }\r\n\r\n return response.data.map((item) => AccountUserSchema.parse(item));\r\n }\r\n\r\n async addToProject({ id_project, users }: AddRemoveProjectUsersParams): Promise<void> {\r\n const { id_account, id_user } = await getUserContext();\r\n const url = `/account/${id_account}/user/${id_user}/projects/${id_project}/users`;\r\n\r\n const response = await api.pages.post<ApiActionResponse>(url, { users });\r\n\r\n if (response.status === 0) {\r\n throw new ApiError(\r\n response.message || 'Erro ao adicionar usuário ao projeto',\r\n 'ADD_PROJECT_USER_FAILED',\r\n 400\r\n );\r\n }\r\n }\r\n\r\n async removeFromProject({ id_project, users }: AddRemoveProjectUsersParams): Promise<void> {\r\n const { id_account, id_user } = await getUserContext();\r\n const url = `/account/${id_account}/user/${id_user}/projects/${id_project}/users`;\r\n\r\n const response = await api.pages.delete<ApiActionResponse>(url, {\r\n body: JSON.stringify({ users }),\r\n });\r\n\r\n if (response.status === 0) {\r\n throw new ApiError(\r\n response.message || 'Erro ao remover usuário do projeto',\r\n 'REMOVE_PROJECT_USER_FAILED',\r\n 400\r\n );\r\n }\r\n }\r\n}\r\n\r\nexport const projectUsersService = new ProjectUsersService();\r\n"],"mappings":"AAAA,OAAO;AAEP,SAAS,WAAW;AACpB,SAAS,gBAAgB;AACzB,SAAS,sBAAsB;AAC/B;AAAA,EAEE;AAAA,EAGA;AAAA,OACK;AAcP,MAAM,oBAAoB;AAAA,EACxB,MAAM,cAAc,YAA4C;AAC9D,UAAM,EAAE,YAAY,QAAQ,IAAI,MAAM,eAAe;AACrD,UAAM,MAAM,YAAY,UAAU,SAAS,OAAO,aAAa,UAAU;AAEzE,UAAM,WAAW,MAAM,IAAI,MAAM,IAAkC,GAAG;AAEtE,QAAI,SAAS,WAAW,GAAG;AACzB,YAAM,IAAI;AAAA,QACR,SAAS,WAAW;AAAA,QACpB;AAAA,QACA;AAAA,MACF;AAAA,IACF;AAEA,WAAO,SAAS,KAAK,IAAI,CAAC,SAAS,kBAAkB,MAAM,IAAI,CAAC;AAAA,EAClE;AAAA,EAEA,MAAM,iBAAiB,YAA4C;AACjE,UAAM,EAAE,WAAW,IAAI,MAAM,eAAe;AAC5C,UAAM,MAAM,aAAa,UAAU,uBAAuB,UAAU;AAEpE,UAAM,WAAW,MAAM,IAAI,KAAK,IAAkC,GAAG;AAErE,QAAI,SAAS,WAAW,GAAG;AACzB,YAAM,IAAI;AAAA,QACR,SAAS,WAAW;AAAA,QACpB;AAAA,QACA;AAAA,MACF;AAAA,IACF;AAEA,WAAO,SAAS,KAAK,IAAI,CAAC,SAAS,kBAAkB,MAAM,IAAI,CAAC;AAAA,EAClE;AAAA,EAEA,MAAM,aAAa,EAAE,YAAY,MAAM,GAA+C;AACpF,UAAM,EAAE,YAAY,QAAQ,IAAI,MAAM,eAAe;AACrD,UAAM,MAAM,YAAY,UAAU,SAAS,OAAO,aAAa,UAAU;AAEzE,UAAM,WAAW,MAAM,IAAI,MAAM,KAAwB,KAAK,EAAE,MAAM,CAAC;AAEvE,QAAI,SAAS,WAAW,GAAG;AACzB,YAAM,IAAI;AAAA,QACR,SAAS,WAAW;AAAA,QACpB;AAAA,QACA;AAAA,MACF;AAAA,IACF;AAAA,EACF;AAAA,EAEA,MAAM,kBAAkB,EAAE,YAAY,MAAM,GAA+C;AACzF,UAAM,EAAE,YAAY,QAAQ,IAAI,MAAM,eAAe;AACrD,UAAM,MAAM,YAAY,UAAU,SAAS,OAAO,aAAa,UAAU;AAEzE,UAAM,WAAW,MAAM,IAAI,MAAM,OAA0B,KAAK;AAAA,MAC9D,MAAM,KAAK,UAAU,EAAE,MAAM,CAAC;AAAA,IAChC,CAAC;AAED,QAAI,SAAS,WAAW,GAAG;AACzB,YAAM,IAAI;AAAA,QACR,SAAS,WAAW;AAAA,QACpB;AAAA,QACA;AAAA,MACF;AAAA,IACF;AAAA,EACF;AACF;AAEO,MAAM,sBAAsB,IAAI,oBAAoB;","names":[]}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
const ProjectUserSchema = z.object({
|
|
3
|
+
id_user: z.union([z.number(), z.string()]).transform(Number),
|
|
4
|
+
id_account: z.union([z.number(), z.string()]).transform(Number),
|
|
5
|
+
id_project: z.union([z.number(), z.string()]).transform(Number),
|
|
6
|
+
name: z.string(),
|
|
7
|
+
email: z.string(),
|
|
8
|
+
profile: z.string().optional(),
|
|
9
|
+
photo: z.string().nullable().optional()
|
|
10
|
+
});
|
|
11
|
+
const AccountUserSchema = z.object({
|
|
12
|
+
id: z.union([z.number(), z.string()]).transform(Number),
|
|
13
|
+
name: z.string(),
|
|
14
|
+
email: z.string(),
|
|
15
|
+
profile: z.string().optional(),
|
|
16
|
+
photo: z.string().nullable().optional()
|
|
17
|
+
});
|
|
18
|
+
export {
|
|
19
|
+
AccountUserSchema,
|
|
20
|
+
ProjectUserSchema
|
|
21
|
+
};
|
|
22
|
+
//# sourceMappingURL=types.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/modules/projects/types.ts"],"sourcesContent":["import { z } from 'zod';\r\n\r\nexport const ProjectUserSchema = z.object({\r\n id_user: z.union([z.number(), z.string()]).transform(Number),\r\n id_account: z.union([z.number(), z.string()]).transform(Number),\r\n id_project: z.union([z.number(), z.string()]).transform(Number),\r\n name: z.string(),\r\n email: z.string(),\r\n profile: z.string().optional(),\r\n photo: z.string().nullable().optional(),\r\n});\r\n\r\nexport type ProjectUser = z.infer<typeof ProjectUserSchema>;\r\n\r\nexport const AccountUserSchema = z.object({\r\n id: z.union([z.number(), z.string()]).transform(Number),\r\n name: z.string(),\r\n email: z.string(),\r\n profile: z.string().optional(),\r\n photo: z.string().nullable().optional(),\r\n});\r\n\r\nexport type AccountUser = z.infer<typeof AccountUserSchema>;\r\n\r\nexport interface AddRemoveProjectUsersParams {\r\n id_project: number;\r\n users: number[];\r\n}\r\n"],"mappings":"AAAA,SAAS,SAAS;AAEX,MAAM,oBAAoB,EAAE,OAAO;AAAA,EACxC,SAAS,EAAE,MAAM,CAAC,EAAE,OAAO,GAAG,EAAE,OAAO,CAAC,CAAC,EAAE,UAAU,MAAM;AAAA,EAC3D,YAAY,EAAE,MAAM,CAAC,EAAE,OAAO,GAAG,EAAE,OAAO,CAAC,CAAC,EAAE,UAAU,MAAM;AAAA,EAC9D,YAAY,EAAE,MAAM,CAAC,EAAE,OAAO,GAAG,EAAE,OAAO,CAAC,CAAC,EAAE,UAAU,MAAM;AAAA,EAC9D,MAAM,EAAE,OAAO;AAAA,EACf,OAAO,EAAE,OAAO;AAAA,EAChB,SAAS,EAAE,OAAO,EAAE,SAAS;AAAA,EAC7B,OAAO,EAAE,OAAO,EAAE,SAAS,EAAE,SAAS;AACxC,CAAC;AAIM,MAAM,oBAAoB,EAAE,OAAO;AAAA,EACxC,IAAI,EAAE,MAAM,CAAC,EAAE,OAAO,GAAG,EAAE,OAAO,CAAC,CAAC,EAAE,UAAU,MAAM;AAAA,EACtD,MAAM,EAAE,OAAO;AAAA,EACf,OAAO,EAAE,OAAO;AAAA,EAChB,SAAS,EAAE,OAAO,EAAE,SAAS;AAAA,EAC7B,OAAO,EAAE,OAAO,EAAE,SAAS,EAAE,SAAS;AACxC,CAAC;","names":[]}
|
package/dist/server.mjs
CHANGED
|
@@ -8,6 +8,11 @@ import { findWhitelabel } from "./modules/whitelabel/actions/find-whitelabel.act
|
|
|
8
8
|
import { validateSessionAction } from "./modules/auth/actions/validate-session.action";
|
|
9
9
|
import { listSubscriptionsAction } from "./modules/subscriptions/actions/list-subscriptions.action";
|
|
10
10
|
import { listIaCreditsAction } from "./modules/ia-credits/actions/list-ia-credits.action";
|
|
11
|
+
import { projectUsersService } from "./modules/projects/services/project-users.service";
|
|
12
|
+
import { listProjectUsersAction } from "./modules/projects/actions/list-project-users.action";
|
|
13
|
+
import { listAvailableUsersAction } from "./modules/projects/actions/list-available-users.action";
|
|
14
|
+
import { addProjectUserAction } from "./modules/projects/actions/add-project-user.action";
|
|
15
|
+
import { removeProjectUserAction } from "./modules/projects/actions/remove-project-user.action";
|
|
11
16
|
import { accountService } from "./modules/accounts/services/account.service";
|
|
12
17
|
import { twoFactorService } from "./modules/accounts/services/two-factor.service";
|
|
13
18
|
import {
|
|
@@ -32,6 +37,7 @@ import { getUserContext } from "./modules/auth/utils/get-user-context";
|
|
|
32
37
|
export {
|
|
33
38
|
ApiClient,
|
|
34
39
|
accountService,
|
|
40
|
+
addProjectUserAction,
|
|
35
41
|
api,
|
|
36
42
|
apiClient,
|
|
37
43
|
authService,
|
|
@@ -49,8 +55,12 @@ export {
|
|
|
49
55
|
getUserContext,
|
|
50
56
|
iaCreditsService,
|
|
51
57
|
listAccountUsersAction,
|
|
58
|
+
listAvailableUsersAction,
|
|
52
59
|
listIaCreditsAction,
|
|
60
|
+
listProjectUsersAction,
|
|
53
61
|
listSubscriptionsAction,
|
|
62
|
+
projectUsersService,
|
|
63
|
+
removeProjectUserAction,
|
|
54
64
|
requestEmailChangeAction,
|
|
55
65
|
requestPhoneChangeAction,
|
|
56
66
|
subscriptionsService,
|
package/dist/server.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/server.ts"],"sourcesContent":["import 'server-only';\r\n\r\n// API Client\r\nexport { ApiClient, api, apiClient } from './infra/api/client';\r\n\r\n// Services\r\nexport { authService } from './modules/auth/services/auth.service';\r\nexport { whitelabelService } from './modules/whitelabel/services/whitelabel.service';\r\nexport { subscriptionsService } from './modules/subscriptions/services/subscriptions.service';\r\nexport { iaCreditsService } from './modules/ia-credits/services/ia-credits.service';\r\n\r\n// Actions\r\nexport { findWhitelabel } from './modules/whitelabel/actions/find-whitelabel.action';\r\nexport { validateSessionAction } from './modules/auth/actions/validate-session.action';\r\nexport { listSubscriptionsAction } from './modules/subscriptions/actions/list-subscriptions.action';\r\nexport { listIaCreditsAction } from './modules/ia-credits/actions/list-ia-credits.action';\r\n\r\n// Account Services & Actions (server-only)\r\nexport { accountService } from './modules/accounts/services/account.service';\r\nexport { twoFactorService } from './modules/accounts/services/two-factor.service';\r\nexport {\r\n listAccountUsersAction,\r\n updateUserAction,\r\n updateAccountAction,\r\n updateAccountUserByIdAction,\r\n deleteAccountUserAction,\r\n deleteAccountAction,\r\n createAccountUserAction,\r\n changePasswordAction,\r\n requestEmailChangeAction,\r\n confirmEmailChangeAction,\r\n requestPhoneChangeAction,\r\n confirmPhoneChangeAction,\r\n generateTwoFactorAction,\r\n confirmTwoFactorAction,\r\n disableTwoFactorAction,\r\n} from './modules/accounts/actions/account-management.action';\r\n\r\n// Server Utils\r\nexport { getClientInfoFromRequest } from './infra/utils/client-info';\r\nexport { getUserContext } from './modules/auth/utils/get-user-context';\r\n"],"mappings":"AAAA,OAAO;AAGP,SAAS,WAAW,KAAK,iBAAiB;AAG1C,SAAS,mBAAmB;AAC5B,SAAS,yBAAyB;AAClC,SAAS,4BAA4B;AACrC,SAAS,wBAAwB;AAGjC,SAAS,sBAAsB;AAC/B,SAAS,6BAA6B;AACtC,SAAS,+BAA+B;AACxC,SAAS,2BAA2B;AAGpC,SAAS,sBAAsB;AAC/B,SAAS,wBAAwB;AACjC;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAGP,SAAS,gCAAgC;AACzC,SAAS,sBAAsB;","names":[]}
|
|
1
|
+
{"version":3,"sources":["../src/server.ts"],"sourcesContent":["import 'server-only';\r\n\r\n// API Client\r\nexport { ApiClient, api, apiClient } from './infra/api/client';\r\n\r\n// Services\r\nexport { authService } from './modules/auth/services/auth.service';\r\nexport { whitelabelService } from './modules/whitelabel/services/whitelabel.service';\r\nexport { subscriptionsService } from './modules/subscriptions/services/subscriptions.service';\r\nexport { iaCreditsService } from './modules/ia-credits/services/ia-credits.service';\r\n\r\n// Actions\r\nexport { findWhitelabel } from './modules/whitelabel/actions/find-whitelabel.action';\r\nexport { validateSessionAction } from './modules/auth/actions/validate-session.action';\r\nexport { listSubscriptionsAction } from './modules/subscriptions/actions/list-subscriptions.action';\r\nexport { listIaCreditsAction } from './modules/ia-credits/actions/list-ia-credits.action';\r\n\r\n// Project Users Services & Actions (server-only)\r\nexport { projectUsersService } from './modules/projects/services/project-users.service';\r\nexport { listProjectUsersAction } from './modules/projects/actions/list-project-users.action';\r\nexport { listAvailableUsersAction } from './modules/projects/actions/list-available-users.action';\r\nexport { addProjectUserAction } from './modules/projects/actions/add-project-user.action';\r\nexport { removeProjectUserAction } from './modules/projects/actions/remove-project-user.action';\r\n\r\n// Account Services & Actions (server-only)\r\nexport { accountService } from './modules/accounts/services/account.service';\r\nexport { twoFactorService } from './modules/accounts/services/two-factor.service';\r\nexport {\r\n listAccountUsersAction,\r\n updateUserAction,\r\n updateAccountAction,\r\n updateAccountUserByIdAction,\r\n deleteAccountUserAction,\r\n deleteAccountAction,\r\n createAccountUserAction,\r\n changePasswordAction,\r\n requestEmailChangeAction,\r\n confirmEmailChangeAction,\r\n requestPhoneChangeAction,\r\n confirmPhoneChangeAction,\r\n generateTwoFactorAction,\r\n confirmTwoFactorAction,\r\n disableTwoFactorAction,\r\n} from './modules/accounts/actions/account-management.action';\r\n\r\n// Server Utils\r\nexport { getClientInfoFromRequest } from './infra/utils/client-info';\r\nexport { getUserContext } from './modules/auth/utils/get-user-context';\r\n"],"mappings":"AAAA,OAAO;AAGP,SAAS,WAAW,KAAK,iBAAiB;AAG1C,SAAS,mBAAmB;AAC5B,SAAS,yBAAyB;AAClC,SAAS,4BAA4B;AACrC,SAAS,wBAAwB;AAGjC,SAAS,sBAAsB;AAC/B,SAAS,6BAA6B;AACtC,SAAS,+BAA+B;AACxC,SAAS,2BAA2B;AAGpC,SAAS,2BAA2B;AACpC,SAAS,8BAA8B;AACvC,SAAS,gCAAgC;AACzC,SAAS,4BAA4B;AACrC,SAAS,+BAA+B;AAGxC,SAAS,sBAAsB;AAC/B,SAAS,wBAAwB;AACjC;AAAA,EACE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,OACK;AAGP,SAAS,gCAAgC;AACzC,SAAS,sBAAsB;","names":[]}
|
package/package.json
CHANGED
|
@@ -10,6 +10,7 @@ import { Command, CommandEmpty, CommandInput, CommandItem, CommandList } from '.
|
|
|
10
10
|
import { Checkbox } from '../ui/form/Checkbox';
|
|
11
11
|
import { Tooltip, TooltipContent, TooltipTrigger } from '../ui/overlay/Tooltip';
|
|
12
12
|
import { cn } from '../../infra/utils/clsx';
|
|
13
|
+
import { useProjectUsers } from '../../modules/projects/hooks/project-users.hook';
|
|
13
14
|
|
|
14
15
|
export interface UserSelectorItem {
|
|
15
16
|
id: number;
|
|
@@ -18,7 +19,20 @@ export interface UserSelectorItem {
|
|
|
18
19
|
checked: boolean;
|
|
19
20
|
}
|
|
20
21
|
|
|
22
|
+
function UserItemSkeleton() {
|
|
23
|
+
return (
|
|
24
|
+
<div className="flex items-center justify-between px-2 py-1.5 gap-2">
|
|
25
|
+
<div className="flex items-center gap-2 flex-1">
|
|
26
|
+
<div className="size-8 rounded-full bg-gray-100 animate-pulse shrink-0" />
|
|
27
|
+
<div className="h-3.5 w-28 rounded bg-gray-100 animate-pulse" />
|
|
28
|
+
</div>
|
|
29
|
+
<div className="size-4 rounded bg-gray-100 animate-pulse shrink-0" />
|
|
30
|
+
</div>
|
|
31
|
+
);
|
|
32
|
+
}
|
|
33
|
+
|
|
21
34
|
export interface UsersSelectorPopoverProps {
|
|
35
|
+
id_project?: number;
|
|
22
36
|
users?: UserSelectorItem[];
|
|
23
37
|
onToggleUser?: (id: number) => void;
|
|
24
38
|
addRoute?: string;
|
|
@@ -29,33 +43,33 @@ export interface UsersSelectorPopoverProps {
|
|
|
29
43
|
contentClassName?: string;
|
|
30
44
|
}
|
|
31
45
|
|
|
32
|
-
|
|
33
|
-
users:
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
46
|
+
interface ContentProps {
|
|
47
|
+
users: UserSelectorItem[];
|
|
48
|
+
isLoading: boolean;
|
|
49
|
+
userCount: number;
|
|
50
|
+
toggleUser: (id: number) => void;
|
|
51
|
+
addRoute: string;
|
|
52
|
+
manageRoute: string;
|
|
53
|
+
side?: UsersSelectorPopoverProps['side'];
|
|
54
|
+
align?: UsersSelectorPopoverProps['align'];
|
|
55
|
+
contentClassName?: string;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
function UsersSelectorPopoverContent({
|
|
59
|
+
users,
|
|
60
|
+
isLoading,
|
|
61
|
+
userCount,
|
|
62
|
+
toggleUser,
|
|
63
|
+
addRoute,
|
|
64
|
+
manageRoute,
|
|
38
65
|
side,
|
|
39
66
|
align,
|
|
40
67
|
contentClassName,
|
|
41
|
-
}:
|
|
68
|
+
}: ContentProps) {
|
|
42
69
|
const route = useRouter();
|
|
43
70
|
const [open, setOpen] = useState(false);
|
|
44
|
-
const [internalUsers, setInternalUsers] = useState<UserSelectorItem[]>(externalUsers ?? []);
|
|
45
71
|
const [hoveredId, setHoveredId] = useState<number | null>(null);
|
|
46
72
|
|
|
47
|
-
const users = externalUsers ?? internalUsers;
|
|
48
|
-
|
|
49
|
-
const toggleUser = (id: number) => {
|
|
50
|
-
if (onToggleUser) {
|
|
51
|
-
onToggleUser(id);
|
|
52
|
-
} else {
|
|
53
|
-
setInternalUsers((prev) =>
|
|
54
|
-
prev.map((u) => (u.id === id ? { ...u, checked: !u.checked } : u))
|
|
55
|
-
);
|
|
56
|
-
}
|
|
57
|
-
};
|
|
58
|
-
|
|
59
73
|
return (
|
|
60
74
|
<Popover open={open} onOpenChange={setOpen}>
|
|
61
75
|
<PopoverTrigger className="cursor-pointer">
|
|
@@ -86,7 +100,6 @@ function UsersSelectorPopover({
|
|
|
86
100
|
<Plus size={16} />
|
|
87
101
|
Adicionar
|
|
88
102
|
</Button>
|
|
89
|
-
|
|
90
103
|
<Tooltip>
|
|
91
104
|
<TooltipTrigger asChild>
|
|
92
105
|
<Button
|
|
@@ -105,48 +118,64 @@ function UsersSelectorPopover({
|
|
|
105
118
|
<Command className="gap-2" value="">
|
|
106
119
|
<CommandInput placeholder="Busque aqui" />
|
|
107
120
|
<CommandList className="custom-scrollbar paragraph-small-medium text-gray-600 h-[162px]">
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
>
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
{
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
121
|
+
{isLoading ? (
|
|
122
|
+
<>
|
|
123
|
+
<UserItemSkeleton />
|
|
124
|
+
<UserItemSkeleton />
|
|
125
|
+
<UserItemSkeleton />
|
|
126
|
+
</>
|
|
127
|
+
) : users.length === 0 ? (
|
|
128
|
+
<div className="flex items-center justify-center h-full">
|
|
129
|
+
<span className="paragraph-small-medium text-center text-gray-500">
|
|
130
|
+
Nenhum usuário encontrado.
|
|
131
|
+
</span>
|
|
132
|
+
</div>
|
|
133
|
+
) : (
|
|
134
|
+
<>
|
|
135
|
+
<CommandEmpty>Nenhum resultado encontrado.</CommandEmpty>
|
|
136
|
+
{users.map((user) => (
|
|
137
|
+
<CommandItem
|
|
138
|
+
key={user.id}
|
|
139
|
+
value={user.name}
|
|
140
|
+
autoFocus={false}
|
|
141
|
+
onPointerEnter={() => setHoveredId(user.id)}
|
|
142
|
+
onPointerLeave={() => setHoveredId(null)}
|
|
143
|
+
onFocus={() => setHoveredId(user.id)}
|
|
144
|
+
onBlur={() => setHoveredId(null)}
|
|
145
|
+
onSelect={() => toggleUser(user.id)}
|
|
146
|
+
className="cursor-pointer"
|
|
147
|
+
>
|
|
148
|
+
<div className="flex items-center justify-between w-full">
|
|
149
|
+
<div className="flex items-center gap-2">
|
|
150
|
+
<Image
|
|
151
|
+
alt="Avatar"
|
|
152
|
+
src={user.avatar}
|
|
153
|
+
width={32}
|
|
154
|
+
height={32}
|
|
155
|
+
className="rounded-full"
|
|
156
|
+
/>
|
|
157
|
+
{user.name}
|
|
158
|
+
</div>
|
|
159
|
+
<Tooltip open={hoveredId === user.id}>
|
|
160
|
+
<TooltipTrigger
|
|
161
|
+
onClick={(e) => e.stopPropagation()}
|
|
162
|
+
onPointerDown={(e) => e.stopPropagation()}
|
|
163
|
+
>
|
|
164
|
+
<Checkbox
|
|
165
|
+
checked={user.checked}
|
|
166
|
+
onCheckedChange={() => toggleUser(user.id)}
|
|
167
|
+
className={hoveredId === user.id ? 'border-gray-950' : ''}
|
|
168
|
+
/>
|
|
169
|
+
</TooltipTrigger>
|
|
170
|
+
<TooltipContent>
|
|
171
|
+
{user.checked ? 'Remover do projeto' : 'Adicionar ao projeto'}
|
|
172
|
+
</TooltipContent>
|
|
173
|
+
</Tooltip>
|
|
174
|
+
</div>
|
|
175
|
+
</CommandItem>
|
|
176
|
+
))}
|
|
177
|
+
</>
|
|
178
|
+
)}
|
|
150
179
|
</CommandList>
|
|
151
180
|
</Command>
|
|
152
181
|
</div>
|
|
@@ -155,4 +184,75 @@ function UsersSelectorPopover({
|
|
|
155
184
|
);
|
|
156
185
|
}
|
|
157
186
|
|
|
187
|
+
function ConnectedUsersSelectorPopover({
|
|
188
|
+
id_project,
|
|
189
|
+
addRoute,
|
|
190
|
+
manageRoute,
|
|
191
|
+
side,
|
|
192
|
+
align,
|
|
193
|
+
contentClassName,
|
|
194
|
+
}: Required<Pick<UsersSelectorPopoverProps, 'id_project'>> &
|
|
195
|
+
Pick<UsersSelectorPopoverProps, 'addRoute' | 'manageRoute' | 'side' | 'align' | 'contentClassName'>) {
|
|
196
|
+
const { users, isLoading, userCount, toggleUser } = useProjectUsers(id_project);
|
|
197
|
+
return (
|
|
198
|
+
<UsersSelectorPopoverContent
|
|
199
|
+
users={users}
|
|
200
|
+
isLoading={isLoading}
|
|
201
|
+
userCount={userCount}
|
|
202
|
+
toggleUser={toggleUser}
|
|
203
|
+
addRoute={addRoute ?? '/my-teams?createNew=true'}
|
|
204
|
+
manageRoute={manageRoute ?? '/my-teams'}
|
|
205
|
+
side={side}
|
|
206
|
+
align={align}
|
|
207
|
+
contentClassName={contentClassName}
|
|
208
|
+
/>
|
|
209
|
+
);
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
function StaticUsersSelectorPopover({
|
|
213
|
+
users: externalUsers = [],
|
|
214
|
+
onToggleUser,
|
|
215
|
+
userCount = 5,
|
|
216
|
+
addRoute = '/my-teams?createNew=true',
|
|
217
|
+
manageRoute = '/my-teams',
|
|
218
|
+
side,
|
|
219
|
+
align,
|
|
220
|
+
contentClassName,
|
|
221
|
+
}: Omit<UsersSelectorPopoverProps, 'id_project'>) {
|
|
222
|
+
const [internalUsers, setInternalUsers] = useState<UserSelectorItem[]>(externalUsers);
|
|
223
|
+
|
|
224
|
+
const users = externalUsers.length > 0 ? externalUsers : internalUsers;
|
|
225
|
+
|
|
226
|
+
const toggleUser = (id: number) => {
|
|
227
|
+
if (onToggleUser) {
|
|
228
|
+
onToggleUser(id);
|
|
229
|
+
} else {
|
|
230
|
+
setInternalUsers((prev) =>
|
|
231
|
+
prev.map((u) => (u.id === id ? { ...u, checked: !u.checked } : u))
|
|
232
|
+
);
|
|
233
|
+
}
|
|
234
|
+
};
|
|
235
|
+
|
|
236
|
+
return (
|
|
237
|
+
<UsersSelectorPopoverContent
|
|
238
|
+
users={users}
|
|
239
|
+
isLoading={false}
|
|
240
|
+
userCount={userCount}
|
|
241
|
+
toggleUser={toggleUser}
|
|
242
|
+
addRoute={addRoute}
|
|
243
|
+
manageRoute={manageRoute}
|
|
244
|
+
side={side}
|
|
245
|
+
align={align}
|
|
246
|
+
contentClassName={contentClassName}
|
|
247
|
+
/>
|
|
248
|
+
);
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
function UsersSelectorPopover(props: UsersSelectorPopoverProps) {
|
|
252
|
+
if (props.id_project != null) {
|
|
253
|
+
return <ConnectedUsersSelectorPopover {...props} id_project={props.id_project} />;
|
|
254
|
+
}
|
|
255
|
+
return <StaticUsersSelectorPopover {...props} />;
|
|
256
|
+
}
|
|
257
|
+
|
|
158
258
|
export { UsersSelectorPopover };
|
package/src/index.ts
CHANGED
|
@@ -10,6 +10,8 @@ export * from './providers/auth.provider';
|
|
|
10
10
|
export * from './providers/whitelabel.provider';
|
|
11
11
|
|
|
12
12
|
// Hooks
|
|
13
|
+
export { useProjectUsers, projectUsersQueryKey } from './modules/projects/hooks/project-users.hook';
|
|
14
|
+
export type { ProjectUser, AccountUser, AddRemoveProjectUsersParams } from './modules/projects/types';
|
|
13
15
|
export { useUserQuery, useUserValidateSession, useInvalidateUser, useSetUserData, USER_QUERY_KEY } from './modules/auth/hooks/useUserQuery';
|
|
14
16
|
export { useSubscriptions, SUBSCRIPTIONS_QUERY_KEY } from './modules/subscriptions/hooks/list-subscriptions.hook';
|
|
15
17
|
export { useActiveSubscription } from './modules/subscriptions/hooks/find-active-subscription.hook';
|