How to Host a Telegram Bot for Free with Webhooks (2026)
Host a Telegram bot for free with webhooks: why they beat polling, a complete bot in Node.js and Python, a secret-token check and a one-command deploy.
- Published
- Reading time
- 4 min
On this page
Key takeaways
- Use webhooks, not polling: Telegram sends each update to your HTTPS URL, so your bot only works when there's a message.
- Because updates arrive as web requests, a webhook bot can run on DockHosting's Free plan: a sleeping app wakes on the next update.
- Protect the endpoint with secret_token: Telegram sends it in the X-Telegram-Bot-Api-Secret-Token header.
Telegram bots are among the easiest bots to host, if you use webhooks. Instead of your bot constantly asking Telegram "anything new?", Telegram pushes each message to an HTTPS URL you control. That means no always-running loop, and it means the bot can run on a free plan.
Webhooks vs polling
Long polling (getUpdates) | Webhook (setWebhook) | |
|---|---|---|
| How it works | Your bot asks Telegram for updates in a loop | Telegram POSTs updates to your URL |
| Needs a public HTTPS URL | No | Yes |
| Needs to run 24/7 | Yes | No (it can wake on request) |
| Good for | Local development | Production |
Every app on DockHosting gets an HTTPS URL like https://mybot.dockhosting.cloud, so the HTTPS requirement is already covered.
1. Create the bot
Message @BotFather on Telegram, send /newbot and follow the prompts. You'll get a token like 123456:ABC-DEF….
2a. Node.js webhook bot
No bot library is needed: the Bot API is plain HTTPS and JSON.
// index.js
import express from "express";
const { BOT_TOKEN, WEBHOOK_SECRET, PORT = 3000 } = process.env;
const api = (method, body) =>
fetch(`https://api.telegram.org/bot${BOT_TOKEN}/${method}`, {
method: "POST",
headers: { "content-type": "application/json" },
body: JSON.stringify(body),
});
const app = express();
app.use(express.json());
app.post("/telegram", async (req, res) => {
// Reject anything that isn't from Telegram.
if (req.get("X-Telegram-Bot-Api-Secret-Token") !== WEBHOOK_SECRET) return res.sendStatus(401);
const msg = req.body.message;
if (msg?.text) await api("sendMessage", { chat_id: msg.chat.id, text: `You said: ${msg.text}` });
res.sendStatus(200);
});
app.get("/", (_, res) => res.send("ok"));
app.listen(PORT);{ "type": "module", "scripts": { "start": "node index.js" }, "dependencies": { "express": "^5" } }2b. Python webhook bot (FastAPI)
# main.py
import os
import httpx
from fastapi import FastAPI, Header, HTTPException, Request
TOKEN = os.environ["BOT_TOKEN"]
SECRET = os.environ["WEBHOOK_SECRET"]
app = FastAPI()
@app.post("/telegram")
async def telegram(request: Request, x_telegram_bot_api_secret_token: str = Header(None)):
if x_telegram_bot_api_secret_token != SECRET:
raise HTTPException(status_code=401)
update = await request.json()
msg = update.get("message") or {}
if "text" in msg:
async with httpx.AsyncClient() as client:
await client.post(f"https://api.telegram.org/bot{TOKEN}/sendMessage",
json={"chat_id": msg["chat"]["id"], "text": f"You said: {msg['text']}"})
return {"ok": True}requirements.txt: fastapi, uvicorn[standard], httpx. FastAPI projects are detected and run with Uvicorn for you. More in the FastAPI deploy guide.
3. Deploy
curl -fsSL https://cli.dockhosting.dev/install.sh | sh # Windows: irm https://cli.dockhosting.dev/install.ps1 | iex
dock login
dock deployIn the project's environment variables, set BOT_TOKEN and a long random WEBHOOK_SECRET (letters, digits, _ and -), then run dock restart.
4. Point Telegram at your URL
Run this once from your terminal, using your app's address:
curl "https://api.telegram.org/bot$BOT_TOKEN/setWebhook" \
-d "url=https://mybot.dockhosting.cloud/telegram" \
-d "secret_token=$WEBHOOK_SECRET"Check it with getWebhookInfo, then message your bot. dock logs shows each request as it arrives.
Free plan vs always on
On the Free plan, the app sleeps after 1 hour without requests. The next Telegram update wakes it, so the reply comes a few seconds later than usual. Telegram also retries updates that fail. For a bot people use all day, Hobby ($4/month) is always on and replies instantly.
Need a long-running bot that keeps a socket open instead? That's how Discord bots work: see hosting a Discord bot 24/7.
Frequently asked questions
Can I host a Telegram bot for free?
Yes, with webhooks. Telegram delivers each update as an HTTPS request, and on DockHosting's Free plan a sleeping app wakes on the next request, so the first reply after a quiet hour can take a few seconds. For instant replies all the time, Hobby ($4/month) is always on.
Webhook or long polling: which should I use?
Polling keeps a process asking Telegram for updates, so it must run all the time. Webhooks let Telegram push updates to your URL, which needs HTTPS but no always-running loop. For hosted bots, webhooks are simpler and cheaper.
Does Telegram need HTTPS for webhooks?
Yes. Every DockHosting app gets HTTPS automatically on its .dockhosting.cloud address, so the URL works as a webhook right away.
- Telegram bot
- Webhooks
- Node.js
- Python
- Tutorial
Written by Doughmi ILYAS
Doughmi builds DockHosting, the developer-first platform behind dock deploy: the build system, the managed databases and the dashboard. On this blog: guides to shipping apps without running servers, written with the commands the platform actually ships.
