はじめに
ここまでの記事では、NestJSとPrismaを組み合わせて、APIの設計・運用基盤を整えてきました。
データモデル設計、リレーション定義、マイグレーション管理、テスト環境構築まで一通り完了し、バックエンドAPIの土台は実用レベルに達しています。
第5回となる今回は、いよいよフロントエンド(React)との接続に進みます。
APIを単独で作って終わるのではなく、ブラウザから実際にデータを操作できる状態に仕上げることが今回のゴールです。
フロントとバックエンドをつなぐ構成の全体像
この回では、次のような全体像を目指して進めていきます。
- Reactでフロントエンド画面を構築し、NestJS APIを呼び出します
- NestJSはAPIだけでなく、Reactでビルドした静的ファイルも配信できるようにします
- PostgreSQL(Dockerコンテナ)がバックエンドDBとして動作し、データの保存・取得を担います
最終的には、Dockerfileとdocker-composeを使ってこれらを一体化し、開発・テスト・本番環境それぞれでスムーズに動かせる構成を作ります。
前回までに準備できている状態の整理
前回(第4回)までで、以下の状態がすでに整っています。
- NestJS+Prismaを使った記事投稿API(/postsエンドポイント)が動作している
- PostgreSQL(Docker)と接続できるようになっている
- 環境変数によるDB接続切り替え(開発・テスト環境)ができている
- テスト環境用のリセットができる
- PrismaClientとNestJSの連携設計が確立されている
つまり、API側はもうすぐにでもフロントエンドと連携できる状態です。今回はこのAPIを活用して、React側からデータ取得・表示・投稿まで進めていきます。
本記事の対象読者は、以下のような方を想定しています。
- NestJSとPrismaでAPI基盤を作れたので、次はフロントエンドをつないで動かしたい方
- Reactを使ったフロントエンド開発をこれから本格的に始めたい方
- Dockerやデプロイ構成まで意識したフルスタック開発にチャレンジしたい方
今回も、一つ一つの作業を積み上げながら、着実に「開発・運用できるアプリケーション」を構築していきましょう。
この連載の全体像と今回の位置づけ
- NestJSで始めるWebアプリ開発 ─ ブログサイトを作りながら学ぶプロジェクト構成と設定管理
- NestJSで記事投稿APIを作ろう ─ Prisma導入とCRUD実装の基本
- アプリの信頼性を高める ─ ロギング・エラーハンドリング・テスト戦略
- PrismaとDB設計を深掘る ─ モデル・リレーション・運用設計
- ReactでUIを構築して本番へデプロイ ─ Dockerと環境構築 ←
今回の記事
今回のゴール
このブログ記事では、NestJS + React + Prisma + PostgreSQL を使って開発したブログアプリを、本番環境にデプロイするまでの一連の流れを記録しています。
具体的には、以下のような構成を目指します:
- フロントエンド(React)とバックエンド(NestJS)を分離開発
- PrismaでDBスキーマを管理し、PostgreSQLと接続
- ViteやTailwind CSSなどの最新のフロントエンド開発環境を活用
- Dockerを使って本番ビルド・統合
- クラウドサービス「Railway」を使って、フルスタック構成を本番公開
また、記事の後半では以下のポイントについても扱います:
- Viteの環境変数の扱いと注意点(VITE_API_URL など)
- Prismaのマイグレーションと本番DBへの適用
- Railwayでの環境変数設定とDockerビルド戦略
- Reactのビルド成果物を NestJS 経由で静的配信する構成
この記事を読み進めることで、個人開発やPoC、スタートアップの立ち上げにも使える「即戦力の本番構成」を、実際の手順に沿って追体験できます。
Reactアプリの作成と基本構成
ここでは、Reactアプリを新規作成し、開発しやすい構成を整えるところまで進めます。
Viteでプロジェクト作成(frontendディレクトリ)
Reactアプリを立ち上げる方法はいくつかありますが、今回はViteを使用して作成する方法を採用します。
(Create React Appでも進められますが、Viteの方がビルド速度が速く、開発体験が向上するためです)
まず、NestJSプロジェクト直下(/backend
と並列の位置)に、frontend
ディレクトリを作成します。
cd <プロジェクトのルート>
npm create vite@latest frontend -- --template react-ts
コマンドの意味:
frontend
という新しいディレクトリにReact+TypeScript構成のViteアプリを作成--template react-ts
により、最初からTypeScript対応
作成が完了したら、依存関係をインストールします。
cd frontend
npm install
これで、Reactアプリの初期セットアップが完了しました。
/frontend
ディレクトリ構成
セットアップ直後のfrontendディレクトリは次のようになっています。
/frontend
├── public/
├── src/
├── App.tsx
├── main.tsx
├── index.html
├── package.json
├── tsconfig.json
├── vite.config.ts
この中のsrc/App.tsx
を編集することで、Reactアプリケーションの画面を作っていく形になります。
Tailwind CSSの導入
今回は、シンプルなUIを素早く作るためにTailwind CSSを導入します。
インストール手順は次の通りです。
npm install tailwindcss @tailwindcss/vite
続いて、vite.config.ts
を以下のように設定します。
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import tailwindcss from '@tailwindcss/vite'
// https://vite.dev/config/
export default defineConfig({
plugins: [react(), tailwindcss()],
})
最後に、src/index.css
を作成し、Tailwindの基本スタイルを読み込ませます。
@import "tailwindcss";
動作確認
セットアップが完了したら、実際に開発サーバーを立ち上げて、動作確認を行います。
cd frontend
npm run dev
ブラウザで http://localhost:5173
にアクセスし、初期画面(Viteのロゴと「Vite + React」表示)が出ればOKです。
さらに、Tailwindが正しく効いているかを確認するために、App.tsx
を軽く編集してみます。
function App() {
return (
<div className="min-h-screen flex items-center justify-center bg-blue-100">
<h1 className="text-4xl font-bold text-blue-800">
Frontend is working!
</h1>
</div>
);
}
export default App;
再読み込みして、背景が薄い青色 (bg-blue-100
)、文字が濃い青色 (text-blue-800
) に変わっていれば、Tailwindも正常に動いています。
NestJSとの連携とAPI通信設定
APIエンドポイントの設定
まず、ReactアプリからNestJSサーバーへリクエストを送るために、環境変数でAPIエンドポイントを管理するようにします。frontend/.env
ファイルを作成し、次のように記述します。
VITE_API_URL=http://localhost:3000
ReactからAPIエンドポイントを参照する際は、import.meta.env.VITE_API_URL
を使います。
(※Viteの仕様上、環境変数にはVITE_プレフィックスが必須です)
記事投稿フォーム(PostForm.tsx)の作成
まず、投稿フォーム用のコンポーネントを作成します。
frontend/src/components/PostForm.tsx
を作成し、次のように記述します。
import { useState } from 'react';
type Props = {
onPostCreated: () => void;
};
export function PostForm({ onPostCreated }: Props) {
const [title, setTitle] = useState('');
const [content, setContent] = useState('');
async function handleSubmit(e: React.FormEvent) {
e.preventDefault();
await fetch(`${import.meta.env.VITE_API_URL}/posts`, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ title, content }),
});
setTitle('');
setContent('');
onPostCreated();
}
return (
<form
onSubmit={handleSubmit}
className="bg-white p-8 rounded shadow-md space-y-4 w-full max-w-md"
>
<h1 className="text-2xl font-bold text-blue-700">新規記事投稿</h1>
<div>
<label className="block text-sm font-medium text-gray-700">タイトル</label>
<input
type="text"
value={title}
onChange={(e) => setTitle(e.target.value)}
className="mt-1 block w-full border-gray-300 rounded-md shadow-sm"
required
/>
</div>
<div>
<label className="block text-sm font-medium text-gray-700">本文</label>
<textarea
value={content}
onChange={(e) => setContent(e.target.value)}
className="mt-1 block w-full border-gray-300 rounded-md shadow-sm"
rows={4}
/>
</div>
<button
type="submit"
className="w-full bg-blue-600 text-white py-2 rounded hover:bg-blue-700 transition"
>
投稿する
</button>
</form>
);
}
- 投稿後に
onPostCreated()
コールバックを呼び、親コンポーネントで一覧を更新できるようにします。
記事一覧表示(PostList.tsx)の作成
続いて、記事一覧用のコンポーネントを作成します。
frontend/src/components/PostList.tsx
を作成し、次のように記述します。
import { useEffect, useState } from 'react';
type Post = {
id: number;
title: string;
content?: string;
};
export function PostList() {
const [posts, setPosts] = useState<Post[]>([]);
async function fetchPosts() {
const response = await fetch(`${import.meta.env.VITE_API_URL}/posts`);
const data = await response.json();
setPosts(data);
}
useEffect(() => {
fetchPosts();
}, []);
return (
<div className="mt-12 w-full max-w-2xl">
<h2 className="text-xl font-bold mb-4 text-blue-700">投稿一覧</h2>
<ul className="space-y-4">
{posts.map((post) => (
<li key={post.id} className="p-4 bg-white rounded shadow">
<h3 className="text-lg font-semibold">{post.title}</h3>
{post.content && <p className="mt-2 text-gray-600">{post.content}</p>}
</li>
))}
</ul>
</div>
);
}
- 初回レンダリング時に記事一覧を取得して表示します。
App.tsx(親コンポーネント)
最後に、src/App.tsx
を次のように編集します。
import { PostForm } from './components/PostForm';
import { PostList } from './components/PostList';
import { useState } from 'react';
function App() {
const [refreshKey, setRefreshKey] = useState(0);
function handlePostCreated() {
setRefreshKey((prev) => prev + 1);
}
return (
<div className="min-h-screen bg-gray-50 flex flex-col items-center p-8">
<PostForm onPostCreated={handlePostCreated} />
<PostList key={refreshKey} />
</div>
);
}
export default App;
- 投稿後に
refreshKey
を更新して、PostList
コンポーネントを再マウントすることで一覧を更新します。
動作確認
ここまで実装できたら、次の手順で動作を確認します。
npm run dev
でReactアプリを起動しますhttp://localhost:5173
にアクセスします- タイトルと本文を入力して「投稿する」ボタンをクリックします
- 成功すると一覧が自動更新され、新しい記事が表示されます
必要に応じて npx prisma studio を起動し、DB上にも投稿内容が登録されていることを確認します
※ CORSエラーが出る場合
ブラウザの仕様により、Reactアプリ(http://localhost:5173
)からNestJSサーバー(http://localhost:3000
)へリクエストを送ると、
セキュリティチェック(プリフライトリクエスト)が発生します。
NestJS側でこれに対応するため、src/main.ts
に以下の設定を追加します。
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import { ValidationPipe } from '@nestjs/common';
import { HttpExceptionFilter } from './common/filters/http/http.filter';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.useGlobalPipes(new ValidationPipe());
app.useGlobalFilters(new HttpExceptionFilter());
+ app.enableCors();
await app.listen(process.env.PORT ?? 3000);
}
bootstrap().catch((err) => {
console.error('Application failed to start', err);
});
これで、ブラウザ側からのリクエストが正しく許可され、登録動作がスムーズに行えるようになります。
ReactアプリをビルドしてNestJSで静的配信する
ReactアプリとNestJS APIが連携できるようになったので、次は、ビルドしたReactアプリをNestJS側で静的ファイルとして配信できる構成を整えます。
これにより、ブラウザからAPIもReact画面も一つのサーバーで扱えるようになり、開発・本番環境ともにシンプルで扱いやすい構成になります。
Reactアプリをビルドする
まず、frontend
ディレクトリでReactアプリをビルドします。
cd frontend
npm run build
正常終了すると、frontend/dist
ディレクトリが生成されます。
この中に、HTMLやCSS、JavaScriptなど、ブラウザで動作する完成ファイル一式が出力されます。
NestJSで静的ファイルを配信する設定
NestJSでReactの静的ファイルを配信できるように、backend/src/main.ts
に次の設定を追加します。
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import { ValidationPipe } from '@nestjs/common';
import { HttpExceptionFilter } from './common/filters/http/http.filter';
+ import { NestExpressApplication } from '@nestjs/platform-express';
+ import { join } from 'path';
async function bootstrap() {
+ const app = await NestFactory.create<NestExpressApplication>(AppModule);
app.useGlobalPipes(new ValidationPipe());
app.useGlobalFilters(new HttpExceptionFilter());
app.enableCors();
+ app.useStaticAssets(join(__dirname, '../../', 'frontend', 'dist'));
await app.listen(process.env.PORT ?? 3000);
}
bootstrap().catch((err) => {
console.error('Application failed to start', err);
});
動作確認
NestJSを起動し、http://localhost:3000
にアクセスすると、Reactで作成した画面が表示されるかと思います。
アクセスできましたら新規投稿もできるか確認します。
フロントエンドとAPIのパス設計を整理する
ここまでで、Reactアプリをビルドし、NestJSで静的ファイルを配信できるようになりました。
しかしこのままだと、Reactアプリ側のパスと、NestJS側のAPIパスが衝突するリスクが残っています。
たとえば、ブラウザで /posts
にアクセスするとき、
NestJSが「静的ファイル」だと誤認してしまったり、
逆にAPIリクエストがReact側に流れてしまったりする可能性があるからです。
そこで、フロントエンドの画面遷移と、バックエンドAPIのリクエストをきれいに分離するために、
APIリクエストには /api/
プレフィックスを付ける設計に切り替えます。
なぜ /api プレフィックスを付けるのか?
- フロントエンドのルーティング(
/posts
、/about
など)と - バックエンドAPIのルーティング(
/api/posts
、/api/users
など)
これを明確に分けることで、
- ページリロード時に正しくindex.htmlを返す
- APIリクエスト時は確実にNestJS側に到達させる
という、自然でトラブルのないリクエストハンドリングができるようになります。
変更作業
NestJS
Controller側で /api
プレフィックスを付ける
たとえば、記事投稿API(PostsController)では次のように設定します。
- @Controller('posts')
+ @Controller('api/posts')
export class PostsController {
constructor(private readonly postsService: PostsService) {}
@Post()
create(@Body() createPostDto: CreatePostDto) {
return this.postsService.create(createPostDto);
}
React
frontend/.env
ファイルを編集し、次のように記述します。
VITE_API_URL=http://localhost:3000/api
動作確認
再度、NestJSを起動し新規投稿と投稿一覧が動くことを確認します。
Docker Composeを使った統合環境(frontend+backend+db)構築
ここまでで、フロントエンド・バックエンド・データベース(PostgreSQL)のそれぞれが個別に動作する状態になりました。次は、これらをDocker Composeを使って一括で起動できる開発環境を構築します。
具体的には、
docker-compose.dev.yml
→ 開発環境(ホットリロード対応)docker-compose.prod.yml
→ 本番環境(ビルドして最適化)
をそれぞれ作り、シーンに応じた最適な起動方法を選べるようにします。
これにより、開発体験もデプロイ体験もスムーズかつ安全になります。
docker-compose.dev.ymlを作成する(開発用)
開発中は、ソースコードのリアルタイム反映を最優先します。そのため、ボリュームマウントでホストとコンテナを同期し、NestJS・React両方をホットリロードで動かします。
docker-compose.dev.yml
services:
db:
image: postgres:15
container_name: nestjs-postgres-dev
ports:
- "5432:5432"
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
POSTGRES_DB: nestjs_blog_dev
volumes:
- db-data-dev:/var/lib/postgresql/data
backend:
build:
context: ./backend
dockerfile: Dockerfile.dev
container_name: nestjs-backend-dev
ports:
- "3000:3000"
environment:
DATABASE_URL: postgres://postgres:postgres@db:5432/nestjs_blog_dev
volumes:
- ./backend:/app
command: npm run start:dev
depends_on:
- db
frontend:
build:
context: ./frontend
dockerfile: Dockerfile.dev
container_name: react-frontend-dev
ports:
- "3001:3000"
volumes:
- ./frontend:/app
- /app/node_modules
command: npm run dev
depends_on:
- backend
volumes:
db-data-dev:
Dockerfile.devを用意する
各サービスに開発専用のDockerfileを置きます。
FROM node:20
WORKDIR /app
COPY package*.json ./
RUN npm install
CMD ["npm", "run", "start:dev"]
FROM node:20
WORKDIR /app
COPY package*.json ./
RUN npm install
CMD ["npm", "run", "dev"]
ポート番号を整理したいのでviteで起動する際のポート番号を変更します。
export default defineConfig({
plugins: [react(), tailwindcss()],
+ server: {
+ host: "0.0.0.0",
+ port: 3000,
+ },
})
バックエンド、フロントエンド両方とも3000で起動し、バッティングしないようフロントエンドは3001でアクセスするように設定しました。
DBを新しく作成しましたのでマイグレーションを流します。
docker-compose exec backend npx prisma migrate deploy
動作確認
下記コマンドで起動します。
docker-compose -f docker-compose.dev.yml up --build
ビルドが毎回いるかというとそうではありません。
依存ライブラリを変えたときやDockerfile.devを変更した際はビルドが必要となりますが、そうでなければ下記コマンドで起動で問題ありません。
docker-compose -f docker-compose.dev.yml up
`http://localhost:3001/``にアクセスし投稿画面が表示されれば正常に起動できています。
ホットリロードが正常に動作するか確認するために「新規記事投稿」→「記事投稿」に修正してみます。
return (
<form
onSubmit={handleSubmit}
className="bg-white p-8 rounded shadow-md space-y-4 w-full max-w-md"
>
- <h1 className="text-2xl font-bold text-blue-700">新規記事投稿</h1>
+ <h1 className="text-2xl font-bold text-blue-700">記事投稿</h1>
<div>
修正内容がブラウザに反映されればOKです。
Railwayを使って本番環境構築
Railwayとは?
Railway は、バックエンドやデータベースを “レールに乗せるように” 簡単にデプロイできる、開発者向けのクラウドプラットフォームです。
特にこんな特徴があります:
- Docker対応:Dockerfileさえ用意すれば、任意のアプリケーションをそのままデプロイ可能
- DB同時構築:PostgreSQL や Redis などのマネージドDBをワンクリックで作成・接続可能
- 環境変数管理がラク:GUIで .env 相当の環境変数をセット、デプロイごとに適用される
- 無料枠あり:軽い検証や個人開発に十分な無料プラン
- Git連携:GitHubと接続すればプッシュごとに自動デプロイされる
こんな人・チームにおすすめ
- 本番環境にとりあえず「今動くもの」を早く立てたい
- フロントエンド + バックエンド + DB を一括で管理したい
- Dockerベースでアプリを構築している
- Heroku の代替を探している
- 技術検証や個人開発で素早く PoC を回したい
Railway は、Dockerアプリ・NestJS・Prisma・PostgreSQL を組み合わせた構成でも、驚くほどスムーズにデプロイできるクラウドプラットフォームでした。複雑なCI/CDやインフラ構築に悩むより、「いま動くものを本番に出す」ための強力な選択肢として、とても信頼できます。
Railwayを使ってアプリを構築していく流れ
このプロジェクトでは、NestJSとReactで構成されたブログアプリを、クラウドプラットフォーム「Railway」を使って本番環境へデプロイします。
Railwayを使うことで、Dockerベースの構成でも柔軟に環境を構築でき、バックエンド・フロントエンド・データベースを一括して管理できます。
ここでは、実際にどのような手順で本番環境を立ち上げるか、流れをざっくり整理しておきます。
-
Dockerfileの準備
バックエンド(NestJS)とフロントエンド(React)をそれぞれDockerでビルドできる構成に
本番用に Dockerfileを用意
フロントはビルド後、NestJSが静的ファイルとして配信 -
Railwayプロジェクトの作成
Railwayにログインし、新しいプロジェクトを作成
「Deploy from GitHub」のテンプレートを使って開始 -
PostgreSQLインスタンスの追加
「Deploy PostgreSQL」から PostgreSQL を選択して追加
自動生成される DATABASE_PUBLIC_URLの環境変数を後で利用する -
Prismaの本番マイグレーション実行
prisma/migrations をベースに、本番用のDBにマイグレーションを適用 -
環境変数(Variables)の設定
.env.production に相当する値を Railway の GUI 上で登録
フロントエンドとバックエンドのビルド時にこれらが参照されるようにする -
Railwayでデプロイをトリガー
GitHub連携によってデプロイを開始
Dockerfileの内容に従ってビルド → コンテナ起動 → アプリ公開 -
動作確認と修正
https://xxxxx.up.railway.app でアプリが公開される
APIのエンドポイントや環境変数にズレがないか確認
必要に応じて再ビルド・再デプロイ
Dockerfileの準備
本番環境では、ソースコードをビルドした上で最適化された成果物のみをコンテナ化します。このため、ホットリロードは不要で、単純なビルド→起動の流れになります。
ローカルで本番環境を起動する機会はあまりないかと思いますが、こちらはこの後外部のサービスにデプロイする際に使用するものとなります。
# ビルドステージ
FROM node:20 AS builder
WORKDIR /app
# backendとfrontend両方コピー
COPY backend/package*.json backend/
COPY frontend/package*.json frontend/
# frontendビルド
WORKDIR /app/frontend
COPY frontend/ .
RUN npm install
ARG VITE_API_URL
ENV VITE_API_URL=$VITE_API_URL
RUN npm run build
# backendビルド
WORKDIR /app/backend
COPY backend/ .
RUN npm install
RUN npm run build
RUN npx prisma generate
# 実行ステージ
FROM node:20-slim
WORKDIR /app
# backendとfrontendまとめてコピー
COPY /app .
ENV NODE_ENV=production
CMD ["node", "backend/dist/main.js"]
Dockerfileでエラーが発生しないかビルドとコンテナの起動で確認します。
docker build -t nestjs-blog-app .
docker run --rm -p 3000:3000 nestjs-blog-app
コンテナを起動すると下記のようにNestJSの起動中にデータベースへのアクセスでエラーが発生します。
本番用のデータベースにアクセスするのですがまだ作成しておりませんのでこのエラーが出てる状態で問題ありません。
Railwayプロジェクトの作成
Railwayにログインし、新しいプロジェクトを作成
下記URLからアカウントを登録します。
アカウントを登録したら、「Deploy from GitHub repo」で今回作成したリポジトリを選択します。
Railwayからアクセス可能なリポジトリについては下記の画面で設定可能です(全てのリポジトリをRailwayに公開する必要はありません)
プロジェクトのトップにあるDockerfileを元に恐らくデプロイが開始しますが失敗すると思います。一旦そのままにしておきます。
PostgreSQLインスタンスの追加
次に本番環境用のデータベースを構築します。下記の画面から「Deploy PostgreSQL」を選択します。
1分ほどで構築完了しデータベースにアクセスするための情報が表示されますのでこちらで「DATABASE_PUBLIC_URL」を控えておきます。
Prismaの本番マイグレーション実行
ローカル環境で先ほど作成したPostgreSQLインスタンスに対してマイグレーションを実行します。
DATABASE_URL="..." npx prisma migrate deploy
- DATABASE_URL: PostgreSQLインスタンスの追加で発行されたDATABASE_PUBLIC_URL
マイグレーションが正常終了するとRailwayからもDB情報を確認できるようになります。
環境変数(Variables)の設定
再びDockerでデプロイするプロジェクトに戻り外部からアクセスするためのDomainを「Generate Domain」で生成します。(Railwayがhttps://xxxxx.up.railway.app
という形式のDomainを生成してくれます)
この値が、最終的にブラウザでアクセスするURLになります。
VariablesでDATABASE_URLとVITE_API_URLを設定します。
- DATABASE_URL: PostgreSQLインスタンスの追加で発行されたDATABASE_PUBLIC_URL
- VITE_API_URL: 「Generate Domain」で発行された
${URL}/api
Railwayでデプロイをトリガー
これで一通り設定が終わりましたのでデプロイを行い確認します。「Deploy from GitHub repo」の場合は対象のブランチにコミットすると自動でデプロイが行われますが、「Redeploy」で手動デプロイをすることも可能です。
動作確認
「Generate Domain」で発行されたURLにアクセスすると今回作成されたブログアプリが表示され、投稿などができるかと思います。
おわりに
ここまでで、NestJS + React + Prisma を組み合わせたブログアプリを、Dockerを使って本番ビルドし、クラウドプラットフォーム Railway にデプロイする一連の流れを整理しました。
単にローカルで動かすだけでなく、
- 本番用のビルドと環境切り替え
- PrismaマイグレーションとDB運用
- フロントエンドとバックエンドの統合配信
- Railwayでのコンテナ管理と環境変数設定
といった「実際に運用していくための準備」まで踏み込んだ内容になっています。
これらの作業は、一見すると地味で手間がかかるように思えるかもしれません。
しかし、開発初期から丁寧に整えておくことで、チーム開発や規模拡大、本番トラブル対応の場面で確実に大きなアドバンテージになります。
また、今回紹介した構成は、個人開発やスタートアップの立ち上げにもすぐに応用できるシンプルかつ強力なベースとなっています。
今後は、さらに運用を意識した改善(例:ステージング環境の構築や監視設定、認証まわり)にも挑戦していきます。
引き続き、より実践的なアプリケーション構成を構築いきましょう。
本記事が、開発・運用スキルの成長に少しでも役立てば嬉しいです。
関連する技術ブログ
NestJSで記事投稿APIを作ろう ─ Prisma導入とCRUD実装の基本
NestJSとPrismaを使って、シンプルな記事投稿APIを一から作っていく手順をまとめました。開発環境の整え方から、データベースとの接続、APIの作成、データのチェック(バリデーション)まで、基本を一歩ずつ丁寧に解説しています。
shinagawa-web.com
NestJSアプリの信頼性を高める ─ ログ・エラーハンドリング・テスト戦略
NestJSアプリを本番品質へと近づけるために、ロギング・例外処理の共通化・ユニットテストとE2Eテストの構築までを丁寧に解説。実践的なコードと構成例を通じて、信頼されるAPI設計の基礎を整えます。
shinagawa-web.com
NestJS × Prismaで深めるDB設計 ─ モデル・リレーション・運用設計
NestJSとPrismaを組み合わせ、実践的なデータベース設計・リレーション定義・マイグレーション運用の基本を整理します。単なるAPI開発に留まらず、運用を見据えた設計力を着実に積み上げ、次回のフロントエンド連携へとつなげます。
shinagawa-web.com
NestJSとReactで始めるWebアプリ開発 ─ ブログサイトを作りながら学ぶプロジェクト構成と設定管理
NestJSでブログアプリを開発しながら、Webバックエンドの基礎と実践を体系的に学ぶ連載の第一歩。プロジェクトの初期構成、環境変数管理、将来の拡張を見据えたモノレポ準備まで、堅実な土台作りを一緒に進めていきます。
shinagawa-web.com
Webアクセシビリティの完全ガイド:Lighthouse / axe による自動テスト、WCAG基準策定、キーボード操作・スクリーンリーダー対応まで
Webアクセシビリティの課題を解決するための包括的なガイド。Lighthouse / axe を活用した自動テストの設定、WCAGガイドラインに基づく評価基準の整備、キーボード操作やスクリーンリーダー対応の改善、カラーコントラストの最適化、ARIAランドマークの導入、フォームやモーダルの操作性向上まで詳しく解説。定期的なアクセシビリティレポートを活用し、継続的な改善を実現する方法も紹介します。
shinagawa-web.com
チャットアプリ(画像・PDF送信、ビデオ通話機能付き)
お客様固有の要件を除き一般的なチャットアプリに求められる最低限の機能を実装しデモアプリとしてご紹介いたします。
shinagawa-web.com
React × Tailwind CSS × Emotionで実践するコンポーネント設計ガイド:デザインシステム・状態管理・再利用性の最適解
React、Tailwind CSS、Emotion、Storybook、Figma、Next.jsを活用したコンポーネント設計のベストプラクティスを紹介。デザインシステムに基づく命名規則、適切な状態管理、再利用性を高める抽象化、アクセシビリティ対応、スタイルガイドラインの整備、テーマ設定、バージョン管理、ドキュメント作成まで、モダンフロントエンド開発に欠かせない知識を徹底解説します。
shinagawa-web.com
Chakra UI・ShadCN・Material UIを活用したデザインシステムの構築と運用
デザインシステムの要件定義から適用ガイドラインの策定、UIコンポーネントの設計・実装、レスポンシブ対応、アクセシビリティ強化まで、幅広い観点で解説。Chakra UI・ShadCN・Material UIなどのUIフレームワークを活用しながら、カラーパレットやタイポグラフィの統一、コードスタイルの整備、開発者・デザイナー向けのドキュメント作成、プロトタイピング、ユーザビリティ向上のためのテスト戦略までを包括的に取り上げます。
shinagawa-web.com
弊社の技術支援サービス
無駄なコストを削減し、投資対効果を最大化する
クラウド費用の高騰、不要なSaaSの乱立、開発工数の増加――これらの課題に悩んでいませんか?本サービスでは、クラウドコストの最適化、開発効率向上、技術選定の最適化 を通じて、単なるコスト削減ではなく、ROIを最大化する最適解 をご提案します。
shinagawa-web.com
最新技術の導入・検証を支援するPoCサービス
Remix、React Server Components、TypeScript移行、クラウドサービス比較、マイクロサービス、サーバーレス、デザインシステムなど、最新技術のPoC(概念実証)を通じて、最適な技術選定と導入を支援します。貴社の開発課題に合わせた検証・実装で、ビジネスの成長を加速させます。
shinagawa-web.com
開発生産性を最大化するための技術支援
開発チームの生産性向上、コードの品質管理、インフラの最適化まで、様々な側面からサポートします。コードベースのリファクタリングから、テスト自動化、オンボーディング強化まで、プロジェクトの成功に必要なすべての支援を提供。御社の開発現場が効率的に機能するように、技術的な障害を取り除き、スムーズな開発を実現します。
shinagawa-web.com
開発品質向上支援 – 効率的で安定したプロダクトを実現
フロントエンドからバックエンド、データベースまで、開発プロセス全体を最適化し、安定したプロダクト作りをサポートします。コードレビューの仕組み、型定義の強化、E2Eテスト環境の構築など、開発の各ステップにおけるベストプラクティスを導入することで、より効率的でバグの少ない、そしてユーザー満足度の高いサービス提供を支援します。
shinagawa-web.com
Webアプリのセキュリティ強化支援
Webアプリの脆弱性対策からインフラのセキュリティ強化まで、包括的なセキュリティ支援を提供。OWASP Top 10対策、JWT認証の最適化、APIのアクセス制御、依存パッケージの監査、セキュアコーディングの標準化など、実践的なアプローチで開発現場の安全性を向上させます。
shinagawa-web.com
目次
お問い合わせ