Contents
1️⃣ LINE Official Account の作成手順
1‑1. アカウントマネージャーでの操作概要
| 手順 | 内容 |
|---|---|
| ① | https://manager.line.biz に管理者アカウントでログイン |
| ② | 左メニューの「アカウント作成」をクリック |
| ③ | 必要情報(アカウント名、プロフィール画像・説明文、カテゴリ) を入力し 「作成」 |
| ④ | 作成完了後に表示される Official Account ID をメモしておく(後続のチャネル設定で必須) |
ポイント
- 無料プランでも Messaging API が利用可能です。
- 画像は 640×640 px、形式は PNG または JPG を推奨します。
1‑2. プロフィール入力のベストプラクティス
- 名前(表示名):ブランドと完全一致させることで認知度が向上。
- 説明文:200文字以内に要点をまとめ、検索結果にも反映されます。
- カテゴリ:サービス内容に最も近いものを選択し、ユーザーの検索ヒット率を高めましょう。
2️⃣ Messaging API の有効化とチャネル設定
2‑1. プロバイダー・チャネル作成手順
- LINE Developers コンソール(https://developers.line.biz)へログイン
- 左メニュー → 「プロバイダー」→「新規作成」で自社名やサービス名を入力
- 作成したプロバイダー内で 「Messaging API」 チャネルを追加し、以下を設定
- チャネル名(例:MyCompany‑Bot)
- 説明文・メールアドレス
-
アイコン画像(640×640 px 推奨)
-
作成完了後に表示される Channel Secret と Access Token を取得し、環境変数やシークレットマネージャーへ安全に保存します。
注意
- Access Token は「短期トークン(30 日)」「長期トークン化(最大60 日)」の2種類が選択可能です。Messaging API ではリフレッシュトークンは提供されません。期限切れになる前に新しいトークンを再取得するスクリプトを用意してください。
2‑2. Webhook URL の登録と SSL 要件
- 必須:HTTPS(TLS 1.2 以上)で公開できるドメイン
- LINE Developers コンソールの「Webhook 設定」ページに
https://yourdomain.com/webhookを入力し、検証ボタンが 成功になることを確認
2‑3. 有効化するイベントだけを選択
| イベント | 用途 |
|---|---|
message |
テキスト・スタンプ等の受信 |
follow / unfollow |
ユーザーが友だち追加/解除したとき |
postback |
ボタンアクションやリッチメニューからのデータ送信 |
3️⃣ Webhook 受信サーバー実装と署名検証
3‑1. Node.js(Express)実装例
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 |
// server.js const express = require('express'); const crypto = require('crypto'); const app = express(); app.use(express.json({ verify: (req, _, buf) => { req.rawBody = buf; } // 生データ保持 })); const CHANNEL_SECRET = process.env.CHANNEL_SECRET; /** * X-Line-Signature の検証 */ function isValidSignature(signature, body) { const hash = crypto.createHmac('sha256', CHANNEL_SECRET) .update(body) .digest('base64'); // ← Base64 エンコードが必須 return hash === signature; } app.post('/webhook', (req, res) => { const signature = req.get('X-Line-Signature'); if (!isValidSignature(signature, req.rawBody)) { return res.status(401).send('Invalid signature'); } // ------- ここからビジネスロジック ------- for (const ev of req.body.events) { if (ev.type === 'message' && ev.message.type === 'text') { console.log('📩 Received:', ev.message.text); // 必要に応じて Reply API を呼び出す } } // ------------------------------------- res.sendStatus(200); // LINE に即時 200 OK を返すことが必須 }); const PORT = process.env.PORT || 3000; app.listen(PORT, () => console.log(`🟢 Webhook listening on ${PORT}`)); |
3‑2. Python(Flask)実装例(署名検証を修正)
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
# app.py import os, hmac, hashlib, base64 from flask import Flask, request, abort, jsonify app = Flask(__name__) CHANNEL_SECRET = os.getenv('CHANNEL_SECRET') def is_valid_signature(signature: str, body: bytes) -> bool: """X-Line-Signature を正しく検証する(Base64 エンコード必須)""" digest = hmac.new( CHANNEL_SECRET.encode('utf-8'), body, hashlib.sha256 ).digest() calculated = base64.b64encode(digest).decode() # ← ここが修正ポイント return calculated == signature @app.route('/webhook', methods=['POST']) def webhook(): sig = request.headers.get('X-Line-Signature') raw_body = request.get_data() if not is_valid_signature(sig, raw_body): abort(401, 'Invalid signature') payload = request.json for ev in payload.get('events', []): if ev['type'] == 'message' and ev['message']['type'] == 'text': print('📩 Received:', ev['message']['text']) return jsonify(status='ok'), 200 if __name__ == '__main__': app.run(host='0.0.0.0', port=int(os.getenv('PORT', 5000))) |
3‑3. テスト環境と本番環境の切り分け
| 項目 | テスト環境 | 本番環境 |
|---|---|---|
| Webhook URL | https://dev.example.com/webhook(LINE コンソールでテスト用に設定) |
https://api.example.com/webhook |
| 署名 | ダミー署名 (dummy-signature) を使用した cURL テストは本番では不可 |
正しい Channel Secret から計算された署名のみ受理 |
| ログレベル | DEBUG(リクエストボディ・署名を出力) | INFO / ERROR に抑制し、機密情報はマスク |
ポイント
テスト時にdummy-signatureを使う場合は必ず本番デプロイ前に削除し、実際の署名検証ロジックが有効になることを確認してください。
4️⃣ アクセストークン管理(長期トークン化と再取得)
4‑1. 長期トークン化の概要
- 短期トークンは30 日で期限切れ。
- 長期トークン化は「アクセストークン」ページから「長期トークンを発行」ボタンで最大60 日間有効なトークンを取得します(リフレッシュトークンは存在しません)。
4‑2. トークン期限切れ前の自動再取得手順
- Channel ID と Channel Secret を使い、
/v2/oauth/accessTokenエンドポイントへclient_credentialsグラントで新しい短期トークンを発行。 - 発行されたトークンはシークレットマネージャーや環境変数に上書き保存し、次回の API 呼び出しに利用します。
Node.js(Axios)サンプル
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
const axios = require('axios'); async function obtainShortLivedToken() { const params = new URLSearchParams({ grant_type: 'client_credentials', client_id: process.env.CHANNEL_ID, client_secret: process.env.CHANNEL_SECRET, }); const {data} = await axios.post( 'https://api.line.me/v2/oauth/accessToken', params ); console.log('✅ New short‑lived token:', data.access_token); // 環境変数やシークレットストアへ保存する処理を追加 } |
Python(requests)サンプル
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
import os, requests def obtain_short_lived_token(): resp = requests.post( 'https://api.line.me/v2/oauth/accessToken', data={ 'grant_type': 'client_credentials', 'client_id': os.getenv('CHANNEL_ID'), 'client_secret': os.getenv('CHANNEL_SECRET') } ) token_info = resp.json() print('✅ New short‑lived token:', token_info['access_token']) # 必要に応じてシークレットストアへ保存 |
重要:トークン取得は 1 日あたり 10 回以下 に抑えることでレートリミット(429)を回避できます。
5️⃣ アカウント連携(Linking Accounts)
5‑1. linkToken の取得フロー
|
1 2 3 |
curl -X POST https://api.line.me/v2/bot/user/{userId}/linkToken \ -H "Authorization: Bearer {CHANNEL_ACCESS_TOKEN}" |
followイベントで受信した userId を使用してlinkTokenを取得- フロントエンドに QR コードやディープリンクとして渡し、ユーザーが自社認証画面へ遷移させる
5‑2. サーバー側での紐付け実装イメージ(Python)
|
1 2 3 4 5 |
def link_line_account(user_id, link_token): # 自社データベースに user_id と内部ユーザー ID を保存 db.save_link(user_id=user_id, token=link_token) # 以降は link_token が有効な間だけ LINE アカウントと連携可能 |
6️⃣ テスト・デプロイ・運用ベストプラクティス
6‑1. ローカル/ステージングでの動作確認
| 手段 | 内容 |
|---|---|
| Official Account Manager の「テスト送信」 | 任意メッセージを自分宛に送信し、Webhook が 200 OK を返すか確認 |
| cURL(ダミー署名) | テスト環境でのみ使用。実際の Channel Secret で計算した署名を付与すると本番と同等の挙動を検証可能 |
| Postman の Pre‑request Script | crypto モジュールで署名を自動生成し、正しいリクエストとして送信できるかテスト |
本番向け cURL 例(実署名計算済み)
|
1 2 3 4 5 6 7 8 9 |
SIGNATURE=$(echo -n '{"events":[...]}' | openssl dgst -sha256 -hmac $CHANNEL_SECRET -binary | base64) curl -X POST https://api.example.com/webhook \ -H "Content-Type: application/json" \ -H "X-Line-Signature: ${SIGNATURE}" \ -d '{"events":[{"type":"message","replyToken":"xxxx","source":{"userId":"U123"},"timestamp":1620000000,"message":{"id":"1001","type":"text","text":"こんにちは"}}]}' |
6‑2. サーバーレスへのデプロイ例
| プラットフォーム | 主な設定ポイント |
|---|---|
| AWS Lambda | serverless.yml に handler: app.handler(aws-serverless-express ラッパー)を記述。API Gateway のエンドポイントを LINE コンソールの Webhook URL として登録。 |
| GCP Cloud Functions | functions-framework==3.* で Flask アプリをラップし、--trigger-http --allow-unauthenticated でデプロイ。環境変数は Cloud Run の「設定」から追加。 |
| Heroku | Procfile に web: gunicorn app:app(Python)または web: node server.js(Node.js)。Config Vars に CHANNEL_SECRET と CHANNEL_ACCESS_TOKEN を登録し、HTTPS が自動で有効になることを確認。 |
タイムアウト注意:Webhook は 5 秒以内に 200 OK を返す必要があります。重い処理はキュー(例:Amazon SQS, Cloud Tasks)へ委譲してください。
6‑3. エラーハンドリングとリトライ戦略
| ステータス | 意味 | 推奨対応 |
|---|---|---|
200 OK |
正常受信 | 即座に返す |
400 Bad Request |
リクエスト形式不正 | ログ出力し、原因を修正 |
401 Unauthorized |
署名検証失敗 | 設定ミスの可能性。テスト環境と本番環境でシークレットが一致しているか確認 |
429 Too Many Requests |
レートリミット超過 | 指数バックオフ(例:1 s → 2 s → 4 s)で再送、1 分以内に10回以上は行わない |
6‑4. 利用規約遵守のチェックポイント
- 同一ユーザーへのメッセージは 24 時間に最大5通 に抑える
- プロモーション配信は事前に オプトイン取得(友だち追加時の同意)を必須とする
- メッセージ本文に LINE のブランドガイドライン に違反しない表現を使用
7️⃣ まとめ
- 公式ドキュメント(2024年11月更新) に沿って、Official Account と Messaging API チャネルを作成
Channel SecretとAccess Tokenを安全に管理し、Webhook の署名検証は Base64 エンコード が必須- 長期トークン化は可能だがリフレッシュトークンは提供されないため、期限切れ前に新しい短期トークンを自動取得する仕組みを実装
- テスト環境と本番環境で 署名・URL の切り替え を明確化し、ダミー署名はテスト専用に限定
- サーバーレスやコンテナデプロイ時の タイムアウト・SSL 要件 に注意しつつ、エラーハンドリングとリトライ戦略を整備
以上の手順とベストプラクティスを守れば、LINE Official Account と Messaging API の連携は安全かつ安定して運用できます。ぜひ本記事のコードや設定例を自社サービスに組み込み、ユーザーエンゲージメント向上に活用してください。