mirror of
https://github.com/documenso/documenso.git
synced 2025-11-15 09:12:02 +10:00
Merge branch 'main' into DOC-190-Dashboard-Metrics
This commit is contained in:
14
.env.example
14
.env.example
@ -13,12 +13,20 @@ NEXT_PUBLIC_WEBAPP_URL='http://localhost:3000'
|
|||||||
NEXTAUTH_SECRET='lorem ipsum sit dolor random string for encryption this could literally be anything'
|
NEXTAUTH_SECRET='lorem ipsum sit dolor random string for encryption this could literally be anything'
|
||||||
NEXTAUTH_URL='http://localhost:3000'
|
NEXTAUTH_URL='http://localhost:3000'
|
||||||
|
|
||||||
# MAIL
|
# MAIL (NODEMAILER)
|
||||||
|
# SENDGRID
|
||||||
# Get a Sendgrid Api key here: https://signup.sendgrid.com
|
# Get a Sendgrid Api key here: https://signup.sendgrid.com
|
||||||
# You can also configure you own SMTP server using Nodemailer in sendMailts. (currently not possible via config)
|
|
||||||
SENDGRID_API_KEY=''
|
SENDGRID_API_KEY=''
|
||||||
|
|
||||||
|
# SMTP
|
||||||
|
# Set SMTP credentials to use SMTP instead of the Sendgrid API.
|
||||||
|
SMTP_MAIL_HOST=''
|
||||||
|
SMTP_MAIL_PORT=''
|
||||||
|
SMTP_MAIL_USER=''
|
||||||
|
SMTP_MAIL_PASSWORD=''
|
||||||
|
|
||||||
# Sender for signing requests and completion mails.
|
# Sender for signing requests and completion mails.
|
||||||
MAIL_FROM=''
|
MAIL_FROM='documenso@localhost.com'
|
||||||
|
|
||||||
#FEATURE FLAGS
|
#FEATURE FLAGS
|
||||||
# Allow users to register via the /signup page. Otherwise they will be redirect to the home page.
|
# Allow users to register via the /signup page. Otherwise they will be redirect to the home page.
|
||||||
|
|||||||
29
README.md
29
README.md
@ -57,6 +57,7 @@
|
|||||||
Signing documents digitally is fast, easy and should be best practice for every document signed worldwide. This is technically quite easy today, but it also introduces a new party to every signature: The signing tool providers. While this is not a problem in itself, it should make us think about how we want these providers of trust to work. Documenso aims to be the world's most trusted document signing tool. This trust is built by empowering you to self-host Documenso and review how it works under the hood. Join us in creating the next generation of open trust infrastructure.
|
Signing documents digitally is fast, easy and should be best practice for every document signed worldwide. This is technically quite easy today, but it also introduces a new party to every signature: The signing tool providers. While this is not a problem in itself, it should make us think about how we want these providers of trust to work. Documenso aims to be the world's most trusted document signing tool. This trust is built by empowering you to self-host Documenso and review how it works under the hood. Join us in creating the next generation of open trust infrastructure.
|
||||||
|
|
||||||
## Community and Next Steps 🎯
|
## Community and Next Steps 🎯
|
||||||
|
|
||||||
The current project goal is to <b>[release a production ready version](https://github.com/documenso/documenso/milestone/1)</b> for self-hosting as soon as possible. If you want to help making that happen you can:
|
The current project goal is to <b>[release a production ready version](https://github.com/documenso/documenso/milestone/1)</b> for self-hosting as soon as possible. If you want to help making that happen you can:
|
||||||
|
|
||||||
- Check out the first source code release in this repository and test it
|
- Check out the first source code release in this repository and test it
|
||||||
@ -67,6 +68,7 @@ The current project goal is to <b>[release a production ready version](https://g
|
|||||||
- Fix or create [issues](https://github.com/documenso/documenso/issues), that are needed for the first production release
|
- Fix or create [issues](https://github.com/documenso/documenso/issues), that are needed for the first production release
|
||||||
|
|
||||||
## Contributing
|
## Contributing
|
||||||
|
|
||||||
- To contribute please see our [contribution guide](https://github.com/documenso/documenso/blob/main/CONTRIBUTING.md).
|
- To contribute please see our [contribution guide](https://github.com/documenso/documenso/blob/main/CONTRIBUTING.md).
|
||||||
|
|
||||||
## Tools
|
## Tools
|
||||||
@ -102,32 +104,37 @@ To run Documenso locally you need
|
|||||||
Follow these steps to setup documenso on you local machnine:
|
Follow these steps to setup documenso on you local machnine:
|
||||||
|
|
||||||
- [Clone the repository](https://help.github.com/articles/cloning-a-repository/) it to your local device.
|
- [Clone the repository](https://help.github.com/articles/cloning-a-repository/) it to your local device.
|
||||||
```sh
|
```sh
|
||||||
git clone https://github.com/documenso/documenso
|
git clone https://github.com/documenso/documenso
|
||||||
```
|
```
|
||||||
- Run <code>npm i</code> in root directory
|
- Run <code>npm i</code> in root directory
|
||||||
- Rename .env.example to .env
|
- Rename <code>.env.example</code> to <code>.env</code>
|
||||||
- Set DATABASE_URL value in .env file
|
- Set DATABASE_URL value in .env file
|
||||||
- You can use the provided test database url (may be wiped at any point)
|
- You can use the provided test database url (may be wiped at any point)
|
||||||
- Or setup a local postgres sql instance (recommened)
|
- Or setup a local postgres sql instance (recommened)
|
||||||
- Set SENDGRID_API_KEY value in .env file
|
- Create the database scheme by running <code>db-migrate:dev</code>
|
||||||
- You need SendGrid account, which you can create [here](https://signup.sendgrid.com/).
|
- Setup your mail provider
|
||||||
- Documenso uses [Nodemailer](https://nodemailer.com/about/) so you can easily use your own smtp server
|
- Set <code>SENDGRID_API_KEY</code> value in .env file
|
||||||
|
- You need a SendGrid account, which you can create [here](https://signup.sendgrid.com/).
|
||||||
|
- Documenso uses [Nodemailer](https://nodemailer.com/about/) so you can easily use your own SMTP server by setting the <code>SMTP\_\* varibles</code> in your .env
|
||||||
- Run <code>npm run dev</code> root directory to start
|
- Run <code>npm run dev</code> root directory to start
|
||||||
- Register a new user at http://localhost:3000/signup
|
- Register a new user at http://localhost:3000/signup
|
||||||
|
|
||||||
---
|
---
|
||||||
|
- Optional: Seed the database using <code>npm run db-seed</code> to create a test user and document
|
||||||
|
- Optional: Upload and sign <code>apps\web\ressources\example.pdf</code> manually to test your setup
|
||||||
|
|
||||||
- Optional: Create your own signing certificate
|
- Optional: Create your own signing certificate
|
||||||
- A demo certificate is provided in /app/web/ressources/certificate.p12
|
- A demo certificate is provided in /app/web/ressources/certificate.p12
|
||||||
- To generate you own using these steps and a linux Terminal or Windows Linux Subsystem see **Create your own signging certificate**.
|
- To generate you own using these steps and a linux Terminal or Windows Linux Subsystem see **Create your own signging certificate**.
|
||||||
|
|
||||||
## Updating
|
## Updating
|
||||||
|
|
||||||
- If you pull the newest version from main, using <code>git pull</code>, it may be neccessary to regenerate your database client
|
- If you pull the newest version from main, using <code>git pull</code>, it may be neccessary to regenerate your database client
|
||||||
- You can do this by running the generate command in /packages/prisma:
|
- You can do this by running the generate command in /packages/prisma:
|
||||||
```sh
|
```sh
|
||||||
npx prisma generate
|
npx prisma generate
|
||||||
```
|
```
|
||||||
- This is not neccessary on first clone
|
- This is not neccessary on first clone
|
||||||
|
|
||||||
# Creating your own signging certificate
|
# Creating your own signging certificate
|
||||||
@ -141,7 +148,7 @@ For the digital signature of you documents you need a signign certificate in .p1
|
|||||||
<code>openssl req -new -x509 -key private.key -out certificate.crt -days 365</code> \
|
<code>openssl req -new -x509 -key private.key -out certificate.crt -days 365</code> \
|
||||||
This will prompt you to enter some information, such as the Common Name (CN) for the certificate. Make sure you enter the correct information. The -days parameter sets the number of days for which the certificate is valid.
|
This will prompt you to enter some information, such as the Common Name (CN) for the certificate. Make sure you enter the correct information. The -days parameter sets the number of days for which the certificate is valid.
|
||||||
3. Combine the private key and the self-signed certificate to create the p12 certificate. You can run the following command to do this: \
|
3. Combine the private key and the self-signed certificate to create the p12 certificate. You can run the following command to do this: \
|
||||||
<code>openssl pkcs12 -export -out certificate.p12 -inkey private.key -in certificate.crt</code>
|
<code>openssl pkcs12 -export -out certificate.p12 -inkey private.key -in certificate.crt</code>
|
||||||
4. You will be prompted to enter a password for the p12 file. Choose a strong password and remember it, as you will need it to use the certificate (**can be empty for dev certificates**)
|
4. You will be prompted to enter a password for the p12 file. Choose a strong password and remember it, as you will need it to use the certificate (**can be empty for dev certificates**)
|
||||||
5. Place the certificate <code>/apps/web/ressource/certificate.p12</code>
|
5. Place the certificate <code>/apps/web/ressource/certificate.p12</code>
|
||||||
|
|
||||||
|
|||||||
@ -50,17 +50,17 @@ export default function PDFEditor(props: any) {
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<div>
|
<div>
|
||||||
<div className="rounded-md bg-blue-50 p-4">
|
<div hidden={!noRecipients} className="rounded-md bg-yellow-50 p-4">
|
||||||
<div className="flex">
|
<div className="flex">
|
||||||
<div className="flex-shrink-0">
|
<div className="flex-shrink-0">
|
||||||
<InformationCircleIcon
|
<InformationCircleIcon
|
||||||
className="h-5 w-5 text-blue-400"
|
className="h-5 w-5 text-yellow-400"
|
||||||
aria-hidden="true"
|
aria-hidden="true"
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<div className="ml-3 flex-1 md:flex md:justify-between">
|
<div className="ml-3 flex-1 md:flex md:justify-between">
|
||||||
<p className="text-sm text-blue-700">
|
<p className="text-sm text-yellow-700">
|
||||||
This document does not have any recipients. Add recipient to
|
This document does not have any recipients. Add recipients to
|
||||||
create fields.
|
create fields.
|
||||||
</p>
|
</p>
|
||||||
<p className="mt-3 text-sm md:mt-0 md:ml-6">
|
<p className="mt-3 text-sm md:mt-0 md:ml-6">
|
||||||
@ -71,7 +71,7 @@ export default function PDFEditor(props: any) {
|
|||||||
props.document.id +
|
props.document.id +
|
||||||
"/recipients"
|
"/recipients"
|
||||||
}
|
}
|
||||||
className="whitespace-nowrap font-medium text-blue-700 hover:text-blue-600"
|
className="whitespace-nowrap font-medium text-yellow-700 hover:text-yellow-600"
|
||||||
>
|
>
|
||||||
Add Recipients
|
Add Recipients
|
||||||
<span aria-hidden="true"> →</span>
|
<span aria-hidden="true"> →</span>
|
||||||
@ -82,7 +82,9 @@ export default function PDFEditor(props: any) {
|
|||||||
</div>
|
</div>
|
||||||
<PDFViewer
|
<PDFViewer
|
||||||
style={{
|
style={{
|
||||||
cursor: `url("https://place-hold.it/110x64/37f095/FFFFFF&text=${selectedFieldType}") 55 32, auto`,
|
cursor: !noRecipients
|
||||||
|
? `url("https://place-hold.it/110x64/37f095/FFFFFF&text=${selectedFieldType}") 55 32, auto`
|
||||||
|
: "",
|
||||||
}}
|
}}
|
||||||
readonly={false}
|
readonly={false}
|
||||||
document={props.document}
|
document={props.document}
|
||||||
@ -119,6 +121,7 @@ export default function PDFEditor(props: any) {
|
|||||||
function addField(e: any, page: number) {
|
function addField(e: any, page: number) {
|
||||||
if (!selectedRecipient) return;
|
if (!selectedRecipient) return;
|
||||||
if (!selectedFieldType) return;
|
if (!selectedFieldType) return;
|
||||||
|
if (noRecipients) return;
|
||||||
|
|
||||||
const signatureField = createField(
|
const signatureField = createField(
|
||||||
e,
|
e,
|
||||||
|
|||||||
@ -19,6 +19,7 @@ import {
|
|||||||
import { getUserFromToken } from "@documenso/lib/server";
|
import { getUserFromToken } from "@documenso/lib/server";
|
||||||
import { getDocumentsForUserFromToken } from "@documenso/lib/query";
|
import { getDocumentsForUserFromToken } from "@documenso/lib/query";
|
||||||
import { truncate } from "fs";
|
import { truncate } from "fs";
|
||||||
|
import { Tooltip as ReactTooltip } from "react-tooltip";
|
||||||
|
|
||||||
type FormValues = {
|
type FormValues = {
|
||||||
document: File;
|
document: File;
|
||||||
@ -106,11 +107,18 @@ const DashboardPage: NextPageWithLayout = (props: any) => {
|
|||||||
d="M19.5 14.25v-2.625a3.375 3.375 0 00-3.375-3.375h-1.5A1.125 1.125 0 0113.5 7.125v-1.5a3.375 3.375 0 00-3.375-3.375H8.25m3.75 9v6m3-3H9m1.5-12H5.625c-.621 0-1.125.504-1.125 1.125v17.25c0 .621.504 1.125 1.125 1.125h12.75c.621 0 1.125-.504 1.125-1.125V11.25a9 9 0 00-9-9z"
|
d="M19.5 14.25v-2.625a3.375 3.375 0 00-3.375-3.375h-1.5A1.125 1.125 0 0113.5 7.125v-1.5a3.375 3.375 0 00-3.375-3.375H8.25m3.75 9v6m3-3H9m1.5-12H5.625c-.621 0-1.125.504-1.125 1.125v17.25c0 .621.504 1.125 1.125 1.125h12.75c.621 0 1.125-.504 1.125-1.125V11.25a9 9 0 00-9-9z"
|
||||||
/>
|
/>
|
||||||
</svg>
|
</svg>
|
||||||
|
<span
|
||||||
<span className="block mt-2 text-sm font-medium text-neon">
|
id="add_document"
|
||||||
Add a new PDF document
|
className="mt-2 block text-sm font-medium text-neon"
|
||||||
|
>
|
||||||
|
Add a new PDF document.
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
|
<ReactTooltip
|
||||||
|
anchorId="add_document"
|
||||||
|
place="bottom"
|
||||||
|
content="No preparation needed. Any PDF will do."
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|||||||
@ -16,10 +16,10 @@ import {
|
|||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import { uploadDocument } from "@documenso/features";
|
import { uploadDocument } from "@documenso/features";
|
||||||
import { DocumentStatus } from "@prisma/client";
|
import { DocumentStatus } from "@prisma/client";
|
||||||
import { Tooltip as ReactTooltip } from "react-tooltip";
|
|
||||||
import { Button, IconButton, SelectBox } from "@documenso/ui";
|
import { Button, IconButton, SelectBox } from "@documenso/ui";
|
||||||
import { NextPageContext } from "next";
|
import { NextPageContext } from "next";
|
||||||
import { deleteDocument, getDocuments } from "@documenso/lib/api";
|
import { deleteDocument, getDocuments } from "@documenso/lib/api";
|
||||||
|
import { Tooltip as ReactTooltip } from "react-tooltip";
|
||||||
|
|
||||||
const DocumentsPage: NextPageWithLayout = (props: any) => {
|
const DocumentsPage: NextPageWithLayout = (props: any) => {
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
@ -406,7 +406,7 @@ const DocumentsPage: NextPageWithLayout = (props: any) => {
|
|||||||
|
|
||||||
<h3 className="mt-2 text-sm font-medium text-gray-900">No documents</h3>
|
<h3 className="mt-2 text-sm font-medium text-gray-900">No documents</h3>
|
||||||
<p className="mt-1 text-sm text-gray-500">
|
<p className="mt-1 text-sm text-gray-500">
|
||||||
Get started by creating a new document.
|
Get started by adding a document. Any PDF will do.
|
||||||
</p>
|
</p>
|
||||||
<div className="mt-6">
|
<div className="mt-6">
|
||||||
<Button
|
<Button
|
||||||
@ -428,6 +428,11 @@ const DocumentsPage: NextPageWithLayout = (props: any) => {
|
|||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<ReactTooltip
|
||||||
|
anchorId="empty"
|
||||||
|
place="bottom"
|
||||||
|
content="No preparation needed. Any PDF will do."
|
||||||
|
/>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
BIN
apps/web/ressources/example.pdf
Normal file
BIN
apps/web/ressources/example.pdf
Normal file
Binary file not shown.
@ -5,6 +5,7 @@
|
|||||||
"dev": "cd apps && cd web && next dev",
|
"dev": "cd apps && cd web && next dev",
|
||||||
"build": "npm i && cd apps && cd web && npm i && next build",
|
"build": "npm i && cd apps && cd web && npm i && next build",
|
||||||
"start": "cd apps && cd web && next start",
|
"start": "cd apps && cd web && next start",
|
||||||
|
"db-migrate:dev": "prisma migrate dev",
|
||||||
"db-seed": "prisma db seed",
|
"db-seed": "prisma db seed",
|
||||||
"db-studio": "prisma studio"
|
"db-studio": "prisma studio"
|
||||||
},
|
},
|
||||||
|
|||||||
@ -11,14 +11,29 @@ export const sendMail = async (
|
|||||||
content: string | Buffer;
|
content: string | Buffer;
|
||||||
}[] = []
|
}[] = []
|
||||||
) => {
|
) => {
|
||||||
if (!process.env.SENDGRID_API_KEY)
|
let transport;
|
||||||
throw new Error("Sendgrid API Key not set.");
|
if (process.env.SENDGRID_API_KEY)
|
||||||
|
transport = nodemailer.createTransport(
|
||||||
|
nodemailerSendgrid({
|
||||||
|
apiKey: process.env.SENDGRID_API_KEY || "",
|
||||||
|
})
|
||||||
|
);
|
||||||
|
|
||||||
|
if (process.env.SMTP_MAIL_HOST)
|
||||||
|
transport = nodemailer.createTransport({
|
||||||
|
host: process.env.SMTP_MAIL_HOST || "",
|
||||||
|
port: Number(process.env.SMTP_MAIL_PORT) || 587,
|
||||||
|
auth: {
|
||||||
|
user: process.env.SMTP_MAIL_USER || "",
|
||||||
|
pass: process.env.SMTP_MAIL_PASSWORD || "",
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!transport)
|
||||||
|
throw new Error(
|
||||||
|
"No valid transport for NodeMailer found. Probably Sendgrid API Key nor SMTP Mail host was set."
|
||||||
|
);
|
||||||
|
|
||||||
const transport = await nodemailer.createTransport(
|
|
||||||
nodemailerSendgrid({
|
|
||||||
apiKey: process.env.SENDGRID_API_KEY || "",
|
|
||||||
})
|
|
||||||
);
|
|
||||||
await transport
|
await transport
|
||||||
.sendMail({
|
.sendMail({
|
||||||
from: process.env.MAIL_FROM,
|
from: process.env.MAIL_FROM,
|
||||||
|
|||||||
@ -0,0 +1,148 @@
|
|||||||
|
-- CreateEnum
|
||||||
|
CREATE TYPE "IdentityProvider" AS ENUM ('DOCUMENSO', 'GOOGLE');
|
||||||
|
|
||||||
|
-- CreateEnum
|
||||||
|
CREATE TYPE "DocumentStatus" AS ENUM ('DRAFT', 'PENDING', 'COMPLETED');
|
||||||
|
|
||||||
|
-- CreateEnum
|
||||||
|
CREATE TYPE "ReadStatus" AS ENUM ('NOT_OPENED', 'OPENED');
|
||||||
|
|
||||||
|
-- CreateEnum
|
||||||
|
CREATE TYPE "SendStatus" AS ENUM ('NOT_SENT', 'SENT');
|
||||||
|
|
||||||
|
-- CreateEnum
|
||||||
|
CREATE TYPE "SigningStatus" AS ENUM ('NOT_SIGNED', 'SIGNED');
|
||||||
|
|
||||||
|
-- CreateEnum
|
||||||
|
CREATE TYPE "FieldType" AS ENUM ('SIGNATURE', 'FREE_SIGNATURE', 'DATE', 'TEXT');
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "User" (
|
||||||
|
"id" SERIAL NOT NULL,
|
||||||
|
"name" TEXT,
|
||||||
|
"email" TEXT NOT NULL,
|
||||||
|
"emailVerified" TIMESTAMP(3),
|
||||||
|
"password" TEXT,
|
||||||
|
"source" TEXT,
|
||||||
|
"identityProvider" "IdentityProvider" NOT NULL DEFAULT 'DOCUMENSO',
|
||||||
|
|
||||||
|
CONSTRAINT "User_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "Account" (
|
||||||
|
"id" TEXT NOT NULL,
|
||||||
|
"userId" INTEGER NOT NULL,
|
||||||
|
"type" TEXT NOT NULL,
|
||||||
|
"provider" TEXT NOT NULL,
|
||||||
|
"providerAccountId" TEXT NOT NULL,
|
||||||
|
"refresh_token" TEXT,
|
||||||
|
"access_token" TEXT,
|
||||||
|
"expires_at" INTEGER,
|
||||||
|
"token_type" TEXT,
|
||||||
|
"scope" TEXT,
|
||||||
|
"id_token" TEXT,
|
||||||
|
"session_state" TEXT,
|
||||||
|
|
||||||
|
CONSTRAINT "Account_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "Session" (
|
||||||
|
"id" TEXT NOT NULL,
|
||||||
|
"sessionToken" TEXT NOT NULL,
|
||||||
|
"userId" INTEGER NOT NULL,
|
||||||
|
"expires" TIMESTAMP(3) NOT NULL,
|
||||||
|
|
||||||
|
CONSTRAINT "Session_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "Document" (
|
||||||
|
"id" SERIAL NOT NULL,
|
||||||
|
"created" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||||
|
"userId" INTEGER NOT NULL,
|
||||||
|
"title" TEXT NOT NULL,
|
||||||
|
"status" "DocumentStatus" NOT NULL DEFAULT 'DRAFT',
|
||||||
|
"document" TEXT NOT NULL,
|
||||||
|
|
||||||
|
CONSTRAINT "Document_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "Recipient" (
|
||||||
|
"id" SERIAL NOT NULL,
|
||||||
|
"documentId" INTEGER NOT NULL,
|
||||||
|
"email" VARCHAR(255) NOT NULL,
|
||||||
|
"name" VARCHAR(255) NOT NULL DEFAULT '',
|
||||||
|
"token" TEXT NOT NULL,
|
||||||
|
"expired" TIMESTAMP(3),
|
||||||
|
"readStatus" "ReadStatus" NOT NULL DEFAULT 'NOT_OPENED',
|
||||||
|
"signingStatus" "SigningStatus" NOT NULL DEFAULT 'NOT_SIGNED',
|
||||||
|
"sendStatus" "SendStatus" NOT NULL DEFAULT 'NOT_SENT',
|
||||||
|
|
||||||
|
CONSTRAINT "Recipient_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "Field" (
|
||||||
|
"id" SERIAL NOT NULL,
|
||||||
|
"documentId" INTEGER NOT NULL,
|
||||||
|
"recipientId" INTEGER,
|
||||||
|
"type" "FieldType" NOT NULL,
|
||||||
|
"page" INTEGER NOT NULL,
|
||||||
|
"positionX" INTEGER NOT NULL DEFAULT 0,
|
||||||
|
"positionY" INTEGER NOT NULL DEFAULT 0,
|
||||||
|
"customText" TEXT NOT NULL,
|
||||||
|
"inserted" BOOLEAN NOT NULL,
|
||||||
|
|
||||||
|
CONSTRAINT "Field_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateTable
|
||||||
|
CREATE TABLE "Signature" (
|
||||||
|
"id" SERIAL NOT NULL,
|
||||||
|
"created" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||||
|
"recipientId" INTEGER NOT NULL,
|
||||||
|
"fieldId" INTEGER NOT NULL,
|
||||||
|
"signatureImageAsBase64" TEXT,
|
||||||
|
"typedSignature" TEXT,
|
||||||
|
|
||||||
|
CONSTRAINT "Signature_pkey" PRIMARY KEY ("id")
|
||||||
|
);
|
||||||
|
|
||||||
|
-- CreateIndex
|
||||||
|
CREATE UNIQUE INDEX "User_email_key" ON "User"("email");
|
||||||
|
|
||||||
|
-- CreateIndex
|
||||||
|
CREATE UNIQUE INDEX "Account_provider_providerAccountId_key" ON "Account"("provider", "providerAccountId");
|
||||||
|
|
||||||
|
-- CreateIndex
|
||||||
|
CREATE UNIQUE INDEX "Session_sessionToken_key" ON "Session"("sessionToken");
|
||||||
|
|
||||||
|
-- CreateIndex
|
||||||
|
CREATE UNIQUE INDEX "Signature_fieldId_key" ON "Signature"("fieldId");
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Account" ADD CONSTRAINT "Account_userId_fkey" FOREIGN KEY ("userId") REFERENCES "User"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Session" ADD CONSTRAINT "Session_userId_fkey" FOREIGN KEY ("userId") REFERENCES "User"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Document" ADD CONSTRAINT "Document_userId_fkey" FOREIGN KEY ("userId") REFERENCES "User"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Recipient" ADD CONSTRAINT "Recipient_documentId_fkey" FOREIGN KEY ("documentId") REFERENCES "Document"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Field" ADD CONSTRAINT "Field_documentId_fkey" FOREIGN KEY ("documentId") REFERENCES "Document"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Field" ADD CONSTRAINT "Field_recipientId_fkey" FOREIGN KEY ("recipientId") REFERENCES "Recipient"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Signature" ADD CONSTRAINT "Signature_recipientId_fkey" FOREIGN KEY ("recipientId") REFERENCES "Recipient"("id") ON DELETE RESTRICT ON UPDATE CASCADE;
|
||||||
|
|
||||||
|
-- AddForeignKey
|
||||||
|
ALTER TABLE "Signature" ADD CONSTRAINT "Signature_fieldId_fkey" FOREIGN KEY ("fieldId") REFERENCES "Field"("id") ON DELETE RESTRICT ON UPDATE CASCADE;
|
||||||
3
packages/prisma/migrations/migration_lock.toml
Normal file
3
packages/prisma/migrations/migration_lock.toml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
# Please do not edit this file manually
|
||||||
|
# It should be added in your version-control system (i.e. Git)
|
||||||
|
provider = "postgresql"
|
||||||
File diff suppressed because one or more lines are too long
Reference in New Issue
Block a user