SaaS・IT

【2026年版】Claude CodeでLINE Bot開発|Webhook実装

LINE Messaging APIとWebhookサーバをClaude Codeで構築する実践手順。チャネル作成からNode.js実装、X-Line-Signature署名検証、ngrok検証、本番デプロイまでコード付きで解説。

【2026年版】Claude CodeでLINE Bot開発|Webhook実装
この記事でわかること:LINE Messaging API を使った LINE Bot(Webhook サーバ)を、Claude Code を相棒に Node.js / TypeScript で構築する実践手順。チャネル作成から署名検証・応答メッセージ・プッシュ配信・ngrok / Cloudflare Tunnel でのローカル検証・本番デプロイまで、つまずきポイントをコードと一緒に解説します。

  • LINE Developers コンソールでのチャネル作成とトークン・シークレットの取得
  • Claude Code による @line/bot-sdk v11 ベースの雛形生成と実装パターン
  • X-Line-Signature 署名検証の中身(HMAC-SHA256 + Base64)と express.json() の罠
  • replyToken の 3 つの制約(一度のみ・1分以内・再送 20 分ルール)と非同期設計
  • 無料 200 通の壁 — reply と push の使い分けで月額 0 円運用を維持する設計

対象読者:JavaScript / TypeScript を書いたことがある開発者・実務担当者。LINE Bot は未経験でも、本記事の手順だけで動くところまで到達できます。なお本記事は一般化された実装手順の解説(実装パターン解説)であり、コードと数値はすべて公式ドキュメントと筆者の手元検証に基づきます。

今日やること:オウム返し Bot を 1 本、自分の LINE アカウントで動かす。

401 Unauthorized でも 404 でもなく、Webhook の検証ボタンを押すたびに返ってくる SignatureValidationFailed。私が初めて LINE Bot を作ったとき、最初の 30 分はこのエラーログを眺めて溶けました。原因はコードのバグではなく、Express のグローバルミドルウェアに置いた express.json() がリクエストボディを先にパースしてしまい、署名検証に使う「生のボディ」が壊れていたこと。LINE Bot 開発のつまずきポイントは、実はこの手の「仕様を知っていれば 1 行で済む話」に集中しています。

本記事では、Slack bot 開発ガイドの姉妹編として、LINE Messaging API + Webhook サーバを Claude Code で設計→実装→検証→デプロイまで通す手順を、失敗ログ込みで解説します。Slack 編は Bolt フレームワークが面倒を見てくれる範囲が広いのに対し、LINE は「署名検証」「replyToken の寿命」「メッセージ通数の課金」という LINE 固有の 3 つの仕様を自分で握る必要があります。逆に言えば、この 3 つさえ押さえれば LINE Bot は驚くほどシンプルです。

LINE Bot 開発の全体像 — Messaging API と Webhook の関係

