
最近流行りのフレームワークたちをlernaを使ってモノレポ化する。
構成はこんな感じになる想定。
.
├── lerna.json
├── package.json
└── packages
├── client <-------- Next.js
│ └── package.json
└── server <-------- NestJS
└── package.json
どこまでやるか
今回モノレポ化したい一番の目的が、package.jsonのscriptsコマンドの一括操作。
つまりリポジトリ直下でyarn devと実行したら、クライアント側とサーバー側の両方のyarn devが実行される形。
node_modulesの共通化はやらない。
クライアントとサーバーを作成する
各自Next.jsとNestJSのコマンドを使って作成する。もうすでにclientとserverのディレクトリが作成済みの人はここの作業は不要。別にNext.jsやNestJSじゃなくても全く構わない。
まずはclientとserverをまとめるためのmonorepoディレクトリを作成する。
mkdir monorepo cd monorepo
今後の作業はこのmonorepoディレクトリの中でおこなっていく。
Next.jsでクライアントの作成
# クライアントの作成 @See https://nextjs.org/docs
npx create-next-app
コマンドを実行するといくつか質問を聞かれるが全部ENTERでOK。最初に聞かれるプロジェクト名だけclientと入力する。
create-next-appで作成すると自動的にgit管理になるが、今回は邪魔になるので.gitを削除しておく。
rm -rf client/.git
yarn devを実行した後、http://localhost:3000にアクセスしてページが表示されたらOK。
cd client
yarn dev
NestJSでサーバーの作成
# サーバーの作成 @See https://docs.nestjs.com/first-steps # 'server'という名前で作成する nest new server
ここもコマンドを実行するといくつか質問を聞かれるが全部ENTERでOK。
nest newで作成すると自動的にgit管理になるが、今回は邪魔になるので.gitを削除しておく。
rm -rf server/.git
yarn start:devを実行した後、http://localhost:3000にアクセスしてページが表示されたらOK。
cd server
yarn start:dev
ただ、このままだとクライアント側とポート番号が3000で衝突して同時に環境を立ち上げることができないのでポート番号を変更しておく。
$ vim src/main.ts
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
await app.listen(3001); // <------- 3001に変更
}
bootstrap();
また、クライアントとサーバー側でscriptsコマンドの名前を同じにしておきたいので、package.jsonも編集しておく。yarn devで環境を立ち上げられるようにする。
$ vim package.json ...略 "scripts": { "dev": "nest start --watch",
lernaを導入してモノレポ化する
さっそくlernaでモノレポ化する。現在のディレクトリ構造は下記。
monorepo
├── client
│ └── package.json
└── server
└── package.json
lernaの導入
npm install -g lerna
npxでその場だけでlernaをインストールしてもいいが、今回はグローバルでインストールしておく。
lerna initで初期環境を構築
cd monorepo
lerna init
実行するとlerna.json,package.json,packagesの3つが作成される。
monorepo ├── lerna.json ├── package.json ├── packages ├── client └── server
client、serverをパッケージ化する
lerna createコマンドでパッケージの作成とともにディレクトリを生成されるが、今回はすでにclient, serverを作ってあるので、それをpackages配下に移動させてからコマンドを実行する。
mv server packages mv client packages lerna create @monorepo/server ./packages/server lerna create @monorepo/client ./packages/client
@monorepoの部分がパッケージ名となるが、あとから変更可能なので気軽につける。
また、lerna createをすると各パッケージ配下にいくつかファイルが作成される。
__tests__やREADME.mdは不要なので削除してもOK。libは必要なので消さないでおく。
scriptsコマンドの一括操作
ディレクトリ直下のpackage.jsonにscriptsコマンドを追加する。
vim package.json { "name": "root", "private": true, "scripts": { "dev": "lerna run dev --parallel --stream --scope=@monorepo/{client,server}" }, "devDependencies": { "lerna": "^4.0.0" } }
ディレクトリ直下でyarn devを実行すると、clientとserverの両方が立ち上がる。
これで終了
コマンドまとめ
mkdir monorepo cd monorepo # クライアント作成 npx create-next-app rm -rf client/.git # サーバー作成 nest new server rm -rf server/.git # モノレポ化 lerna init mv server packages mv client packages lerna create @monorepo/server ./packages/server lerna create @monorepo/client ./packages/client
終わり
ただ、node_modulesの共通化はyarn workspaceとlernaをセットで使ったりと、少し複雑になってきそうだったのでやらなかったけど、モノレポ化と言ったらリポジトリの軽量化みたいなところもあるので別の機会でちゃんとやる。