Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 2 additions & 10 deletions apps/remix/app/components/forms/signup.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -411,19 +411,11 @@ export const SignUpForm = ({
<p className="mt-6 text-muted-foreground text-xs">
<Trans>
By proceeding, you agree to our{' '}
<Link
to="https://documen.so/terms"
target="_blank"
className="text-documenso-700 duration-200 hover:opacity-70"
>
<Link to="/terms" className="text-documenso-700 duration-200 hover:opacity-70">
Terms of Service
</Link>{' '}
and{' '}
<Link
to="https://documen.so/privacy"
target="_blank"
className="text-documenso-700 duration-200 hover:opacity-70"
>
<Link to="/privacy" className="text-documenso-700 duration-200 hover:opacity-70">
Privacy Policy
</Link>
.
Expand Down
16 changes: 8 additions & 8 deletions apps/remix/app/routes/_share+/share.$slug.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,15 +12,15 @@ export function meta({ params: { slug } }: Route.MetaArgs) {
}

return [
{ title: 'Documenso - Share' },
{ description: 'I just signed a document in style with Documenso!' },
{ title: 'Crove Sign - Share' },
{ description: 'I just signed a document in style with Crove Sign!' },
{
property: 'og:title',
content: 'Documenso - Join the open source signing revolution',
content: 'Crove Sign - Electronic signatures for the Crove OS ecosystem',
},
{
property: 'og:description',
content: 'I just signed with Documenso!',
content: 'I just signed with Crove Sign!',
},
{
property: 'og:type',
Expand All @@ -32,7 +32,7 @@ export function meta({ params: { slug } }: Route.MetaArgs) {
},
{
name: 'twitter:site',
content: '@documenso',
content: '@crovedos',
},
{
name: 'twitter:card',
Expand All @@ -44,7 +44,7 @@ export function meta({ params: { slug } }: Route.MetaArgs) {
},
{
name: 'twitter:description',
content: 'I just signed with Documenso!',
content: 'I just signed with Crove Sign!',
},
];
}
Expand All @@ -69,8 +69,8 @@ export const loader = async ({ request, params: { slug } }: Route.LoaderArgs) =>
return {};
}

// Is hardcoded because this whole meta is hardcoded anyway for Documenso.
throw redirect('https://documenso.com');
// Non-share visitors (bots excluded above) land on the app home.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 IMPORTANT: Missing fallback for NEXT_PUBLIC_WEBAPP_URL() in redirect

Failure Trace:

  1. A user visits a share link that is not accessible (e.g., expired or private).
    2. The loader executes throw redirect(NEXT_PUBLIC_WEBAPP_URL());.
    3. If the NEXT_PUBLIC_WEBAPP_URL environment variable is not defined in the deployment environment, NEXT_PUBLIC_WEBAPP_URL() returns undefined (or an empty string, depending on the env implementation).
    4. redirect(undefined) results in an invalid redirect target, causing a 500 Internal Server Error or a broken redirect instead of landing on the app home.
Suggested change
// Non-share visitors (bots excluded above) land on the app home.
throw redirect(NEXT_PUBLIC_WEBAPP_URL() || '/');

throw redirect(NEXT_PUBLIC_WEBAPP_URL());
};

export default function SharePage() {
Expand Down
97 changes: 97 additions & 0 deletions apps/remix/app/routes/_unauthenticated+/privacy.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
import { Button } from '@documenso/ui/primitives/button';
import { Trans } from '@lingui/react/macro';
import { Link } from 'react-router';

// PLACEHOLDER LEGAL TEXT: replace with a privacy policy reviewed for the
// operating entity before relying on it commercially.
export default function PrivacyPolicy() {
return (
<div>
<article className="prose dark:prose-invert">
<h1>
<Trans>Privacy Policy</Trans>
</h1>

<p>
<Trans>
Last updated: September 2026. This policy explains what personal data Crove Sign processes, why, and the
choices you have.
</Trans>
</p>

<h2>
<Trans>1. Data We Process</Trans>
</h2>
<p>
<Trans>
Account data (name, email, avatar) synced from your identity provider, the documents you upload, signature
and audit metadata, and technical logs such as IP address and user agent required to operate the service.
</Trans>
</p>

<h2>
<Trans>2. Why We Process It</Trans>
</h2>
<p>
<Trans>
To provide the signing service, keep documents and audit trails verifiable, send you transactional emails
about your documents, prevent abuse, and comply with legal obligations.
</Trans>
</p>

<h2>
<Trans>3. Document Confidentiality</Trans>
</h2>
<p>
<Trans>
Your documents are processed only to deliver the service. We do not use your document contents for
advertising or train models on them.
</Trans>
</p>

<h2>
<Trans>4. Data Sharing</Trans>
</h2>
<p>
<Trans>
We share data only with the infrastructure providers that operate the Crove OS ecosystem, with recipients
and senders involved in a signing workflow, and where required by law.
</Trans>
</p>

<h2>
<Trans>5. Retention</Trans>
</h2>
<p>
<Trans>
Documents and audit records are retained while your account is active and as required for the integrity of
completed signings. You can request deletion of your account and associated data.
</Trans>
</p>

<h2>
<Trans>6. Your Rights</Trans>
</h2>
<p>
<Trans>
You can access, correct, export, or delete your personal data through your account settings or by contacting
support through the Crove OS ecosystem channels.
</Trans>
</p>

<h2>
<Trans>7. Contact</Trans>
</h2>
<p>
<Trans>Privacy questions can be sent through the support channels of the Crove OS ecosystem.</Trans>
</p>
</article>

<Link to="/signin" className="mt-8 inline-block">
<Button>
<Trans>Back to sign in</Trans>
</Button>
</Link>
</div>
);
}
119 changes: 119 additions & 0 deletions apps/remix/app/routes/_unauthenticated+/terms.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
import { Button } from '@documenso/ui/primitives/button';
import { Trans } from '@lingui/react/macro';
import { Link } from 'react-router';

// PLACEHOLDER LEGAL TEXT: replace with terms reviewed for the operating
// entity before relying on them commercially.
export default function TermsOfService() {
return (
<div>
<article className="prose dark:prose-invert">
<h1>
<Trans>Terms of Service</Trans>
</h1>

<p>
<Trans>
Last updated: September 2026. These terms govern your use of Crove Sign, the electronic signature service
operated as part of the Crove OS ecosystem.
</Trans>
</p>

<h2>
<Trans>1. Acceptance of Terms</Trans>
</h2>
<p>
<Trans>
By creating an account or using Crove Sign you agree to these Terms of Service. If you use the service on
behalf of an organisation, you confirm that you are authorised to bind that organisation.
</Trans>
</p>

<h2>
<Trans>2. The Service</Trans>
</h2>
<p>
<Trans>
Crove Sign lets you prepare, send, sign, and manage documents electronically, including advanced electronic
signatures and optional blockchain-sealed attestation records. The service is provided through the web
application and its associated APIs.
</Trans>
</p>

<h2>
<Trans>3. Your Account</Trans>
</h2>
<p>
<Trans>
You are responsible for safeguarding the credentials to your identity provider account, for the accuracy of
the information you provide, and for all activity carried out under your account.
</Trans>
</p>

<h2>
<Trans>4. Your Documents and Content</Trans>
</h2>
<p>
<Trans>
You retain all rights to the documents you upload and the signatures you apply. You grant us only the
limited rights needed to store, process, and deliver those documents as part of providing the service.
</Trans>
</p>

<h2>
<Trans>5. Legal Effect of Electronic Signatures</Trans>
</h2>
<p>
<Trans>
Electronic signatures carry legal effect under applicable law when the signatory intends to sign. You are
responsible for ensuring that your use of electronic signatures satisfies the legal requirements of your
jurisdiction and document type.
</Trans>
</p>

<h2>
<Trans>6. Acceptable Use</Trans>
</h2>
<p>
<Trans>
You may not use the service to send unwanted signing requests, to mislead signers about what they are
signing, or for any unlawful purpose.
</Trans>
</p>

<h2>
<Trans>7. Availability and Changes</Trans>
</h2>
<p>
<Trans>
We may modify or discontinue features, and may update these terms. Material changes will be communicated
through the service before taking effect.
</Trans>
</p>

<h2>
<Trans>8. Limitation of Liability</Trans>
</h2>
<p>
<Trans>
To the maximum extent permitted by law, the service is provided "as is" and we are not liable for indirect
or consequential damages arising from your use of the service.
</Trans>
</p>

<h2>
<Trans>9. Contact</Trans>
</h2>
<p>
<Trans>Questions about these terms can be sent through the support channels of the Crove OS ecosystem.</Trans>
</p>
</article>

<Link to="/signin" className="mt-8 inline-block">
<Button>
<Trans>Back to sign in</Trans>
</Button>
</Link>
</div>
);
}
Binary file modified apps/remix/public/android-chrome-192x192.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/android-chrome-512x512.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/apple-touch-icon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/favicon-16x16.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/favicon-32x32.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/favicon.ico
Binary file not shown.
Binary file modified apps/remix/public/opengraph-image.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/static/logo.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added apps/remix/public/static/og-share-frame.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/remix/public/static/og-share-frame2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified packages/assets/logo_icon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified packages/assets/static/logo.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified packages/assets/static/og-share-frame.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified packages/assets/static/og-share-frame2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const TemplateBrandingLogo = ({ assetBaseUrl, className = 'mb-4 h-6' }: T
if (!hasCustomBrandingLogo) {
const documensoLogoUrl = getEmailAssetUrl(assetBaseUrl, 'static/logo.png');

return <Img src={documensoLogoUrl} alt="Documenso Logo" className={className} />;
return <Img src={documensoLogoUrl} alt="Crove Sign Logo" className={className} />;
}

const brandingLogo = <Img src={branding.brandingLogo} alt="Branding Logo" className={className} />;
Expand Down
16 changes: 12 additions & 4 deletions packages/email/template-components/template-footer.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import { APP_COMPANY_DETAILS, NEXT_PUBLIC_WEBAPP_URL } from '@documenso/lib/constants/app';
import { Trans } from '@lingui/react/macro';
import { Fragment } from 'react';

Expand Down Expand Up @@ -33,7 +34,7 @@ export const TemplateFooter = ({ isDocument = true, reportUrl }: TemplateFooterP
<Text className="my-4 text-base text-muted-foreground">
<Trans>
This document was sent using{' '}
<Link className="text-primary" href="https://documen.so/mail-footer">
<Link className="text-primary" href={NEXT_PUBLIC_WEBAPP_URL()}>

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 IMPORTANT: Brand/Contract Mismatch in Email Footer

Failure Trace:

  1. The diff updates the href of the footer link to NEXT_PUBLIC_WEBAPP_URL() (which resolves to the Crove Sign domain, e.g., https://crove.com).
    2. However, the visible text content of the <Link> remains hardcoded as Documenso (line 37 in the new file context, corresponding to the line Documenso inside the <Link> tag).
    3. When an email is rendered, the user sees "This document was sent using Documenso" but clicking it navigates to the Crove Sign website.
    4. This contradicts the explicit branding intent of the PR (which renames the product to "Crove Sign" in metadata, logos, and other components) and creates a confusing user experience where the brand name in the email does not match the destination site.
Suggested change
<Link className="text-primary" href={NEXT_PUBLIC_WEBAPP_URL()}>
<Link className="text-primary" href={NEXT_PUBLIC_WEBAPP_URL()}>
Crove Sign
</Link>

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 IMPORTANT: Brand Mismatch in Email Footer Link Text

Failure Trace:

  1. The diff modifies template-footer.tsx to change the href of the footer link from https://documen.so/mail-footer to NEXT_PUBLIC_WEBAPP_URL() (which resolves to the Crove Sign domain, e.g., https://crove.com).
    2. However, the text content inside the <Link> tag remains hardcoded as Documenso (line 37 in the new file context: Documenso).
    3. When an email is rendered, the user sees "This document was sent using Documenso" with a hyperlink pointing to the Crove Sign website.
    4. This contradicts the explicit branding intent of the PR (renaming to "Crove Sign" in metadata, logos, and other components) and creates a confusing user experience where the brand name in the text does not match the destination of the link.
Suggested change
<Link className="text-primary" href={NEXT_PUBLIC_WEBAPP_URL()}>
<Link className="text-primary" href={NEXT_PUBLIC_WEBAPP_URL()}>
Crove Sign
</Link>

Documenso
</Link>
.
Expand Down Expand Up @@ -64,9 +65,16 @@ export const TemplateFooter = ({ isDocument = true, reportUrl }: TemplateFooterP

{!branding.brandingEnabled && (
<Text className="my-8 text-muted-foreground text-sm">
Documenso, Inc.
<br />
2261 Market Street, #5211, San Francisco, CA 94114, USA
{APP_COMPANY_DETAILS()
.split('\n')
.map((line, idx) => {
return (
<Fragment key={idx}>
{idx > 0 && <br />}
{line}
</Fragment>
);
})}
</Text>
)}
</Section>
Expand Down
2 changes: 1 addition & 1 deletion packages/email/templates/admin-user-created.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ export const AdminUserCreatedTemplate = ({
<Section>
<Container className="mx-auto mt-8 mb-2 max-w-xl rounded-lg border border-border border-solid p-4 backdrop-blur-sm">
<Section>
<Img src={getEmailAssetUrl(assetBaseUrl, 'static/logo.png')} alt="Documenso Logo" className="mb-4 h-6" />
<Img src={getEmailAssetUrl(assetBaseUrl, 'static/logo.png')} alt="Crove Sign Logo" className="mb-4 h-6" />

<TemplateAdminUserCreated resetPasswordLink={resetPasswordLink} assetBaseUrl={assetBaseUrl} />
</Section>
Expand Down
7 changes: 7 additions & 0 deletions packages/lib/constants/app.ts
Original file line number Diff line number Diff line change
Expand Up @@ -184,3 +184,10 @@ export const CSC_INSTANCE_SIGNATURE_LEVEL = (): TSignatureLevel => {
};

export const DOCUMENSO_CLOUD_ENTERPRISE_CTA_URL = 'https://documen.so/enterprise-cta';

/**
* Company identity rendered in the email footer when an organisation has no
* custom branding. Override per deployment (legal address, site, etc.) via
* the NEXT_PRIVATE_BRANDING_COMPANY_DETAILS env (newline-separated lines).
*/
export const APP_COMPANY_DETAILS = () => env('NEXT_PRIVATE_BRANDING_COMPANY_DETAILS') || 'Crove\nhttps://crove.com';
Loading
Loading