mirror of
https://github.com/documenso/documenso.git
synced 2026-09-29 16:24:30 +10:00
feat: hide the reject option when the document disallows rejection
Hides the reject dialog on the V2 signing page sidebar and mobile menu, the embed V1 signing page and the multi-sign embed view when the document's allowDocumentRejection is false. In embeds the reject option is shown only when both the embed's allowDocumentRejection option and the document setting allow it, and the embed V1 footer layout follows the same condition. Exposes the field in the multi-sign document response so the embed view can read it. Documents the relationship between the embed's allowDocumentRejection option and the document setting in the iframe and embedded editor docs, and in the API description of the field. Part of #2561
This commit is contained in:
@@ -186,6 +186,15 @@ Controls envelope configuration options. Set to `null` to hide envelope settings
|
||||
| `allowConfigureEmailSender` | `boolean` | `true` | Allow configuring the email sender |
|
||||
| `allowConfigureEmailReplyTo` | `boolean` | `true` | Allow configuring the email reply-to |
|
||||
|
||||
<Callout title="Allow Document Rejection">
|
||||
The settings dialog also contains an "Allow Document Rejection" option that is always shown. It sets the document's
|
||||
own rejection setting (`meta.allowDocumentRejection` in the API) and defaults to the organisation or team document
|
||||
preference. This
|
||||
is separate from the `allowDocumentRejection` option of the embedded signing views: that option only controls the
|
||||
signing embed's UI, while this one is stored on the document and enforced by the server. A recipient can reject only
|
||||
when both allow it.
|
||||
</Callout>
|
||||
|
||||
### Actions
|
||||
|
||||
Controls available actions during editing:
|
||||
|
||||
@@ -47,10 +47,20 @@ Documenso expects the fragment to be **base64** of:
|
||||
| `lockEmail` | `boolean` | Lock the email field (prevents editing). |
|
||||
| `language` | `string` | Force the embed language (e.g. `en`). |
|
||||
| `darkModeDisabled` | `boolean` | Disable dark mode behavior. |
|
||||
| `allowDocumentRejection` | `boolean` | Allow or disallow document rejection. |
|
||||
| `allowDocumentRejection` | `boolean` | Show the reject option in the embed. Defaults to `false`. The document must also allow rejection, see below. |
|
||||
| `css` | `string` | Inject custom CSS into the embed. |
|
||||
| `cssVars` | `object` | Override embed CSS variables (see the CSS Variables page). |
|
||||
|
||||
<Callout title="allowDocumentRejection and the document's own setting">
|
||||
Two settings control whether a recipient can reject a document in an embed, and both must allow it:
|
||||
|
||||
- `allowDocumentRejection` above, which you pass per embed. It only controls your embed's UI and defaults to `false`.
|
||||
- The document's own "Allow Document Rejection" setting. Its default comes from the organisation or team document
|
||||
preferences, and it can be changed per document in the editor or through the API (`meta.allowDocumentRejection`).
|
||||
When it is disabled, the reject option stays hidden even if you pass `allowDocumentRejection: true`, and the server
|
||||
refuses rejection requests for that document.
|
||||
</Callout>
|
||||
|
||||
#### Example
|
||||
|
||||
```ts
|
||||
|
||||
@@ -96,6 +96,9 @@ export const EmbedSignDocumentV1ClientPage = ({
|
||||
|
||||
const [allowDocumentRejection, setAllowDocumentRejection] = useState(false);
|
||||
|
||||
// Both the embed host and the document settings must allow rejection.
|
||||
const isDocumentRejectionAllowed = allowDocumentRejection && (metadata?.allowDocumentRejection ?? true);
|
||||
|
||||
const selectedSigner = allRecipients.find((r) => r.id === selectedSignerId);
|
||||
const isAssistantMode = recipient.role === RecipientRole.ASSISTANT;
|
||||
|
||||
@@ -303,7 +306,7 @@ export const EmbedSignDocumentV1ClientPage = ({
|
||||
<div className="embed--Actions mb-4 flex w-full flex-row-reverse items-baseline justify-between">
|
||||
<DocumentSigningAttachmentsPopover envelopeId={envelopeId} token={token} />
|
||||
|
||||
{allowDocumentRejection && (
|
||||
{isDocumentRejectionAllowed && (
|
||||
<DocumentSigningRejectDialog documentId={documentId} token={token} onRejected={onDocumentRejected} />
|
||||
)}
|
||||
</div>
|
||||
@@ -502,7 +505,7 @@ export const EmbedSignDocumentV1ClientPage = ({
|
||||
</Button>
|
||||
) : (
|
||||
<Button
|
||||
className={allowDocumentRejection ? 'col-start-2' : 'col-span-2'}
|
||||
className={isDocumentRejectionAllowed ? 'col-start-2' : 'col-span-2'}
|
||||
disabled={isThrottled}
|
||||
loading={isSubmitting}
|
||||
onClick={() => throttledOnCompleteClick()}
|
||||
|
||||
@@ -228,7 +228,7 @@ export const MultiSignDocumentSigningView = ({
|
||||
</Button>
|
||||
</div>
|
||||
|
||||
{allowDocumentRejection && (
|
||||
{allowDocumentRejection && (document.documentMeta?.allowDocumentRejection ?? true) && (
|
||||
<div className="embed--Actions mt-8 mb-4 flex w-full flex-row-reverse items-baseline justify-between">
|
||||
<DocumentSigningRejectDialog documentId={document.id} token={token} onRejected={onRejected} />
|
||||
</div>
|
||||
|
||||
+5
-1
@@ -63,6 +63,10 @@ export const DocumentSigningPageViewV2 = () => {
|
||||
onDocumentRejected,
|
||||
} = useEmbedSigningContext() || {};
|
||||
|
||||
// Both the document settings and the embed host (if any) must allow rejection.
|
||||
const isDocumentRejectionAllowed =
|
||||
envelope.type === EnvelopeType.DOCUMENT && envelope.documentMeta.allowDocumentRejection && allowDocumentRejection;
|
||||
|
||||
const { t } = useLingui();
|
||||
const [isSidebarCollapsed, setIsSidebarCollapsed] = useState(false);
|
||||
|
||||
@@ -193,7 +197,7 @@ export const DocumentSigningPageViewV2 = () => {
|
||||
}
|
||||
/>
|
||||
|
||||
{envelope.type === EnvelopeType.DOCUMENT && allowDocumentRejection && (
|
||||
{isDocumentRejectionAllowed && (
|
||||
<DocumentSigningRejectDialog
|
||||
documentId={mapSecondaryIdToDocumentId(envelope.secondaryId)}
|
||||
token={recipient.token}
|
||||
|
||||
@@ -87,7 +87,11 @@ export const EnvelopeSignerHeader = () => {
|
||||
const MobileDropdownMenu = () => {
|
||||
const { envelope, recipient } = useRequiredEnvelopeSigningContext();
|
||||
|
||||
const { allowDocumentRejection } = useEmbedSigningContext() || {};
|
||||
const { allowDocumentRejection = true } = useEmbedSigningContext() || {};
|
||||
|
||||
// Both the document settings and the embed host (if any) must allow rejection.
|
||||
const isDocumentRejectionAllowed =
|
||||
envelope.type === EnvelopeType.DOCUMENT && envelope.documentMeta.allowDocumentRejection && allowDocumentRejection;
|
||||
|
||||
return (
|
||||
<DropdownMenu>
|
||||
@@ -113,7 +117,7 @@ const MobileDropdownMenu = () => {
|
||||
}
|
||||
/>
|
||||
|
||||
{envelope.type === EnvelopeType.DOCUMENT && allowDocumentRejection !== false && (
|
||||
{isDocumentRejectionAllowed && (
|
||||
<DocumentSigningRejectDialog
|
||||
documentId={mapSecondaryIdToDocumentId(envelope.secondaryId)}
|
||||
token={recipient.token}
|
||||
|
||||
@@ -108,7 +108,9 @@ export const ZDocumentMetaUploadSignatureEnabledSchema = z
|
||||
|
||||
export const ZDocumentMetaAllowDocumentRejectionSchema = z
|
||||
.boolean()
|
||||
.describe('Whether to allow recipients to reject the document from the signing page.');
|
||||
.describe(
|
||||
'Whether recipients can reject the document from the signing page. Defaults to the organisation or team document preference. In embedded signing the embed must also enable its own allowDocumentRejection option.',
|
||||
);
|
||||
|
||||
/**
|
||||
* Note: Any updates to this will cause public API changes. You will need to update
|
||||
|
||||
@@ -31,6 +31,7 @@ export const ZGetMultiSignDocumentResponseSchema = ZDocumentLiteSchema.extend({
|
||||
uploadSignatureEnabled: true,
|
||||
drawSignatureEnabled: true,
|
||||
allowDictateNextSigner: true,
|
||||
allowDocumentRejection: true,
|
||||
language: true,
|
||||
emailSettings: true,
|
||||
}).nullable(),
|
||||
|
||||
Reference in New Issue
Block a user