Docker上でNext.js/Express.jsを環境構築
はじめに
初めまして、きょうへいと申します。
この度は私の記事をご覧いただきありがとうございます!
私は未経験からエンジニアとして就職し、現在の企業でTypeScript、Next.js、Express.jsを使用した開発に携わっています。
まだまだ駆け出しのエンジニアなので、技術についての理解を深めるために本記事を作成しました。
良ければお付き合い下さい!
本記事の目的
- Docker を使用したフルスタック開発環境の構築方法の解説
- Next.js(フロントエンド)とExpress.js(バックエンド)の連携環境の作成
- データベース(PostgreSQL)を含めた実践的な開発環境の構築
前提知識
環境構築の流れ
1.プロジェクト構成
2.docker-compose.yaml作成
3.Next.jsの環境構築
4.Expreess.jsの環境構築
プロジェクト構成
今回は以下のような構成で進めようと思います。
project-root/
├── front/
│ ├── Dockerfile
│ └── (Next.jsプロジェクトファイル)
├── back/
│ ├── Dockerfile
│ └── (Express.jsプロジェクトファイル)
└── docker-compose.yml
リポジトリの作成とサブモジュール化
まずは、リポジトリを作成していきます。
※リポジトリの作成方法については、公式の記事を参照ください。
今回は
- project-root(任意のファイル名)
- front
- back
この3つのリポジトリを作成したのち、front
,back
はproject-root
のサブモジュール化します。
サブモジュール化は以下のコードで行って下さい。
git submodule add <frontリポジトリのSSH> front
git submodule add <backリポジトリのSSH> back
project-root
をリモートリポジトリにpushしてback@〇〇〇〇〇〇〇
のようになっていれば反映できています。
dockerfileの作成
Dokcerfileの作成
front
、back
にdockerfile
を作成し、以下のように記載してください
FROM node:20
WORKDIR /app
Docker Compose設定
また、docker-compose.yml
は以下のようになります。
services:
front:
build:
context: ./front
dockerfile: Dockerfile
ports:
- "3000:3000" # Next.jsのデフォルトポート
volumes:
- ./front:/app # ソースコードの同期
environment:
- NEXT_PUBLIC_API_URL=http://back:8000 # バックエンドのURL
depends_on:
- back
restart: unless-stopped
back:
build:
context: ./back
dockerfile: Dockerfile
ports:
- "8000:8000" # Express.jsのポート
volumes:
- ./back:/app
- /app/node_modules # node_modulesはコンテナ内に保持
environment:
- DATABASE_URL=postgresql://user:password@db:5432/dbname
depends_on:
- db
restart: unless-stopped
db:
image: postgres:15
ports:
- "5432:5432"
volumes:
- postgres_data:/var/lib/postgresql/data # データの永続化
environment:
- POSTGRES_USER=user
- POSTGRES_PASSWORD=password # 本番環境では必ず変更してください
- POSTGRES_DB=dbname
restart: unless-stopped
volumes:
postgres_data: # PostgreSQLのデータを永続化
設定が完了したら、以下のコマンドでビルドを実行します。
docker-compose build
next.jsの環境構築
プロジェクトの作成
まず、Dockerfileを一時的にルートディレクトリに移動します(権限の問題を回避するため)
移動させた後、Next.jsプロジェクトを作成します。
root-projectに戻り以下のコマンドを実行してください
docker-compose run --rm front npx create-next-app .
すると、next.jsで以下の内容を使用するか出てくるので好きなように選んでください。
今回、僕は初期のままにしています。
Would you like to use TypeScript? … No / Yes
→ 型安全な開発のために推奨
✔ Would you like to use ESLint? … No / Yes
→ コード品質管理のために推奨
✔ Would you like to use Tailwind CSS? … No / Yes
→ CSSフレームワークの導入
✔ Would you like to use `src/` directory? … No / Yes
→ ソースコードの整理のために推奨
✔ Would you like to use App Router? (recommended) … No / Yes
→ 新しいルーティングシステムの採用
✔ Would you like to customize the default import alias (@/*)? … No / Yes
→ インポートパスの簡略化
Dockerfileの更新
Dockerfileにこちらを追記してfront
に戻してください
FROM node:20
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
RUN npm run build
EXPOSE 3000
CMD ["npm", "start"]
ビルドと動作確認
再度buildを行い、dockerとnext.jsの初期化を実施します。
docker-compose build
docker-compose run --rm front npx next build
next.jsのビルドが終わると起動の確認ができます。
必要があれば適宜確認を行ってみてください。
docker-compose up front
Expreess.jsの環境構築
root-projectにて以下のコマンドを使用します。
以下のコマンドを使用することにより、npmの初期化と必要なパッケージのインストールを行います。
docker-compose run --rm back npm init -y
docker-compose run --rm back npm install express
docker-compose run --rm back npm install typescript @types/express @types/node ts-node nodemon -D
Dockerfileの更新
Dockerのコンテナ内で処理を行うため、Dockerfileに以下の記載を行ってイメージをビルドします。
FROM node:20
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
#tscの初期化を行ったらコメントアウトを外す RUN npm run build
EXPOSE 8000
CMD ["npm", "run", "dev"]
Dockerfileの変更を行なったら、再度ビルドを行って下さい。
docker-compose build
TypeScript設定
ビルドが終わり次第、TypeScriptの設定を行なっていきます。
以下のコマンドで初期化を行うようにしましょう。
docker-compose run --rm back npx tsc --init
package.jsonの更新
TypeScriptの初期化が終わったら、Express.jsの立ち上げを行なっていきます。
まずは、dockerを立ち上げにExpress.jsが動作するようにpackage.jsonを書き換えていきます。
以下の内容に修正を行って下さい。
{
"name": "app",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"dev": "npx nodemon --exec ts-node src/server.ts",
"build": "tsc",
"start": "node dist/app.js"
},
"keywords": [],
"author": "",
"license": "ISC",
"dependencies": {
"express": "^4.21.1"
},
"devDependencies": {
"@types/express": "^5.0.0",
"@types/node": "^22.8.1",
"nodemon": "^3.1.7",
"ts-node": "^10.9.2",
"typescript": "^5.6.3"
}
}
サーバーの作成
package.jsonへの記載変更が終了したら、実際にテスト用のサーバーを作成していきます。
以下のような記載を行って、Express.jsにてHello World!
が表示されるようにしていきます。
import express from "express";
import { Request, Response } from "express";
const app = express();
const port = 8000;
app.get("/", (req: Request, res: Response) => {
res.send("Hello World!");
});
app.listen(port, () => {
console.log(`Example app listening on port ${port}`);
})
動作確認
以上の記載が終了すれば、localhost:8000
上に表示が行えているはずです。
dockerのビルドを行ったのち、確認を行ってみて下さい。
docker compose build
dcoker compose up
正常に動作していれば、http://localhost:8000 にアクセスすると「Hello World!」が表示されるはずです。
終わりに
今回初めて技術記事の作成を行いました。
今後もアプリケーション作成時に行った実装についての記事を作成していこうと思っていますので、よければそちらも読んでいただけると嬉しいです!
Discussion