Hello Worldとローカル実行
Honoの概要を理解したところで、実際に手を動かして最初のアプリケーションを作成してみましょう。「百聞は一見にしかず」ということで、実践を通じて学んでいきます。
プロジェクトの初期化
まず、新しいプロジェクトを作成しましょう。
# 新しいディレクトリを作成
mkdir hono-tutorial
cd hono-tutorial
# package.jsonを初期化
npm init -y
# Honoをインストール
npm install hono
# 開発用の依存関係をインストール
npm install -D typescript @types/node tsx
「tsxは、TypeScriptファイルを直接実行できる便利なツールです。」
最初のHello World
src/index.tsファイルを作成します:
import { Hono } from "hono";
const app = new Hono();
app.get("/", (c) => {
return c.text("Hello Hono!");
});
export default app;
「たったこれだけでWebサーバーが完成です!Express.jsを使ったことがある方なら、すぐに理解できますよね。」
ローカル実行のセットアップ
Node.js環境での実行
src/server.tsファイルを作成します:
import { serve } from "@hono/node-server";
import app from "./index";
const port = 3000;
console.log(`Server is running on port ${port}`);
serve({
fetch: app.fetch,
port,
});
「@hono/node-serverをインストールしましょう:」
npm install @hono/node-server
package.jsonの設定
package.jsonのscriptsセクションを更新します:
{
"name": "hono-tutorial",
"version": "1.0.0",
"type": "module",
"scripts": {
"dev": "tsx watch src/server.ts",
"start": "node dist/server.js",
"build": "tsc"
},
"dependencies": {
"hono": "^3.12.0",
"@hono/node-server": "^1.8.0"
},
"devDependencies": {
"typescript": "^5.0.0",
"@types/node": "^20.0.0",
"tsx": "^4.7.0"
}
}
TypeScript設定
tsconfig.jsonファイルを作成します:
{
"compilerOptions": {
"target": "ES2022",
"module": "ES2022",
"moduleResolution": "bundler",
"allowSyntheticDefaultImports": true,
"esModuleInterop": true,
"allowJs": true,
"strict": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,
"outDir": "./dist",
"rootDir": "./src"
},
"include": ["src/**/*"]
}
実行してみよう!
開発サーバーを起動します:
npm run dev
ブラウザでhttp://localhost:3000にアクセスすると、「Hello Hono!」が表示されます。
ファイルを保存すると自動的にサーバーが再起動される(ホットリロード)ので、開発がとても快適です。
基本的なルートを追加
src/index.tsを拡張して、いくつかのルートを追加してみましょう:
import { Hono } from "hono";
const app = new Hono();
app.get("/", (c) => {
return c.text("Hello Hono!");
});
app.get("/hello/:name", (c) => {
const name = c.req.param("name");
return c.text(`Hello, ${name}!`);
});
app.get("/json", (c) => {
return c.json({
message: "Hello World",
timestamp: new Date().toISOString(),
});
});
app.get("/html", (c) => {
return c.html(`
<html>
<head>
<title>Hono App</title>
</head>
<body>
<h1>Hello from Hono!</h1>
<p>This is HTML response</p>
</body>
</html>
`);
});
export default app;
これで以下のエンドポイントが利用できます:
GET /- テキストレスポンスGET /hello/:name- パラメータ付きレスポンスGET /json- JSON レスポンスGET /html- HTML レスポンス
さまざまなランタイムでの実行
Honoの魅力の1つは、同じコードが様々な環境で動作することです。
Bunでの実行
Bunがインストールされている場合:
// bun-server.ts
import app from "./src/index";
export default {
port: 3000,
fetch: app.fetch,
};
実行:
bun run bun-server.ts
Denoでの実行
// deno-server.ts
import app from "./src/index.ts";
Deno.serve(app.fetch);
実行:
deno run --allow-net deno-server.ts
同じHonoアプリケーションコードが、Node.js、Bun、Denoで動作します。素晴らしいですね!
開発時のTIPS
1. ホットリロードの活用
tsx watchを使うことで、ファイルの変更を自動的に検知してサーバーを再起動できます:
npm run dev
2. デバッグ情報の表示
開発時は、リクエストの詳細情報を確認したい場合があります:
import { Hono } from "hono";
import { logger } from "hono/logger";
const app = new Hono();
// ログ出力ミドルウェアを追加
app.use("*", logger());
app.get("/", (c) => {
console.log("Request received:", c.req.url);
return c.text("Hello Hono!");
});
export default app;
3. CORSの設定(フロントエンドとの連携時)
フロントエンドアプリケーションから呼び出す場合:
import { Hono } from "hono";
import { cors } from "hono/cors";
const app = new Hono();
// CORS設定
app.use(
"*",
cors({
origin: ["http://localhost:3000", "http://localhost:5173"],
allowMethods: ["GET", "POST", "PUT", "DELETE"],
}),
);
// 以降のルート定義...
エラーのトラブルシューティング
よくあるエラーと対処法
1. モジュール読み込みエラー
Error [ERR_MODULE_NOT_FOUND]: Cannot find module
対処法:
package.jsonに"type": "module"が設定されているか確認- import文でファイル拡張子が正しく指定されているか確認
2. ポートが使用中のエラー
Error: listen EADDRINUSE: address already in use :::3000
対処法:
# 使用中のプロセスを確認
lsof -i :3000
# または別のポートを使用
serve({
fetch: app.fetch,
port: 3001
})
3. TypeScriptの型エラー
Property 'param' does not exist on type 'HonoRequest'
対処法:
@types/nodeがインストールされているか確認- TypeScript設定が正しいか確認
ディレクトリ構造の確認
現在のプロジェクト構造は以下のようになっているはずです:
hono-tutorial/
├── package.json
├── tsconfig.json
├── src/
│ ├── index.ts # メインのアプリケーション
│ └── server.ts # Node.js用のサーバー起動
├── bun-server.ts # Bun用(オプション)
└── deno-server.ts # Deno用(オプション)
次のステップ
Hello Worldアプリケーションが動作するようになったら、次の章でルーティングについてより詳しく学んでいきましょう。RESTful APIの設計方法や、より複雑なルート定義について説明します。
やってみよう!
-
基本的なAPIエンドポイントを追加
/ping- "pong"を返すエンドポイント/time- 現在時刻を返すエンドポイント
-
パラメータを使った動的なレスポンス
/greet/:language/:name- 言語に応じた挨拶を返すエンドポイント
-
異なるランタイムでの実行
- BunやDenoがインストールされていれば、同じコードで動作確認
ポイント
- シンプルなセットアップ:最小限の設定でHonoアプリケーションを開始
- ホットリロード:
tsx watchによる開発効率の向上 - マルチランタイム対応:Node.js、Bun、Denoで同じコードが動作
- 型安全性:TypeScriptによる開発時のエラー検知
- Express風API:親しみやすいルート定義方法