Add document type to the new ui

Signed-off-by: Sacha Al Himdani <sacha@getprobo.com>
This commit is contained in:
Sacha Al Himdani
2025-06-12 18:19:58 -07:00
parent 737accc787
commit c657325295
9 changed files with 96 additions and 18 deletions

View File

@@ -5,8 +5,13 @@ export const documentSchema = z.object({
title: z.string(),
content: z.string(),
ownerId: z.string(),
documentType: z.enum(["OTHER", "ISMS", "POLICY"]),
});
export const useDocumentForm = () => {
return useFormWithSchema(documentSchema, {});
return useFormWithSchema(documentSchema, {
defaultValues: {
documentType: "POLICY",
},
});
};

View File

@@ -1,5 +1,5 @@
/**
* @generated SignedSource<<db2f3c23a3ecbb61ac692a46e93da44a>>
* @generated SignedSource<<3318d21bcfef8523d95b650c01bc7973>>
* @lightSyntaxTransform
* @nogrep
*/
@@ -146,6 +146,13 @@ return {
"name": "description",
"storageKey": null
},
{
"alias": null,
"args": null,
"kind": "ScalarField",
"name": "documentType",
"storageKey": null
},
{
"alias": null,
"args": null,
@@ -333,12 +340,12 @@ return {
]
},
"params": {
"cacheID": "d567583accd89d49f0c40fe1bac5ed84",
"cacheID": "edc04f86b008ac09088a88a6b7918cbe",
"id": null,
"metadata": {},
"name": "DocumentGraphListQuery",
"operationKind": "query",
"text": "query DocumentGraphListQuery(\n $organizationId: ID!\n) {\n organization: node(id: $organizationId) {\n __typename\n id\n ...DocumentsPageListFragment\n }\n}\n\nfragment DocumentsPageListFragment on Organization {\n documents(first: 100) {\n edges {\n node {\n id\n ...DocumentsPageRowFragment\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n }\n }\n}\n\nfragment DocumentsPageRowFragment on Document {\n id\n title\n description\n updatedAt\n owner {\n id\n fullName\n }\n versions(first: 1) {\n edges {\n node {\n id\n status\n signatures(first: 100) {\n edges {\n node {\n id\n state\n }\n }\n }\n }\n }\n }\n}\n"
"text": "query DocumentGraphListQuery(\n $organizationId: ID!\n) {\n organization: node(id: $organizationId) {\n __typename\n id\n ...DocumentsPageListFragment\n }\n}\n\nfragment DocumentsPageListFragment on Organization {\n documents(first: 100) {\n edges {\n node {\n id\n ...DocumentsPageRowFragment\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n }\n }\n}\n\nfragment DocumentsPageRowFragment on Document {\n id\n title\n description\n documentType\n updatedAt\n owner {\n id\n fullName\n }\n versions(first: 1) {\n edges {\n node {\n id\n status\n signatures(first: 100) {\n edges {\n node {\n id\n state\n }\n }\n }\n }\n }\n }\n}\n"
}
};
})();

View File

