From 50371e2ea41d5e5ac5e7712c0fcedefc998cafe5 Mon Sep 17 00:00:00 2001 From: Anthony Shew Date: Thu, 9 Jan 2025 10:43:24 -0700 Subject: [PATCH 1/2] docs: Edits for Prisma guide. --- docs/repo-docs/guides/tools/prisma.mdx | 20 ++++++++++++++++---- 1 file changed, 16 insertions(+), 4 deletions(-) diff --git a/docs/repo-docs/guides/tools/prisma.mdx b/docs/repo-docs/guides/tools/prisma.mdx index c132da8ac36f5..666e17b847bc4 100644 --- a/docs/repo-docs/guides/tools/prisma.mdx +++ b/docs/repo-docs/guides/tools/prisma.mdx @@ -116,10 +116,23 @@ Now, run `turbo db:push db:generate` from the root of our repository to automati ## Exporting your client -Next, export the `@prisma/client` so it can used in your applications. Let's add an `index.ts` file to `packages/database`: +Set up the Prisma client for the package. + +```ts title="packages/database/src/client.ts" +import { PrismaClient } from '../generated/client'; + +const globalForPrisma = global as unknown as { prisma: PrismaClient }; + +export const prisma = globalForPrisma.prisma || new PrismaClient(); + +if (process.env.NODE_ENV !== 'production') globalForPrisma.prisma = prisma; +``` + +Next, export the `@prisma/client` and types so it can used in your applications. Let's add an `index.ts` file to `packages/database`: ```ts title="packages/database/src/index.ts" -export * from '@prisma/client'; +export { prisma } from './client'; // exports instance of prisma +export * from '../generated/client'; // exports generated types from prisma ``` Following the [Just-in-Time packaging pattern](/repo/docs/core-concepts/internal-packages#just-in-time-packages), you'll also create an entrypoint to the package inside `packages/database/package.json`. @@ -127,9 +140,8 @@ Following the [Just-in-Time packaging pattern](/repo/docs/core-concepts/internal ```json title="packages/database/package.json" { "exports": { - // [!code highlight] ".": "./src/index.ts" // [!code highlight] - } // [!code highlight] + } } ``` From d67d4e113a6e92d177419c468bb183b4c447e6c3 Mon Sep 17 00:00:00 2001 From: Anthony Shew Date: Thu, 9 Jan 2025 16:13:14 -0700 Subject: [PATCH 2/2] WIP --- docs/repo-docs/guides/tools/prisma.mdx | 244 +------------------------ 1 file changed, 9 insertions(+), 235 deletions(-) diff --git a/docs/repo-docs/guides/tools/prisma.mdx b/docs/repo-docs/guides/tools/prisma.mdx index 666e17b847bc4..c0c090afb928b 100644 --- a/docs/repo-docs/guides/tools/prisma.mdx +++ b/docs/repo-docs/guides/tools/prisma.mdx @@ -10,244 +10,18 @@ import { CreateTurboCallout } from './create-turbo-callout.tsx'; [Prisma](https://www.prisma.io/) unlocks a new level of developer experience when working with databases thanks to its intuitive data model, automated migrations, type-safety & auto-completion. - +[Their official guide](https://www.prisma.io/docs/guides/using-prisma-orm-with-turborepo#1-create-your-monorepo-using-turborepo) describes how to integrate Prisma into a Turborepo, including: -This guide shows you how to: +- Prisma client initialization +- Packaging the client as an [Internal Package](/repo/docs/core-concepts/internal-packages) +- Performing migrations +- Working on your applications locally +- Deploying -1. Set up Prisma in a monorepo -2. Handle migration and code generation scripts -3. Ensure that they're always run whenever `dev` or `build` is run +## Example -If you've already got Prisma set up in your database, you can skip to [step 4](#create-scripts). - - - - -## Create your monorepo - -If you don't have an existing project, use our [quickstart](/repo/docs/getting-started/installation) to create a new monorepo. - - - -## Add a new `database` package - -Create a new folder called `database` inside packages with a `package.json` inside: - -```json title="packages/database/package.json" -{ - "name": "@repo/db", - "version": "0.0.0", - "dependencies": { - "@prisma/client": "latest" // Replace with latest version - }, - "devDependencies": { - "prisma": "latest" // Replace with latest version - } -} -``` - -Run your package manager's install step to install the new dependencies. - - - - -## Run `prisma init` - -`cd` into `packages/database`: +To get started with our community-supported Prisma example, run: ```bash title="Terminal" -cd packages/database -``` - -Run `npx prisma init`. - -This should create several files inside `packages/database`: - -- `schema.prisma` is where your [Prisma schema](https://www.prisma.io/docs/concepts/components/prisma-schema) lives. Here, you'll be able to modify the shape of your database. -- `.gitignore` adds some ignored files to git -- `.env` lets you manually specify your `DATABASE_URL` for prisma. - -At this point, you should refer to the Prisma docs for [connecting your database to Prisma](https://www.prisma.io/docs/getting-started/setup-prisma/start-from-scratch/relational-databases/connect-your-database-typescript-postgres). - -Once you've got a database connected and have a few data tables to work with, you can move on. - - - - -## Create scripts - -Let's add some scripts to the `package.json` inside `packages/database`: - -```json title="packages/database/package.json" -{ - "scripts": { - "db:generate": "prisma generate", - "db:push": "prisma db push --skip-generate" - } -} -``` - -Let's also add these scripts to `turbo.json` in the root: - -```json title="./turbo.json" -{ - "tasks": { - "db:generate": { - "cache": false - }, - "db:push": { - "cache": false - } - } -} -``` - -Now, run `turbo db:push db:generate` from the root of our repository to automatically migrate our database and generate our type-safe Prisma client. - - - Use the `--skip-generate` flag on `db:push` to ensure it doesn't automatically - run `prisma generate` after migrating the database. This ends up being faster - when using Turborepo because it automatically parallelizes the tasks. - - - - - - -## Exporting your client - -Set up the Prisma client for the package. - -```ts title="packages/database/src/client.ts" -import { PrismaClient } from '../generated/client'; - -const globalForPrisma = global as unknown as { prisma: PrismaClient }; - -export const prisma = globalForPrisma.prisma || new PrismaClient(); - -if (process.env.NODE_ENV !== 'production') globalForPrisma.prisma = prisma; +npx create-turbo@latest -e with-prisma ``` - -Next, export the `@prisma/client` and types so it can used in your applications. Let's add an `index.ts` file to `packages/database`: - -```ts title="packages/database/src/index.ts" -export { prisma } from './client'; // exports instance of prisma -export * from '../generated/client'; // exports generated types from prisma -``` - -Following the [Just-in-Time packaging pattern](/repo/docs/core-concepts/internal-packages#just-in-time-packages), you'll also create an entrypoint to the package inside `packages/database/package.json`. - -```json title="packages/database/package.json" -{ - "exports": { - ".": "./src/index.ts" // [!code highlight] - } -} -``` - - - Note that you're using [the Just-in-Time Package - pattern](/repo/docs/core-concepts/internal-packages#just-in-time-packages) - here, which assumes your application can consume TypeScript directly. You may - need to adjust to a different strategy as if needed. - - -### Importing `database` - -Import the database package into one of our apps. - -Let's say you have an app at `apps/web`. Add the dependency to `apps/web/package.json`: - - - - ```json title="apps/web/package.json" - { - "dependencies": { - "@repo/db": "*" - } - } - ``` - - - ```json title="apps/web/package.json" - { - "dependencies": { - "@repo/db": "*" - } - } - ``` - - - ```json title="apps/web/package.json" - { - "dependencies": { - "@repo/db": "workspace:*" - } - } - ``` - - - -Run your package manager's install command. - -You can now import `PrismaClient` from `database` anywhere in your app: - -```ts title="./apps/web/app/page.tsx" -import { PrismaClient } from '@repo/db'; - -const client = new PrismaClient(); -``` - - - - - -## Figuring out the scripts - -You now have a reusable `@repo/db` package that you can import into any of your applications and a `turbo db:push` script to push schema changes - -However, your `db:generate` scripts aren't optimized yet. They provide crucial code to our `dev` and `build` tasks. If a new developer runs `turbo dev` on an application without running `db:generate` first, they'll get errors. - -So, let's make sure that `db:generate` is always run _before_ you run `dev`: - -```json title="./turbo.json" -{ - "tasks": { - "dev": { - "dependsOn": ["^db:generate"], - "cache": false - }, - "build": { - "dependsOn": ["^db:generate"], - "outputs": ["your-outputs-here"] - }, - "db:generate": { - "cache": false - } - } -} -``` - -Check out the section on [running tasks](/repo/docs/crafting-your-repository/running-tasks) to learn more about the `^db:generate` syntax. - -### Caching the results of `prisma generate` - -`prisma generate` outputs files to the filesystem, usually inside `node_modules`. In theory, it should be possible to cache the output of `prisma generate` with Turborepo to save a few seconds. - -However, Prisma behaves differently with different package managers. This can lead to unpredictable results, which might lead to broken deployments in some situations. Instead of documenting the intricacies of each approach, we recommend _not_ caching the results of `prisma generate`. Since `prisma generate` usually only takes 5-6 seconds, and tends not to take longer with larger `schema` files, this seems like a fine trade-off. - -You may also wish to experiment with caching the generated files in a way that satisfies the constraints for your repository. - - - - - -## Going to production - -Now that you've made it this far, you're ready to deploy your application. Depending on where your database lives, you'll want to design your deployment pipeline according to the documentation for your database's setup. - -There are many factors to take into consideration from this point on, so we can't provide a one-size-fits-all solution. You likely want to visit the documentation for your database and its deployment platform to learn more. - - - -