mirror of
https://github.com/fosrl/pangolin.git
synced 2026-05-18 14:55:22 +00:00
Add new user and role selectors for pagination
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@@ -6,11 +6,9 @@ import { useEnvContext } from "@app/hooks/useEnvContext";
|
|||||||
import { useOrgContext } from "@app/hooks/useOrgContext";
|
import { useOrgContext } from "@app/hooks/useOrgContext";
|
||||||
import { usePaidStatus } from "@app/hooks/usePaidStatus";
|
import { usePaidStatus } from "@app/hooks/usePaidStatus";
|
||||||
|
|
||||||
import { getUserDisplayName } from "@app/lib/getUserDisplayName";
|
|
||||||
import { orgQueries } from "@app/lib/queries";
|
import { orgQueries } from "@app/lib/queries";
|
||||||
import { build } from "@server/build";
|
import { build } from "@server/build";
|
||||||
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
import { tierMatrix } from "@server/lib/billing/tierMatrix";
|
||||||
import { UserType } from "@server/types/UserTypes";
|
|
||||||
import { useQuery } from "@tanstack/react-query";
|
import { useQuery } from "@tanstack/react-query";
|
||||||
import { useTranslations } from "next-intl";
|
import { useTranslations } from "next-intl";
|
||||||
|
|
||||||
@@ -51,12 +49,6 @@ export function EditPolicyForm({
|
|||||||
env.server.maxmind_asn_path && env.server.maxmind_asn_path.length > 0
|
env.server.maxmind_asn_path && env.server.maxmind_asn_path.length > 0
|
||||||
);
|
);
|
||||||
|
|
||||||
const { data: orgRoles = [], isLoading: isLoadingOrgRoles } = useQuery(
|
|
||||||
orgQueries.roles({ orgId: org.org.orgId })
|
|
||||||
);
|
|
||||||
const { data: orgUsers = [], isLoading: isLoadingOrgUsers } = useQuery(
|
|
||||||
orgQueries.users({ orgId: org.org.orgId })
|
|
||||||
);
|
|
||||||
const { data: orgIdps = [], isLoading: isLoadingOrgIdps } = useQuery(
|
const { data: orgIdps = [], isLoading: isLoadingOrgIdps } = useQuery(
|
||||||
orgQueries.identityProviders({
|
orgQueries.identityProviders({
|
||||||
orgId: org.org.orgId,
|
orgId: org.org.orgId,
|
||||||
@@ -64,26 +56,6 @@ export function EditPolicyForm({
|
|||||||
})
|
})
|
||||||
);
|
);
|
||||||
|
|
||||||
const allRoles = useMemo(
|
|
||||||
() =>
|
|
||||||
orgRoles
|
|
||||||
.map((role) => ({
|
|
||||||
id: role.roleId.toString(),
|
|
||||||
text: role.name
|
|
||||||
}))
|
|
||||||
.filter((role) => role.text !== "Admin"),
|
|
||||||
[orgRoles]
|
|
||||||
);
|
|
||||||
|
|
||||||
const allUsers = useMemo(
|
|
||||||
() =>
|
|
||||||
orgUsers.map((user) => ({
|
|
||||||
id: user.id.toString(),
|
|
||||||
text: `${getUserDisplayName({ email: user.email, username: user.username })}${user.type !== UserType.Internal ? ` (${user.idpName})` : ""}`
|
|
||||||
})),
|
|
||||||
[orgUsers]
|
|
||||||
);
|
|
||||||
|
|
||||||
const allIdps = useMemo(() => {
|
const allIdps = useMemo(() => {
|
||||||
if (build === "saas") {
|
if (build === "saas") {
|
||||||
if (isPaidUser(tierMatrix.orgOidc)) {
|
if (isPaidUser(tierMatrix.orgOidc)) {
|
||||||
@@ -98,17 +70,18 @@ export function EditPolicyForm({
|
|||||||
return [];
|
return [];
|
||||||
}, [orgIdps, isPaidUser]);
|
}, [orgIdps, isPaidUser]);
|
||||||
|
|
||||||
if (isLoadingOrgRoles || isLoadingOrgUsers || isLoadingOrgIdps) {
|
if (isLoadingOrgIdps) {
|
||||||
return <></>;
|
return <></>;
|
||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<SettingsContainer>
|
<SettingsContainer>
|
||||||
{!hidePolicyNameForm && <EditPolicyNameSectionForm readonly={readonly} />}
|
{!hidePolicyNameForm && (
|
||||||
|
<EditPolicyNameSectionForm readonly={readonly} />
|
||||||
|
)}
|
||||||
|
|
||||||
<EditPolicyUsersRolesSectionForm
|
<EditPolicyUsersRolesSectionForm
|
||||||
allRoles={allRoles}
|
orgId={org.org.orgId}
|
||||||
allUsers={allUsers}
|
|
||||||
allIdps={allIdps}
|
allIdps={allIdps}
|
||||||
readonly={readonly}
|
readonly={readonly}
|
||||||
/>
|
/>
|
||||||
|
|||||||
@@ -23,8 +23,9 @@ import type { AxiosResponse } from "axios";
|
|||||||
import { useRouter } from "next/navigation";
|
import { useRouter } from "next/navigation";
|
||||||
import { createPolicySchema } from ".";
|
import { createPolicySchema } from ".";
|
||||||
|
|
||||||
|
import { RolesSelector } from "@app/components/roles-selector";
|
||||||
|
import { UsersSelector } from "@app/components/users-selector";
|
||||||
import { SwitchInput } from "@app/components/SwitchInput";
|
import { SwitchInput } from "@app/components/SwitchInput";
|
||||||
import { Tag, TagInput } from "@app/components/tags/tag-input";
|
|
||||||
import { Button } from "@app/components/ui/button";
|
import { Button } from "@app/components/ui/button";
|
||||||
import {
|
import {
|
||||||
Form,
|
Form,
|
||||||
@@ -50,15 +51,13 @@ import { useForm, useWatch } from "react-hook-form";
|
|||||||
// ─── PolicyUsersRolesSection ──────────────────────────────────────────────────
|
// ─── PolicyUsersRolesSection ──────────────────────────────────────────────────
|
||||||
|
|
||||||
type PolicyUsersRolesSectionProps = {
|
type PolicyUsersRolesSectionProps = {
|
||||||
allRoles: { id: string; text: string }[];
|
orgId: string;
|
||||||
allUsers: { id: string; text: string }[];
|
|
||||||
allIdps: { id: number; text: string }[];
|
allIdps: { id: number; text: string }[];
|
||||||
readonly?: boolean;
|
readonly?: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export function EditPolicyUsersRolesSectionForm({
|
export function EditPolicyUsersRolesSectionForm({
|
||||||
allRoles,
|
orgId,
|
||||||
allUsers,
|
|
||||||
allIdps,
|
allIdps,
|
||||||
readonly
|
readonly
|
||||||
}: PolicyUsersRolesSectionProps) {
|
}: PolicyUsersRolesSectionProps) {
|
||||||
@@ -98,12 +97,6 @@ export function EditPolicyUsersRolesSectionForm({
|
|||||||
control: form.control,
|
control: form.control,
|
||||||
name: "skipToIdpId"
|
name: "skipToIdpId"
|
||||||
});
|
});
|
||||||
const [activeRolesTagIndex, setActiveRolesTagIndex] = useState<
|
|
||||||
number | null
|
|
||||||
>(null);
|
|
||||||
const [activeUsersTagIndex, setActiveUsersTagIndex] = useState<
|
|
||||||
number | null
|
|
||||||
>(null);
|
|
||||||
|
|
||||||
const [, formAction, isSubmitting] = useActionState(onSubmit, null);
|
const [, formAction, isSubmitting] = useActionState(onSubmit, null);
|
||||||
|
|
||||||
@@ -190,43 +183,21 @@ export function EditPolicyUsersRolesSectionForm({
|
|||||||
{t("roles")}
|
{t("roles")}
|
||||||
</FormLabel>
|
</FormLabel>
|
||||||
<FormControl>
|
<FormControl>
|
||||||
<TagInput
|
<RolesSelector
|
||||||
{...field}
|
orgId={orgId}
|
||||||
activeTagIndex={
|
selectedRoles={
|
||||||
activeRolesTagIndex
|
field.value
|
||||||
}
|
}
|
||||||
setActiveTagIndex={
|
onSelectRoles={(
|
||||||
setActiveRolesTagIndex
|
roles
|
||||||
}
|
) =>
|
||||||
placeholder={t(
|
|
||||||
"accessRoleSelect2"
|
|
||||||
)}
|
|
||||||
size="sm"
|
|
||||||
tags={
|
|
||||||
form.getValues()
|
|
||||||
.roles
|
|
||||||
}
|
|
||||||
setTags={(newRoles) => {
|
|
||||||
form.setValue(
|
form.setValue(
|
||||||
"roles",
|
"roles",
|
||||||
newRoles as [
|
roles
|
||||||
Tag,
|
)
|
||||||
...Tag[]
|
|
||||||
]
|
|
||||||
);
|
|
||||||
}}
|
|
||||||
enableAutocomplete={
|
|
||||||
true
|
|
||||||
}
|
}
|
||||||
autocompleteOptions={
|
|
||||||
allRoles
|
|
||||||
}
|
|
||||||
allowDuplicates={false}
|
|
||||||
restrictTagsToAutocompleteOptions={
|
|
||||||
true
|
|
||||||
}
|
|
||||||
sortTags={true}
|
|
||||||
disabled={readonly}
|
disabled={readonly}
|
||||||
|
restrictAdminRole
|
||||||
/>
|
/>
|
||||||
</FormControl>
|
</FormControl>
|
||||||
<FormMessage />
|
<FormMessage />
|
||||||
@@ -247,42 +218,19 @@ export function EditPolicyUsersRolesSectionForm({
|
|||||||
{t("users")}
|
{t("users")}
|
||||||
</FormLabel>
|
</FormLabel>
|
||||||
<FormControl>
|
<FormControl>
|
||||||
<TagInput
|
<UsersSelector
|
||||||
{...field}
|
orgId={orgId}
|
||||||
activeTagIndex={
|
selectedUsers={
|
||||||
activeUsersTagIndex
|
field.value
|
||||||
}
|
}
|
||||||
setActiveTagIndex={
|
onSelectUsers={(
|
||||||
setActiveUsersTagIndex
|
users
|
||||||
}
|
) =>
|
||||||
placeholder={t(
|
|
||||||
"accessUserSelect"
|
|
||||||
)}
|
|
||||||
size="sm"
|
|
||||||
tags={
|
|
||||||
form.getValues()
|
|
||||||
.users
|
|
||||||
}
|
|
||||||
setTags={(newUsers) => {
|
|
||||||
form.setValue(
|
form.setValue(
|
||||||
"users",
|
"users",
|
||||||
newUsers as [
|
users
|
||||||
Tag,
|
)
|
||||||
...Tag[]
|
|
||||||
]
|
|
||||||
);
|
|
||||||
}}
|
|
||||||
enableAutocomplete={
|
|
||||||
true
|
|
||||||
}
|
}
|
||||||
autocompleteOptions={
|
|
||||||
allUsers
|
|
||||||
}
|
|
||||||
allowDuplicates={false}
|
|
||||||
restrictTagsToAutocompleteOptions={
|
|
||||||
true
|
|
||||||
}
|
|
||||||
sortTags={true}
|
|
||||||
disabled={readonly}
|
disabled={readonly}
|
||||||
/>
|
/>
|
||||||
</FormControl>
|
</FormControl>
|
||||||
|
|||||||
@@ -18,12 +18,14 @@ export type UsersSelectorProps = {
|
|||||||
orgId: string;
|
orgId: string;
|
||||||
selectedUsers?: SelectedUser[];
|
selectedUsers?: SelectedUser[];
|
||||||
onSelectUsers: (users: SelectedUser[]) => void;
|
onSelectUsers: (users: SelectedUser[]) => void;
|
||||||
|
disabled?: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export function UsersSelector({
|
export function UsersSelector({
|
||||||
orgId,
|
orgId,
|
||||||
selectedUsers = [],
|
selectedUsers = [],
|
||||||
onSelectUsers
|
onSelectUsers,
|
||||||
|
disabled
|
||||||
}: UsersSelectorProps) {
|
}: UsersSelectorProps) {
|
||||||
const t = useTranslations();
|
const t = useTranslations();
|
||||||
const [userSearchQuery, setUserSearchQuery] = useState("");
|
const [userSearchQuery, setUserSearchQuery] = useState("");
|
||||||
@@ -58,6 +60,7 @@ export function UsersSelector({
|
|||||||
options={usersShown}
|
options={usersShown}
|
||||||
value={selectedUsers}
|
value={selectedUsers}
|
||||||
onChange={onSelectUsers}
|
onChange={onSelectUsers}
|
||||||
|
disabled={disabled}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user