@@ -1,5 +1,5 @@
/**
* @generated SignedSource<<91fae4ffa86907530e46f054c89f36c3>>
* @generated SignedSource<<5c3e7dba407e37cfc0203138d5db8318>>
* @lightSyntaxTransform
* @nogrep
*/
@@ -186,6 +186,13 @@ return {
"name": "title",
"storageKey": null
},
{
"alias": null,
"args": null,
"kind": "ScalarField",
"name": "documentType",
"storageKey": null
},
{
"alias": null,
"args": null,
@@ -520,12 +527,12 @@ return {
]
},
"params": {
"cacheID": "389866b9db384ce6c9f4e79caab3a6fd",
"cacheID": "ad8c2b55a545807ab1fe72c21ed8f9c1",
"id": null,
"metadata": {},
"name": "DocumentGraphNodeQuery",
"operationKind": "query",
"text": "query DocumentGraphNodeQuery(\n $documentId: ID!\n) {\n node(id: $documentId) {\n __typename\n ... on Document {\n ...DocumentDetailPageDocumentFragment\n }\n id\n }\n}\n\nfragment DocumentControlsTabFragment on Document {\n id\n controls(first: 20) {\n edges {\n node {\n id\n ...LinkedControlsCardFragment\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n hasPreviousPage\n startCursor\n }\n }\n}\n\nfragment DocumentDetailPageDocumentFragment on Document {\n id\n title\n owner {\n id\n fullName\n }\n ...DocumentControlsTabFragment\n controlsInfo: controls(first: 0) {\n totalCount\n }\n versions(first: 20) {\n edges {\n node {\n id\n content\n status\n publishedAt\n version\n updatedAt\n signatures(first: 100) {\n edges {\n node {\n id\n state\n signedBy {\n id\n }\n ...DocumentSignaturesDialog_signature\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n }\n }\n ...DocumentVersionHistoryDialogFragment\n ...DocumentSignaturesDialog_version\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n }\n }\n}\n\nfragment DocumentSignaturesDialog_signature on DocumentVersionSignature {\n id\n state\n signedAt\n requestedAt\n signedBy {\n fullName\n primaryEmailAddress\n id\n }\n}\n\nfragment DocumentSignaturesDialog_version on DocumentVersion {\n version\n status\n publishedAt\n updatedAt\n}\n\nfragment DocumentVersionHistoryDialogFragment on DocumentVersion {\n id\n version\n status\n content\n changelog\n publishedAt\n updatedAt\n publishedBy {\n fullName\n id\n }\n}\n\nfragment LinkedControlsCardFragment on Control {\n id\n name\n sectionTitle\n framework {\n id\n name\n }\n}\n"
"text": "query DocumentGraphNodeQuery(\n $documentId: ID!\n) {\n node(id: $documentId) {\n __typename\n ... on Document {\n ...DocumentDetailPageDocumentFragment\n }\n id\n }\n}\n\nfragment DocumentControlsTabFragment on Document {\n id\n controls(first: 20) {\n edges {\n node {\n id\n ...LinkedControlsCardFragment\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n hasPreviousPage\n startCursor\n }\n }\n}\n\nfragment DocumentDetailPageDocumentFragment on Document {\n id\n title\n documentType\n owner {\n id\n fullName\n }\n ...DocumentControlsTabFragment\n controlsInfo: controls(first: 0) {\n totalCount\n }\n versions(first: 20) {\n edges {\n node {\n id\n content\n status\n publishedAt\n version\n updatedAt\n signatures(first: 100) {\n edges {\n node {\n id\n state\n signedBy {\n id\n }\n ...DocumentSignaturesDialog_signature\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n }\n }\n ...DocumentVersionHistoryDialogFragment\n ...DocumentSignaturesDialog_version\n __typename\n }\n cursor\n }\n pageInfo {\n endCursor\n hasNextPage\n }\n }\n}\n\nfragment DocumentSignaturesDialog_signature on DocumentVersionSignature {\n id\n state\n signedAt\n requestedAt\n signedBy {\n fullName\n primaryEmailAddress\n id\n }\n}\n\nfragment DocumentSignaturesDialog_version on DocumentVersion {\n version\n status\n publishedAt\n updatedAt\n}\n\nfragment DocumentVersionHistoryDialogFragment on DocumentVersion {\n id\n version\n status\n content\n changelog\n publishedAt\n updatedAt\n publishedBy {\n fullName\n id\n }\n}\n\nfragment LinkedControlsCardFragment on Control {\n id\n name\n sectionTitle\n framework {\n id\n name\n }\n}\n"
}
};
})();

View File