LINE Bot は「LINE 公式アカウント」の応答を、自前のサーバ(ボットサーバ)でプログラム制御する仕組みです。登場人物は 3 つだけです。

  1. ユーザーの LINE アプリ — 公式アカウントを友だち追加し、メッセージを送る
  2. LINE プラットフォーム — メッセージ等のイベントを受け取り、開発者が登録した Webhook URL へ HTTPS POST で転送する
  3. ボットサーバ(今回作るもの) — Webhook を受信し、Messaging API(https://api.line.me)経由で返信・配信する

メッセージ送信の経路は大きく 2 系統あります。この違いが後述の料金設計に直結するので、最初に整理しておきます。

送信方式 エンドポイント トリガー 無料メッセージ通数への算入
応答(reply) POST /v2/bot/message/reply Webhook イベント受信時のみ。replyToken が必要 カウントされない(無料)
プッシュ(push) POST /v2/bot/message/push 任意のタイミングでサーバ側から送信 カウントされる

つまり「ユーザーの発話に返事をする」だけなら通数課金はかからず、「サーバ側から能動的に通知する」と通数を消費します(LINEヤフー for Business 公式の料金ページ・2026年6月時点)。チャットボット型のユースケースなら、月額 0 円のままかなりのところまで行けます。

用語も最低限だけ押さえます。チャネルは Bot 1 体に対応する設定の単位、チャネルシークレットは署名検証に使う秘密鍵、チャネルアクセストークンは Messaging API を叩くための認証トークンです。この 2 つの credential の役割の違い(受信の検証用と送信の認証用)を混同すると、後でエラーの切り分けに迷うので注意してください。

準備 — LINE Developers コンソールでチャネルを作る

公式アカウントと Messaging API の有効化

手順は LINE Developers コンソール(developers.line.biz)から進めます。LINE 公式アカウントを作成し、そのアカウントで Messaging API を有効化すると、Messaging API チャネルとして扱えるようになります。コンソールの画面構成は更新が入ることがあるため、迷ったら公式ドキュメントの「Messaging API を始めよう」を正としてください。

作成後、コンソールで次の 2 つを控えます。

  • チャネルシークレット — 「チャネル基本設定」タブ
  • チャネルアクセストークン(長期) — 「Messaging API設定」タブで発行

どちらも環境変数で渡す前提で、コードや Git リポジトリには絶対に書き込まないでください。万一コミットしてしまった場合は、コンソールから再発行して旧トークンを無効化したうえで、履歴からも削除します。

応答設定 — 「自動応答」を切らないと二重返信になる

ハマりどころその 1 がここです。LINE 公式アカウントには管理画面(LINE Official Account Manager)側の「応答メッセージ」(定型文の自動返信)機能があり、初期状態で有効になっている場合があります。これを残したまま Bot を動かすと、ユーザーには「定型文」と「Bot の返信」が 2 通届きます

管理画面の応答設定で以下を確認してください。

  • 応答メッセージ:オフ
  • Webhook:オン

私はこの設定を忘れたまま 1 時間ほど「なぜ二重に返ってくるのか」をコード側で探したことがあります。コードは無罪でした。

Claude Code でプロジェクトを初期化する — @line/bot-sdk v11

動作環境とSDKのバージョン

本記事の検証環境は以下です。

  • Node.js 22(LTS)/ TypeScript 5 系 / Express
  • @line/bot-sdk v11.0.1(2026年6月時点の最新。npm / GitHub releases で確認)
  • Claude Code(Anthropic 公式 CLI・2026年6月時点)

SDK のバージョンは重要です。2026年5月リリースの v11.0.0 で、旧来の axios ベースのレガシー API(new line.Client()OAuth)が削除されました(GitHub の v11.0.0 リリースノートより)。Web 上の日本語チュートリアルの多くは旧 Client 前提で書かれており、そのままコピーすると v11 ではコンパイルが通りません。v8.0.0 以降に導入された fetch ベースのクライアントが現行で、v11 では統一クライアント LineBotClient が利用できます。依存パッケージもほぼゼロ(@types/node のみ)になり、かなり身軽になりました。

ここが Claude Code を使う最大の理由のひとつでもあります。学習データに古い SDK の書き方が混ざっている可能性があるからこそ、CLAUDE.md にバージョンと API スタイルを明記して「古い書き方を禁止」するのが効きます。

CLAUDE.md を先に書く

プロジェクトのルートに、最初に CLAUDE.md を置きます。私のテンプレートはこうです。

# LINE Bot プロジェクト規約

## 技術スタック
- Node.js 22 / TypeScript 5 / Express
- @line/bot-sdk v11(レガシー Client / OAuth は削除済み。使用禁止)
- クライアントは LineBotClient.fromChannelAccessToken() で生成する

## 実装ルール
- 署名検証は line.middleware() に任せる。express.json() を
  Webhook ルートより前にグローバル適用しない
- replyToken は一度のみ・受信から1分以内。ハンドラは即 200 を返し、
  重い処理は後段に逃がす
- channel secret / access token は process.env からのみ読む。
  ハードコード禁止
- push は通数課金されるため、reply で済む処理に push を使わない

プロンプト例 1:雛形生成

CLAUDE.md を置いたら、Claude Code に最初の指示を出します。

LINE Messaging API の Webhook サーバの雛形を作ってください。

要件:
- TypeScript + Express + @line/bot-sdk v11
- POST /webhook で Webhook を受信し、テキストメッセージを
  オウム返しする
- GET /health でヘルスチェック 200 を返す
- 環境変数: CHANNEL_SECRET, CHANNEL_ACCESS_TOKEN, PORT
- npm scripts: dev(tsx watch), build, start

不足している情報があれば、最初に質問してから作業を開始してください。

生成された雛形の核となる部分はこうなります(公式 SDK ドキュメントの synopsis に準拠した v11 スタイル)。

import * as line from '@line/bot-sdk';
import express from 'express';

const config = {
  channelSecret: process.env.CHANNEL_SECRET!,
};

const client = line.LineBotClient.fromChannelAccessToken({
  channelAccessToken: process.env.CHANNEL_ACCESS_TOKEN!,
});

const app = express();

app.get('/health', (_req, res) => res.status(200).send('ok'));

app.post('/webhook', line.middleware(config), (req, res) => {
  // 先に 200 を返し、イベント処理はその後に実行する
  res.status(200).end();
  Promise.all(req.body.events.map(handleEvent)).catch((err) => {
    console.error('event handling error:', err);
  });
});

async function handleEvent(event: any): Promise<void> {
  if (event.type !== 'message' || event.message.type !== 'text') {
    return;
  }
  await client.replyMessage({
    replyToken: event.replyToken,
    messages: [{ type: 'text', text: event.message.text }],
  });
}

const port = Number(process.env.PORT ?? 3000);
app.listen(port, () => console.log(`listening on ${port}`));

ポイントは 2 つ。line.middleware(config) が署名検証とボディのパースを兼ねていること、そしてハンドラが先に 200 を返してからイベントを処理していることです。理由は次の 2 セクションで順に説明します。

Webhook サーバ実装 — X-Line-Signature 署名検証の中身

LINE プラットフォームは Webhook リクエストに x-line-signature ヘッダーを付与します。ボットサーバは「このリクエストが本当に LINE から来たか」を、このヘッダーで必ず検証する必要があります。検証しないエンドポイントは、誰でも偽イベントを投げられる公開 API になってしまいます。

署名検証のアルゴリズム

仕様は公式ドキュメント「Webhookの署名を検証する」に定義されています(developers.line.biz・2026年6月時点)。

  1. チャネルシークレットを秘密鍵として、リクエストボディ(生の文字列)の HMAC-SHA256 ダイジェストを計算する
  2. ダイジェストを Base64 エンコードする
  3. その値が x-line-signature ヘッダーの値と一致するか比較する

SDK の line.middleware() はこれを自動でやってくれますが、中身を知っておくとエラー時の切り分けが速くなります。手動実装するとこの 10 行です。

import crypto from 'node:crypto';

function validateSignature(
  rawBody: string,
  channelSecret: string,
  signature: string,
): boolean {
  const digest = crypto
    .createHmac('SHA256', channelSecret)
    .update(rawBody, 'utf8')
    .digest('base64');
  const a = Buffer.from(digest);
  const b = Buffer.from(signature);
  // 長さが違う場合 timingSafeEqual は例外を投げるため先に弾く
  return a.length === b.length && crypto.timingSafeEqual(a, b);
}

比較に === ではなく crypto.timingSafeEqual() を使うのは、比較時間の差から署名を推測されるタイミング攻撃への定石対策です。

最重要の罠 — express.json() と「生のボディ」

冒頭の失敗ログの正体がこれです。署名はパース前の生のリクエストボディ文字列に対して計算されます。公式ドキュメントにも、署名検証の前にボディをパース・デシリアライズしてはいけない旨が明記されています。

失敗パターン:Express のグローバルに app.use(express.json()) を置く → ボディが先に JSON オブジェクト化され、SDK の middleware が生ボディを取得できず署名検証が失敗する

正解:Webhook ルートには line.middleware(config) だけを適用し、express.json() が必要な他のルート(自前の管理 API など)には個別に適用する

// NG: これが /webhook より前にあると署名検証が壊れる
// app.use(express.json());

// OK: ルート単位で使い分ける
app.post('/webhook', line.middleware(config), webhookHandler);
app.post('/admin/api', express.json(), adminHandler);

プロンプト例 2:署名検証のテストを書かせる

署名検証まわりは「動いているように見えて検証をスキップしている」事故が怖い領域なので、テストを Claude Code に書かせておきます。

validateSignature 関数のユニットテストを vitest で書いてください。

ケース:
1. 正しいシークレットとボディで計算した署名 → true
2. ボディを 1 文字改変 → false
3. 署名ヘッダーが空文字 → false(例外を投げない)
4. 署名の長さが異なる → false(timingSafeEqual の例外を踏まない)

仮定した点は必ず「仮定」と明記してください。

4 番のケースは実際に私が踏んだバグです。timingSafeEqual は引数のバッファ長が異なると比較結果を返す前に例外を投げるため、長さチェックを先にしていないと、攻撃的な入力どころか単なる不正リクエストでプロセスが 500 を量産します。Claude Code はこの仕様を指摘したうえでテストを書いてくれました。こういう「仕様の角」を拾ってくれるのは、レビュー相手として優秀です。

応答メッセージの実装 — replyToken の 3 つの制約

Webhook イベントには replyToken が含まれ、これを使って POST /v2/bot/message/reply で返信します。この replyToken には公式リファレンスで明記された制約があります(developers.line.biz・2026年6月時点)。

  1. 一度のみ使用できる — 同じトークンで 2 回返信はできない
  2. Webhook を受信してから 1 分以内に使用する — 1 分を超える場合の動作は保証されない
  3. 再送された Webhook のトークンも再送受信から 1 分以内なら使えるが、元のトークンを使用済みの場合と、イベント発生から 20 分が経過した場合は使えない

さらに公式は「時間制限は予告なく変更される可能性があるため、時間制限に依存した実装をせず、可能な限り早く使用する」ことを求めています。設計への落とし込みはシンプルで、「Webhook ハンドラは即 200 を返す」「reply は受信直後に送る」「時間のかかる処理の結果は push で送る」の 3 点です。

async function handleEvent(event: any): Promise<void> {
  if (event.type !== 'message' || event.message.type !== 'text') {
    return;
  }

  // 1) まず replyToken を即消費して一次応答(1分制限に対応)
  await client.replyMessage({
    replyToken: event.replyToken,
    messages: [
      {
        type: 'text',
        text: 'お問い合わせを受け付けました\n回答を準備しています…',
      },
    ],
  });

  // 2) 時間のかかる処理(DB 照会・外部 API・LLM 呼び出し等)
  const answer = await heavyTask(event.message.text);

  // 3) 結果は push で送る(replyToken はもう使えない)
  await client.pushMessage({
    to: event.source.userId,
    messages: [{ type: 'text', text: answer }],
  });
}

なお 1 回の reply / push リクエストで送れるメッセージオブジェクトは最大 5 件です(公式リファレンス・2026年6月時点)。テキスト+画像+確認テンプレートのような組み合わせ送信はできますが、6 件以上に分けたい場合は設計を見直すサインだと考えてください。

Webhook への応答自体にもルールがあります。ボットサーバが 200 番台のステータスコードを返さなかった場合、LINE プラットフォームは Webhook を再送します(公式ドキュメント・2026年6月時点)。再送自体は取りこぼし防止の仕組みですが、ハンドラが冪等でないと「同じ問い合わせに 2 回返信する」事故になります。先に 200 を返す設計と、webhookEventId 等での重複排除を組み合わせるのが安全です。

プロンプト例 3:イベントハンドラの拡張

handleEvent を拡張してください。

要件:
- follow イベント(友だち追加)に挨拶メッセージを返す
- テキスト「予約」を受けたらクイックリプライで
  「本日 / 明日 / それ以外」の 3 択を提示する
- postback イベントで選択結果を受けて返信する
- イベントタイプごとに関数を分割し、switch で振り分ける

数字と固有名詞は、根拠(出典/計算式)を添えてください。

クイックリプライやテンプレートメッセージの JSON 構造は、ネストが深く手書きだと typo りやすい領域です。Slack 編で Block Kit の JSON 生成が Claude Code の得意分野だったのと同じで、LINE のメッセージオブジェクト生成も「仕様 URL を貼って構造を作らせる」のが最短でした。

プッシュ通知と料金 — 無料 200 通の壁

push を使い始める前に、料金体系を押さえます。LINE 公式アカウントの料金プランは 3 つです(LINEヤフー for Business 公式・税別・2026年6月時点)。

プラン 月額固定費 無料メッセージ通数 追加メッセージ
コミュニケーションプラン 0円 200通 不可
ライトプラン 5,000円 5,000通 不可
スタンダードプラン 15,000円 30,000通 約3円/通

ここで効いてくるのが冒頭の表です。応答メッセージ(reply)は通数にカウントされません。カウントされるのは push・multicast・broadcast などの能動的配信で、しかも「1 回の配信 × 友だち数」で数えます。100 人に毎朝 push を送ると、それだけで 1 日 100 通、月 3,000 通です。無料プランの 200 通は 2 日で蒸発します。

設計指針はこうなります。

  • ユーザー起点のやりとりは reply で完結させる(0 円)
  • push は「ユーザーが明示的に求めた通知」に絞る(リマインダー登録など)
  • 全員一斉配信(broadcast)を Bot に実装する前に、月間通数を試算する

レート制限も一応頭に入れておきます。Messaging API の多くのエンドポイントはチャネル単位・エンドポイントごとに 2,000 リクエスト/秒が上限です(公式リファレンス・2026年6月時点)。個人開発や社内 Bot で当たる数字ではありませんが、超過すると 429 Too Many Requests が返ること、無料通数超過時にも 429(You have reached your monthly limit.)が返ることは知っておくとエラー対応が速くなります。

プロンプト例 4:定期 push バッチ

毎朝 9:00 JST に登録ユーザーへ天気概況を push するバッチを
作ってください。

要件:
- 実行は node-cron ではなく systemd timer(ユニットファイルも生成)
- 送信先 userId のリストは data/subscribers.json から読む
- 送信結果(成功/失敗件数)を標準出力にログする
- 月間の push 送信数を概算するコメントを冒頭に書く
  (送信数 = 配信回数 × 購読者数で計算)

不足している情報があれば、最初に質問してから作業を開始してください。

このプロンプトの最後の要件がポイントで、Claude Code に課金影響をコメントとして書かせると、後からコードを触る人(未来の自分を含む)が通数の感覚を持てます。バッチの定期実行を Claude Code 自体に組み込みたい場合は、Claude Code ヘッドレス自動実行ガイドで解説した -p フラグ + cron の構成がそのまま使えます。

ngrok / Cloudflare Tunnel でローカル検証する

Webhook URL は有効な HTTPS の URLである必要があります(公式リファレンス・2026年6月時点)。つまり http://localhost:3000 は直接登録できません。ローカル開発では、ローカルポートを HTTPS の公開 URL にトンネルするツールを使います。代表は ngrok と Cloudflare Tunnel の 2 つです。

ngrok の場合

# インストール後、アカウントの authtoken を設定して
ngrok http 3000

# 出力例
# Forwarding  https://a1b2-203-0-113-1.ngrok-free.app -> http://localhost:3000

表示された https://〜 の URL に /webhook を付けて、LINE Developers コンソールの「Messaging API設定」→ Webhook URL に登録します。注意点は、無料利用の既定ではトンネルを張り直すたびに URL が変わること。再起動のたびにコンソールへ URL を貼り直す手間が発生します(固定ドメインの提供条件は ngrok 公式で確認してください)。

Cloudflare Tunnel(クイックトンネル)の場合

brew install cloudflared   # macOS の場合
cloudflared tunnel --url http://localhost:3000

# 出力例
# https://example-random-words.trycloudflare.com

cloudflared のクイックトンネルはアカウント登録なしで試せる手軽さが魅力です。こちらも起動ごとに URL が変わるため、開発が長期化するなら Cloudflare アカウントに紐づけた名前付きトンネル(独自ドメイン固定)に移行すると、URL 貼り直し作業から解放されます。私は使い捨て検証は cloudflared、継続開発は名前付きトンネル、と使い分けています。

検証ボタンと実機テスト

Webhook URL を保存したら、コンソールの「検証」ボタンを押します。成功すれば、自分のスマホで公式アカウントを友だち追加してメッセージを送り、オウム返しが返れば一次完成です。検証が失敗する場合は、後述のエラー一覧の上から順に潰してください。

プロンプト例 5:Webhook をローカルでエミュレートする

トンネルすら張らずに署名検証込みのテストをしたい場合、正しい署名付きのリクエストを curl で再現できます。これも Claude Code に作らせると速いです。

LINE の Webhook リクエストをローカルにエミュレートする
シェルスクリプトを作ってください。

要件:
- fixtures/message-event.json をボディとして読み込む
- CHANNEL_SECRET 環境変数で HMAC-SHA256 → Base64 の署名を
  openssl で計算し x-line-signature ヘッダーに付与する
- curl で http://localhost:3000/webhook へ POST し、
  HTTP ステータスを表示する

仮定した点は必ず「仮定」と明記してください。

署名計算の 1 行は公式ドキュメントの例と同じ openssl dgst -sha256 -hmac "$CHANNEL_SECRET" -binary | openssl base64 です。このスクリプトを CI に組み込めば、LINE プラットフォームに依存しない回帰テストが回せます。

本番デプロイとシークレット管理

Webhook 受信型の Bot は、HTTPS で外部公開された常時起動プロセスが必要です。選択肢は大きく 3 系統です。

構成 向いているケース 注意点
VPS + systemd + リバースプロキシ 常駐バッチや DB を同居させたい社内 Bot TLS 証明書と OS 運用を自分で持つ
コンテナ系 PaaS(Cloud Run 等) トラフィック変動が大きい・運用を薄くしたい コールドスタートで Webhook 応答が遅れる場合がある
サーバレス関数 イベント数が少ない個人用途 生ボディ取得の方法がプラットフォームごとに異なり署名検証でハマりやすい

どの構成でも共通する原則は 2 つです。第一に、チャネルシークレットとアクセストークンは環境変数または秘密情報マネージャーで注入し、イメージやリポジトリに焼き込まないこと。第二に、デプロイ後に必ず本番 URL で「検証」ボタン → 実機テストまで通すこと。手元で動いたコードが本番のプロキシ設定(ボディの変形・ヘッダー欠落)で署名検証だけ落ちる、というのは定番の事故です。

ユーザー識別を伴う Bot(社内ツールの本人確認、会員連携など)に発展させる場合は、LINEログインとの連携や自前の認証層の設計が必要になります。認証まわりの実装パターンは認証・ログイン機能を Claude Code で実装する実践ガイドで詳しく扱っているので、そちらを参照してください。

よくあるエラーと Claude Code での直し方

最後に、LINE Bot 開発で実際に遭遇頻度の高いエラーを、原因と対処のセットでまとめます。エラーメッセージをそのまま Claude Code に貼って「原因の仮説を 3 つ、確度順に挙げて」と聞くデバッグサイクルは LINE Bot でも有効でした。

エラー 1:SignatureValidationFailed(署名検証失敗)

原因の 9 割はボディの変形です。チェック順は、(1) express.json() 等のボディパーサーが Webhook ルートより前に挟まっていないか、(2) リバースプロキシやミドルウェアがボディを書き換えていないか、(3) チャネルシークレットの環境変数が正しいチャネルのものか(複数チャネル運用時の取り違え)、の順が効率的です。

エラー 2:Invalid reply token(400 Bad Request)

公式リファレンスによると、このエラーは「有効期限切れの replyToken を使った」か「使用済みの replyToken を使った」場合に返ります。ハンドラ内で同じイベントに対して reply を 2 回呼んでいないか、処理が 1 分を超えてから reply していないかを確認します。時間がかかる処理は本記事の「reply で一次応答 → push で本応答」パターンに書き換えてください。

エラー 3:返信が二重に届く

コードのバグではなく、管理画面の「応答メッセージ」がオンのまま残っているケースが大半です。準備セクションの応答設定を見直してください。Webhook の再送(非 2xx 応答時)による二重処理の場合は、webhookEventId をキーにした重複排除を入れます。

エラー 4:Webhook がそもそも届かない

コンソールの「Webhook の利用」がオフ、URL の typo、HTTPS 証明書の不備、トンネルの停止の 4 つをまず疑います。コンソールの「検証」ボタンはこの切り分けの一次情報になるので、デプロイのたびに押す癖をつけてください。

エラー 5:昨日まで動いていた開発環境が今日動かない

ngrok / cloudflared のクイックトンネルは再起動で URL が変わります。コンソールに登録した Webhook URL が古いままになっていないかを確認してください。「トンネル起動 → 新 URL をコンソールに反映」までをシェルスクリプト化して Claude Code に管理させると、この手戻り自体がなくなります。

まとめ — Slack 編との比較と次のステップ

LINE Bot 開発の勘所を一言でまとめると、「署名は生ボディ、reply は即時、push は課金」です。Slack bot(Bolt)と比べると、LINE はフレームワークの抽象化が薄いぶん、HTTP と暗号の素の仕様に触れる場面が多い。だからこそ、仕様 URL を渡して実装させ、テストまで書かせる Claude Code との相性は良好でした。私の体感では、雛形生成・メッセージオブジェクトの JSON 組み立て・エラーの原因切り分けの 3 つで特に時間が節約できています。

次のアクション(3つ)

  1. LINE Developers コンソールでチャネルを作成し、シークレットとトークンを環境変数に設定する
  2. Claude Code に本記事のプロンプト例 1 を投げ、cloudflared のクイックトンネルでオウム返し Bot を動かす
  3. 自分の業務の問い合わせ対応・リマインダーをひとつ、reply 中心設計で Bot 化してみる

LINE Bot・社内チャットボット開発や Claude Code 活用でお困りの場合は、Uravation の無料相談からご連絡ください。社内ツール開発のスポットコンサルも対応しています。

FAQ

Q. LINE Bot の開発・運用に費用はかかりますか?

Messaging API 自体の利用と応答メッセージ(reply)は無料です。費用が発生するのは push などの能動的配信が月の無料通数(コミュニケーションプランは 200 通)を超える場合と、サーバのホスティング費用です(LINEヤフー for Business 公式・2026年6月時点)。reply 中心の設計なら月額 0 円+ サーバ代だけで運用できます。

Q. replyToken の有効期限はどれくらいですか?

公式リファレンスでは「Webhook を受信してから 1 分以内に使用する必要があり、1 分を超える場合の動作は保証されない」「一度のみ使用できる」と定義されています。また時間制限は予告なく変更される可能性があるため、制限値に依存せず可能な限り早く使う実装が推奨されています。

Q. 古いチュートリアルの new line.Client() のコードが動きません。

@line/bot-sdk v11.0.0(2026年5月リリース)でレガシーの Client / OAuth API が削除されたためです。現行は LineBotClient.fromChannelAccessToken() で生成する統一クライアント、または v8 以降の fetch ベースクライアントを使います。Claude Code に移行させる場合は、CLAUDE.md に「v11・レガシー API 禁止」と明記してください。

Q. ngrok と Cloudflare Tunnel はどちらを使うべきですか?

どちらでも開発はできます。アカウントなしで即試せる手軽さなら cloudflared のクイックトンネル、チーム利用や管理機能を重視するなら ngrok が候補です。いずれも無料のクイック利用では再起動ごとに URL が変わるため、開発が長期化するなら固定 URL を確保して Webhook URL の貼り直しをなくすのがおすすめです。

Q. Claude Code は LINE Bot 開発のどこで特に役立ちましたか?

3 つあります。第一に v11 SDK スタイルでの雛形生成(CLAUDE.md で旧 API を禁止しておくのが前提)。第二にクイックリプライやテンプレートメッセージの深くネストした JSON の組み立て。第三にエラーログを貼っての原因切り分けです。特に署名検証エラーは「express.json() の位置」という非自明な原因を一発で指摘してくれました。

S
佐藤傑(さとう・すぐる)
株式会社Uravation 代表取締役。X(@SuguruKun_ai)フォロワー約10万人。100社以上の企業向けAI研修・導入支援を手がける。著書『AIエージェント仕事術』(SBクリエイティブ)。SoftBank IT連載7回執筆。Claude Code の業務活用・内製化支援を専門とする。
参考・確認ソース:
developers.line.biz Messaging APIリファレンス(replyToken・レート制限・エンドポイント仕様) /
Webhookの署名を検証する(HMAC-SHA256 署名検証仕様) /
line-bot-sdk-nodejs Releases(v11.0.0 の破壊的変更) /
LINEヤフー for Business 料金プラン(3 プランの通数・料金)

Next Step

この事例を、自社の業務に置き換える。

対象業務、利用データ、評価基準、社内展開の順番まで整理すると、Claude Code導入の失敗を減らせます。

導入を相談する