TurborepoでのPrismaの利用
Prisma (新しいタブで開きます)は、自動マイグレーション、型安全性、統合されたツールを備えた非常に人気のあるORMです。Turborepoと組み合わせて使用すると、コード生成にかかる時間を削減し、生成されたPrismaコードが常に最新の状態であることを簡単に確認できます。
ガイド
このガイドでは、以下の方法を示します。
- モノレポにPrismaを設定する
- マイグレーションとコード生成スクリプトを処理する
- Turborepoでそれらのスクリプトをキャッシュする
dev
またはbuild
が実行されるたびに、常に実行されるようにする
データベースにPrismaがすでに設定されている場合は、ステップ4に進むことができます。
1. モノレポを作成する
既存のプロジェクトがない場合は、クイックスタートを使用して、新しいモノレポを作成します。
2. 新しいdatabase
パッケージを追加する
packages内にdatabase
という新しいフォルダを作成し、その中にpackage.json
を作成します。
{
"name": "database",
"version": "0.0.0",
"dependencies": {
"@prisma/client": "latest"
},
"devDependencies": {
// Replace "latest" with the latest version
"prisma": "latest"
}
}
pnpm
を使用している場合は、ルートに.npmrc
というファイルを追加する必要があります。
public-hoist-pattern[]=*prisma*
パッケージマネージャーのインストール手順を実行して、新しい依存関係をインストールします。
3. prisma init
を実行する
packages/database
にcd
します。
cd packages/database
npx prisma init
を実行します。
これにより、packages/database
内にいくつかのファイルが作成されます。
prisma/schema.prisma
.gitignore
.env
schema.prisma
は、Prismaスキーマ (新しいタブで開きます)が配置される場所です。ここでは、データベースの形状を変更できます。.gitignore
は、gitで無視するファイルを追加します。.env
では、Prisma用のDATABASE_URL
を手動で指定できます。
この時点で、PrismaのドキュメントにあるPrismaへのデータベース接続 (新しいタブで開く)を参照してください。
データベースが接続されたら、次に進むことができます。
4. スクリプトの設定
package.json
内の packages/database
にいくつかのスクリプトを追加しましょう。
{
"scripts": {
"db:generate": "prisma generate",
"db:push": "prisma db push --skip-generate"
}
}
また、これらのスクリプトをルートのturbo.json
に追加しましょう。
{
"pipeline": {
"db:generate": {
"cache": false
},
"db:push": {
"cache": false
}
}
}
リポジトリのルートからturbo db:push db:generate
を実行することで、データベースを自動的に移行し、タイプセーフなPrismaクライアントを生成できます。
db:push
に --skip-generate
フラグを使用することで、データベースの移行後に prisma generate
が自動的に実行されないようにします。これは、Turborepoを使用している場合にタスクを自動的に並列化するため、結果的に高速になります。
5. クライアントのエクスポート
次に、アプリケーションで使用できるように、@prisma/client
をエクスポートする必要があります。index.ts
ファイルを packages/database
に追加しましょう。
export * from '@prisma/client';
内部パッケージパターンに従い、index.ts
を main
および types
を packages/database/package.json
内に追加する必要があります。
{
"main": "./index.ts",
"types": "./index.ts"
}
database
のインポート
次に、データベースパッケージをいずれかのアプリにインポートしてテストしてみましょう。apps/web
にアプリがあると仮定します。apps/web/package.json
に依存関係を追加します。
{
"dependencies": {
"database": "*"
}
}
パッケージマネージャーのインストールコマンドを実行します。
これで、アプリ内の任意の場所から database
から PrismaClient
をインポートできます。
import { PrismaClient } from 'database'
const client = new PrismaClient();
内部パッケージを実行できるようにするには、アプリケーション内で構成が必要な場合もあります。詳細については、内部パッケージのドキュメントを参照してください。
6. スクリプトの把握
これでかなり良い状態になりました。再利用可能なdatabase
モジュールがあり、どのアプリケーションにもインポートできます。turbo db:push
スクリプトを使用して、変更をデータベースにプッシュできます。
ただし、db:generate
スクリプトはまだ最適化されていません。これらは、dev
およびbuild
タスクに重要なコードを提供します。新しい開発者が最初にdb:generate
を実行せずにアプリケーションでdev
を実行すると、エラーが発生します。
したがって、ユーザーがdev
を実行する前に、常にdb:generate
が実行されるようにしましょう。
{
"pipeline": {
"dev": {
"dependsOn": ["^db:generate"],
"cache": false
},
"build": {
"dependsOn": ["^db:generate"],
"outputs": ["your-outputs-here"]
},
"db:generate": {
"cache": false
}
}
}
^db:generate
構文の詳細については、タスクの実行に関するセクションを参照してください。
7. prisma generate
の結果のキャッシュ
prisma generate
は、通常 node_modules
内のファイルシステムにファイルを出力します。理論的には、prisma generate
の出力をTurborepoでキャッシュして、数秒を節約できるはずです。
ただし、Prismaはパッケージマネージャーによって異なる動作をします。これにより、予測できない結果が生じ、場合によってはデプロイが破損する可能性があります。各アプローチの複雑さを文書化する代わりに、prisma generate
の結果をキャッシュしないことをお勧めします。prisma generate
は通常5〜6秒しかかからず、大規模なschema
ファイルでもそれほど時間がかからない傾向があるため、これは妥当なトレードオフと思われます。
ご自身でこれを試してみることもできます。うまくいくと感じる解決策が見つかった場合は、issueを追加 (新しいタブで開く)してください。このセクションを更新できます。
- 本番環境への移行
ここまで来たら、アプリケーションをデプロイする準備ができています。データベースがどこにあるかによって、データベースのセットアップに関するドキュメントに従ってデプロイパイプラインを設計する必要があります。この時点から考慮すべき要素はたくさんあるため、単一のソリューションを提供することはできません。詳細については、データベースとそのデプロイプラットフォームのドキュメントを参照することをお勧めします。