@@ -37,7 +37,7 @@ import {
import { useOrganizationId } from "/hooks/useOrganizationId";
import { Button } from "@probo/ui";
import { useMutationWithToasts } from "/hooks/useMutationWithToasts";
import { sprintf } from "@probo/helpers";
import { sprintf, getDocumentTypeLabel } from "@probo/helpers";
import { Outlet, useNavigate } from "react-router";
import UpdateVersionDialog from "./dialogs/UpdateVersionDialog";
import { useRef } from "react";
@@ -52,6 +52,7 @@ const documentFragment = graphql`
fragment DocumentDetailPageDocumentFragment on Document {
id
title
documentType
owner {
id
fullName
@@ -266,6 +267,11 @@ export default function DocumentDetailPage(props: Props) {
{document.owner?.fullName}
</Badge>
</PropertyRow>
<PropertyRow label={__("Type")}>
<div className="text-sm text-txt-secondary">
{getDocumentTypeLabel(__, document.documentType)}
</div>
</PropertyRow>
<PropertyRow label={__("Status")}>
<Badge
variant={isDraft ? "highlight" : "success"}

View File

@@ -29,7 +29,7 @@ import {
} from "/hooks/graph/DocumentGraph";
import type { DocumentsPageListFragment$key } from "./__generated__/DocumentsPageListFragment.graphql";
import { usePageTitle } from "@probo/hooks";
import { sprintf } from "@probo/helpers";
import { sprintf, getDocumentTypeLabel } from "@probo/helpers";
import { CreateDocumentDialog } from "./dialogs/CreateDocumentDialog";
import type { DocumentsPageRowFragment$key } from "./__generated__/DocumentsPageRowFragment.graphql";
@@ -71,7 +71,7 @@ export default function DocumentsPage(props: Props) {
<div className="space-y-6">
<PageHeader
title={__("Documents")}
description={__("Manage your organization’s documents")}
description={__("Manage your organization's documents")}
>
<CreateDocumentDialog
connection={connectionId}
@@ -83,6 +83,7 @@ export default function DocumentsPage(props: Props) {
<Tr>
<Th>{__("Name")}</Th>
<Th>{__("Status")}</Th>
<Th>{__("Type")}</Th>
<Th>{__("Owner")}</Th>
<Th>{__("Last update")}</Th>
<Th>{__("Signatures")}</Th>
@@ -109,6 +110,7 @@ const rowFragment = graphql`
id
title
description
documentType
updatedAt
owner {
id
@@ -195,6 +197,9 @@ function DocumentRow({
{isDraft ? __("Draft") : __("Published")}
</Badge>
</Td>
<Td>
{getDocumentTypeLabel(__, document.documentType)}
</Td>
<Td>
<div className="flex gap-2 items-center">
<Avatar name={document.owner.fullName} />

View File

@@ -1,5 +1,5 @@
/**
* @generated SignedSource<<de19bed523a0a3e24807f5e7ecfef466>>
* @generated SignedSource<<4318aaecefe001fe6f42e6db26c421b4>>
* @lightSyntaxTransform
* @nogrep
*/
@@ -10,12 +10,14 @@
import { ReaderFragment } from 'relay-runtime';
export type DocumentStatus = "DRAFT" | "PUBLISHED";
export type DocumentType = "ISMS" | "OTHER" | "POLICY";
export type DocumentVersionSignatureState = "REQUESTED" | "SIGNED";
import { FragmentRefs } from "relay-runtime";
export type DocumentDetailPageDocumentFragment$data = {
readonly controlsInfo: {
readonly totalCount: number;
};
readonly documentType: DocumentType;
readonly id: string;
readonly owner: {
readonly fullName: string;
@@ -147,6 +149,13 @@ return {
"name": "title",
"storageKey": null
},
{
"alias": null,
"args": null,
"kind": "ScalarField",
"name": "documentType",
"storageKey": null
},
{
"alias": null,
"args": null,
@@ -346,6 +355,6 @@ return {
};
})();
(node as any).hash = "ffd58750acd50c91d62a674ba158836c";
(node as any).hash = "da1a4055d701fa9c3e0e0e50df24860f";
export default node;

View File

@@ -1,5 +1,5 @@
/**
* @generated SignedSource<<394470df6f042c06c640caad2df537cc>>
* @generated SignedSource<<428295a295761694c38d77aa3476d01f>>
* @lightSyntaxTransform
* @nogrep
*/
@@ -10,10 +10,12 @@
import { ReaderFragment } from 'relay-runtime';
export type DocumentStatus = "DRAFT" | "PUBLISHED";
export type DocumentType = "ISMS" | "OTHER" | "POLICY";
export type DocumentVersionSignatureState = "REQUESTED" | "SIGNED";
import { FragmentRefs } from "relay-runtime";
export type DocumentsPageRowFragment$data = {
readonly description: string;
readonly documentType: DocumentType;
readonly id: string;
readonly owner: {
readonly fullName: string;
@@ -73,6 +75,13 @@ return {
"name": "description",
"storageKey": null
},
{
"alias": null,
"args": null,
"kind": "ScalarField",
"name": "documentType",
"storageKey": null
},
{
"alias": null,
"args": null,
@@ -199,6 +208,6 @@ return {
};
})();
(node as any).hash = "b5339e945b607000f177036cad41e0d4";
(node as any).hash = "c8543275dc108732ad2377806efacfc1";
export default node;

View File

@@ -11,6 +11,7 @@ import {
PropertyRow,
Textarea,
useDialogRef,
Option,
} from "@probo/ui";
import { type ReactNode } from "react";
import { graphql } from "relay-runtime";
@@ -19,6 +20,7 @@ import { useDocumentForm } from "/hooks/forms/useDocumentForm";
import { useMutationWithToasts } from "/hooks/useMutationWithToasts";
import { PeopleSelectField } from "/components/form/PeopleSelectField";
import type { CreateDocumentDialogMutation } from "./__generated__/CreateDocumentDialogMutation.graphql";
import { ControlledField } from "/components/form/ControlledField";
type Props = {
trigger?: ReactNode;
@@ -60,7 +62,6 @@ export function CreateDocumentDialog({ trigger, connection }: Props) {
input: {
...data,
organizationId,
documentType: "POLICY",
},
connections: [connection!],
},
@@ -110,6 +111,28 @@ export function CreateDocumentDialog({ trigger, connection }: Props) {
</Badge>
</PropertyRow>
<PropertyRow
id="documentType"
label={__("Type")}
error={errors.documentType?.message}
>
<ControlledField
control={control}
name="documentType"
type="select"
>
<Option value="POLICY">
{__("Policy")}
</Option>
<Option value="ISMS">
{__("ISMS")}
</Option>
<Option value="OTHER">
{__("Other")}
</Option>
</ControlledField>
</PropertyRow>
<PropertyRow
id="ownerId"
label={__("Owner")}

View File

@@ -1,5 +1,5 @@
/**
* @generated SignedSource<<99814a217713cd574beb65c91802dc74>>
* @generated SignedSource<<ce2f4f138b340f04b4e413ecbfff2ea1>>
* @lightSyntaxTransform
* @nogrep
*/
@@ -163,6 +163,13 @@ return {
"name": "description",
"storageKey": null
},
{
"alias": null,
"args": null,
"kind": "ScalarField",
"name": "documentType",
"storageKey": null
},
{
"alias": null,
"args": null,
@@ -311,12 +318,12 @@ return {
]
},
"params": {
"cacheID": "d535d393c2ab2e1a9798d193bcc8c17f",
"cacheID": "e60a87953e4157e808e0d4ce4436ed3b",
"id": null,
"metadata": {},
"name": "CreateDocumentDialogMutation",
"operationKind": "mutation",
"text": "mutation CreateDocumentDialogMutation(\n $input: CreateDocumentInput!\n) {\n createDocument(input: $input) {\n documentEdge {\n node {\n id\n ...DocumentsPageRowFragment\n }\n }\n }\n}\n\nfragment DocumentsPageRowFragment on Document {\n id\n title\n description\n updatedAt\n owner {\n id\n fullName\n }\n versions(first: 1) {\n edges {\n node {\n id\n status\n signatures(first: 100) {\n edges {\n node {\n id\n state\n }\n }\n }\n }\n }\n }\n}\n"
"text": "mutation CreateDocumentDialogMutation(\n $input: CreateDocumentInput!\n) {\n createDocument(input: $input) {\n documentEdge {\n node {\n id\n ...DocumentsPageRowFragment\n }\n }\n }\n}\n\nfragment DocumentsPageRowFragment on Document {\n id\n title\n description\n documentType\n updatedAt\n owner {\n id\n fullName\n }\n versions(first: 1) {\n edges {\n node {\n id\n status\n signatures(first: 100) {\n edges {\n node {\n id\n state\n }\n }\n }\n }\n }\n }\n}\n"
}
};
})();