SvelteKitとVercelでTelegramボットを作成する

SvelteKitを使ってTelegramボットを書いてみましょう。このボットは設定不要でSvelteKitをサポートするVercel上で動作します。

すでにTelegramボットを登録済みで、そのトークンがBOT_TOKEN環境変数にあるとしましょう。

このボットはポーリングではなく、webhook方式を使用します。

webhookで動くTelegramボットの核心は、Telegramサーバからのコールバックを受け取るPOSTエンドポイントです。POSTエンドポイントがリクエストを受け取り、JSONからペイロードをデシリアライズした後、それを"node-telegram-bot-api"ライブラリに渡して処理します。

今回のボットは、SvelteKitでTelegramからのリクエストをどう扱うかを示すために、非常にシンプルなものにします。受け取ったテキストメッセージをエコーバックするだけです。

"npm create svelte"でプロジェクトを作成した後、"node-telegram-bot-api"でTelegramライブラリをインストールし、"svelte.config.js"に次の設定を追加します:

const config = {
        ...
        kit: {
            ...
            csrf: {
                checkOrigin: false,
            }
       }
};

全画面表示モードから抜け出す

"./routes"ディレクトリに"+server.ts"ファイルを作成しましょう。

import { bot } from "./bot";

export async function POST({ request }) {
    try {
        bot.processUpdate(await request.json());
        return new Response("", { status: 200 });
    } catch (e) {
        console.error(e);
        return new Response("", { status: 500 });
    }
}

全画面表示モードから抜け出す

"bot.ts"ファイルは、受け取ったメッセージをエコーバックする機能を実装しています。

export const bot = new TelegramBot(BOT_TOKEN);
console.log("bot", BOT_TOKEN);

export const history: any[] = [];
bot.on("message", async (msg) => {
    try {
        await bot.sendMessage(msg.chat.id, msg.text + ", and?");
        history.push({ when: new Date(), msg });
    } catch (e) {
        console.error(e);
    }
});

全画面表示モードから抜け出す

これで完了です。

コードをgitリポジトリにプッシュし、例えば"https://sveltekit-bot.vercel.app"でVercelによってデプロイされた後、Telegramがボットにアップデートを配送できるようにwebhookを設定する必要があります。

これは一度だけ行う必要があります:

curl -X POST https://api.telegram.org/bot$(BOT_TOKEN)/setWebhook \
    -H "Content-type: application/json" \
    -d '{"url": "https://sveltekit-bot.vercel.app"}'

全画面表示モードから抜け出す

その後、ボットとチャットを始めることができます!

注:Vercelへのこのボットのデプロイはステートレスです。トラフィックがないとき、Vercelはエンドポイントを停止し、トラフィックが来たときに再度起動します。この実装ではデータの永続性はありません。実際のボットでは、データベースのような外部ストレージを使って、ボットの状態を保持するかもしれません。

プロジェクトの完全なソースはこちらで利用可能です:
https://github.com/begoon/sveltekit-bot/.

プロジェクトには、デモンストレーション目的で、メッセージを保存するための簡単なインメモリストレージと、それらを表示するページが含まれています。活動がない期間が終わると、Vercelによってデプロイが再スタートし、メッセージストレージはリセットされます。

こちらの記事はdev.toの良い記事を日本人向けに翻訳しています。
https://dev.to/begoon/writing-a-telegram-bot-with-sveltekit-and-vercel-1noe