Add trust center configuration
Signed-off-by: Sacha Al Himdani <sacha@getprobo.com>
This commit is contained in:
@@ -0,0 +1,175 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import {
|
||||||
|
Card,
|
||||||
|
Button,
|
||||||
|
Tr,
|
||||||
|
Td,
|
||||||
|
Table,
|
||||||
|
Thead,
|
||||||
|
Tbody,
|
||||||
|
Th,
|
||||||
|
IconChevronDown,
|
||||||
|
IconCheckmark1,
|
||||||
|
IconCrossLargeX,
|
||||||
|
Badge,
|
||||||
|
} from "@probo/ui";
|
||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import { useFragment } from "react-relay";
|
||||||
|
import { useMemo, useState } from "react";
|
||||||
|
import { sprintf, getAuditStateVariant, getAuditStateLabel } from "@probo/helpers";
|
||||||
|
import { useOrganizationId } from "/hooks/useOrganizationId";
|
||||||
|
import clsx from "clsx";
|
||||||
|
import type { TrustCenterAuditsCardFragment$key } from "./__generated__/TrustCenterAuditsCardFragment.graphql";
|
||||||
|
|
||||||
|
const trustCenterAuditFragment = graphql`
|
||||||
|
fragment TrustCenterAuditsCardFragment on Audit {
|
||||||
|
id
|
||||||
|
framework {
|
||||||
|
name
|
||||||
|
}
|
||||||
|
validFrom
|
||||||
|
validUntil
|
||||||
|
state
|
||||||
|
showOnTrustCenter
|
||||||
|
createdAt
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
type Mutation<Params> = (p: {
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
id: string;
|
||||||
|
showOnTrustCenter: boolean;
|
||||||
|
} & Params;
|
||||||
|
};
|
||||||
|
}) => void;
|
||||||
|
|
||||||
|
type Props<Params> = {
|
||||||
|
audits: TrustCenterAuditsCardFragment$key[];
|
||||||
|
params: Params;
|
||||||
|
disabled?: boolean;
|
||||||
|
onToggleVisibility: Mutation<Params>;
|
||||||
|
variant?: "card" | "table";
|
||||||
|
};
|
||||||
|
|
||||||
|
export function TrustCenterAuditsCard<Params>(props: Props<Params>) {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
const [limit, setLimit] = useState<number | null>(4);
|
||||||
|
const audits = useMemo(() => {
|
||||||
|
return limit ? props.audits.slice(0, limit) : props.audits;
|
||||||
|
}, [props.audits, limit]);
|
||||||
|
const showMoreButton = limit !== null && props.audits.length > limit;
|
||||||
|
const variant = props.variant ?? "table";
|
||||||
|
|
||||||
|
const onToggleVisibility = (auditId: string, showOnTrustCenter: boolean) => {
|
||||||
|
props.onToggleVisibility({
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
id: auditId,
|
||||||
|
showOnTrustCenter,
|
||||||
|
...props.params,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const Wrapper = variant === "card" ? Card : "div";
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Wrapper {...(variant === "card" ? { padded: true } : {})} className="space-y-[10px]">
|
||||||
|
<Table className={clsx(variant === "card" && "bg-invert")}>
|
||||||
|
<Thead>
|
||||||
|
<Tr>
|
||||||
|
<Th>{__("Framework")}</Th>
|
||||||
|
<Th>{__("Valid Until")}</Th>
|
||||||
|
<Th>{__("State")}</Th>
|
||||||
|
<Th>{__("Visibility")}</Th>
|
||||||
|
<Th></Th>
|
||||||
|
</Tr>
|
||||||
|
</Thead>
|
||||||
|
<Tbody>
|
||||||
|
{audits.length === 0 && (
|
||||||
|
<Tr>
|
||||||
|
<Td colSpan={5} className="text-center text-txt-secondary">
|
||||||
|
{__("No audits available")}
|
||||||
|
</Td>
|
||||||
|
</Tr>
|
||||||
|
)}
|
||||||
|
{audits.map((audit, index) => (
|
||||||
|
<AuditRow
|
||||||
|
key={index}
|
||||||
|
audit={audit}
|
||||||
|
onToggleVisibility={onToggleVisibility}
|
||||||
|
disabled={props.disabled}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
</Tbody>
|
||||||
|
</Table>
|
||||||
|
{showMoreButton && (
|
||||||
|
<Button
|
||||||
|
variant="tertiary"
|
||||||
|
onClick={() => setLimit(null)}
|
||||||
|
className="mt-3 mx-auto"
|
||||||
|
icon={IconChevronDown}
|
||||||
|
>
|
||||||
|
{sprintf(__("Show %s more"), props.audits.length - limit)}
|
||||||
|
</Button>
|
||||||
|
)}
|
||||||
|
</Wrapper>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function AuditRow(props: {
|
||||||
|
audit: TrustCenterAuditsCardFragment$key;
|
||||||
|
onToggleVisibility: (auditId: string, showOnTrustCenter: boolean) => void;
|
||||||
|
disabled?: boolean;
|
||||||
|
}) {
|
||||||
|
const audit = useFragment(trustCenterAuditFragment, props.audit);
|
||||||
|
const organizationId = useOrganizationId();
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
const validUntilFormatted = audit.validUntil
|
||||||
|
? new Date(audit.validUntil).toLocaleDateString()
|
||||||
|
: __("No expiry");
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Tr to={`/organizations/${organizationId}/audits/${audit.id}`}>
|
||||||
|
<Td>
|
||||||
|
<div className="flex gap-4 items-center">
|
||||||
|
{audit.framework.name}
|
||||||
|
</div>
|
||||||
|
</Td>
|
||||||
|
<Td>{validUntilFormatted}</Td>
|
||||||
|
<Td>
|
||||||
|
<Badge variant={getAuditStateVariant(audit.state)}>
|
||||||
|
{getAuditStateLabel(__, audit.state)}
|
||||||
|
</Badge>
|
||||||
|
</Td>
|
||||||
|
<Td>
|
||||||
|
<div className="flex items-center gap-2">
|
||||||
|
{audit.showOnTrustCenter ? (
|
||||||
|
<>
|
||||||
|
<IconCheckmark1 className="w-4 h-4 text-txt-primary" />
|
||||||
|
<span className="text-txt-primary">{__("Visible")}</span>
|
||||||
|
</>
|
||||||
|
) : (
|
||||||
|
<>
|
||||||
|
<IconCrossLargeX className="w-4 h-4 text-txt-tertiary" />
|
||||||
|
<span className="text-txt-tertiary">{__("Hidden")}</span>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</Td>
|
||||||
|
<Td noLink width={100} className="text-end">
|
||||||
|
<Button
|
||||||
|
variant="secondary"
|
||||||
|
onClick={() => props.onToggleVisibility(audit.id, !audit.showOnTrustCenter)}
|
||||||
|
icon={audit.showOnTrustCenter ? IconCrossLargeX : IconCheckmark1}
|
||||||
|
disabled={props.disabled}
|
||||||
|
>
|
||||||
|
{audit.showOnTrustCenter ? __("Hide") : __("Show")}
|
||||||
|
</Button>
|
||||||
|
</Td>
|
||||||
|
</Tr>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -0,0 +1,99 @@
|
|||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import {
|
||||||
|
Dialog,
|
||||||
|
DialogContent,
|
||||||
|
DialogFooter,
|
||||||
|
Button,
|
||||||
|
useDialogRef,
|
||||||
|
} from "@probo/ui";
|
||||||
|
import { type ReactNode } from "react";
|
||||||
|
import { useFragment, graphql } from "react-relay";
|
||||||
|
import type { TrustCenterDocumentsCardFragment$key } from "./__generated__/TrustCenterDocumentsCardFragment.graphql";
|
||||||
|
|
||||||
|
const trustCenterDocumentDialogFragment = graphql`
|
||||||
|
fragment TrustCenterDocumentDialogFragment on Document {
|
||||||
|
id
|
||||||
|
title
|
||||||
|
showOnTrustCenter
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
type Props = {
|
||||||
|
children: ReactNode;
|
||||||
|
documents: (TrustCenterDocumentsCardFragment$key & { id: string })[];
|
||||||
|
onToggleVisibility: (documentId: string, showOnTrustCenter: boolean) => void;
|
||||||
|
disabled?: boolean;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default function TrustCenterDocumentDialog({
|
||||||
|
children,
|
||||||
|
documents,
|
||||||
|
onToggleVisibility,
|
||||||
|
disabled,
|
||||||
|
}: Props) {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
const dialogRef = useDialogRef();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<span onClick={() => !disabled && dialogRef.current?.open()}>
|
||||||
|
{children}
|
||||||
|
</span>
|
||||||
|
<Dialog ref={dialogRef}>
|
||||||
|
<DialogContent>
|
||||||
|
<div className="text-lg font-semibold mb-4">
|
||||||
|
{__("Manage Document Visibility on Trust Center")}
|
||||||
|
</div>
|
||||||
|
<div className="py-4">
|
||||||
|
<p className="text-txt-secondary mb-4">
|
||||||
|
{__("Control which documents are visible on your public trust center.")}
|
||||||
|
</p>
|
||||||
|
<div className="space-y-2 max-h-96 overflow-y-auto">
|
||||||
|
{documents.map((documentKey) => (
|
||||||
|
<DocumentDialogRow
|
||||||
|
key={documentKey.id}
|
||||||
|
document={documentKey}
|
||||||
|
onToggleVisibility={onToggleVisibility}
|
||||||
|
disabled={disabled}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<DialogFooter>
|
||||||
|
<Button onClick={() => dialogRef.current?.close()}>
|
||||||
|
{__("Close")}
|
||||||
|
</Button>
|
||||||
|
</DialogFooter>
|
||||||
|
</DialogContent>
|
||||||
|
</Dialog>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function DocumentDialogRow({
|
||||||
|
document: documentKey,
|
||||||
|
onToggleVisibility,
|
||||||
|
disabled,
|
||||||
|
}: {
|
||||||
|
document: TrustCenterDocumentsCardFragment$key & { id: string };
|
||||||
|
onToggleVisibility: (documentId: string, showOnTrustCenter: boolean) => void;
|
||||||
|
disabled?: boolean;
|
||||||
|
}) {
|
||||||
|
const document = useFragment(trustCenterDocumentDialogFragment, documentKey);
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="flex items-center justify-between p-3 border border-border-solid rounded">
|
||||||
|
<div className="flex-1">
|
||||||
|
<div className="font-medium">{document.title}</div>
|
||||||
|
</div>
|
||||||
|
<Button
|
||||||
|
variant="secondary"
|
||||||
|
onClick={() => onToggleVisibility(document.id, !document.showOnTrustCenter)}
|
||||||
|
disabled={disabled}
|
||||||
|
>
|
||||||
|
{document.showOnTrustCenter ? __("Hide") : __("Show")}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -0,0 +1,177 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import {
|
||||||
|
Card,
|
||||||
|
Button,
|
||||||
|
Tr,
|
||||||
|
Td,
|
||||||
|
Table,
|
||||||
|
Thead,
|
||||||
|
Tbody,
|
||||||
|
Th,
|
||||||
|
IconChevronDown,
|
||||||
|
IconCheckmark1,
|
||||||
|
IconCrossLargeX,
|
||||||
|
DocumentVersionBadge,
|
||||||
|
DocumentTypeBadge,
|
||||||
|
} from "@probo/ui";
|
||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import type { TrustCenterDocumentsCardFragment$key } from "./__generated__/TrustCenterDocumentsCardFragment.graphql";
|
||||||
|
import { useFragment } from "react-relay";
|
||||||
|
import { useMemo, useState } from "react";
|
||||||
|
import { sprintf } from "@probo/helpers";
|
||||||
|
import { useOrganizationId } from "/hooks/useOrganizationId";
|
||||||
|
import clsx from "clsx";
|
||||||
|
|
||||||
|
const trustCenterDocumentFragment = graphql`
|
||||||
|
fragment TrustCenterDocumentsCardFragment on Document {
|
||||||
|
id
|
||||||
|
title
|
||||||
|
createdAt
|
||||||
|
documentType
|
||||||
|
showOnTrustCenter
|
||||||
|
versions(first: 1) {
|
||||||
|
edges {
|
||||||
|
node {
|
||||||
|
id
|
||||||
|
status
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
type Mutation<Params> = (p: {
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
id: string;
|
||||||
|
showOnTrustCenter: boolean;
|
||||||
|
} & Params;
|
||||||
|
};
|
||||||
|
}) => void;
|
||||||
|
|
||||||
|
type Props<Params> = {
|
||||||
|
documents: TrustCenterDocumentsCardFragment$key[];
|
||||||
|
params: Params;
|
||||||
|
disabled?: boolean;
|
||||||
|
onToggleVisibility: Mutation<Params>;
|
||||||
|
variant?: "card" | "table";
|
||||||
|
};
|
||||||
|
|
||||||
|
export function TrustCenterDocumentsCard<Params>(props: Props<Params>) {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
const [limit, setLimit] = useState<number | null>(4);
|
||||||
|
const documents = useMemo(() => {
|
||||||
|
return limit ? props.documents.slice(0, limit) : props.documents;
|
||||||
|
}, [props.documents, limit]);
|
||||||
|
const showMoreButton = limit !== null && props.documents.length > limit;
|
||||||
|
const variant = props.variant ?? "table";
|
||||||
|
|
||||||
|
const onToggleVisibility = (documentId: string, showOnTrustCenter: boolean) => {
|
||||||
|
props.onToggleVisibility({
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
id: documentId,
|
||||||
|
showOnTrustCenter,
|
||||||
|
...props.params,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const Wrapper = variant === "card" ? Card : "div";
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Wrapper padded className="space-y-[10px]">
|
||||||
|
<Table className={clsx(variant === "card" && "bg-invert")}>
|
||||||
|
<Thead>
|
||||||
|
<Tr>
|
||||||
|
<Th>{__("Name")}</Th>
|
||||||
|
<Th>{__("Type")}</Th>
|
||||||
|
<Th>{__("State")}</Th>
|
||||||
|
<Th>{__("Visibility")}</Th>
|
||||||
|
<Th></Th>
|
||||||
|
</Tr>
|
||||||
|
</Thead>
|
||||||
|
<Tbody>
|
||||||
|
{documents.length === 0 && (
|
||||||
|
<Tr>
|
||||||
|
<Td colSpan={5} className="text-center text-txt-secondary">
|
||||||
|
{__("No documents available")}
|
||||||
|
</Td>
|
||||||
|
</Tr>
|
||||||
|
)}
|
||||||
|
{documents.map((document, index) => (
|
||||||
|
<DocumentRow
|
||||||
|
key={index}
|
||||||
|
document={document}
|
||||||
|
onToggleVisibility={onToggleVisibility}
|
||||||
|
disabled={props.disabled}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
|
||||||
|
</Tbody>
|
||||||
|
</Table>
|
||||||
|
{showMoreButton && (
|
||||||
|
<Button
|
||||||
|
variant="tertiary"
|
||||||
|
onClick={() => setLimit(null)}
|
||||||
|
className="mt-3 mx-auto"
|
||||||
|
icon={IconChevronDown}
|
||||||
|
>
|
||||||
|
{sprintf(__("Show %s more"), props.documents.length - limit)}
|
||||||
|
</Button>
|
||||||
|
)}
|
||||||
|
</Wrapper>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function DocumentRow(props: {
|
||||||
|
document: TrustCenterDocumentsCardFragment$key;
|
||||||
|
onToggleVisibility: (documentId: string, showOnTrustCenter: boolean) => void;
|
||||||
|
disabled?: boolean;
|
||||||
|
}) {
|
||||||
|
const document = useFragment(trustCenterDocumentFragment, props.document);
|
||||||
|
const organizationId = useOrganizationId();
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Tr to={`/organizations/${organizationId}/documents/${document.id}`}>
|
||||||
|
<Td>
|
||||||
|
<div className="flex gap-4 items-center">
|
||||||
|
{document.title}
|
||||||
|
</div>
|
||||||
|
</Td>
|
||||||
|
<Td>
|
||||||
|
<DocumentTypeBadge type={document.documentType} />
|
||||||
|
</Td>
|
||||||
|
<Td>
|
||||||
|
<DocumentVersionBadge state={document.versions?.edges?.[0]?.node?.status} />
|
||||||
|
</Td>
|
||||||
|
<Td>
|
||||||
|
<div className="flex items-center gap-2">
|
||||||
|
{document.showOnTrustCenter ? (
|
||||||
|
<>
|
||||||
|
<IconCheckmark1 className="w-4 h-4 text-txt-primary" />
|
||||||
|
<span className="text-txt-primary">{__("Visible")}</span>
|
||||||
|
</>
|
||||||
|
) : (
|
||||||
|
<>
|
||||||
|
<IconCrossLargeX className="w-4 h-4 text-txt-tertiary" />
|
||||||
|
<span className="text-txt-tertiary">{__("Hidden")}</span>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</Td>
|
||||||
|
<Td noLink width={100} className="text-end">
|
||||||
|
<Button
|
||||||
|
variant="secondary"
|
||||||
|
onClick={() => props.onToggleVisibility(document.id, !document.showOnTrustCenter)}
|
||||||
|
icon={document.showOnTrustCenter ? IconCrossLargeX : IconCheckmark1}
|
||||||
|
disabled={props.disabled}
|
||||||
|
>
|
||||||
|
{document.showOnTrustCenter ? __("Hide") : __("Show")}
|
||||||
|
</Button>
|
||||||
|
</Td>
|
||||||
|
</Tr>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -0,0 +1,166 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import {
|
||||||
|
Card,
|
||||||
|
Button,
|
||||||
|
Tr,
|
||||||
|
Td,
|
||||||
|
Table,
|
||||||
|
Thead,
|
||||||
|
Tbody,
|
||||||
|
Th,
|
||||||
|
IconChevronDown,
|
||||||
|
IconCheckmark1,
|
||||||
|
IconCrossLargeX,
|
||||||
|
Badge,
|
||||||
|
} from "@probo/ui";
|
||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import { useFragment } from "react-relay";
|
||||||
|
import { useMemo, useState } from "react";
|
||||||
|
import { sprintf } from "@probo/helpers";
|
||||||
|
import { useOrganizationId } from "/hooks/useOrganizationId";
|
||||||
|
import clsx from "clsx";
|
||||||
|
import type { TrustCenterVendorsCardFragment$key } from "./__generated__/TrustCenterVendorsCardFragment.graphql";
|
||||||
|
|
||||||
|
const trustCenterVendorFragment = graphql`
|
||||||
|
fragment TrustCenterVendorsCardFragment on Vendor {
|
||||||
|
id
|
||||||
|
name
|
||||||
|
category
|
||||||
|
description
|
||||||
|
showOnTrustCenter
|
||||||
|
createdAt
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
type Mutation<Params> = (p: {
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
id: string;
|
||||||
|
showOnTrustCenter: boolean;
|
||||||
|
} & Params;
|
||||||
|
};
|
||||||
|
}) => void;
|
||||||
|
|
||||||
|
type Props<Params> = {
|
||||||
|
vendors: TrustCenterVendorsCardFragment$key[];
|
||||||
|
params: Params;
|
||||||
|
disabled?: boolean;
|
||||||
|
onToggleVisibility: Mutation<Params>;
|
||||||
|
variant?: "card" | "table";
|
||||||
|
};
|
||||||
|
|
||||||
|
export function TrustCenterVendorsCard<Params>(props: Props<Params>) {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
const [limit, setLimit] = useState<number | null>(4);
|
||||||
|
const vendors = useMemo(() => {
|
||||||
|
return limit ? props.vendors.slice(0, limit) : props.vendors;
|
||||||
|
}, [props.vendors, limit]);
|
||||||
|
const showMoreButton = limit !== null && props.vendors.length > limit;
|
||||||
|
const variant = props.variant ?? "table";
|
||||||
|
|
||||||
|
const onToggleVisibility = (vendorId: string, showOnTrustCenter: boolean) => {
|
||||||
|
props.onToggleVisibility({
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
id: vendorId,
|
||||||
|
showOnTrustCenter,
|
||||||
|
...props.params,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const Wrapper = variant === "card" ? Card : "div";
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Wrapper padded className="space-y-[10px]">
|
||||||
|
<Table className={clsx(variant === "card" && "bg-invert")}>
|
||||||
|
<Thead>
|
||||||
|
<Tr>
|
||||||
|
<Th>{__("Name")}</Th>
|
||||||
|
<Th>{__("Category")}</Th>
|
||||||
|
<Th>{__("Visibility")}</Th>
|
||||||
|
<Th></Th>
|
||||||
|
</Tr>
|
||||||
|
</Thead>
|
||||||
|
<Tbody>
|
||||||
|
{vendors.length === 0 && (
|
||||||
|
<Tr>
|
||||||
|
<Td colSpan={4} className="text-center text-txt-secondary">
|
||||||
|
{__("No vendors available")}
|
||||||
|
</Td>
|
||||||
|
</Tr>
|
||||||
|
)}
|
||||||
|
{vendors.map((vendor, index) => (
|
||||||
|
<VendorRow
|
||||||
|
key={index}
|
||||||
|
vendor={vendor}
|
||||||
|
onToggleVisibility={onToggleVisibility}
|
||||||
|
disabled={props.disabled}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
</Tbody>
|
||||||
|
</Table>
|
||||||
|
{showMoreButton && (
|
||||||
|
<Button
|
||||||
|
variant="tertiary"
|
||||||
|
onClick={() => setLimit(null)}
|
||||||
|
className="mt-3 mx-auto"
|
||||||
|
icon={IconChevronDown}
|
||||||
|
>
|
||||||
|
{sprintf(__("Show %s more"), props.vendors.length - limit)}
|
||||||
|
</Button>
|
||||||
|
)}
|
||||||
|
</Wrapper>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function VendorRow(props: {
|
||||||
|
vendor: TrustCenterVendorsCardFragment$key;
|
||||||
|
onToggleVisibility: (vendorId: string, showOnTrustCenter: boolean) => void;
|
||||||
|
disabled?: boolean;
|
||||||
|
}) {
|
||||||
|
const vendor = useFragment(trustCenterVendorFragment, props.vendor);
|
||||||
|
const organizationId = useOrganizationId();
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Tr to={`/organizations/${organizationId}/vendors/${vendor.id}`}>
|
||||||
|
<Td>
|
||||||
|
<div className="flex gap-4 items-center">
|
||||||
|
{vendor.name}
|
||||||
|
</div>
|
||||||
|
</Td>
|
||||||
|
<Td>
|
||||||
|
<Badge variant="neutral">
|
||||||
|
{vendor.category}
|
||||||
|
</Badge>
|
||||||
|
</Td>
|
||||||
|
<Td>
|
||||||
|
<div className="flex items-center gap-2">
|
||||||
|
{vendor.showOnTrustCenter ? (
|
||||||
|
<>
|
||||||
|
<IconCheckmark1 className="w-4 h-4 text-txt-primary" />
|
||||||
|
<span className="text-txt-primary">{__("Visible")}</span>
|
||||||
|
</>
|
||||||
|
) : (
|
||||||
|
<>
|
||||||
|
<IconCrossLargeX className="w-4 h-4 text-txt-tertiary" />
|
||||||
|
<span className="text-txt-tertiary">{__("Hidden")}</span>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</Td>
|
||||||
|
<Td noLink width={100} className="text-end">
|
||||||
|
<Button
|
||||||
|
variant="secondary"
|
||||||
|
onClick={() => props.onToggleVisibility(vendor.id, !vendor.showOnTrustCenter)}
|
||||||
|
icon={vendor.showOnTrustCenter ? IconCrossLargeX : IconCheckmark1}
|
||||||
|
disabled={props.disabled}
|
||||||
|
>
|
||||||
|
{vendor.showOnTrustCenter ? __("Hide") : __("Show")}
|
||||||
|
</Button>
|
||||||
|
</Td>
|
||||||
|
</Tr>
|
||||||
|
);
|
||||||
|
}
|
||||||
104
apps/console/src/components/trustCenter/__generated__/TrustCenterAuditsCardFragment.graphql.ts
generated
Normal file
104
apps/console/src/components/trustCenter/__generated__/TrustCenterAuditsCardFragment.graphql.ts
generated
Normal file
@@ -0,0 +1,104 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<794277d17daabd92807ccfaa5a1c2dbb>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ReaderFragment } from 'relay-runtime';
|
||||||
|
export type AuditState = "COMPLETED" | "IN_PROGRESS" | "NOT_STARTED" | "OUTDATED" | "REJECTED";
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type TrustCenterAuditsCardFragment$data = {
|
||||||
|
readonly createdAt: any;
|
||||||
|
readonly framework: {
|
||||||
|
readonly name: string;
|
||||||
|
};
|
||||||
|
readonly id: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
readonly state: AuditState;
|
||||||
|
readonly validFrom: any | null | undefined;
|
||||||
|
readonly validUntil: any | null | undefined;
|
||||||
|
readonly " $fragmentType": "TrustCenterAuditsCardFragment";
|
||||||
|
};
|
||||||
|
export type TrustCenterAuditsCardFragment$key = {
|
||||||
|
readonly " $data"?: TrustCenterAuditsCardFragment$data;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterAuditsCardFragment">;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ReaderFragment = {
|
||||||
|
"argumentDefinitions": [],
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterAuditsCardFragment",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Framework",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "framework",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "name",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "validFrom",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "validUntil",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "state",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "createdAt",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Audit",
|
||||||
|
"abstractKey": null
|
||||||
|
};
|
||||||
|
|
||||||
|
(node as any).hash = "9c9291dffd5c057c0e70e2567a897362";
|
||||||
|
|
||||||
|
export default node;
|
||||||
58
apps/console/src/components/trustCenter/__generated__/TrustCenterDocumentDialogFragment.graphql.ts
generated
Normal file
58
apps/console/src/components/trustCenter/__generated__/TrustCenterDocumentDialogFragment.graphql.ts
generated
Normal file
@@ -0,0 +1,58 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<3ff483dcc660e6b45d676db7fc05a30e>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ReaderFragment } from 'relay-runtime';
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type TrustCenterDocumentDialogFragment$data = {
|
||||||
|
readonly id: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
readonly title: string;
|
||||||
|
readonly " $fragmentType": "TrustCenterDocumentDialogFragment";
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentDialogFragment$key = {
|
||||||
|
readonly " $data"?: TrustCenterDocumentDialogFragment$data;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterDocumentDialogFragment">;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ReaderFragment = {
|
||||||
|
"argumentDefinitions": [],
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterDocumentDialogFragment",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "title",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Document",
|
||||||
|
"abstractKey": null
|
||||||
|
};
|
||||||
|
|
||||||
|
(node as any).hash = "d886df25fdf197161a91bbc693c9fac8";
|
||||||
|
|
||||||
|
export default node;
|
||||||
134
apps/console/src/components/trustCenter/__generated__/TrustCenterDocumentsCardFragment.graphql.ts
generated
Normal file
134
apps/console/src/components/trustCenter/__generated__/TrustCenterDocumentsCardFragment.graphql.ts
generated
Normal file
@@ -0,0 +1,134 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<711a0b67f3e93814ae3297a2578373c6>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ReaderFragment } from 'relay-runtime';
|
||||||
|
export type DocumentStatus = "DRAFT" | "PUBLISHED";
|
||||||
|
export type DocumentType = "ISMS" | "OTHER" | "POLICY";
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type TrustCenterDocumentsCardFragment$data = {
|
||||||
|
readonly createdAt: any;
|
||||||
|
readonly documentType: DocumentType;
|
||||||
|
readonly id: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
readonly title: string;
|
||||||
|
readonly versions: {
|
||||||
|
readonly edges: ReadonlyArray<{
|
||||||
|
readonly node: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly status: DocumentStatus;
|
||||||
|
};
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
readonly " $fragmentType": "TrustCenterDocumentsCardFragment";
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentsCardFragment$key = {
|
||||||
|
readonly " $data"?: TrustCenterDocumentsCardFragment$data;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterDocumentsCardFragment">;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ReaderFragment = (function(){
|
||||||
|
var v0 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
};
|
||||||
|
return {
|
||||||
|
"argumentDefinitions": [],
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterDocumentsCardFragment",
|
||||||
|
"selections": [
|
||||||
|
(v0/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "title",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "createdAt",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "documentType",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Literal",
|
||||||
|
"name": "first",
|
||||||
|
"value": 1
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "DocumentVersionConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "versions",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersionEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersion",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v0/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "status",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "versions(first:1)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Document",
|
||||||
|
"abstractKey": null
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "88d5e5e3a2d9f4b730428efcea644f25";
|
||||||
|
|
||||||
|
export default node;
|
||||||
83
apps/console/src/components/trustCenter/__generated__/TrustCenterVendorsCardFragment.graphql.ts
generated
Normal file
83
apps/console/src/components/trustCenter/__generated__/TrustCenterVendorsCardFragment.graphql.ts
generated
Normal file
@@ -0,0 +1,83 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<b3d65d827fc901aa002b24df72f79ee2>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ReaderFragment } from 'relay-runtime';
|
||||||
|
export type VendorCategory = "ANALYTICS" | "CLOUD_MONITORING" | "CLOUD_PROVIDER" | "COLLABORATION" | "CUSTOMER_SUPPORT" | "DATA_STORAGE_AND_PROCESSING" | "DOCUMENT_MANAGEMENT" | "EMPLOYEE_MANAGEMENT" | "ENGINEERING" | "FINANCE" | "IDENTITY_PROVIDER" | "IT" | "MARKETING" | "OFFICE_OPERATIONS" | "OTHER" | "PASSWORD_MANAGEMENT" | "PRODUCT_AND_DESIGN" | "PROFESSIONAL_SERVICES" | "RECRUITING" | "SALES" | "SECURITY" | "VERSION_CONTROL";
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type TrustCenterVendorsCardFragment$data = {
|
||||||
|
readonly category: VendorCategory;
|
||||||
|
readonly createdAt: any;
|
||||||
|
readonly description: string | null | undefined;
|
||||||
|
readonly id: string;
|
||||||
|
readonly name: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
readonly " $fragmentType": "TrustCenterVendorsCardFragment";
|
||||||
|
};
|
||||||
|
export type TrustCenterVendorsCardFragment$key = {
|
||||||
|
readonly " $data"?: TrustCenterVendorsCardFragment$data;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterVendorsCardFragment">;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ReaderFragment = {
|
||||||
|
"argumentDefinitions": [],
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterVendorsCardFragment",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "name",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "category",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "description",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "createdAt",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Vendor",
|
||||||
|
"abstractKey": null
|
||||||
|
};
|
||||||
|
|
||||||
|
(node as any).hash = "72b637589fd9299b5e982450fccbfd12";
|
||||||
|
|
||||||
|
export default node;
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
/**
|
/**
|
||||||
* @generated SignedSource<<95aa70195a3e90acb366441fd037c2f2>>
|
* @generated SignedSource<<faa26838a242a98d5df14f51ff257950>>
|
||||||
* @lightSyntaxTransform
|
* @lightSyntaxTransform
|
||||||
* @nogrep
|
* @nogrep
|
||||||
*/
|
*/
|
||||||
@@ -26,6 +26,7 @@ export type UpdateVendorInput = {
|
|||||||
securityOwnerId?: string | null | undefined;
|
securityOwnerId?: string | null | undefined;
|
||||||
securityPageUrl?: string | null | undefined;
|
securityPageUrl?: string | null | undefined;
|
||||||
serviceLevelAgreementUrl?: string | null | undefined;
|
serviceLevelAgreementUrl?: string | null | undefined;
|
||||||
|
showOnTrustCenter?: boolean | null | undefined;
|
||||||
statusPageUrl?: string | null | undefined;
|
statusPageUrl?: string | null | undefined;
|
||||||
subprocessorsListUrl?: string | null | undefined;
|
subprocessorsListUrl?: string | null | undefined;
|
||||||
termsOfServiceUrl?: string | null | undefined;
|
termsOfServiceUrl?: string | null | undefined;
|
||||||
|
|||||||
28
apps/console/src/hooks/graph/TrustCenterAuditGraph.ts
Normal file
28
apps/console/src/hooks/graph/TrustCenterAuditGraph.ts
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import { useMutationWithToasts } from "/hooks/useMutationWithToasts";
|
||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import type { TrustCenterAuditGraphUpdateMutation } from "./__generated__/TrustCenterAuditGraphUpdateMutation.graphql";
|
||||||
|
|
||||||
|
export const trustCenterAuditUpdateMutation = graphql`
|
||||||
|
mutation TrustCenterAuditGraphUpdateMutation($input: UpdateAuditInput!) {
|
||||||
|
updateAudit(input: $input) {
|
||||||
|
audit {
|
||||||
|
id
|
||||||
|
showOnTrustCenter
|
||||||
|
...TrustCenterAuditsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
export function useTrustCenterAuditUpdate() {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
return useMutationWithToasts<TrustCenterAuditGraphUpdateMutation>(
|
||||||
|
trustCenterAuditUpdateMutation,
|
||||||
|
{
|
||||||
|
successMessage: __("Audit visibility updated successfully."),
|
||||||
|
errorMessage: __("Failed to update audit visibility. Please try again."),
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
46
apps/console/src/hooks/graph/TrustCenterDocumentGraph.ts
Normal file
46
apps/console/src/hooks/graph/TrustCenterDocumentGraph.ts
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import { useMutationWithToasts } from "/hooks/useMutationWithToasts";
|
||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import type { TrustCenterDocumentGraphUpdateMutation } from "./__generated__/TrustCenterDocumentGraphUpdateMutation.graphql";
|
||||||
|
|
||||||
|
export const trustCenterDocumentsQuery = graphql`
|
||||||
|
query TrustCenterDocumentGraphQuery($organizationId: ID!) {
|
||||||
|
organization: node(id: $organizationId) {
|
||||||
|
... on Organization {
|
||||||
|
id
|
||||||
|
documents(first: 100) {
|
||||||
|
edges {
|
||||||
|
node {
|
||||||
|
id
|
||||||
|
...TrustCenterDocumentsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
export const updateDocumentVisibilityMutation = graphql`
|
||||||
|
mutation TrustCenterDocumentGraphUpdateMutation($input: UpdateDocumentInput!) {
|
||||||
|
updateDocument(input: $input) {
|
||||||
|
document {
|
||||||
|
id
|
||||||
|
showOnTrustCenter
|
||||||
|
...TrustCenterDocumentsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
export function useUpdateDocumentVisibilityMutation() {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
return useMutationWithToasts<TrustCenterDocumentGraphUpdateMutation>(
|
||||||
|
updateDocumentVisibilityMutation,
|
||||||
|
{
|
||||||
|
successMessage: __("Document visibility updated successfully."),
|
||||||
|
errorMessage: __("Failed to update document visibility. Please try again."),
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
68
apps/console/src/hooks/graph/TrustCenterGraph.ts
Normal file
68
apps/console/src/hooks/graph/TrustCenterGraph.ts
Normal file
@@ -0,0 +1,68 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import { useMutationWithToasts } from "/hooks/useMutationWithToasts";
|
||||||
|
import type { TrustCenterGraphUpdateMutation } from "./__generated__/TrustCenterGraphUpdateMutation.graphql";
|
||||||
|
|
||||||
|
export const trustCenterQuery = graphql`
|
||||||
|
query TrustCenterGraphQuery($organizationId: ID!) {
|
||||||
|
organization: node(id: $organizationId) {
|
||||||
|
... on Organization {
|
||||||
|
id
|
||||||
|
name
|
||||||
|
trustCenter {
|
||||||
|
id
|
||||||
|
active
|
||||||
|
slug
|
||||||
|
createdAt
|
||||||
|
updatedAt
|
||||||
|
}
|
||||||
|
documents(first: 100) {
|
||||||
|
edges {
|
||||||
|
node {
|
||||||
|
id
|
||||||
|
...TrustCenterDocumentsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
audits(first: 100) {
|
||||||
|
edges {
|
||||||
|
node {
|
||||||
|
id
|
||||||
|
...TrustCenterAuditsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
vendors(first: 100) {
|
||||||
|
edges {
|
||||||
|
node {
|
||||||
|
id
|
||||||
|
...TrustCenterVendorsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
export const updateTrustCenterMutation = graphql`
|
||||||
|
mutation TrustCenterGraphUpdateMutation($input: UpdateTrustCenterInput!) {
|
||||||
|
updateTrustCenter(input: $input) {
|
||||||
|
trustCenter {
|
||||||
|
id
|
||||||
|
active
|
||||||
|
slug
|
||||||
|
updatedAt
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
export function useUpdateTrustCenterMutation() {
|
||||||
|
return useMutationWithToasts<TrustCenterGraphUpdateMutation>(
|
||||||
|
updateTrustCenterMutation,
|
||||||
|
{
|
||||||
|
successMessage: "Trust center updated successfully",
|
||||||
|
errorMessage: "Failed to update trust center",
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
28
apps/console/src/hooks/graph/TrustCenterVendorGraph.ts
Normal file
28
apps/console/src/hooks/graph/TrustCenterVendorGraph.ts
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
import { graphql } from "relay-runtime";
|
||||||
|
import { useMutationWithToasts } from "/hooks/useMutationWithToasts";
|
||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import type { TrustCenterVendorGraphUpdateMutation } from "./__generated__/TrustCenterVendorGraphUpdateMutation.graphql";
|
||||||
|
|
||||||
|
export const trustCenterVendorUpdateMutation = graphql`
|
||||||
|
mutation TrustCenterVendorGraphUpdateMutation($input: UpdateVendorInput!) {
|
||||||
|
updateVendor(input: $input) {
|
||||||
|
vendor {
|
||||||
|
id
|
||||||
|
showOnTrustCenter
|
||||||
|
...TrustCenterVendorsCardFragment
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
`;
|
||||||
|
|
||||||
|
export function useTrustCenterVendorUpdate() {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
|
||||||
|
return useMutationWithToasts<TrustCenterVendorGraphUpdateMutation>(
|
||||||
|
trustCenterVendorUpdateMutation,
|
||||||
|
{
|
||||||
|
successMessage: __("Vendor visibility updated successfully."),
|
||||||
|
errorMessage: __("Failed to update vendor visibility. Please try again."),
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
/**
|
/**
|
||||||
* @generated SignedSource<<f55547fed473a026bb7c43be28a2c6dc>>
|
* @generated SignedSource<<d2c542541d5bfda5464af2b34ccae603>>
|
||||||
* @lightSyntaxTransform
|
* @lightSyntaxTransform
|
||||||
* @nogrep
|
* @nogrep
|
||||||
*/
|
*/
|
||||||
@@ -12,6 +12,7 @@ import { ConcreteRequest } from 'relay-runtime';
|
|||||||
export type AuditState = "COMPLETED" | "IN_PROGRESS" | "NOT_STARTED" | "OUTDATED" | "REJECTED";
|
export type AuditState = "COMPLETED" | "IN_PROGRESS" | "NOT_STARTED" | "OUTDATED" | "REJECTED";
|
||||||
export type UpdateAuditInput = {
|
export type UpdateAuditInput = {
|
||||||
id: string;
|
id: string;
|
||||||
|
showOnTrustCenter?: boolean | null | undefined;
|
||||||
state?: AuditState | null | undefined;
|
state?: AuditState | null | undefined;
|
||||||
validFrom?: any | null | undefined;
|
validFrom?: any | null | undefined;
|
||||||
validUntil?: any | null | undefined;
|
validUntil?: any | null | undefined;
|
||||||
|
|||||||
118
apps/console/src/hooks/graph/__generated__/TrustCenterAuditGraphUpdateMutation.graphql.ts
generated
Normal file
118
apps/console/src/hooks/graph/__generated__/TrustCenterAuditGraphUpdateMutation.graphql.ts
generated
Normal file
@@ -0,0 +1,118 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<92803a3585816e3db509c46a86d083e9>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ConcreteRequest } from 'relay-runtime';
|
||||||
|
export type AuditState = "COMPLETED" | "IN_PROGRESS" | "NOT_STARTED" | "OUTDATED" | "REJECTED";
|
||||||
|
export type UpdateAuditInput = {
|
||||||
|
id: string;
|
||||||
|
showOnTrustCenter?: boolean | null | undefined;
|
||||||
|
state?: AuditState | null | undefined;
|
||||||
|
validFrom?: any | null | undefined;
|
||||||
|
validUntil?: any | null | undefined;
|
||||||
|
};
|
||||||
|
export type TrustCenterAuditGraphUpdateMutation$variables = {
|
||||||
|
input: UpdateAuditInput;
|
||||||
|
};
|
||||||
|
export type TrustCenterAuditGraphUpdateMutation$data = {
|
||||||
|
readonly updateAudit: {
|
||||||
|
readonly audit: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
export type TrustCenterAuditGraphUpdateMutation = {
|
||||||
|
response: TrustCenterAuditGraphUpdateMutation$data;
|
||||||
|
variables: TrustCenterAuditGraphUpdateMutation$variables;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ConcreteRequest = (function(){
|
||||||
|
var v0 = [
|
||||||
|
{
|
||||||
|
"defaultValue": null,
|
||||||
|
"kind": "LocalArgument",
|
||||||
|
"name": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v1 = [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Variable",
|
||||||
|
"name": "input",
|
||||||
|
"variableName": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "UpdateAuditPayload",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "updateAudit",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Audit",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "audit",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
];
|
||||||
|
return {
|
||||||
|
"fragment": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterAuditGraphUpdateMutation",
|
||||||
|
"selections": (v1/*: any*/),
|
||||||
|
"type": "Mutation",
|
||||||
|
"abstractKey": null
|
||||||
|
},
|
||||||
|
"kind": "Request",
|
||||||
|
"operation": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Operation",
|
||||||
|
"name": "TrustCenterAuditGraphUpdateMutation",
|
||||||
|
"selections": (v1/*: any*/)
|
||||||
|
},
|
||||||
|
"params": {
|
||||||
|
"cacheID": "1ecc930abe6daebb184b1e55ccebc65c",
|
||||||
|
"id": null,
|
||||||
|
"metadata": {},
|
||||||
|
"name": "TrustCenterAuditGraphUpdateMutation",
|
||||||
|
"operationKind": "mutation",
|
||||||
|
"text": "mutation TrustCenterAuditGraphUpdateMutation(\n $input: UpdateAuditInput!\n) {\n updateAudit(input: $input) {\n audit {\n id\n showOnTrustCenter\n }\n }\n}\n"
|
||||||
|
}
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "ebf90264b72bb993d60f48d1d3fc4fb7";
|
||||||
|
|
||||||
|
export default node;
|
||||||
288
apps/console/src/hooks/graph/__generated__/TrustCenterDocumentGraphQuery.graphql.ts
generated
Normal file
288
apps/console/src/hooks/graph/__generated__/TrustCenterDocumentGraphQuery.graphql.ts
generated
Normal file
@@ -0,0 +1,288 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<6676a9b480eeef26f00ff97963b39b86>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ConcreteRequest } from 'relay-runtime';
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type TrustCenterDocumentGraphQuery$variables = {
|
||||||
|
organizationId: string;
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentGraphQuery$data = {
|
||||||
|
readonly organization: {
|
||||||
|
readonly documents?: {
|
||||||
|
readonly edges: ReadonlyArray<{
|
||||||
|
readonly node: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterDocumentsCardFragment">;
|
||||||
|
};
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
readonly id?: string;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentGraphQuery = {
|
||||||
|
response: TrustCenterDocumentGraphQuery$data;
|
||||||
|
variables: TrustCenterDocumentGraphQuery$variables;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ConcreteRequest = (function(){
|
||||||
|
var v0 = [
|
||||||
|
{
|
||||||
|
"defaultValue": null,
|
||||||
|
"kind": "LocalArgument",
|
||||||
|
"name": "organizationId"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v1 = [
|
||||||
|
{
|
||||||
|
"kind": "Variable",
|
||||||
|
"name": "id",
|
||||||
|
"variableName": "organizationId"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v2 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
v3 = [
|
||||||
|
{
|
||||||
|
"kind": "Literal",
|
||||||
|
"name": "first",
|
||||||
|
"value": 100
|
||||||
|
}
|
||||||
|
];
|
||||||
|
return {
|
||||||
|
"fragment": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterDocumentGraphQuery",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": "organization",
|
||||||
|
"args": (v1/*: any*/),
|
||||||
|
"concreteType": null,
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"kind": "InlineFragment",
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v3/*: any*/),
|
||||||
|
"concreteType": "DocumentConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "documents",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Document",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"args": null,
|
||||||
|
"kind": "FragmentSpread",
|
||||||
|
"name": "TrustCenterDocumentsCardFragment"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "documents(first:100)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Organization",
|
||||||
|
"abstractKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Query",
|
||||||
|
"abstractKey": null
|
||||||
|
},
|
||||||
|
"kind": "Request",
|
||||||
|
"operation": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Operation",
|
||||||
|
"name": "TrustCenterDocumentGraphQuery",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": "organization",
|
||||||
|
"args": (v1/*: any*/),
|
||||||
|
"concreteType": null,
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "__typename",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"kind": "InlineFragment",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v3/*: any*/),
|
||||||
|
"concreteType": "DocumentConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "documents",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Document",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "title",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "createdAt",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "documentType",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Literal",
|
||||||
|
"name": "first",
|
||||||
|
"value": 1
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "DocumentVersionConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "versions",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersionEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersion",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "status",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "versions(first:1)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "documents(first:100)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Organization",
|
||||||
|
"abstractKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"params": {
|
||||||
|
"cacheID": "f8e5f4d7adcf1e794bc046ef21317f89",
|
||||||
|
"id": null,
|
||||||
|
"metadata": {},
|
||||||
|
"name": "TrustCenterDocumentGraphQuery",
|
||||||
|
"operationKind": "query",
|
||||||
|
"text": "query TrustCenterDocumentGraphQuery(\n $organizationId: ID!\n) {\n organization: node(id: $organizationId) {\n __typename\n ... on Organization {\n id\n documents(first: 100) {\n edges {\n node {\n id\n ...TrustCenterDocumentsCardFragment\n }\n }\n }\n }\n id\n }\n}\n\nfragment TrustCenterDocumentsCardFragment on Document {\n id\n title\n createdAt\n documentType\n showOnTrustCenter\n versions(first: 1) {\n edges {\n node {\n id\n status\n }\n }\n }\n}\n"
|
||||||
|
}
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "f4e34ac09a2b56c2298bc319d9701f4d";
|
||||||
|
|
||||||
|
export default node;
|
||||||
222
apps/console/src/hooks/graph/__generated__/TrustCenterDocumentGraphUpdateMutation.graphql.ts
generated
Normal file
222
apps/console/src/hooks/graph/__generated__/TrustCenterDocumentGraphUpdateMutation.graphql.ts
generated
Normal file
@@ -0,0 +1,222 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<5b8f324da8c4dc9302cb6f821062757d>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ConcreteRequest } from 'relay-runtime';
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type DocumentType = "ISMS" | "OTHER" | "POLICY";
|
||||||
|
export type UpdateDocumentInput = {
|
||||||
|
content?: string | null | undefined;
|
||||||
|
createdBy?: string | null | undefined;
|
||||||
|
documentType?: DocumentType | null | undefined;
|
||||||
|
id: string;
|
||||||
|
ownerId?: string | null | undefined;
|
||||||
|
showOnTrustCenter?: boolean | null | undefined;
|
||||||
|
title?: string | null | undefined;
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentGraphUpdateMutation$variables = {
|
||||||
|
input: UpdateDocumentInput;
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentGraphUpdateMutation$data = {
|
||||||
|
readonly updateDocument: {
|
||||||
|
readonly document: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterDocumentsCardFragment">;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
export type TrustCenterDocumentGraphUpdateMutation = {
|
||||||
|
response: TrustCenterDocumentGraphUpdateMutation$data;
|
||||||
|
variables: TrustCenterDocumentGraphUpdateMutation$variables;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ConcreteRequest = (function(){
|
||||||
|
var v0 = [
|
||||||
|
{
|
||||||
|
"defaultValue": null,
|
||||||
|
"kind": "LocalArgument",
|
||||||
|
"name": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v1 = [
|
||||||
|
{
|
||||||
|
"kind": "Variable",
|
||||||
|
"name": "input",
|
||||||
|
"variableName": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v2 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
v3 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
};
|
||||||
|
return {
|
||||||
|
"fragment": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterDocumentGraphUpdateMutation",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v1/*: any*/),
|
||||||
|
"concreteType": "UpdateDocumentPayload",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "updateDocument",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Document",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "document",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
(v3/*: any*/),
|
||||||
|
{
|
||||||
|
"args": null,
|
||||||
|
"kind": "FragmentSpread",
|
||||||
|
"name": "TrustCenterDocumentsCardFragment"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Mutation",
|
||||||
|
"abstractKey": null
|
||||||
|
},
|
||||||
|
"kind": "Request",
|
||||||
|
"operation": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Operation",
|
||||||
|
"name": "TrustCenterDocumentGraphUpdateMutation",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v1/*: any*/),
|
||||||
|
"concreteType": "UpdateDocumentPayload",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "updateDocument",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Document",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "document",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
(v3/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "title",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "createdAt",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "documentType",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Literal",
|
||||||
|
"name": "first",
|
||||||
|
"value": 1
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "DocumentVersionConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "versions",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersionEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersion",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "status",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "versions(first:1)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"params": {
|
||||||
|
"cacheID": "b112314d6ef35feebf49bd2f8c636b33",
|
||||||
|
"id": null,
|
||||||
|
"metadata": {},
|
||||||
|
"name": "TrustCenterDocumentGraphUpdateMutation",
|
||||||
|
"operationKind": "mutation",
|
||||||
|
"text": "mutation TrustCenterDocumentGraphUpdateMutation(\n $input: UpdateDocumentInput!\n) {\n updateDocument(input: $input) {\n document {\n id\n showOnTrustCenter\n ...TrustCenterDocumentsCardFragment\n }\n }\n}\n\nfragment TrustCenterDocumentsCardFragment on Document {\n id\n title\n createdAt\n documentType\n showOnTrustCenter\n versions(first: 1) {\n edges {\n node {\n id\n status\n }\n }\n }\n}\n"
|
||||||
|
}
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "46f72a664d3edb0e5665b1ecea69e31a";
|
||||||
|
|
||||||
|
export default node;
|
||||||
558
apps/console/src/hooks/graph/__generated__/TrustCenterGraphQuery.graphql.ts
generated
Normal file
558
apps/console/src/hooks/graph/__generated__/TrustCenterGraphQuery.graphql.ts
generated
Normal file
@@ -0,0 +1,558 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<46a922efef96e5c7d015bd0f27467bf3>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ConcreteRequest } from 'relay-runtime';
|
||||||
|
import { FragmentRefs } from "relay-runtime";
|
||||||
|
export type TrustCenterGraphQuery$variables = {
|
||||||
|
organizationId: string;
|
||||||
|
};
|
||||||
|
export type TrustCenterGraphQuery$data = {
|
||||||
|
readonly organization: {
|
||||||
|
readonly audits?: {
|
||||||
|
readonly edges: ReadonlyArray<{
|
||||||
|
readonly node: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterAuditsCardFragment">;
|
||||||
|
};
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
readonly documents?: {
|
||||||
|
readonly edges: ReadonlyArray<{
|
||||||
|
readonly node: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterDocumentsCardFragment">;
|
||||||
|
};
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
readonly id?: string;
|
||||||
|
readonly name?: string;
|
||||||
|
readonly trustCenter?: {
|
||||||
|
readonly active: boolean;
|
||||||
|
readonly createdAt: any;
|
||||||
|
readonly id: string;
|
||||||
|
readonly slug: string;
|
||||||
|
readonly updatedAt: any;
|
||||||
|
} | null | undefined;
|
||||||
|
readonly vendors?: {
|
||||||
|
readonly edges: ReadonlyArray<{
|
||||||
|
readonly node: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly " $fragmentSpreads": FragmentRefs<"TrustCenterVendorsCardFragment">;
|
||||||
|
};
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
export type TrustCenterGraphQuery = {
|
||||||
|
response: TrustCenterGraphQuery$data;
|
||||||
|
variables: TrustCenterGraphQuery$variables;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ConcreteRequest = (function(){
|
||||||
|
var v0 = [
|
||||||
|
{
|
||||||
|
"defaultValue": null,
|
||||||
|
"kind": "LocalArgument",
|
||||||
|
"name": "organizationId"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v1 = [
|
||||||
|
{
|
||||||
|
"kind": "Variable",
|
||||||
|
"name": "id",
|
||||||
|
"variableName": "organizationId"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v2 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
v3 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "name",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
v4 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "createdAt",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
v5 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "TrustCenter",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "trustCenter",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "active",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "slug",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v4/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "updatedAt",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
v6 = [
|
||||||
|
{
|
||||||
|
"kind": "Literal",
|
||||||
|
"name": "first",
|
||||||
|
"value": 100
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v7 = {
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
};
|
||||||
|
return {
|
||||||
|
"fragment": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterGraphQuery",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": "organization",
|
||||||
|
"args": (v1/*: any*/),
|
||||||
|
"concreteType": null,
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"kind": "InlineFragment",
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
(v3/*: any*/),
|
||||||
|
(v5/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v6/*: any*/),
|
||||||
|
"concreteType": "DocumentConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "documents",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Document",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"args": null,
|
||||||
|
"kind": "FragmentSpread",
|
||||||
|
"name": "TrustCenterDocumentsCardFragment"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "documents(first:100)"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v6/*: any*/),
|
||||||
|
"concreteType": "AuditConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "audits",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "AuditEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Audit",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"args": null,
|
||||||
|
"kind": "FragmentSpread",
|
||||||
|
"name": "TrustCenterAuditsCardFragment"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "audits(first:100)"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v6/*: any*/),
|
||||||
|
"concreteType": "VendorConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "vendors",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "VendorEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Vendor",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"args": null,
|
||||||
|
"kind": "FragmentSpread",
|
||||||
|
"name": "TrustCenterVendorsCardFragment"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "vendors(first:100)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Organization",
|
||||||
|
"abstractKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Query",
|
||||||
|
"abstractKey": null
|
||||||
|
},
|
||||||
|
"kind": "Request",
|
||||||
|
"operation": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Operation",
|
||||||
|
"name": "TrustCenterGraphQuery",
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": "organization",
|
||||||
|
"args": (v1/*: any*/),
|
||||||
|
"concreteType": null,
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "__typename",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"kind": "InlineFragment",
|
||||||
|
"selections": [
|
||||||
|
(v3/*: any*/),
|
||||||
|
(v5/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v6/*: any*/),
|
||||||
|
"concreteType": "DocumentConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "documents",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Document",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "title",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v4/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "documentType",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v7/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Literal",
|
||||||
|
"name": "first",
|
||||||
|
"value": 1
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "DocumentVersionConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "versions",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersionEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "DocumentVersion",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "status",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "versions(first:1)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "documents(first:100)"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v6/*: any*/),
|
||||||
|
"concreteType": "AuditConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "audits",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "AuditEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Audit",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Framework",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "framework",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v3/*: any*/),
|
||||||
|
(v2/*: any*/)
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "validFrom",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "validUntil",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "state",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v7/*: any*/),
|
||||||
|
(v4/*: any*/)
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "audits(first:100)"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": (v6/*: any*/),
|
||||||
|
"concreteType": "VendorConnection",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "vendors",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "VendorEdge",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "edges",
|
||||||
|
"plural": true,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Vendor",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "node",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
(v2/*: any*/),
|
||||||
|
(v3/*: any*/),
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "category",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "description",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
(v7/*: any*/),
|
||||||
|
(v4/*: any*/)
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": "vendors(first:100)"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"type": "Organization",
|
||||||
|
"abstractKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"params": {
|
||||||
|
"cacheID": "a22d734ee326d24f3f67ffecf4653b2f",
|
||||||
|
"id": null,
|
||||||
|
"metadata": {},
|
||||||
|
"name": "TrustCenterGraphQuery",
|
||||||
|
"operationKind": "query",
|
||||||
|
"text": "query TrustCenterGraphQuery(\n $organizationId: ID!\n) {\n organization: node(id: $organizationId) {\n __typename\n ... on Organization {\n id\n name\n trustCenter {\n id\n active\n slug\n createdAt\n updatedAt\n }\n documents(first: 100) {\n edges {\n node {\n id\n ...TrustCenterDocumentsCardFragment\n }\n }\n }\n audits(first: 100) {\n edges {\n node {\n id\n ...TrustCenterAuditsCardFragment\n }\n }\n }\n vendors(first: 100) {\n edges {\n node {\n id\n ...TrustCenterVendorsCardFragment\n }\n }\n }\n }\n id\n }\n}\n\nfragment TrustCenterAuditsCardFragment on Audit {\n id\n framework {\n name\n id\n }\n validFrom\n validUntil\n state\n showOnTrustCenter\n createdAt\n}\n\nfragment TrustCenterDocumentsCardFragment on Document {\n id\n title\n createdAt\n documentType\n showOnTrustCenter\n versions(first: 1) {\n edges {\n node {\n id\n status\n }\n }\n }\n}\n\nfragment TrustCenterVendorsCardFragment on Vendor {\n id\n name\n category\n description\n showOnTrustCenter\n createdAt\n}\n"
|
||||||
|
}
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "260529b3ca03240b07989f278bb7a539";
|
||||||
|
|
||||||
|
export default node;
|
||||||
131
apps/console/src/hooks/graph/__generated__/TrustCenterGraphUpdateMutation.graphql.ts
generated
Normal file
131
apps/console/src/hooks/graph/__generated__/TrustCenterGraphUpdateMutation.graphql.ts
generated
Normal file
@@ -0,0 +1,131 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<c257950f58c4b876a6ff7ef6083f005b>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ConcreteRequest } from 'relay-runtime';
|
||||||
|
export type UpdateTrustCenterInput = {
|
||||||
|
active?: boolean | null | undefined;
|
||||||
|
slug?: string | null | undefined;
|
||||||
|
trustCenterId: string;
|
||||||
|
};
|
||||||
|
export type TrustCenterGraphUpdateMutation$variables = {
|
||||||
|
input: UpdateTrustCenterInput;
|
||||||
|
};
|
||||||
|
export type TrustCenterGraphUpdateMutation$data = {
|
||||||
|
readonly updateTrustCenter: {
|
||||||
|
readonly trustCenter: {
|
||||||
|
readonly active: boolean;
|
||||||
|
readonly id: string;
|
||||||
|
readonly slug: string;
|
||||||
|
readonly updatedAt: any;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
export type TrustCenterGraphUpdateMutation = {
|
||||||
|
response: TrustCenterGraphUpdateMutation$data;
|
||||||
|
variables: TrustCenterGraphUpdateMutation$variables;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ConcreteRequest = (function(){
|
||||||
|
var v0 = [
|
||||||
|
{
|
||||||
|
"defaultValue": null,
|
||||||
|
"kind": "LocalArgument",
|
||||||
|
"name": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v1 = [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Variable",
|
||||||
|
"name": "input",
|
||||||
|
"variableName": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "UpdateTrustCenterPayload",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "updateTrustCenter",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "TrustCenter",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "trustCenter",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "active",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "slug",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "updatedAt",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
];
|
||||||
|
return {
|
||||||
|
"fragment": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterGraphUpdateMutation",
|
||||||
|
"selections": (v1/*: any*/),
|
||||||
|
"type": "Mutation",
|
||||||
|
"abstractKey": null
|
||||||
|
},
|
||||||
|
"kind": "Request",
|
||||||
|
"operation": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Operation",
|
||||||
|
"name": "TrustCenterGraphUpdateMutation",
|
||||||
|
"selections": (v1/*: any*/)
|
||||||
|
},
|
||||||
|
"params": {
|
||||||
|
"cacheID": "18e80937923185923d9b427819334337",
|
||||||
|
"id": null,
|
||||||
|
"metadata": {},
|
||||||
|
"name": "TrustCenterGraphUpdateMutation",
|
||||||
|
"operationKind": "mutation",
|
||||||
|
"text": "mutation TrustCenterGraphUpdateMutation(\n $input: UpdateTrustCenterInput!\n) {\n updateTrustCenter(input: $input) {\n trustCenter {\n id\n active\n slug\n updatedAt\n }\n }\n}\n"
|
||||||
|
}
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "988f3baf354e729d6cc9482129040898";
|
||||||
|
|
||||||
|
export default node;
|
||||||
133
apps/console/src/hooks/graph/__generated__/TrustCenterVendorGraphUpdateMutation.graphql.ts
generated
Normal file
133
apps/console/src/hooks/graph/__generated__/TrustCenterVendorGraphUpdateMutation.graphql.ts
generated
Normal file
@@ -0,0 +1,133 @@
|
|||||||
|
/**
|
||||||
|
* @generated SignedSource<<012c4e605372a38efef4780c63d40888>>
|
||||||
|
* @lightSyntaxTransform
|
||||||
|
* @nogrep
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* tslint:disable */
|
||||||
|
/* eslint-disable */
|
||||||
|
// @ts-nocheck
|
||||||
|
|
||||||
|
import { ConcreteRequest } from 'relay-runtime';
|
||||||
|
export type VendorCategory = "ANALYTICS" | "CLOUD_MONITORING" | "CLOUD_PROVIDER" | "COLLABORATION" | "CUSTOMER_SUPPORT" | "DATA_STORAGE_AND_PROCESSING" | "DOCUMENT_MANAGEMENT" | "EMPLOYEE_MANAGEMENT" | "ENGINEERING" | "FINANCE" | "IDENTITY_PROVIDER" | "IT" | "MARKETING" | "OFFICE_OPERATIONS" | "OTHER" | "PASSWORD_MANAGEMENT" | "PRODUCT_AND_DESIGN" | "PROFESSIONAL_SERVICES" | "RECRUITING" | "SALES" | "SECURITY" | "VERSION_CONTROL";
|
||||||
|
export type UpdateVendorInput = {
|
||||||
|
businessAssociateAgreementUrl?: string | null | undefined;
|
||||||
|
businessOwnerId?: string | null | undefined;
|
||||||
|
category?: VendorCategory | null | undefined;
|
||||||
|
certifications?: ReadonlyArray<string> | null | undefined;
|
||||||
|
dataProcessingAgreementUrl?: string | null | undefined;
|
||||||
|
description?: string | null | undefined;
|
||||||
|
headquarterAddress?: string | null | undefined;
|
||||||
|
id: string;
|
||||||
|
legalName?: string | null | undefined;
|
||||||
|
name?: string | null | undefined;
|
||||||
|
privacyPolicyUrl?: string | null | undefined;
|
||||||
|
securityOwnerId?: string | null | undefined;
|
||||||
|
securityPageUrl?: string | null | undefined;
|
||||||
|
serviceLevelAgreementUrl?: string | null | undefined;
|
||||||
|
showOnTrustCenter?: boolean | null | undefined;
|
||||||
|
statusPageUrl?: string | null | undefined;
|
||||||
|
subprocessorsListUrl?: string | null | undefined;
|
||||||
|
termsOfServiceUrl?: string | null | undefined;
|
||||||
|
trustPageUrl?: string | null | undefined;
|
||||||
|
websiteUrl?: string | null | undefined;
|
||||||
|
};
|
||||||
|
export type TrustCenterVendorGraphUpdateMutation$variables = {
|
||||||
|
input: UpdateVendorInput;
|
||||||
|
};
|
||||||
|
export type TrustCenterVendorGraphUpdateMutation$data = {
|
||||||
|
readonly updateVendor: {
|
||||||
|
readonly vendor: {
|
||||||
|
readonly id: string;
|
||||||
|
readonly showOnTrustCenter: boolean;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
export type TrustCenterVendorGraphUpdateMutation = {
|
||||||
|
response: TrustCenterVendorGraphUpdateMutation$data;
|
||||||
|
variables: TrustCenterVendorGraphUpdateMutation$variables;
|
||||||
|
};
|
||||||
|
|
||||||
|
const node: ConcreteRequest = (function(){
|
||||||
|
var v0 = [
|
||||||
|
{
|
||||||
|
"defaultValue": null,
|
||||||
|
"kind": "LocalArgument",
|
||||||
|
"name": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
v1 = [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": [
|
||||||
|
{
|
||||||
|
"kind": "Variable",
|
||||||
|
"name": "input",
|
||||||
|
"variableName": "input"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"concreteType": "UpdateVendorPayload",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "updateVendor",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"concreteType": "Vendor",
|
||||||
|
"kind": "LinkedField",
|
||||||
|
"name": "vendor",
|
||||||
|
"plural": false,
|
||||||
|
"selections": [
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "id",
|
||||||
|
"storageKey": null
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"alias": null,
|
||||||
|
"args": null,
|
||||||
|
"kind": "ScalarField",
|
||||||
|
"name": "showOnTrustCenter",
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"storageKey": null
|
||||||
|
}
|
||||||
|
];
|
||||||
|
return {
|
||||||
|
"fragment": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Fragment",
|
||||||
|
"metadata": null,
|
||||||
|
"name": "TrustCenterVendorGraphUpdateMutation",
|
||||||
|
"selections": (v1/*: any*/),
|
||||||
|
"type": "Mutation",
|
||||||
|
"abstractKey": null
|
||||||
|
},
|
||||||
|
"kind": "Request",
|
||||||
|
"operation": {
|
||||||
|
"argumentDefinitions": (v0/*: any*/),
|
||||||
|
"kind": "Operation",
|
||||||
|
"name": "TrustCenterVendorGraphUpdateMutation",
|
||||||
|
"selections": (v1/*: any*/)
|
||||||
|
},
|
||||||
|
"params": {
|
||||||
|
"cacheID": "44e483af96833ea9efb1567fa5983282",
|
||||||
|
"id": null,
|
||||||
|
"metadata": {},
|
||||||
|
"name": "TrustCenterVendorGraphUpdateMutation",
|
||||||
|
"operationKind": "mutation",
|
||||||
|
"text": "mutation TrustCenterVendorGraphUpdateMutation(\n $input: UpdateVendorInput!\n) {\n updateVendor(input: $input) {\n vendor {\n id\n showOnTrustCenter\n }\n }\n}\n"
|
||||||
|
}
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
|
||||||
|
(node as any).hash = "e561918e67c08f1e3fae85dfb04591d1";
|
||||||
|
|
||||||
|
export default node;
|
||||||
@@ -14,6 +14,7 @@ import {
|
|||||||
IconTodo,
|
IconTodo,
|
||||||
IconListStack,
|
IconListStack,
|
||||||
IconBox,
|
IconBox,
|
||||||
|
IconShield,
|
||||||
Layout,
|
Layout,
|
||||||
SidebarItem,
|
SidebarItem,
|
||||||
UserDropdown as UserDropdownRoot,
|
UserDropdown as UserDropdownRoot,
|
||||||
@@ -137,6 +138,11 @@ export function MainLayout() {
|
|||||||
icon={IconCheckmark1}
|
icon={IconCheckmark1}
|
||||||
to={`${prefix}/audits`}
|
to={`${prefix}/audits`}
|
||||||
/>
|
/>
|
||||||
|
<SidebarItem
|
||||||
|
label={__("Trust Center")}
|
||||||
|
icon={IconShield}
|
||||||
|
to={`${prefix}/trust-center`}
|
||||||
|
/>
|
||||||
<SidebarItem
|
<SidebarItem
|
||||||
label={__("Settings")}
|
label={__("Settings")}
|
||||||
icon={IconSettingsGear2}
|
icon={IconSettingsGear2}
|
||||||
|
|||||||
240
apps/console/src/pages/organizations/TrustCenterPage.tsx
Normal file
240
apps/console/src/pages/organizations/TrustCenterPage.tsx
Normal file
@@ -0,0 +1,240 @@
|
|||||||
|
import { useTranslate } from "@probo/i18n";
|
||||||
|
import { usePageTitle } from "@probo/hooks";
|
||||||
|
import {
|
||||||
|
Button,
|
||||||
|
Card,
|
||||||
|
Checkbox,
|
||||||
|
Field,
|
||||||
|
Input,
|
||||||
|
PageHeader,
|
||||||
|
Spinner,
|
||||||
|
useToast,
|
||||||
|
Tabs,
|
||||||
|
TabLink,
|
||||||
|
TabItem,
|
||||||
|
} from "@probo/ui";
|
||||||
|
import { usePreloadedQuery, type PreloadedQuery } from "react-relay";
|
||||||
|
import { trustCenterQuery, useUpdateTrustCenterMutation } from "/hooks/graph/TrustCenterGraph";
|
||||||
|
import type { TrustCenterGraphQuery } from "/hooks/graph/__generated__/TrustCenterGraphQuery.graphql";
|
||||||
|
import { useState } from "react";
|
||||||
|
import { useOrganizationId } from "/hooks/useOrganizationId";
|
||||||
|
import { Outlet, useLocation, Link } from "react-router";
|
||||||
|
|
||||||
|
type Props = {
|
||||||
|
queryRef: PreloadedQuery<TrustCenterGraphQuery>;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default function TrustCenterPage({ queryRef }: Props) {
|
||||||
|
const { __ } = useTranslate();
|
||||||
|
const { toast } = useToast();
|
||||||
|
const organizationId = useOrganizationId();
|
||||||
|
const location = useLocation();
|
||||||
|
const { organization } = usePreloadedQuery(trustCenterQuery, queryRef);
|
||||||
|
|
||||||
|
const [updateTrustCenter, isUpdating] = useUpdateTrustCenterMutation();
|
||||||
|
const [isActive, setIsActive] = useState(organization.trustCenter?.active || false);
|
||||||
|
const [slug, setSlug] = useState(organization.trustCenter?.slug || "");
|
||||||
|
const [isUpdatingSlug, setIsUpdatingSlug] = useState(false);
|
||||||
|
|
||||||
|
usePageTitle(__("Trust Center"));
|
||||||
|
|
||||||
|
const handleToggleActive = async (active: boolean) => {
|
||||||
|
if (!organization.trustCenter?.id) {
|
||||||
|
toast({
|
||||||
|
title: __("Error"),
|
||||||
|
description: __("Trust center not found"),
|
||||||
|
variant: "error",
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setIsActive(active);
|
||||||
|
|
||||||
|
updateTrustCenter({
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
trustCenterId: organization.trustCenter.id,
|
||||||
|
active,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
onError: () => {
|
||||||
|
setIsActive(!active);
|
||||||
|
},
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleSlugUpdate = async () => {
|
||||||
|
if (!organization.trustCenter?.id) {
|
||||||
|
toast({
|
||||||
|
title: __("Error"),
|
||||||
|
description: __("Trust center not found"),
|
||||||
|
variant: "error",
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!slug.trim()) {
|
||||||
|
toast({
|
||||||
|
title: __("Error"),
|
||||||
|
description: __("Slug cannot be empty"),
|
||||||
|
variant: "error",
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setIsUpdatingSlug(true);
|
||||||
|
|
||||||
|
updateTrustCenter({
|
||||||
|
variables: {
|
||||||
|
input: {
|
||||||
|
trustCenterId: organization.trustCenter.id,
|
||||||
|
slug: slug.trim(),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
onCompleted: () => {
|
||||||
|
setIsUpdatingSlug(false);
|
||||||
|
},
|
||||||
|
onError: () => {
|
||||||
|
setIsUpdatingSlug(false);
|
||||||
|
setSlug(organization.trustCenter?.slug || "");
|
||||||
|
},
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const trustCenterUrl = organization.trustCenter?.slug
|
||||||
|
? `${window.location.origin}/trust/${organization.trustCenter.slug}`
|
||||||
|
: null;
|
||||||
|
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="space-y-6">
|
||||||
|
<PageHeader
|
||||||
|
title={__("Trust Center")}
|
||||||
|
description={__(
|
||||||
|
"Configure your public trust center to showcase your security and compliance posture."
|
||||||
|
)}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<div className="space-y-4">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
<h2 className="text-base font-medium">{__("Trust Center Status")}</h2>
|
||||||
|
{isUpdating && <Spinner />}
|
||||||
|
</div>
|
||||||
|
<Card padded className="space-y-4">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
<div className="space-y-1">
|
||||||
|
<h3 className="font-medium">{__("Activate Trust Center")}</h3>
|
||||||
|
<p className="text-sm text-txt-tertiary">
|
||||||
|
{__("Make your trust center publicly accessible to build customer confidence")}
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
<Checkbox
|
||||||
|
checked={isActive}
|
||||||
|
onChange={handleToggleActive}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{isActive && trustCenterUrl && (
|
||||||
|
<div className="mt-4 p-4 bg-accent-light rounded-lg border border-accent">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
<div>
|
||||||
|
<h4 className="font-medium text-accent-dark">
|
||||||
|
{__("Your Trust Center is Live!")}
|
||||||
|
</h4>
|
||||||
|
<p className="text-sm text-accent-dark mt-1">
|
||||||
|
{__("Your customers can now access your trust center at:")}
|
||||||
|
</p>
|
||||||
|
<a
|
||||||
|
href={trustCenterUrl}
|
||||||
|
target="_blank"
|
||||||
|
rel="noopener noreferrer"
|
||||||
|
className="text-sm font-mono text-accent underline hover:no-underline"
|
||||||
|
>
|
||||||
|
{trustCenterUrl}
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<Button
|
||||||
|
variant="secondary"
|
||||||
|
onClick={() => window.open(trustCenterUrl, '_blank', 'noopener,noreferrer')}
|
||||||
|
>
|
||||||
|
{__("View")}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
|
||||||
|
{!isActive && (
|
||||||
|
<div className="mt-4 p-4 bg-tertiary rounded-lg border border-border-solid">
|
||||||
|
<h4 className="font-medium text-txt-secondary">
|
||||||
|
{__("Trust Center is Inactive")}
|
||||||
|
</h4>
|
||||||
|
<p className="text-sm text-txt-tertiary mt-1">
|
||||||
|
{__("Your trust center is currently not accessible to the public. Enable it to start sharing your compliance status.")}
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</Card>
|
||||||
|
</div>
|
||||||
|
<div className="space-y-4">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
<h2 className="text-base font-medium">{__("Configuration")}</h2>
|
||||||
|
{isUpdatingSlug && <Spinner />}
|
||||||
|
</div>
|
||||||
|
<Card padded className="space-y-4">
|
||||||
|
<div className="space-y-2">
|
||||||
|
<Field
|
||||||
|
label={__("Slug")}
|
||||||
|
help={__("The unique identifier for your trust center URL")}
|
||||||
|
>
|
||||||
|
<div className="flex items-center space-x-2">
|
||||||
|
<div className="flex items-center">
|
||||||
|
<Input
|
||||||
|
value={slug}
|
||||||
|
onChange={(e) => setSlug(e.target.value)}
|
||||||
|
placeholder={__("your-organization")}
|
||||||
|
className="min-w-[200px]"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<Button
|
||||||
|
variant="secondary"
|
||||||
|
onClick={handleSlugUpdate}
|
||||||
|
disabled={
|
||||||
|
isUpdatingSlug ||
|
||||||
|
!slug.trim() ||
|
||||||
|
slug === organization.trustCenter?.slug
|
||||||
|
}
|
||||||
|
>
|
||||||
|
{__("Update")}
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</Field>
|
||||||
|
</div>
|
||||||
|
</Card>
|
||||||
|
</div>
|
||||||
|
<div className="space-y-4">
|
||||||
|
<h2 className="text-base font-medium">{__("Content")}</h2>
|
||||||
|
<Tabs>
|
||||||
|
<TabItem
|
||||||
|
asChild
|
||||||
|
active={
|
||||||
|
location.pathname === `/organizations/${organizationId}/trust-center` ||
|
||||||
|
location.pathname === `/organizations/${organizationId}/trust-center/audits`
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Link to={`/organizations/${organizationId}/trust-center/audits`}>
|
||||||
|
{__("Audits")}
|
||||||
|
</Link>
|
||||||
|
</TabItem>
|
||||||
|
<TabLink to={`/organizations/${organizationId}/trust-center/vendors`}>
|
||||||
|
{__("Vendors")}
|
||||||
|
</TabLink>
|
||||||
|
<TabLink to={`/organizations/${organizationId}/trust-center/documents`}>
|
||||||
|
{__("Documents")}
|
||||||
|
</TabLink>
|
||||||
|
</Tabs>
|
||||||
|
|
||||||
|
<Outlet context={{ organization }} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -0,0 +1,39 @@
|
|||||||
|
import { Card, Spinner } from "@probo/ui";
|
||||||
|
import { useOutletContext } from "react-router";
|
||||||
|
import { TrustCenterAuditsCard } from "/components/trustCenter/TrustCenterAuditsCard";
|
||||||
|
import { useTrustCenterAuditUpdate } from "/hooks/graph/TrustCenterAuditGraph";
|
||||||
|
import type { TrustCenterAuditsCardFragment$key } from "/components/trustCenter/__generated__/TrustCenterAuditsCardFragment.graphql";
|
||||||
|
|
||||||
|
type ContextType = {
|
||||||
|
organization: {
|
||||||
|
audits?: {
|
||||||
|
edges: Array<{
|
||||||
|
node: TrustCenterAuditsCardFragment$key;
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
export default function TrustCenterAuditsTab() {
|
||||||
|
const { organization } = useOutletContext<ContextType>();
|
||||||
|
const [updateAuditVisibility, isUpdatingAudits] = useTrustCenterAuditUpdate();
|
||||||
|
|
||||||
|
const audits = (organization.audits?.edges ?? []).map((edge) => edge.node);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="space-y-4">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
{isUpdatingAudits && <Spinner />}
|
||||||
|
</div>
|
||||||
|
<Card padded>
|
||||||
|
<TrustCenterAuditsCard
|
||||||
|
audits={audits}
|
||||||
|
params={{}}
|
||||||
|
disabled={isUpdatingAudits}
|
||||||
|
onToggleVisibility={updateAuditVisibility}
|
||||||
|
variant="table"
|
||||||
|
/>
|
||||||
|
</Card>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -0,0 +1,39 @@
|
|||||||
|
import { Card, Spinner } from "@probo/ui";
|
||||||
|
import { useOutletContext } from "react-router";
|
||||||
|
import { TrustCenterDocumentsCard } from "/components/trustCenter/TrustCenterDocumentsCard";
|
||||||
|
import { useUpdateDocumentVisibilityMutation } from "/hooks/graph/TrustCenterDocumentGraph";
|
||||||
|
import type { TrustCenterDocumentsCardFragment$key } from "/components/trustCenter/__generated__/TrustCenterDocumentsCardFragment.graphql";
|
||||||
|
|
||||||
|
type ContextType = {
|
||||||
|
organization: {
|
||||||
|
documents?: {
|
||||||
|
edges: Array<{
|
||||||
|
node: TrustCenterDocumentsCardFragment$key;
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
export default function TrustCenterDocumentsTab() {
|
||||||
|
const { organization } = useOutletContext<ContextType>();
|
||||||
|
const [updateDocumentVisibility, isUpdatingDocuments] = useUpdateDocumentVisibilityMutation();
|
||||||
|
|
||||||
|
const documents = organization.documents?.edges?.map((edge) => edge.node) || [];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="space-y-4">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
{isUpdatingDocuments && <Spinner />}
|
||||||
|
</div>
|
||||||
|
<Card padded>
|
||||||
|
<TrustCenterDocumentsCard
|
||||||
|
documents={documents}
|
||||||
|
params={{}}
|
||||||
|
disabled={isUpdatingDocuments}
|
||||||
|
onToggleVisibility={updateDocumentVisibility}
|
||||||
|
variant="table"
|
||||||
|
/>
|
||||||
|
</Card>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -0,0 +1,39 @@
|
|||||||
|
import { Card, Spinner } from "@probo/ui";
|
||||||
|
import { useOutletContext } from "react-router";
|
||||||
|
import { TrustCenterVendorsCard } from "/components/trustCenter/TrustCenterVendorsCard";
|
||||||
|
import { useTrustCenterVendorUpdate } from "/hooks/graph/TrustCenterVendorGraph";
|
||||||
|
import type { TrustCenterVendorsCardFragment$key } from "/components/trustCenter/__generated__/TrustCenterVendorsCardFragment.graphql";
|
||||||
|
|
||||||
|
type ContextType = {
|
||||||
|
organization: {
|
||||||
|
vendors?: {
|
||||||
|
edges: Array<{
|
||||||
|
node: TrustCenterVendorsCardFragment$key;
|
||||||
|
}>;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
export default function TrustCenterVendorsTab() {
|
||||||
|
const { organization } = useOutletContext<ContextType>();
|
||||||
|
const [updateVendorVisibility, isUpdatingVendors] = useTrustCenterVendorUpdate();
|
||||||
|
|
||||||
|
const vendors = organization.vendors?.edges?.map((edge) => edge.node) || [];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="space-y-4">
|
||||||
|
<div className="flex items-center justify-between">
|
||||||
|
{isUpdatingVendors && <Spinner />}
|
||||||
|
</div>
|
||||||
|
<Card padded>
|
||||||
|
<TrustCenterVendorsCard
|
||||||
|
vendors={vendors}
|
||||||
|
params={{}}
|
||||||
|
disabled={isUpdatingVendors}
|
||||||
|
onToggleVisibility={updateVendorVisibility}
|
||||||
|
variant="table"
|
||||||
|
/>
|
||||||
|
</Card>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -28,6 +28,7 @@ import { taskRoutes } from "./routes/taskRoutes.ts";
|
|||||||
import { dataRoutes } from "./routes/dataRoutes.ts";
|
import { dataRoutes } from "./routes/dataRoutes.ts";
|
||||||
import { assetRoutes } from "./routes/assetRoutes.ts";
|
import { assetRoutes } from "./routes/assetRoutes.ts";
|
||||||
import { auditRoutes } from "./routes/auditRoutes.ts";
|
import { auditRoutes } from "./routes/auditRoutes.ts";
|
||||||
|
import { trustCenterRoutes } from "./routes/trustCenterRoutes.ts";
|
||||||
import { lazy } from "@probo/react-lazy";
|
import { lazy } from "@probo/react-lazy";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -136,6 +137,7 @@ const routes = [
|
|||||||
...assetRoutes,
|
...assetRoutes,
|
||||||
...dataRoutes,
|
...dataRoutes,
|
||||||
...auditRoutes,
|
...auditRoutes,
|
||||||
|
...trustCenterRoutes,
|
||||||
{
|
{
|
||||||
path: "*",
|
path: "*",
|
||||||
Component: PageError,
|
Component: PageError,
|
||||||
|
|||||||
49
apps/console/src/routes/trustCenterRoutes.ts
Normal file
49
apps/console/src/routes/trustCenterRoutes.ts
Normal file
@@ -0,0 +1,49 @@
|
|||||||
|
import { loadQuery } from "react-relay";
|
||||||
|
import { relayEnvironment } from "/providers/RelayProviders";
|
||||||
|
import { PageSkeleton } from "/components/skeletons/PageSkeleton";
|
||||||
|
import { LinkCardSkeleton } from "/components/skeletons/LinkCardSkeleton";
|
||||||
|
import { lazy } from "@probo/react-lazy";
|
||||||
|
import { trustCenterQuery } from "../hooks/graph/TrustCenterGraph";
|
||||||
|
import type { AppRoute } from "/routes";
|
||||||
|
|
||||||
|
export const trustCenterRoutes = [
|
||||||
|
{
|
||||||
|
path: "trust-center",
|
||||||
|
fallback: PageSkeleton,
|
||||||
|
queryLoader: ({ organizationId }) =>
|
||||||
|
loadQuery(relayEnvironment, trustCenterQuery, { organizationId }),
|
||||||
|
Component: lazy(
|
||||||
|
() => import("/pages/organizations/TrustCenterPage")
|
||||||
|
),
|
||||||
|
children: [
|
||||||
|
{
|
||||||
|
index: true,
|
||||||
|
fallback: LinkCardSkeleton,
|
||||||
|
Component: lazy(
|
||||||
|
() => import("/pages/organizations/trustCenter/TrustCenterAuditsTab")
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "audits",
|
||||||
|
fallback: LinkCardSkeleton,
|
||||||
|
Component: lazy(
|
||||||
|
() => import("/pages/organizations/trustCenter/TrustCenterAuditsTab")
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "vendors",
|
||||||
|
fallback: LinkCardSkeleton,
|
||||||
|
Component: lazy(
|
||||||
|
() => import("/pages/organizations/trustCenter/TrustCenterVendorsTab")
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "documents",
|
||||||
|
fallback: LinkCardSkeleton,
|
||||||
|
Component: lazy(
|
||||||
|
() => import("/pages/organizations/trustCenter/TrustCenterDocumentsTab")
|
||||||
|
),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
] satisfies AppRoute[];
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
import type { HTMLAttributes, PropsWithChildren } from "react";
|
import type { HTMLAttributes, PropsWithChildren } from "react";
|
||||||
import { NavLink } from "react-router";
|
import { NavLink, type NavLinkProps } from "react-router";
|
||||||
import { Root, List } from "@radix-ui/react-tabs";
|
import { Root, List } from "@radix-ui/react-tabs";
|
||||||
import { Slot, type AsChildProps } from "../Slot";
|
import { Slot, type AsChildProps } from "../Slot";
|
||||||
import { tv } from "tailwind-variants";
|
import { tv } from "tailwind-variants";
|
||||||
@@ -41,7 +41,7 @@ export function TabItem({
|
|||||||
return <Component {...props} className={cls.item({ active })} />;
|
return <Component {...props} className={cls.item({ active })} />;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function TabLink(props: PropsWithChildren<{ to: string }>) {
|
export function TabLink(props: PropsWithChildren<NavLinkProps & { isActive?: () => boolean }>) {
|
||||||
return (
|
return (
|
||||||
<NavLink
|
<NavLink
|
||||||
className={(params) => cls.item({ active: params.isActive })}
|
className={(params) => cls.item({ active: params.isActive })}
|
||||||
|
|||||||
@@ -28,15 +28,16 @@ import (
|
|||||||
|
|
||||||
type (
|
type (
|
||||||
Audit struct {
|
Audit struct {
|
||||||
ID gid.GID `db:"id"`
|
ID gid.GID `db:"id"`
|
||||||
OrganizationID gid.GID `db:"organization_id"`
|
OrganizationID gid.GID `db:"organization_id"`
|
||||||
FrameworkID gid.GID `db:"framework_id"`
|
FrameworkID gid.GID `db:"framework_id"`
|
||||||
ReportID *gid.GID `db:"report_id"`
|
ReportID *gid.GID `db:"report_id"`
|
||||||
ValidFrom *time.Time `db:"valid_from"`
|
ValidFrom *time.Time `db:"valid_from"`
|
||||||
ValidUntil *time.Time `db:"valid_until"`
|
ValidUntil *time.Time `db:"valid_until"`
|
||||||
State AuditState `db:"state"`
|
State AuditState `db:"state"`
|
||||||
CreatedAt time.Time `db:"created_at"`
|
ShowOnTrustCenter bool `db:"show_on_trust_center"`
|
||||||
UpdatedAt time.Time `db:"updated_at"`
|
CreatedAt time.Time `db:"created_at"`
|
||||||
|
UpdatedAt time.Time `db:"updated_at"`
|
||||||
}
|
}
|
||||||
|
|
||||||
Audits []*Audit
|
Audits []*Audit
|
||||||
@@ -72,6 +73,7 @@ SELECT
|
|||||||
valid_from,
|
valid_from,
|
||||||
valid_until,
|
valid_until,
|
||||||
state,
|
state,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -150,6 +152,7 @@ SELECT
|
|||||||
valid_from,
|
valid_from,
|
||||||
valid_until,
|
valid_until,
|
||||||
state,
|
state,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -196,6 +199,7 @@ INSERT INTO audits (
|
|||||||
valid_from,
|
valid_from,
|
||||||
valid_until,
|
valid_until,
|
||||||
state,
|
state,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
) VALUES (
|
) VALUES (
|
||||||
@@ -207,22 +211,24 @@ INSERT INTO audits (
|
|||||||
@valid_from,
|
@valid_from,
|
||||||
@valid_until,
|
@valid_until,
|
||||||
@state,
|
@state,
|
||||||
|
@show_on_trust_center,
|
||||||
@created_at,
|
@created_at,
|
||||||
@updated_at
|
@updated_at
|
||||||
)
|
)
|
||||||
`
|
`
|
||||||
|
|
||||||
args := pgx.StrictNamedArgs{
|
args := pgx.StrictNamedArgs{
|
||||||
"id": a.ID,
|
"id": a.ID,
|
||||||
"tenant_id": scope.GetTenantID(),
|
"tenant_id": scope.GetTenantID(),
|
||||||
"organization_id": a.OrganizationID,
|
"organization_id": a.OrganizationID,
|
||||||
"framework_id": a.FrameworkID,
|
"framework_id": a.FrameworkID,
|
||||||
"report_id": a.ReportID,
|
"report_id": a.ReportID,
|
||||||
"valid_from": a.ValidFrom,
|
"valid_from": a.ValidFrom,
|
||||||
"valid_until": a.ValidUntil,
|
"valid_until": a.ValidUntil,
|
||||||
"state": a.State,
|
"state": a.State,
|
||||||
"created_at": a.CreatedAt,
|
"show_on_trust_center": a.ShowOnTrustCenter,
|
||||||
"updated_at": a.UpdatedAt,
|
"created_at": a.CreatedAt,
|
||||||
|
"updated_at": a.UpdatedAt,
|
||||||
}
|
}
|
||||||
|
|
||||||
_, err := conn.Exec(ctx, q, args)
|
_, err := conn.Exec(ctx, q, args)
|
||||||
@@ -245,6 +251,7 @@ SET
|
|||||||
valid_from = @valid_from,
|
valid_from = @valid_from,
|
||||||
valid_until = @valid_until,
|
valid_until = @valid_until,
|
||||||
state = @state,
|
state = @state,
|
||||||
|
show_on_trust_center = @show_on_trust_center,
|
||||||
updated_at = @updated_at
|
updated_at = @updated_at
|
||||||
WHERE
|
WHERE
|
||||||
%s
|
%s
|
||||||
@@ -254,12 +261,13 @@ WHERE
|
|||||||
q = fmt.Sprintf(q, scope.SQLFragment())
|
q = fmt.Sprintf(q, scope.SQLFragment())
|
||||||
|
|
||||||
args := pgx.StrictNamedArgs{
|
args := pgx.StrictNamedArgs{
|
||||||
"id": a.ID,
|
"id": a.ID,
|
||||||
"report_id": a.ReportID,
|
"report_id": a.ReportID,
|
||||||
"valid_from": a.ValidFrom,
|
"valid_from": a.ValidFrom,
|
||||||
"valid_until": a.ValidUntil,
|
"valid_until": a.ValidUntil,
|
||||||
"state": a.State,
|
"state": a.State,
|
||||||
"updated_at": a.UpdatedAt,
|
"show_on_trust_center": a.ShowOnTrustCenter,
|
||||||
|
"updated_at": a.UpdatedAt,
|
||||||
}
|
}
|
||||||
maps.Copy(args, scope.SQLArguments())
|
maps.Copy(args, scope.SQLArguments())
|
||||||
|
|
||||||
|
|||||||
@@ -34,6 +34,7 @@ type (
|
|||||||
Title string `db:"title"`
|
Title string `db:"title"`
|
||||||
DocumentType DocumentType `db:"document_type"`
|
DocumentType DocumentType `db:"document_type"`
|
||||||
CurrentPublishedVersion *int `db:"current_published_version"`
|
CurrentPublishedVersion *int `db:"current_published_version"`
|
||||||
|
ShowOnTrustCenter bool `db:"show_on_trust_center"`
|
||||||
CreatedAt time.Time `db:"created_at"`
|
CreatedAt time.Time `db:"created_at"`
|
||||||
UpdatedAt time.Time `db:"updated_at"`
|
UpdatedAt time.Time `db:"updated_at"`
|
||||||
}
|
}
|
||||||
@@ -68,6 +69,7 @@ SELECT
|
|||||||
title,
|
title,
|
||||||
document_type,
|
document_type,
|
||||||
current_published_version,
|
current_published_version,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -147,6 +149,7 @@ SELECT
|
|||||||
title,
|
title,
|
||||||
document_type,
|
document_type,
|
||||||
current_published_version,
|
current_published_version,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -195,6 +198,7 @@ INSERT INTO
|
|||||||
title,
|
title,
|
||||||
document_type,
|
document_type,
|
||||||
current_published_version,
|
current_published_version,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
)
|
)
|
||||||
@@ -206,6 +210,7 @@ VALUES (
|
|||||||
@title,
|
@title,
|
||||||
@document_type,
|
@document_type,
|
||||||
@current_published_version,
|
@current_published_version,
|
||||||
|
@show_on_trust_center,
|
||||||
@created_at,
|
@created_at,
|
||||||
@updated_at
|
@updated_at
|
||||||
);
|
);
|
||||||
@@ -219,6 +224,7 @@ VALUES (
|
|||||||
"title": p.Title,
|
"title": p.Title,
|
||||||
"document_type": p.DocumentType,
|
"document_type": p.DocumentType,
|
||||||
"current_published_version": p.CurrentPublishedVersion,
|
"current_published_version": p.CurrentPublishedVersion,
|
||||||
|
"show_on_trust_center": p.ShowOnTrustCenter,
|
||||||
"created_at": p.CreatedAt,
|
"created_at": p.CreatedAt,
|
||||||
"updated_at": p.UpdatedAt,
|
"updated_at": p.UpdatedAt,
|
||||||
}
|
}
|
||||||
@@ -257,6 +263,7 @@ SET
|
|||||||
current_published_version = @current_published_version,
|
current_published_version = @current_published_version,
|
||||||
owner_id = @owner_id,
|
owner_id = @owner_id,
|
||||||
document_type = @document_type,
|
document_type = @document_type,
|
||||||
|
show_on_trust_center = @show_on_trust_center,
|
||||||
updated_at = @updated_at
|
updated_at = @updated_at
|
||||||
WHERE %s
|
WHERE %s
|
||||||
AND id = @document_id
|
AND id = @document_id
|
||||||
@@ -270,6 +277,7 @@ WHERE %s
|
|||||||
"current_published_version": p.CurrentPublishedVersion,
|
"current_published_version": p.CurrentPublishedVersion,
|
||||||
"owner_id": p.OwnerID,
|
"owner_id": p.OwnerID,
|
||||||
"document_type": p.DocumentType,
|
"document_type": p.DocumentType,
|
||||||
|
"show_on_trust_center": p.ShowOnTrustCenter,
|
||||||
}
|
}
|
||||||
maps.Copy(args, scope.SQLArguments())
|
maps.Copy(args, scope.SQLArguments())
|
||||||
|
|
||||||
@@ -342,6 +350,7 @@ WITH plcs AS (
|
|||||||
p.title,
|
p.title,
|
||||||
p.document_type,
|
p.document_type,
|
||||||
p.current_published_version,
|
p.current_published_version,
|
||||||
|
p.show_on_trust_center,
|
||||||
p.created_at,
|
p.created_at,
|
||||||
p.updated_at
|
p.updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -358,6 +367,7 @@ SELECT
|
|||||||
title,
|
title,
|
||||||
document_type,
|
document_type,
|
||||||
current_published_version,
|
current_published_version,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -448,6 +458,7 @@ WITH plcs AS (
|
|||||||
p.title,
|
p.title,
|
||||||
p.document_type,
|
p.document_type,
|
||||||
p.current_published_version,
|
p.current_published_version,
|
||||||
|
p.show_on_trust_center,
|
||||||
p.created_at,
|
p.created_at,
|
||||||
p.updated_at
|
p.updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -464,6 +475,7 @@ SELECT
|
|||||||
title,
|
title,
|
||||||
document_type,
|
document_type,
|
||||||
current_published_version,
|
current_published_version,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
|
|||||||
@@ -37,4 +37,5 @@ const (
|
|||||||
DatumEntityType
|
DatumEntityType
|
||||||
AuditEntityType
|
AuditEntityType
|
||||||
ReportEntityType
|
ReportEntityType
|
||||||
|
TrustCenterEntityType
|
||||||
)
|
)
|
||||||
|
|||||||
51
pkg/coredata/migrations/20250724T135155Z.sql
Normal file
51
pkg/coredata/migrations/20250724T135155Z.sql
Normal file
@@ -0,0 +1,51 @@
|
|||||||
|
CREATE EXTENSION IF NOT EXISTS unaccent;
|
||||||
|
|
||||||
|
CREATE TABLE trust_centers (
|
||||||
|
id TEXT PRIMARY KEY,
|
||||||
|
organization_id TEXT NOT NULL REFERENCES organizations(id) ON DELETE CASCADE,
|
||||||
|
tenant_id TEXT NOT NULL,
|
||||||
|
active BOOLEAN NOT NULL,
|
||||||
|
slug TEXT NOT NULL CHECK (slug ~ '^[a-z0-9_-]+$'),
|
||||||
|
created_at TIMESTAMP WITH TIME ZONE NOT NULL,
|
||||||
|
updated_at TIMESTAMP WITH TIME ZONE NOT NULL,
|
||||||
|
UNIQUE(slug)
|
||||||
|
);
|
||||||
|
|
||||||
|
INSERT INTO trust_centers (
|
||||||
|
id,
|
||||||
|
organization_id,
|
||||||
|
tenant_id,
|
||||||
|
active,
|
||||||
|
slug,
|
||||||
|
created_at,
|
||||||
|
updated_at
|
||||||
|
)
|
||||||
|
SELECT
|
||||||
|
generate_gid(decode_base64_unpadded(o.tenant_id), 22),
|
||||||
|
o.id,
|
||||||
|
o.tenant_id,
|
||||||
|
false,
|
||||||
|
LOWER(
|
||||||
|
REGEXP_REPLACE(
|
||||||
|
REGEXP_REPLACE(
|
||||||
|
unaccent(o.name),
|
||||||
|
'[^a-zA-Z0-9\s]', '', 'g'
|
||||||
|
),
|
||||||
|
'\s+', '-', 'g'
|
||||||
|
)
|
||||||
|
),
|
||||||
|
NOW(),
|
||||||
|
NOW()
|
||||||
|
FROM organizations o;
|
||||||
|
|
||||||
|
ALTER TABLE documents ADD COLUMN show_on_trust_center BOOLEAN NOT NULL DEFAULT false;
|
||||||
|
|
||||||
|
ALTER TABLE audits ADD COLUMN show_on_trust_center BOOLEAN NOT NULL DEFAULT false;
|
||||||
|
|
||||||
|
ALTER TABLE vendors ADD COLUMN show_on_trust_center BOOLEAN NOT NULL DEFAULT false;
|
||||||
|
|
||||||
|
ALTER TABLE documents ALTER COLUMN show_on_trust_center DROP DEFAULT;
|
||||||
|
|
||||||
|
ALTER TABLE audits ALTER COLUMN show_on_trust_center DROP DEFAULT;
|
||||||
|
|
||||||
|
ALTER TABLE vendors ALTER COLUMN show_on_trust_center DROP DEFAULT;
|
||||||
213
pkg/coredata/trust_center.go
Normal file
213
pkg/coredata/trust_center.go
Normal file
@@ -0,0 +1,213 @@
|
|||||||
|
// Copyright (c) 2025 Probo Inc <hello@getprobo.com>.
|
||||||
|
//
|
||||||
|
// Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
// purpose with or without fee is hereby granted, provided that the above
|
||||||
|
// copyright notice and this permission notice appear in all copies.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
||||||
|
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||||
|
// AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||||
|
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||||
|
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||||
|
// OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||||
|
// PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
|
||||||
|
package coredata
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"fmt"
|
||||||
|
"maps"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/getprobo/probo/pkg/gid"
|
||||||
|
"github.com/getprobo/probo/pkg/page"
|
||||||
|
"github.com/jackc/pgx/v5"
|
||||||
|
"go.gearno.de/kit/pg"
|
||||||
|
)
|
||||||
|
|
||||||
|
type (
|
||||||
|
TrustCenter struct {
|
||||||
|
ID gid.GID `db:"id"`
|
||||||
|
OrganizationID gid.GID `db:"organization_id"`
|
||||||
|
TenantID gid.TenantID `db:"tenant_id"`
|
||||||
|
Active bool `db:"active"`
|
||||||
|
Slug string `db:"slug"`
|
||||||
|
CreatedAt time.Time `db:"created_at"`
|
||||||
|
UpdatedAt time.Time `db:"updated_at"`
|
||||||
|
}
|
||||||
|
|
||||||
|
TrustCenters []*TrustCenter
|
||||||
|
)
|
||||||
|
|
||||||
|
func (tc *TrustCenter) CursorKey(orderBy TrustCenterOrderField) page.CursorKey {
|
||||||
|
switch orderBy {
|
||||||
|
case TrustCenterOrderFieldCreatedAt:
|
||||||
|
return page.NewCursorKey(tc.ID, tc.CreatedAt)
|
||||||
|
}
|
||||||
|
|
||||||
|
panic(fmt.Sprintf("unsupported order by: %s", orderBy))
|
||||||
|
}
|
||||||
|
|
||||||
|
func (tc *TrustCenter) LoadByID(
|
||||||
|
ctx context.Context,
|
||||||
|
conn pg.Conn,
|
||||||
|
scope Scoper,
|
||||||
|
trustCenterID gid.GID,
|
||||||
|
) error {
|
||||||
|
q := `
|
||||||
|
SELECT
|
||||||
|
id,
|
||||||
|
organization_id,
|
||||||
|
tenant_id,
|
||||||
|
active,
|
||||||
|
slug,
|
||||||
|
created_at,
|
||||||
|
updated_at
|
||||||
|
FROM
|
||||||
|
trust_centers
|
||||||
|
WHERE
|
||||||
|
%s
|
||||||
|
AND id = @trust_center_id
|
||||||
|
LIMIT 1;
|
||||||
|
`
|
||||||
|
|
||||||
|
q = fmt.Sprintf(q, scope.SQLFragment())
|
||||||
|
|
||||||
|
args := pgx.StrictNamedArgs{"trust_center_id": trustCenterID}
|
||||||
|
maps.Copy(args, scope.SQLArguments())
|
||||||
|
|
||||||
|
rows, err := conn.Query(ctx, q, args)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot query trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
trustCenter, err := pgx.CollectExactlyOneRow(rows, pgx.RowToStructByName[TrustCenter])
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot collect trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
*tc = trustCenter
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (tc *TrustCenter) LoadByOrganizationID(
|
||||||
|
ctx context.Context,
|
||||||
|
conn pg.Conn,
|
||||||
|
scope Scoper,
|
||||||
|
organizationID gid.GID,
|
||||||
|
) error {
|
||||||
|
q := `
|
||||||
|
SELECT
|
||||||
|
id,
|
||||||
|
organization_id,
|
||||||
|
tenant_id,
|
||||||
|
active,
|
||||||
|
slug,
|
||||||
|
created_at,
|
||||||
|
updated_at
|
||||||
|
FROM
|
||||||
|
trust_centers
|
||||||
|
WHERE
|
||||||
|
%s
|
||||||
|
AND organization_id = @organization_id
|
||||||
|
LIMIT 1;
|
||||||
|
`
|
||||||
|
|
||||||
|
q = fmt.Sprintf(q, scope.SQLFragment())
|
||||||
|
|
||||||
|
args := pgx.StrictNamedArgs{"organization_id": organizationID}
|
||||||
|
maps.Copy(args, scope.SQLArguments())
|
||||||
|
|
||||||
|
rows, err := conn.Query(ctx, q, args)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot query trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
trustCenter, err := pgx.CollectExactlyOneRow(rows, pgx.RowToStructByName[TrustCenter])
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot collect trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
*tc = trustCenter
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (tc *TrustCenter) Insert(
|
||||||
|
ctx context.Context,
|
||||||
|
conn pg.Conn,
|
||||||
|
scope Scoper,
|
||||||
|
) error {
|
||||||
|
q := `
|
||||||
|
INSERT INTO trust_centers (
|
||||||
|
id,
|
||||||
|
organization_id,
|
||||||
|
tenant_id,
|
||||||
|
active,
|
||||||
|
slug,
|
||||||
|
created_at,
|
||||||
|
updated_at
|
||||||
|
) VALUES (
|
||||||
|
@id,
|
||||||
|
@organization_id,
|
||||||
|
@tenant_id,
|
||||||
|
@active,
|
||||||
|
@slug,
|
||||||
|
@created_at,
|
||||||
|
@updated_at
|
||||||
|
)
|
||||||
|
`
|
||||||
|
|
||||||
|
args := pgx.StrictNamedArgs{
|
||||||
|
"id": tc.ID,
|
||||||
|
"organization_id": tc.OrganizationID,
|
||||||
|
"tenant_id": tc.TenantID,
|
||||||
|
"active": tc.Active,
|
||||||
|
"slug": tc.Slug,
|
||||||
|
"created_at": tc.CreatedAt,
|
||||||
|
"updated_at": tc.UpdatedAt,
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err := conn.Exec(ctx, q, args)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot insert trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (tc *TrustCenter) Update(
|
||||||
|
ctx context.Context,
|
||||||
|
conn pg.Conn,
|
||||||
|
scope Scoper,
|
||||||
|
) error {
|
||||||
|
q := `
|
||||||
|
UPDATE trust_centers
|
||||||
|
SET
|
||||||
|
active = @active,
|
||||||
|
slug = @slug,
|
||||||
|
updated_at = @updated_at
|
||||||
|
WHERE
|
||||||
|
%s
|
||||||
|
AND id = @id
|
||||||
|
`
|
||||||
|
|
||||||
|
q = fmt.Sprintf(q, scope.SQLFragment())
|
||||||
|
|
||||||
|
args := pgx.StrictNamedArgs{
|
||||||
|
"id": tc.ID,
|
||||||
|
"active": tc.Active,
|
||||||
|
"slug": tc.Slug,
|
||||||
|
"updated_at": tc.UpdatedAt,
|
||||||
|
}
|
||||||
|
maps.Copy(args, scope.SQLArguments())
|
||||||
|
|
||||||
|
_, err := conn.Exec(ctx, q, args)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot update trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
38
pkg/coredata/trust_center_order_field.go
Normal file
38
pkg/coredata/trust_center_order_field.go
Normal file
@@ -0,0 +1,38 @@
|
|||||||
|
// Copyright (c) 2025 Probo Inc <hello@getprobo.com>.
|
||||||
|
//
|
||||||
|
// Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
// purpose with or without fee is hereby granted, provided that the above
|
||||||
|
// copyright notice and this permission notice appear in all copies.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
||||||
|
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||||
|
// AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||||
|
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||||
|
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||||
|
// OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||||
|
// PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
|
||||||
|
package coredata
|
||||||
|
|
||||||
|
type TrustCenterOrderField string
|
||||||
|
|
||||||
|
const (
|
||||||
|
TrustCenterOrderFieldCreatedAt TrustCenterOrderField = "CREATED_AT"
|
||||||
|
)
|
||||||
|
|
||||||
|
func (p TrustCenterOrderField) Column() string {
|
||||||
|
return string(p)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p TrustCenterOrderField) String() string {
|
||||||
|
return string(p)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p TrustCenterOrderField) MarshalText() ([]byte, error) {
|
||||||
|
return []byte(p.String()), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *TrustCenterOrderField) UnmarshalText(text []byte) error {
|
||||||
|
*p = TrustCenterOrderField(text)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
@@ -49,6 +49,7 @@ type (
|
|||||||
TermsOfServiceURL *string `db:"terms_of_service_url"`
|
TermsOfServiceURL *string `db:"terms_of_service_url"`
|
||||||
SecurityPageURL *string `db:"security_page_url"`
|
SecurityPageURL *string `db:"security_page_url"`
|
||||||
TrustPageURL *string `db:"trust_page_url"`
|
TrustPageURL *string `db:"trust_page_url"`
|
||||||
|
ShowOnTrustCenter bool `db:"show_on_trust_center"`
|
||||||
CreatedAt time.Time `db:"created_at"`
|
CreatedAt time.Time `db:"created_at"`
|
||||||
UpdatedAt time.Time `db:"updated_at"`
|
UpdatedAt time.Time `db:"updated_at"`
|
||||||
}
|
}
|
||||||
@@ -98,6 +99,7 @@ SELECT
|
|||||||
terms_of_service_url,
|
terms_of_service_url,
|
||||||
security_page_url,
|
security_page_url,
|
||||||
trust_page_url,
|
trust_page_url,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -158,6 +160,7 @@ INSERT INTO
|
|||||||
terms_of_service_url,
|
terms_of_service_url,
|
||||||
security_page_url,
|
security_page_url,
|
||||||
trust_page_url,
|
trust_page_url,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
)
|
)
|
||||||
@@ -183,6 +186,7 @@ VALUES (
|
|||||||
@terms_of_service_url,
|
@terms_of_service_url,
|
||||||
@security_page_url,
|
@security_page_url,
|
||||||
@trust_page_url,
|
@trust_page_url,
|
||||||
|
@show_on_trust_center,
|
||||||
@created_at,
|
@created_at,
|
||||||
@updated_at
|
@updated_at
|
||||||
)
|
)
|
||||||
@@ -210,6 +214,7 @@ VALUES (
|
|||||||
"terms_of_service_url": v.TermsOfServiceURL,
|
"terms_of_service_url": v.TermsOfServiceURL,
|
||||||
"security_page_url": v.SecurityPageURL,
|
"security_page_url": v.SecurityPageURL,
|
||||||
"trust_page_url": v.TrustPageURL,
|
"trust_page_url": v.TrustPageURL,
|
||||||
|
"show_on_trust_center": v.ShowOnTrustCenter,
|
||||||
"created_at": v.CreatedAt,
|
"created_at": v.CreatedAt,
|
||||||
"updated_at": v.UpdatedAt,
|
"updated_at": v.UpdatedAt,
|
||||||
}
|
}
|
||||||
@@ -297,6 +302,7 @@ SELECT
|
|||||||
terms_of_service_url,
|
terms_of_service_url,
|
||||||
security_page_url,
|
security_page_url,
|
||||||
trust_page_url,
|
trust_page_url,
|
||||||
|
show_on_trust_center,
|
||||||
created_at,
|
created_at,
|
||||||
updated_at
|
updated_at
|
||||||
FROM
|
FROM
|
||||||
@@ -353,6 +359,7 @@ SET
|
|||||||
trust_page_url = @trust_page_url,
|
trust_page_url = @trust_page_url,
|
||||||
business_owner_id = @business_owner_id,
|
business_owner_id = @business_owner_id,
|
||||||
security_owner_id = @security_owner_id,
|
security_owner_id = @security_owner_id,
|
||||||
|
show_on_trust_center = @show_on_trust_center,
|
||||||
updated_at = @updated_at
|
updated_at = @updated_at
|
||||||
WHERE %s
|
WHERE %s
|
||||||
AND id = @vendor_id
|
AND id = @vendor_id
|
||||||
@@ -380,6 +387,7 @@ WHERE %s
|
|||||||
"trust_page_url": v.TrustPageURL,
|
"trust_page_url": v.TrustPageURL,
|
||||||
"business_owner_id": v.BusinessOwnerID,
|
"business_owner_id": v.BusinessOwnerID,
|
||||||
"security_owner_id": v.SecurityOwnerID,
|
"security_owner_id": v.SecurityOwnerID,
|
||||||
|
"show_on_trust_center": v.ShowOnTrustCenter,
|
||||||
}
|
}
|
||||||
|
|
||||||
maps.Copy(args, scope.SQLArguments())
|
maps.Copy(args, scope.SQLArguments())
|
||||||
|
|||||||
@@ -39,10 +39,11 @@ type (
|
|||||||
}
|
}
|
||||||
|
|
||||||
UpdateAuditRequest struct {
|
UpdateAuditRequest struct {
|
||||||
ID gid.GID
|
ID gid.GID
|
||||||
ValidFrom *time.Time
|
ValidFrom *time.Time
|
||||||
ValidUntil *time.Time
|
ValidUntil *time.Time
|
||||||
State *coredata.AuditState
|
State *coredata.AuditState
|
||||||
|
ShowOnTrustCenter *bool
|
||||||
}
|
}
|
||||||
|
|
||||||
UpdateAuditStateRequest struct {
|
UpdateAuditStateRequest struct {
|
||||||
@@ -87,14 +88,15 @@ func (s *AuditService) Create(
|
|||||||
now := time.Now()
|
now := time.Now()
|
||||||
|
|
||||||
audit := &coredata.Audit{
|
audit := &coredata.Audit{
|
||||||
ID: gid.New(s.svc.scope.GetTenantID(), coredata.AuditEntityType),
|
ID: gid.New(s.svc.scope.GetTenantID(), coredata.AuditEntityType),
|
||||||
OrganizationID: req.OrganizationID,
|
OrganizationID: req.OrganizationID,
|
||||||
FrameworkID: req.FrameworkID,
|
FrameworkID: req.FrameworkID,
|
||||||
ValidFrom: req.ValidFrom,
|
ValidFrom: req.ValidFrom,
|
||||||
ValidUntil: req.ValidUntil,
|
ValidUntil: req.ValidUntil,
|
||||||
State: coredata.AuditStateNotStarted,
|
State: coredata.AuditStateNotStarted,
|
||||||
CreatedAt: now,
|
ShowOnTrustCenter: false,
|
||||||
UpdatedAt: now,
|
CreatedAt: now,
|
||||||
|
UpdatedAt: now,
|
||||||
}
|
}
|
||||||
|
|
||||||
if req.State != nil {
|
if req.State != nil {
|
||||||
@@ -151,6 +153,9 @@ func (s *AuditService) Update(
|
|||||||
if req.State != nil {
|
if req.State != nil {
|
||||||
audit.State = *req.State
|
audit.State = *req.State
|
||||||
}
|
}
|
||||||
|
if req.ShowOnTrustCenter != nil {
|
||||||
|
audit.ShowOnTrustCenter = *req.ShowOnTrustCenter
|
||||||
|
}
|
||||||
|
|
||||||
audit.UpdatedAt = time.Now()
|
audit.UpdatedAt = time.Now()
|
||||||
|
|
||||||
|
|||||||
@@ -297,11 +297,12 @@ func (s *DocumentService) Create(
|
|||||||
people := &coredata.People{}
|
people := &coredata.People{}
|
||||||
|
|
||||||
document := &coredata.Document{
|
document := &coredata.Document{
|
||||||
ID: documentID,
|
ID: documentID,
|
||||||
Title: req.Title,
|
Title: req.Title,
|
||||||
DocumentType: req.DocumentType,
|
DocumentType: req.DocumentType,
|
||||||
CreatedAt: now,
|
ShowOnTrustCenter: false,
|
||||||
UpdatedAt: now,
|
CreatedAt: now,
|
||||||
|
UpdatedAt: now,
|
||||||
}
|
}
|
||||||
|
|
||||||
documentVersion := &coredata.DocumentVersion{
|
documentVersion := &coredata.DocumentVersion{
|
||||||
@@ -984,6 +985,7 @@ func (s *DocumentService) Update(
|
|||||||
newOwnerID *gid.GID,
|
newOwnerID *gid.GID,
|
||||||
documentType *coredata.DocumentType,
|
documentType *coredata.DocumentType,
|
||||||
title *string,
|
title *string,
|
||||||
|
showOnTrustCenter *bool,
|
||||||
) (*coredata.Document, error) {
|
) (*coredata.Document, error) {
|
||||||
document := &coredata.Document{}
|
document := &coredata.Document{}
|
||||||
people := &coredata.People{}
|
people := &coredata.People{}
|
||||||
@@ -1011,6 +1013,10 @@ func (s *DocumentService) Update(
|
|||||||
document.Title = *title
|
document.Title = *title
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if showOnTrustCenter != nil {
|
||||||
|
document.ShowOnTrustCenter = *showOnTrustCenter
|
||||||
|
}
|
||||||
|
|
||||||
document.UpdatedAt = now
|
document.UpdatedAt = now
|
||||||
|
|
||||||
if err := document.Update(ctx, tx, s.svc.scope); err != nil {
|
if err := document.Update(ctx, tx, s.svc.scope); err != nil {
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ import (
|
|||||||
"github.com/getprobo/probo/pkg/coredata"
|
"github.com/getprobo/probo/pkg/coredata"
|
||||||
"github.com/getprobo/probo/pkg/filevalidation"
|
"github.com/getprobo/probo/pkg/filevalidation"
|
||||||
"github.com/getprobo/probo/pkg/gid"
|
"github.com/getprobo/probo/pkg/gid"
|
||||||
|
"github.com/getprobo/probo/pkg/slug"
|
||||||
"go.gearno.de/crypto/uuid"
|
"go.gearno.de/crypto/uuid"
|
||||||
"go.gearno.de/kit/pg"
|
"go.gearno.de/kit/pg"
|
||||||
)
|
)
|
||||||
@@ -65,13 +66,27 @@ func (s OrganizationService) Create(
|
|||||||
UpdatedAt: now,
|
UpdatedAt: now,
|
||||||
}
|
}
|
||||||
|
|
||||||
err := s.svc.pg.WithConn(
|
err := s.svc.pg.WithTx(
|
||||||
ctx,
|
ctx,
|
||||||
func(tx pg.Conn) error {
|
func(tx pg.Conn) error {
|
||||||
if err := organization.Insert(ctx, tx); err != nil {
|
if err := organization.Insert(ctx, tx); err != nil {
|
||||||
return fmt.Errorf("cannot insert organization: %w", err)
|
return fmt.Errorf("cannot insert organization: %w", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
trustCenter := &coredata.TrustCenter{
|
||||||
|
ID: gid.New(s.svc.scope.GetTenantID(), coredata.TrustCenterEntityType),
|
||||||
|
OrganizationID: organization.ID,
|
||||||
|
TenantID: organization.TenantID,
|
||||||
|
Active: false,
|
||||||
|
Slug: slug.Make(organization.Name),
|
||||||
|
CreatedAt: now,
|
||||||
|
UpdatedAt: now,
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := trustCenter.Insert(ctx, tx, s.svc.scope); err != nil {
|
||||||
|
return fmt.Errorf("cannot insert trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
|||||||
@@ -65,6 +65,7 @@ type (
|
|||||||
Data *DatumService
|
Data *DatumService
|
||||||
Audits *AuditService
|
Audits *AuditService
|
||||||
Reports *ReportService
|
Reports *ReportService
|
||||||
|
TrustCenters *TrustCenterService
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -144,5 +145,6 @@ func (s *Service) WithTenant(tenantID gid.TenantID) *TenantService {
|
|||||||
tenantService.Data = &DatumService{svc: tenantService}
|
tenantService.Data = &DatumService{svc: tenantService}
|
||||||
tenantService.Audits = &AuditService{svc: tenantService}
|
tenantService.Audits = &AuditService{svc: tenantService}
|
||||||
tenantService.Reports = &ReportService{svc: tenantService}
|
tenantService.Reports = &ReportService{svc: tenantService}
|
||||||
|
tenantService.TrustCenters = &TrustCenterService{svc: tenantService}
|
||||||
return tenantService
|
return tenantService
|
||||||
}
|
}
|
||||||
|
|||||||
124
pkg/probo/trust_center_service.go
Normal file
124
pkg/probo/trust_center_service.go
Normal file
@@ -0,0 +1,124 @@
|
|||||||
|
// Copyright (c) 2025 Probo Inc <hello@getprobo.com>.
|
||||||
|
//
|
||||||
|
// Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
// purpose with or without fee is hereby granted, provided that the above
|
||||||
|
// copyright notice and this permission notice appear in all copies.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
||||||
|
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||||
|
// AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||||
|
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||||
|
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||||
|
// OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||||
|
// PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
|
||||||
|
package probo
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"fmt"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/getprobo/probo/pkg/coredata"
|
||||||
|
"github.com/getprobo/probo/pkg/gid"
|
||||||
|
"go.gearno.de/kit/pg"
|
||||||
|
)
|
||||||
|
|
||||||
|
type (
|
||||||
|
TrustCenterService struct {
|
||||||
|
svc *TenantService
|
||||||
|
}
|
||||||
|
|
||||||
|
UpdateTrustCenterRequest struct {
|
||||||
|
ID gid.GID
|
||||||
|
Active *bool
|
||||||
|
Slug *string
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
func (s TrustCenterService) Get(
|
||||||
|
ctx context.Context,
|
||||||
|
trustCenterID gid.GID,
|
||||||
|
) (*coredata.TrustCenter, error) {
|
||||||
|
trustCenter := &coredata.TrustCenter{}
|
||||||
|
|
||||||
|
err := s.svc.pg.WithConn(
|
||||||
|
ctx,
|
||||||
|
func(conn pg.Conn) error {
|
||||||
|
err := trustCenter.LoadByID(ctx, conn, s.svc.scope, trustCenterID)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot load trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return trustCenter, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s TrustCenterService) GetByOrganizationID(
|
||||||
|
ctx context.Context,
|
||||||
|
organizationID gid.GID,
|
||||||
|
) (*coredata.TrustCenter, error) {
|
||||||
|
trustCenter := &coredata.TrustCenter{}
|
||||||
|
|
||||||
|
err := s.svc.pg.WithConn(
|
||||||
|
ctx,
|
||||||
|
func(conn pg.Conn) error {
|
||||||
|
err := trustCenter.LoadByOrganizationID(ctx, conn, s.svc.scope, organizationID)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cannot load trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return trustCenter, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *TrustCenterService) Update(
|
||||||
|
ctx context.Context,
|
||||||
|
req *UpdateTrustCenterRequest,
|
||||||
|
) (*coredata.TrustCenter, error) {
|
||||||
|
trustCenter := &coredata.TrustCenter{}
|
||||||
|
|
||||||
|
err := s.svc.pg.WithTx(
|
||||||
|
ctx,
|
||||||
|
func(conn pg.Conn) error {
|
||||||
|
if err := trustCenter.LoadByID(ctx, conn, s.svc.scope, req.ID); err != nil {
|
||||||
|
return fmt.Errorf("cannot load trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
if req.Active != nil {
|
||||||
|
trustCenter.Active = *req.Active
|
||||||
|
}
|
||||||
|
if req.Slug != nil {
|
||||||
|
trustCenter.Slug = *req.Slug
|
||||||
|
}
|
||||||
|
|
||||||
|
trustCenter.UpdatedAt = time.Now()
|
||||||
|
|
||||||
|
if err := trustCenter.Update(ctx, conn, s.svc.scope); err != nil {
|
||||||
|
return fmt.Errorf("cannot update trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return trustCenter, nil
|
||||||
|
}
|
||||||
@@ -72,6 +72,7 @@ type (
|
|||||||
StatusPageURL *string
|
StatusPageURL *string
|
||||||
BusinessOwnerID *gid.GID
|
BusinessOwnerID *gid.GID
|
||||||
SecurityOwnerID *gid.GID
|
SecurityOwnerID *gid.GID
|
||||||
|
ShowOnTrustCenter *bool
|
||||||
}
|
}
|
||||||
|
|
||||||
AssessVendorRequest struct {
|
AssessVendorRequest struct {
|
||||||
@@ -259,6 +260,10 @@ func (s VendorService) Update(
|
|||||||
vendor.SecurityPageURL = req.SecurityPageURL
|
vendor.SecurityPageURL = req.SecurityPageURL
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if req.ShowOnTrustCenter != nil {
|
||||||
|
vendor.ShowOnTrustCenter = *req.ShowOnTrustCenter
|
||||||
|
}
|
||||||
|
|
||||||
if req.TrustPageURL != nil {
|
if req.TrustPageURL != nil {
|
||||||
vendor.TrustPageURL = req.TrustPageURL
|
vendor.TrustPageURL = req.TrustPageURL
|
||||||
}
|
}
|
||||||
@@ -385,6 +390,7 @@ func (s VendorService) Create(
|
|||||||
TrustPageURL: req.TrustPageURL,
|
TrustPageURL: req.TrustPageURL,
|
||||||
StatusPageURL: req.StatusPageURL,
|
StatusPageURL: req.StatusPageURL,
|
||||||
TermsOfServiceURL: req.TermsOfServiceURL,
|
TermsOfServiceURL: req.TermsOfServiceURL,
|
||||||
|
ShowOnTrustCenter: false,
|
||||||
}
|
}
|
||||||
|
|
||||||
err := s.svc.pg.WithTx(
|
err := s.svc.pg.WithTx(
|
||||||
|
|||||||
@@ -703,6 +703,14 @@ input RiskFilter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
# Core Types
|
# Core Types
|
||||||
|
type TrustCenter implements Node {
|
||||||
|
id: ID!
|
||||||
|
active: Boolean!
|
||||||
|
slug: String!
|
||||||
|
createdAt: Datetime!
|
||||||
|
updatedAt: Datetime!
|
||||||
|
}
|
||||||
|
|
||||||
type Organization implements Node {
|
type Organization implements Node {
|
||||||
id: ID!
|
id: ID!
|
||||||
name: String!
|
name: String!
|
||||||
@@ -816,6 +824,8 @@ type Organization implements Node {
|
|||||||
orderBy: AuditOrder
|
orderBy: AuditOrder
|
||||||
): AuditConnection! @goField(forceResolver: true)
|
): AuditConnection! @goField(forceResolver: true)
|
||||||
|
|
||||||
|
trustCenter: TrustCenter @goField(forceResolver: true)
|
||||||
|
|
||||||
createdAt: Datetime!
|
createdAt: Datetime!
|
||||||
updatedAt: Datetime!
|
updatedAt: Datetime!
|
||||||
}
|
}
|
||||||
@@ -891,6 +901,7 @@ type Vendor implements Node {
|
|||||||
headquarterAddress: String
|
headquarterAddress: String
|
||||||
legalName: String
|
legalName: String
|
||||||
websiteUrl: String
|
websiteUrl: String
|
||||||
|
showOnTrustCenter: Boolean!
|
||||||
createdAt: Datetime!
|
createdAt: Datetime!
|
||||||
updatedAt: Datetime!
|
updatedAt: Datetime!
|
||||||
}
|
}
|
||||||
@@ -1052,6 +1063,7 @@ type Document implements Node {
|
|||||||
description: String!
|
description: String!
|
||||||
documentType: DocumentType!
|
documentType: DocumentType!
|
||||||
currentPublishedVersion: Int
|
currentPublishedVersion: Int
|
||||||
|
showOnTrustCenter: Boolean!
|
||||||
owner: People! @goField(forceResolver: true)
|
owner: People! @goField(forceResolver: true)
|
||||||
organization: Organization! @goField(forceResolver: true)
|
organization: Organization! @goField(forceResolver: true)
|
||||||
|
|
||||||
@@ -1134,6 +1146,7 @@ type Audit implements Node {
|
|||||||
report: Report @goField(forceResolver: true)
|
report: Report @goField(forceResolver: true)
|
||||||
reportUrl: String @goField(forceResolver: true)
|
reportUrl: String @goField(forceResolver: true)
|
||||||
state: AuditState!
|
state: AuditState!
|
||||||
|
showOnTrustCenter: Boolean!
|
||||||
createdAt: Datetime!
|
createdAt: Datetime!
|
||||||
updatedAt: Datetime!
|
updatedAt: Datetime!
|
||||||
}
|
}
|
||||||
@@ -1397,6 +1410,10 @@ type Mutation {
|
|||||||
input: UpdateOrganizationInput!
|
input: UpdateOrganizationInput!
|
||||||
): UpdateOrganizationPayload!
|
): UpdateOrganizationPayload!
|
||||||
|
|
||||||
|
updateTrustCenter(
|
||||||
|
input: UpdateTrustCenterInput!
|
||||||
|
): UpdateTrustCenterPayload!
|
||||||
|
|
||||||
# User mutations
|
# User mutations
|
||||||
confirmEmail(input: ConfirmEmailInput!): ConfirmEmailPayload!
|
confirmEmail(input: ConfirmEmailInput!): ConfirmEmailPayload!
|
||||||
inviteUser(input: InviteUserInput!): InviteUserPayload!
|
inviteUser(input: InviteUserInput!): InviteUserPayload!
|
||||||
@@ -1563,6 +1580,12 @@ input UpdateOrganizationInput {
|
|||||||
logo: Upload
|
logo: Upload
|
||||||
}
|
}
|
||||||
|
|
||||||
|
input UpdateTrustCenterInput {
|
||||||
|
trustCenterId: ID!
|
||||||
|
active: Boolean
|
||||||
|
slug: String
|
||||||
|
}
|
||||||
|
|
||||||
input CreateVendorInput {
|
input CreateVendorInput {
|
||||||
organizationId: ID!
|
organizationId: ID!
|
||||||
name: String!
|
name: String!
|
||||||
@@ -1605,6 +1628,7 @@ input UpdateVendorInput {
|
|||||||
trustPageUrl: String
|
trustPageUrl: String
|
||||||
businessOwnerId: ID
|
businessOwnerId: ID
|
||||||
securityOwnerId: ID
|
securityOwnerId: ID
|
||||||
|
showOnTrustCenter: Boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
input DeleteVendorInput {
|
input DeleteVendorInput {
|
||||||
@@ -1836,6 +1860,7 @@ input UpdateDocumentInput {
|
|||||||
ownerId: ID
|
ownerId: ID
|
||||||
createdBy: ID
|
createdBy: ID
|
||||||
documentType: DocumentType
|
documentType: DocumentType
|
||||||
|
showOnTrustCenter: Boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
input ExportDocumentVersionPDFInput {
|
input ExportDocumentVersionPDFInput {
|
||||||
@@ -1897,6 +1922,7 @@ input UpdateAuditInput {
|
|||||||
validFrom: Datetime
|
validFrom: Datetime
|
||||||
validUntil: Datetime
|
validUntil: Datetime
|
||||||
state: AuditState
|
state: AuditState
|
||||||
|
showOnTrustCenter: Boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
input DeleteAuditInput {
|
input DeleteAuditInput {
|
||||||
@@ -1921,6 +1947,10 @@ type UpdateOrganizationPayload {
|
|||||||
organization: Organization!
|
organization: Organization!
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type UpdateTrustCenterPayload {
|
||||||
|
trustCenter: TrustCenter!
|
||||||
|
}
|
||||||
|
|
||||||
type CreateControlPayload {
|
type CreateControlPayload {
|
||||||
controlEdge: ControlEdge!
|
controlEdge: ControlEdge!
|
||||||
}
|
}
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -54,12 +54,13 @@ func NewAuditConnection(
|
|||||||
|
|
||||||
func NewAudit(a *coredata.Audit) *Audit {
|
func NewAudit(a *coredata.Audit) *Audit {
|
||||||
return &Audit{
|
return &Audit{
|
||||||
ID: a.ID,
|
ID: a.ID,
|
||||||
ValidFrom: a.ValidFrom,
|
ValidFrom: a.ValidFrom,
|
||||||
ValidUntil: a.ValidUntil,
|
ValidUntil: a.ValidUntil,
|
||||||
State: a.State,
|
State: a.State,
|
||||||
CreatedAt: a.CreatedAt,
|
ShowOnTrustCenter: a.ShowOnTrustCenter,
|
||||||
UpdatedAt: a.UpdatedAt,
|
CreatedAt: a.CreatedAt,
|
||||||
|
UpdatedAt: a.UpdatedAt,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -79,6 +79,7 @@ func NewDocument(document *coredata.Document) *Document {
|
|||||||
Title: document.Title,
|
Title: document.Title,
|
||||||
DocumentType: document.DocumentType,
|
DocumentType: document.DocumentType,
|
||||||
CurrentPublishedVersion: document.CurrentPublishedVersion,
|
CurrentPublishedVersion: document.CurrentPublishedVersion,
|
||||||
|
ShowOnTrustCenter: document.ShowOnTrustCenter,
|
||||||
CreatedAt: document.CreatedAt,
|
CreatedAt: document.CreatedAt,
|
||||||
UpdatedAt: document.UpdatedAt,
|
UpdatedAt: document.UpdatedAt,
|
||||||
}
|
}
|
||||||
|
|||||||
29
pkg/server/api/console/v1/types/trust_center.go
Normal file
29
pkg/server/api/console/v1/types/trust_center.go
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
// Copyright (c) 2025 Probo Inc <hello@getprobo.com>.
|
||||||
|
//
|
||||||
|
// Permission to use, copy, modify, and/or distribute this software for any
|
||||||
|
// purpose with or without fee is hereby granted, provided that the above
|
||||||
|
// copyright notice and this permission notice appear in all copies.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
||||||
|
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||||
|
// AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
||||||
|
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
||||||
|
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
||||||
|
// OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
||||||
|
// PERFORMANCE OF THIS SOFTWARE.
|
||||||
|
|
||||||
|
package types
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/getprobo/probo/pkg/coredata"
|
||||||
|
)
|
||||||
|
|
||||||
|
func NewTrustCenter(tc *coredata.TrustCenter) *TrustCenter {
|
||||||
|
return &TrustCenter{
|
||||||
|
ID: tc.ID,
|
||||||
|
Active: tc.Active,
|
||||||
|
Slug: tc.Slug,
|
||||||
|
CreatedAt: tc.CreatedAt,
|
||||||
|
UpdatedAt: tc.UpdatedAt,
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -57,16 +57,17 @@ type AssignTaskPayload struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type Audit struct {
|
type Audit struct {
|
||||||
ID gid.GID `json:"id"`
|
ID gid.GID `json:"id"`
|
||||||
Organization *Organization `json:"organization"`
|
Organization *Organization `json:"organization"`
|
||||||
Framework *Framework `json:"framework"`
|
Framework *Framework `json:"framework"`
|
||||||
ValidFrom *time.Time `json:"validFrom,omitempty"`
|
ValidFrom *time.Time `json:"validFrom,omitempty"`
|
||||||
ValidUntil *time.Time `json:"validUntil,omitempty"`
|
ValidUntil *time.Time `json:"validUntil,omitempty"`
|
||||||
Report *Report `json:"report,omitempty"`
|
Report *Report `json:"report,omitempty"`
|
||||||
ReportURL *string `json:"reportUrl,omitempty"`
|
ReportURL *string `json:"reportUrl,omitempty"`
|
||||||
State coredata.AuditState `json:"state"`
|
State coredata.AuditState `json:"state"`
|
||||||
CreatedAt time.Time `json:"createdAt"`
|
ShowOnTrustCenter bool `json:"showOnTrustCenter"`
|
||||||
UpdatedAt time.Time `json:"updatedAt"`
|
CreatedAt time.Time `json:"createdAt"`
|
||||||
|
UpdatedAt time.Time `json:"updatedAt"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (Audit) IsNode() {}
|
func (Audit) IsNode() {}
|
||||||
@@ -582,6 +583,7 @@ type Document struct {
|
|||||||
Description string `json:"description"`
|
Description string `json:"description"`
|
||||||
DocumentType coredata.DocumentType `json:"documentType"`
|
DocumentType coredata.DocumentType `json:"documentType"`
|
||||||
CurrentPublishedVersion *int `json:"currentPublishedVersion,omitempty"`
|
CurrentPublishedVersion *int `json:"currentPublishedVersion,omitempty"`
|
||||||
|
ShowOnTrustCenter bool `json:"showOnTrustCenter"`
|
||||||
Owner *People `json:"owner"`
|
Owner *People `json:"owner"`
|
||||||
Organization *Organization `json:"organization"`
|
Organization *Organization `json:"organization"`
|
||||||
Versions *DocumentVersionConnection `json:"versions"`
|
Versions *DocumentVersionConnection `json:"versions"`
|
||||||
@@ -800,24 +802,25 @@ type Mutation struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type Organization struct {
|
type Organization struct {
|
||||||
ID gid.GID `json:"id"`
|
ID gid.GID `json:"id"`
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
LogoURL *string `json:"logoUrl,omitempty"`
|
LogoURL *string `json:"logoUrl,omitempty"`
|
||||||
Users *UserConnection `json:"users"`
|
Users *UserConnection `json:"users"`
|
||||||
Connectors *ConnectorConnection `json:"connectors"`
|
Connectors *ConnectorConnection `json:"connectors"`
|
||||||
Frameworks *FrameworkConnection `json:"frameworks"`
|
Frameworks *FrameworkConnection `json:"frameworks"`
|
||||||
Controls *ControlConnection `json:"controls"`
|
Controls *ControlConnection `json:"controls"`
|
||||||
Vendors *VendorConnection `json:"vendors"`
|
Vendors *VendorConnection `json:"vendors"`
|
||||||
Peoples *PeopleConnection `json:"peoples"`
|
Peoples *PeopleConnection `json:"peoples"`
|
||||||
Documents *DocumentConnection `json:"documents"`
|
Documents *DocumentConnection `json:"documents"`
|
||||||
Measures *MeasureConnection `json:"measures"`
|
Measures *MeasureConnection `json:"measures"`
|
||||||
Risks *RiskConnection `json:"risks"`
|
Risks *RiskConnection `json:"risks"`
|
||||||
Tasks *TaskConnection `json:"tasks"`
|
Tasks *TaskConnection `json:"tasks"`
|
||||||
Assets *AssetConnection `json:"assets"`
|
Assets *AssetConnection `json:"assets"`
|
||||||
Data *DatumConnection `json:"data"`
|
Data *DatumConnection `json:"data"`
|
||||||
Audits *AuditConnection `json:"audits"`
|
Audits *AuditConnection `json:"audits"`
|
||||||
CreatedAt time.Time `json:"createdAt"`
|
TrustCenter *TrustCenter `json:"trustCenter,omitempty"`
|
||||||
UpdatedAt time.Time `json:"updatedAt"`
|
CreatedAt time.Time `json:"createdAt"`
|
||||||
|
UpdatedAt time.Time `json:"updatedAt"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (Organization) IsNode() {}
|
func (Organization) IsNode() {}
|
||||||
@@ -992,6 +995,17 @@ type TaskEdge struct {
|
|||||||
Node *Task `json:"node"`
|
Node *Task `json:"node"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type TrustCenter struct {
|
||||||
|
ID gid.GID `json:"id"`
|
||||||
|
Active bool `json:"active"`
|
||||||
|
Slug string `json:"slug"`
|
||||||
|
CreatedAt time.Time `json:"createdAt"`
|
||||||
|
UpdatedAt time.Time `json:"updatedAt"`
|
||||||
|
}
|
||||||
|
|
||||||
|
func (TrustCenter) IsNode() {}
|
||||||
|
func (this TrustCenter) GetID() gid.GID { return this.ID }
|
||||||
|
|
||||||
type UnassignTaskInput struct {
|
type UnassignTaskInput struct {
|
||||||
TaskID gid.GID `json:"taskId"`
|
TaskID gid.GID `json:"taskId"`
|
||||||
}
|
}
|
||||||
@@ -1016,10 +1030,11 @@ type UpdateAssetPayload struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type UpdateAuditInput struct {
|
type UpdateAuditInput struct {
|
||||||
ID gid.GID `json:"id"`
|
ID gid.GID `json:"id"`
|
||||||
ValidFrom *time.Time `json:"validFrom,omitempty"`
|
ValidFrom *time.Time `json:"validFrom,omitempty"`
|
||||||
ValidUntil *time.Time `json:"validUntil,omitempty"`
|
ValidUntil *time.Time `json:"validUntil,omitempty"`
|
||||||
State *coredata.AuditState `json:"state,omitempty"`
|
State *coredata.AuditState `json:"state,omitempty"`
|
||||||
|
ShowOnTrustCenter *bool `json:"showOnTrustCenter,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type UpdateAuditPayload struct {
|
type UpdateAuditPayload struct {
|
||||||
@@ -1052,12 +1067,13 @@ type UpdateDatumPayload struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type UpdateDocumentInput struct {
|
type UpdateDocumentInput struct {
|
||||||
ID gid.GID `json:"id"`
|
ID gid.GID `json:"id"`
|
||||||
Title *string `json:"title,omitempty"`
|
Title *string `json:"title,omitempty"`
|
||||||
Content *string `json:"content,omitempty"`
|
Content *string `json:"content,omitempty"`
|
||||||
OwnerID *gid.GID `json:"ownerId,omitempty"`
|
OwnerID *gid.GID `json:"ownerId,omitempty"`
|
||||||
CreatedBy *gid.GID `json:"createdBy,omitempty"`
|
CreatedBy *gid.GID `json:"createdBy,omitempty"`
|
||||||
DocumentType *coredata.DocumentType `json:"documentType,omitempty"`
|
DocumentType *coredata.DocumentType `json:"documentType,omitempty"`
|
||||||
|
ShowOnTrustCenter *bool `json:"showOnTrustCenter,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type UpdateDocumentPayload struct {
|
type UpdateDocumentPayload struct {
|
||||||
@@ -1151,6 +1167,16 @@ type UpdateTaskPayload struct {
|
|||||||
Task *Task `json:"task"`
|
Task *Task `json:"task"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type UpdateTrustCenterInput struct {
|
||||||
|
TrustCenterID gid.GID `json:"trustCenterId"`
|
||||||
|
Active *bool `json:"active,omitempty"`
|
||||||
|
Slug *string `json:"slug,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type UpdateTrustCenterPayload struct {
|
||||||
|
TrustCenter *TrustCenter `json:"trustCenter"`
|
||||||
|
}
|
||||||
|
|
||||||
type UpdateVendorInput struct {
|
type UpdateVendorInput struct {
|
||||||
ID gid.GID `json:"id"`
|
ID gid.GID `json:"id"`
|
||||||
Name *string `json:"name,omitempty"`
|
Name *string `json:"name,omitempty"`
|
||||||
@@ -1171,6 +1197,7 @@ type UpdateVendorInput struct {
|
|||||||
TrustPageURL *string `json:"trustPageUrl,omitempty"`
|
TrustPageURL *string `json:"trustPageUrl,omitempty"`
|
||||||
BusinessOwnerID *gid.GID `json:"businessOwnerId,omitempty"`
|
BusinessOwnerID *gid.GID `json:"businessOwnerId,omitempty"`
|
||||||
SecurityOwnerID *gid.GID `json:"securityOwnerId,omitempty"`
|
SecurityOwnerID *gid.GID `json:"securityOwnerId,omitempty"`
|
||||||
|
ShowOnTrustCenter *bool `json:"showOnTrustCenter,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type UpdateVendorPayload struct {
|
type UpdateVendorPayload struct {
|
||||||
@@ -1261,6 +1288,7 @@ type Vendor struct {
|
|||||||
HeadquarterAddress *string `json:"headquarterAddress,omitempty"`
|
HeadquarterAddress *string `json:"headquarterAddress,omitempty"`
|
||||||
LegalName *string `json:"legalName,omitempty"`
|
LegalName *string `json:"legalName,omitempty"`
|
||||||
WebsiteURL *string `json:"websiteUrl,omitempty"`
|
WebsiteURL *string `json:"websiteUrl,omitempty"`
|
||||||
|
ShowOnTrustCenter bool `json:"showOnTrustCenter"`
|
||||||
CreatedAt time.Time `json:"createdAt"`
|
CreatedAt time.Time `json:"createdAt"`
|
||||||
UpdatedAt time.Time `json:"updatedAt"`
|
UpdatedAt time.Time `json:"updatedAt"`
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -79,6 +79,7 @@ func NewVendor(v *coredata.Vendor) *Vendor {
|
|||||||
LegalName: v.LegalName,
|
LegalName: v.LegalName,
|
||||||
WebsiteURL: v.WebsiteURL,
|
WebsiteURL: v.WebsiteURL,
|
||||||
Category: v.Category,
|
Category: v.Category,
|
||||||
|
ShowOnTrustCenter: v.ShowOnTrustCenter,
|
||||||
UpdatedAt: v.UpdatedAt,
|
UpdatedAt: v.UpdatedAt,
|
||||||
CreatedAt: v.CreatedAt,
|
CreatedAt: v.CreatedAt,
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -980,6 +980,24 @@ func (r *mutationResolver) UpdateOrganization(ctx context.Context, input types.U
|
|||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// UpdateTrustCenter is the resolver for the updateTrustCenter field.
|
||||||
|
func (r *mutationResolver) UpdateTrustCenter(ctx context.Context, input types.UpdateTrustCenterInput) (*types.UpdateTrustCenterPayload, error) {
|
||||||
|
prb := r.ProboService(ctx, input.TrustCenterID.TenantID())
|
||||||
|
|
||||||
|
trustCenter, err := prb.TrustCenters.Update(ctx, &probo.UpdateTrustCenterRequest{
|
||||||
|
ID: input.TrustCenterID,
|
||||||
|
Active: input.Active,
|
||||||
|
Slug: input.Slug,
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
return nil, fmt.Errorf("cannot update trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return &types.UpdateTrustCenterPayload{
|
||||||
|
TrustCenter: types.NewTrustCenter(trustCenter),
|
||||||
|
}, nil
|
||||||
|
}
|
||||||
|
|
||||||
// ConfirmEmail is the resolver for the confirmEmail field.
|
// ConfirmEmail is the resolver for the confirmEmail field.
|
||||||
func (r *mutationResolver) ConfirmEmail(ctx context.Context, input types.ConfirmEmailInput) (*types.ConfirmEmailPayload, error) {
|
func (r *mutationResolver) ConfirmEmail(ctx context.Context, input types.ConfirmEmailInput) (*types.ConfirmEmailPayload, error) {
|
||||||
err := r.usrmgrSvc.ConfirmEmail(ctx, input.Token)
|
err := r.usrmgrSvc.ConfirmEmail(ctx, input.Token)
|
||||||
@@ -1158,6 +1176,7 @@ func (r *mutationResolver) UpdateVendor(ctx context.Context, input types.UpdateV
|
|||||||
Certifications: input.Certifications,
|
Certifications: input.Certifications,
|
||||||
BusinessOwnerID: input.BusinessOwnerID,
|
BusinessOwnerID: input.BusinessOwnerID,
|
||||||
SecurityOwnerID: input.SecurityOwnerID,
|
SecurityOwnerID: input.SecurityOwnerID,
|
||||||
|
ShowOnTrustCenter: input.ShowOnTrustCenter,
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, fmt.Errorf("cannot update vendor: %w", err)
|
return nil, fmt.Errorf("cannot update vendor: %w", err)
|
||||||
@@ -1879,6 +1898,7 @@ func (r *mutationResolver) UpdateDocument(ctx context.Context, input types.Updat
|
|||||||
input.OwnerID,
|
input.OwnerID,
|
||||||
input.DocumentType,
|
input.DocumentType,
|
||||||
input.Title,
|
input.Title,
|
||||||
|
input.ShowOnTrustCenter,
|
||||||
)
|
)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -2300,10 +2320,11 @@ func (r *mutationResolver) UpdateAudit(ctx context.Context, input types.UpdateAu
|
|||||||
prb := r.ProboService(ctx, input.ID.TenantID())
|
prb := r.ProboService(ctx, input.ID.TenantID())
|
||||||
|
|
||||||
req := probo.UpdateAuditRequest{
|
req := probo.UpdateAuditRequest{
|
||||||
ID: input.ID,
|
ID: input.ID,
|
||||||
ValidFrom: input.ValidFrom,
|
ValidFrom: input.ValidFrom,
|
||||||
ValidUntil: input.ValidUntil,
|
ValidUntil: input.ValidUntil,
|
||||||
State: input.State,
|
State: input.State,
|
||||||
|
ShowOnTrustCenter: input.ShowOnTrustCenter,
|
||||||
}
|
}
|
||||||
|
|
||||||
audit, err := prb.Audits.Update(ctx, &req)
|
audit, err := prb.Audits.Update(ctx, &req)
|
||||||
@@ -2718,6 +2739,18 @@ func (r *organizationResolver) Audits(ctx context.Context, obj *types.Organizati
|
|||||||
return types.NewAuditConnection(page, r, obj.ID), nil
|
return types.NewAuditConnection(page, r, obj.ID), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TrustCenter is the resolver for the trustCenter field.
|
||||||
|
func (r *organizationResolver) TrustCenter(ctx context.Context, obj *types.Organization) (*types.TrustCenter, error) {
|
||||||
|
prb := r.ProboService(ctx, obj.ID.TenantID())
|
||||||
|
|
||||||
|
trustCenter, err := prb.TrustCenters.GetByOrganizationID(ctx, obj.ID)
|
||||||
|
if err != nil {
|
||||||
|
return nil, fmt.Errorf("cannot get trust center: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return types.NewTrustCenter(trustCenter), nil
|
||||||
|
}
|
||||||
|
|
||||||
// TotalCount is the resolver for the totalCount field.
|
// TotalCount is the resolver for the totalCount field.
|
||||||
func (r *peopleConnectionResolver) TotalCount(ctx context.Context, obj *types.PeopleConnection) (int, error) {
|
func (r *peopleConnectionResolver) TotalCount(ctx context.Context, obj *types.PeopleConnection) (int, error) {
|
||||||
prb := r.ProboService(ctx, obj.ParentID.TenantID())
|
prb := r.ProboService(ctx, obj.ParentID.TenantID())
|
||||||
@@ -2849,6 +2882,12 @@ func (r *queryResolver) Node(ctx context.Context, id gid.GID) (types.Node, error
|
|||||||
panic(fmt.Errorf("cannot get report: %w", err))
|
panic(fmt.Errorf("cannot get report: %w", err))
|
||||||
}
|
}
|
||||||
return types.NewReport(report), nil
|
return types.NewReport(report), nil
|
||||||
|
case coredata.TrustCenterEntityType:
|
||||||
|
trustCenter, err := prb.TrustCenters.GetByOrganizationID(ctx, id)
|
||||||
|
if err != nil {
|
||||||
|
panic(fmt.Errorf("cannot get trust center: %w", err))
|
||||||
|
}
|
||||||
|
return types.NewTrustCenter(trustCenter), nil
|
||||||
default:
|
default:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user