Remove create trust center access mutation from console api

Signed-off-by: Émile Ré <emile@getprobo.com>
This commit is contained in:
Émile Ré
2026-03-05 15:02:49 +04:00
parent 0d1bcd21aa
commit e1fb61979b
11 changed files with 6 additions and 868 deletions

View File

@@ -1,13 +1,11 @@
import { useTranslate } from "@probo/i18n";
import { Button, IconPlusLarge, Spinner, Table, Tbody, Td, Tr, useDialogRef } from "@probo/ui";
import { useState } from "react";
import { Spinner, Table, Tbody, Td, Tr } from "@probo/ui";
import { type PreloadedQuery, usePreloadedQuery } from "react-relay";
import { ConnectionHandler, graphql } from "relay-runtime";
import { graphql } from "relay-runtime";
import type { CompliancePageAccessPageQuery } from "#/__generated__/core/CompliancePageAccessPageQuery.graphql";
import { CompliancePageAccessList } from "./_components/CompliancePageAccessList";
import { NewCompliancePageAccessDialog } from "./_components/NewCompliancePageAccessDialog";
export const compliancePageAccessPageQuery = graphql`
query CompliancePageAccessPageQuery($organizationId: ID!) {
@@ -16,7 +14,6 @@ export const compliancePageAccessPageQuery = graphql`
... on Organization {
compliancePage: trustCenter @required(action: THROW) {
id
canCreateAccess: permission(action: "core:trust-center-access:create")
...CompliancePageAccessListFragment
}
}
@@ -28,20 +25,12 @@ export function CompliancePageAccessPage(props: { queryRef: PreloadedQuery<Compl
const { queryRef } = props;
const { __ } = useTranslate();
const dialogRef = useDialogRef();
const [editingAccessId, setEditingAccessId] = useState<string | null>(null);
const { organization } = usePreloadedQuery<CompliancePageAccessPageQuery>(compliancePageAccessPageQuery, queryRef);
if (organization.__typename !== "Organization") {
throw new Error("invalid type for node");
}
const connectionId = ConnectionHandler.getConnectionID(
organization.compliancePage.id,
"CompliancePageAccessList_accesses",
{ orderBy: { field: "CREATED_AT", direction: "DESC" } },
);
return (
<div className="space-y-4">
<div className="flex items-center justify-between">
@@ -53,23 +42,11 @@ export function CompliancePageAccessPage(props: { queryRef: PreloadedQuery<Compl
)}
</p>
</div>
{organization.compliancePage?.id
&& organization.compliancePage.canCreateAccess && (
<Button
icon={IconPlusLarge}
onClick={() => {
dialogRef.current?.open();
}}
>
{__("Add Access")}
</Button>
)}
</div>
{organization.compliancePage
? (
<CompliancePageAccessList
editingAccessId={editingAccessId}
fragmentRef={organization.compliancePage}
/>
)
@@ -84,13 +61,6 @@ export function CompliancePageAccessPage(props: { queryRef: PreloadedQuery<Compl
</Tbody>
</Table>
)}
<NewCompliancePageAccessDialog
connectionId={connectionId}
compliancePageId={organization.compliancePage.id}
onCreate={setEditingAccessId}
ref={dialogRef}
/>
</div>
);
}

View File

@@ -41,9 +41,8 @@ const fragment = graphql`
export function CompliancePageAccessList(props: {
fragmentRef: CompliancePageAccessListFragment$key;
editingAccessId: string | null;
}) {
const { editingAccessId, fragmentRef } = props;
const { fragmentRef } = props;
const { __ } = useTranslate();
@@ -86,9 +85,8 @@ export function CompliancePageAccessList(props: {
<Tbody>
{accesses.edges.map(({ node: access }) => (
<CompliancePageAccessListItem
key={`${access.id}-${editingAccessId === access.id}`}
key={access.id}
fragmentRef={access}
dialogOpen={editingAccessId === access.id}
/>
))}
</Tbody>

View File

@@ -53,12 +53,11 @@ const toggleAccessStateMutation = graphql`
export function CompliancePageAccessListItem(props: {
fragmentRef: CompliancePageAccessListItemFragment$key;
dialogOpen: boolean;
}) {
const { fragmentRef, dialogOpen: initialDialogOpen } = props;
const { fragmentRef } = props;
const { __ } = useTranslate();
const [dialogOpen, setDialogOpen] = useState<boolean>(initialDialogOpen);
const [dialogOpen, setDialogOpen] = useState<boolean>(false);
const access = useFragment<CompliancePageAccessListItemFragment$key>(fragment, fragmentRef);

View File

@@ -1,127 +0,0 @@
import { useTranslate } from "@probo/i18n";
import { Button, Dialog, DialogContent, DialogFooter, type DialogRef, Field, Spinner } from "@probo/ui";
import { type DataID, graphql } from "relay-runtime";
import { z } from "zod";
import type { NewCompliancePageAccessDialogMutation } from "#/__generated__/core/NewCompliancePageAccessDialogMutation.graphql";
import { useFormWithSchema } from "#/hooks/useFormWithSchema";
import { useMutationWithToasts } from "#/hooks/useMutationWithToasts";
const createCompliancePageAccessMutation = graphql`
mutation NewCompliancePageAccessDialogMutation(
$input: CreateTrustCenterAccessInput!
$connections: [ID!]!
) {
createTrustCenterAccess(input: $input) {
trustCenterAccessEdge @prependEdge(connections: $connections) {
cursor
node {
id
...CompliancePageAccessListItemFragment
}
}
}
}
`;
export function NewCompliancePageAccessDialog(props: {
connectionId: DataID;
compliancePageId: string;
ref: DialogRef;
onCreate: (accessId: string) => void;
}) {
const { connectionId, compliancePageId, ref, onCreate } = props;
const { __ } = useTranslate();
const inviteSchema = z.object({
name: z
.string()
.min(1, __("Name is required"))
.min(2, __("Name must be at least 2 characters long")),
email: z
.string()
.min(1, __("Email is required"))
.email(__("Please enter a valid email address")),
});
const inviteForm = useFormWithSchema(inviteSchema, {
defaultValues: { name: "", email: "" },
});
const [createInvitation, isCreating] = useMutationWithToasts<NewCompliancePageAccessDialogMutation>(
createCompliancePageAccessMutation,
{
successMessage: __("Access created successfully"),
errorMessage: __("Failed to create access"),
},
);
const handleInvite = async (data: z.infer<typeof inviteSchema>) => {
const email = data.email.trim();
await createInvitation({
variables: {
input: {
trustCenterId: compliancePageId,
email: email,
name: data.name.trim(),
},
connections: connectionId ? [connectionId] : [],
},
onCompleted: (response, errors) => {
if (errors?.length) {
return;
}
const newAccess = response.createTrustCenterAccess.trustCenterAccessEdge.node;
onCreate(newAccess.id);
setTimeout(() => {
inviteForm.reset();
ref.current?.close();
}, 50);
setTimeout(() => {
inviteForm.reset();
}, 300);
},
});
};
return (
<Dialog ref={ref} title={__("Invite External Access")}>
<form onSubmit={e => void inviteForm.handleSubmit(handleInvite)(e)}>
<DialogContent padded className="space-y-6">
<div>
<p className="text-txt-secondary text-sm mb-4">
{__("Give a person access to your compliance page")}
</p>
<Field
label={__("Full Name")}
required
error={inviteForm.formState.errors.name?.message}
{...inviteForm.register("name")}
placeholder={__("John Doe")}
/>
<div className="mt-4">
<Field
label={__("Email Address")}
required
error={inviteForm.formState.errors.email?.message}
type="email"
{...inviteForm.register("email")}
placeholder={__("john@example.com")}
/>
</div>
</div>
</DialogContent>
<DialogFooter>
<Button type="submit" disabled={isCreating}>
{isCreating && <Spinner />}
{__("Create Access")}
</Button>
</DialogFooter>
</form>
</Dialog>
);
}