mirror of
https://github.com/documenso/documenso.git
synced 2025-11-13 16:23:06 +10:00
## Description This PR introduces global settings for teams. At the moment, it allows team admins to configure the following: * The default visibility of the documents uploaded to the team account * Whether to include the document owner (sender) details when sending emails to the recipients. ### Include Sender Details If the Sender Details setting is enabled, the emails sent by the team will include the sender's name: > "Example User" on behalf of "Example Team" has invited you to sign "document.pdf" Otherwise, the email will say: > "Example Team" has invited you to sign "document.pdf" ### Default Document Visibility This new option allows users to set the default visibility for the documents uploaded to the team account. It can have the following values: * Everyone * Manager and above * Admins only If the default document visibility isn't set, the document will be set to the role of the user who created the document: * If a user with the "User" role creates a document, the document's visibility is set to "Everyone". * Manager role -> "Manager and above" * Admin role -> "Admins only" Otherwise, if there is a default document visibility value, it uses that value. #### Gotcha To avoid issues, the `document owner` and the `recipient` can access the document irrespective of their role. For example: * If a team member with the role "Member" uploads a document and the default document visibility is "Admins", only the document owner and admins can access the document. * Similar to the other scenarios. * If an admin uploads a document and the default document visibility is "Admins", the recipient can access the document. * The admins have access to all the documents. * Managers have access to documents with the visibility set to "Everyone" and "Manager and above" * Members have access only to the documents with the visibility set to "Everyone". ## Testing Performed Tested it locally.
234 lines
6.8 KiB
TypeScript
234 lines
6.8 KiB
TypeScript
import { z } from 'zod';
|
|
|
|
import { SUPPORTED_LANGUAGE_CODES } from '@documenso/lib/constants/i18n';
|
|
import {
|
|
ZDocumentAccessAuthTypesSchema,
|
|
ZDocumentActionAuthTypesSchema,
|
|
} from '@documenso/lib/types/document-auth';
|
|
import { ZDocumentEmailSettingsSchema } from '@documenso/lib/types/document-email';
|
|
import { ZBaseTableSearchParamsSchema } from '@documenso/lib/types/search-params';
|
|
import { isValidRedirectUrl } from '@documenso/lib/utils/is-valid-redirect-url';
|
|
import {
|
|
DocumentDistributionMethod,
|
|
DocumentSigningOrder,
|
|
DocumentSource,
|
|
DocumentStatus,
|
|
DocumentVisibility,
|
|
FieldType,
|
|
RecipientRole,
|
|
} from '@documenso/prisma/client';
|
|
|
|
export const ZFindDocumentsQuerySchema = ZBaseTableSearchParamsSchema.extend({
|
|
teamId: z.number().min(1).optional(),
|
|
templateId: z.number().min(1).optional(),
|
|
search: z
|
|
.string()
|
|
.optional()
|
|
.catch(() => undefined),
|
|
source: z.nativeEnum(DocumentSource).optional(),
|
|
status: z.nativeEnum(DocumentStatus).optional(),
|
|
orderBy: z
|
|
.object({
|
|
column: z.enum(['createdAt']),
|
|
direction: z.enum(['asc', 'desc']),
|
|
})
|
|
.optional(),
|
|
}).omit({ query: true });
|
|
|
|
export const ZFindDocumentAuditLogsQuerySchema = ZBaseTableSearchParamsSchema.extend({
|
|
documentId: z.number().min(1),
|
|
cursor: z.string().optional(),
|
|
filterForRecentActivity: z.boolean().optional(),
|
|
orderBy: z
|
|
.object({
|
|
column: z.enum(['createdAt', 'type']),
|
|
direction: z.enum(['asc', 'desc']),
|
|
})
|
|
.optional(),
|
|
});
|
|
|
|
export const ZGetDocumentByIdQuerySchema = z.object({
|
|
id: z.number().min(1),
|
|
teamId: z.number().min(1).optional(),
|
|
});
|
|
|
|
export type TGetDocumentByIdQuerySchema = z.infer<typeof ZGetDocumentByIdQuerySchema>;
|
|
|
|
export const ZGetDocumentByTokenQuerySchema = z.object({
|
|
token: z.string().min(1),
|
|
});
|
|
|
|
export type TGetDocumentByTokenQuerySchema = z.infer<typeof ZGetDocumentByTokenQuerySchema>;
|
|
|
|
export const ZGetDocumentWithDetailsByIdQuerySchema = z.object({
|
|
id: z.number().min(1),
|
|
teamId: z.number().min(1).optional(),
|
|
});
|
|
|
|
export type TGetDocumentWithDetailsByIdQuerySchema = z.infer<
|
|
typeof ZGetDocumentWithDetailsByIdQuerySchema
|
|
>;
|
|
|
|
export const ZCreateDocumentMutationSchema = z.object({
|
|
title: z.string().min(1),
|
|
documentDataId: z.string().min(1),
|
|
teamId: z.number().optional(),
|
|
});
|
|
|
|
export type TCreateDocumentMutationSchema = z.infer<typeof ZCreateDocumentMutationSchema>;
|
|
|
|
export const ZSetSettingsForDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().min(1).optional(),
|
|
data: z.object({
|
|
title: z.string().min(1).optional(),
|
|
externalId: z.string().nullish(),
|
|
visibility: z.nativeEnum(DocumentVisibility).optional(),
|
|
globalAccessAuth: ZDocumentAccessAuthTypesSchema.nullable().optional(),
|
|
globalActionAuth: ZDocumentActionAuthTypesSchema.nullable().optional(),
|
|
}),
|
|
meta: z.object({
|
|
timezone: z.string(),
|
|
dateFormat: z.string(),
|
|
redirectUrl: z
|
|
.string()
|
|
.optional()
|
|
.refine((value) => value === undefined || value === '' || isValidRedirectUrl(value), {
|
|
message:
|
|
'Please enter a valid URL, make sure you include http:// or https:// part of the url.',
|
|
}),
|
|
language: z.enum(SUPPORTED_LANGUAGE_CODES).optional(),
|
|
}),
|
|
});
|
|
|
|
export type TSetGeneralSettingsForDocumentMutationSchema = z.infer<
|
|
typeof ZSetSettingsForDocumentMutationSchema
|
|
>;
|
|
|
|
export const ZSetTitleForDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().min(1).optional(),
|
|
title: z.string().min(1),
|
|
});
|
|
|
|
export type TSetTitleForDocumentMutationSchema = z.infer<typeof ZSetTitleForDocumentMutationSchema>;
|
|
|
|
export const ZSetRecipientsForDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().min(1).optional(),
|
|
recipients: z.array(
|
|
z.object({
|
|
id: z.number().nullish(),
|
|
email: z.string().min(1).email(),
|
|
name: z.string(),
|
|
role: z.nativeEnum(RecipientRole),
|
|
}),
|
|
),
|
|
});
|
|
|
|
export type TSetRecipientsForDocumentMutationSchema = z.infer<
|
|
typeof ZSetRecipientsForDocumentMutationSchema
|
|
>;
|
|
|
|
export const ZSetFieldsForDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
fields: z.array(
|
|
z.object({
|
|
id: z.number().nullish(),
|
|
type: z.nativeEnum(FieldType),
|
|
signerEmail: z.string().min(1),
|
|
pageNumber: z.number().min(1),
|
|
pageX: z.number().min(0),
|
|
pageY: z.number().min(0),
|
|
pageWidth: z.number().min(0),
|
|
pageHeight: z.number().min(0),
|
|
}),
|
|
),
|
|
});
|
|
|
|
export type TSetFieldsForDocumentMutationSchema = z.infer<
|
|
typeof ZSetFieldsForDocumentMutationSchema
|
|
>;
|
|
|
|
export const ZSendDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().optional(),
|
|
meta: z.object({
|
|
subject: z.string(),
|
|
message: z.string(),
|
|
timezone: z.string().optional(),
|
|
dateFormat: z.string().optional(),
|
|
distributionMethod: z.nativeEnum(DocumentDistributionMethod).optional(),
|
|
redirectUrl: z
|
|
.string()
|
|
.optional()
|
|
.refine((value) => value === undefined || value === '' || isValidRedirectUrl(value), {
|
|
message:
|
|
'Please enter a valid URL, make sure you include http:// or https:// part of the url.',
|
|
}),
|
|
emailSettings: ZDocumentEmailSettingsSchema.optional(),
|
|
}),
|
|
});
|
|
|
|
export const ZSetPasswordForDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
password: z.string(),
|
|
});
|
|
|
|
export type TSetPasswordForDocumentMutationSchema = z.infer<
|
|
typeof ZSetPasswordForDocumentMutationSchema
|
|
>;
|
|
|
|
export const ZSetSigningOrderForDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
signingOrder: z.nativeEnum(DocumentSigningOrder),
|
|
});
|
|
|
|
export type TSetSigningOrderForDocumentMutationSchema = z.infer<
|
|
typeof ZSetSigningOrderForDocumentMutationSchema
|
|
>;
|
|
|
|
export const ZUpdateTypedSignatureSettingsMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().optional(),
|
|
typedSignatureEnabled: z.boolean(),
|
|
});
|
|
|
|
export type TUpdateTypedSignatureSettingsMutationSchema = z.infer<
|
|
typeof ZUpdateTypedSignatureSettingsMutationSchema
|
|
>;
|
|
|
|
export const ZResendDocumentMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
recipients: z.array(z.number()).min(1),
|
|
teamId: z.number().min(1).optional(),
|
|
});
|
|
|
|
export type TSendDocumentMutationSchema = z.infer<typeof ZSendDocumentMutationSchema>;
|
|
|
|
export const ZDeleteDraftDocumentMutationSchema = z.object({
|
|
id: z.number().min(1),
|
|
teamId: z.number().min(1).optional(),
|
|
});
|
|
|
|
export type TDeleteDraftDocumentMutationSchema = z.infer<typeof ZDeleteDraftDocumentMutationSchema>;
|
|
|
|
export const ZSearchDocumentsMutationSchema = z.object({
|
|
query: z.string(),
|
|
});
|
|
|
|
export const ZDownloadAuditLogsMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().optional(),
|
|
});
|
|
|
|
export const ZDownloadCertificateMutationSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number().optional(),
|
|
});
|
|
|
|
export const ZMoveDocumentsToTeamSchema = z.object({
|
|
documentId: z.number(),
|
|
teamId: z.number(),
|
|
});
|