d8b102fbf98d3fea9736c89d6aaa633a4dca4c2b
All checks were successful
Docker Build / build-and-push-image (push) Successful in 42s
DisallowUnknownFields rejected real Telegram payloads (entities, from, date, etc. that our minimal structs don't cover). Lenient decode is the right default for an upstream webhook we don't control.
telegram-gateway
Telegram webhook gateway for the Arcodange home lab. Replaces polling-based bots (e.g. those scheduled in Cowork) with direct webhook delivery from Telegram, routed to per-bot handlers running on the k3s cluster.
Phase 1 (MVP): single sync
echohandler, end-to-end flow validated. Phase 2 (planned):httpforward handler + Postgres-backed durable queue. Phase 3 (planned): asyncshell/script/ollamahandlers.
See the design doc at ~/.claude/plans/pour-les-notifications-on-inherited-seal.md.
Architecture (current)
Telegram → Cloudflare Tunnel (tg.arcodange.fr) → Service telegram-gateway:8080
→ /bot/<slug> → secret_token check → handler dispatch → Bot API sendMessage
Routes
| Method | Path | Description |
|---|---|---|
| GET | /healthz |
Liveness probe |
| GET | /readyz |
Readiness probe |
| POST | /bot/{slug} |
Telegram webhook entry (validates secret) |
Local dev
# 1. Provide a config + env
export BOT_FACTORY_TOKEN='8737289837:…' # from @BotFather
export BOT_FACTORY_SECRET=$(openssl rand -hex 32)
# 2. Run
make run # uses bots.example.yaml
# 3. Smoke a webhook
curl -X POST -H "X-Telegram-Bot-Api-Secret-Token: $BOT_FACTORY_SECRET" \
-H 'Content-Type: application/json' \
-d '{"update_id":1,"message":{"chat":{"id":<your-chat-id>},"text":"hi"}}' \
http://localhost:8080/bot/factory
Set / delete webhook
# Once the gateway is reachable at https://tg.arcodange.fr:
export BOT_FACTORY_TOKEN=…
export BOT_FACTORY_SECRET=…
make setwebhook SLUG=factory BASE_URL=https://tg.arcodange.fr
make deletewebhook SLUG=factory
Configuration
- Routing (non-secret): YAML at
$CONFIG_PATH(default/etc/telegram-gateway/bots.yaml, mounted from a ConfigMap in cluster). - Secrets: per-bot env vars
BOT_<UPPER_SLUG>_TOKEN,BOT_<UPPER_SLUG>_SECRET. Sourced from Vault pathkvv2/telegram-gateway/configvia Vault Secrets Operator.
Cluster deploy
- Image:
gitea.arcodange.lab/arcodange/telegram-gateway:<tag> - Helm chart:
chart/ - ArgoCD app:
telegram-gateway(infactory/argocd/values.yaml) - Public URL:
https://tg.arcodange.fr(Cloudflare déjà configuré pour router*.arcodange.frvers le home lab → Traefik route par Host) - Secrets Phase 1 :
kubectl create secret generic telegram-gateway-bots …(sans Vault). Migration vers Vault Secrets Operator en Phase 2+ viavault.enabled: truedanschart/values.yaml.
Voir DEPLOY.md pour la procédure end-to-end.
Layout
.
├── main.go # bootstrap, subcommand dispatch
├── server.go # HTTP routes
├── middleware.go # secret validation, recover, access log
├── handlers.go # Handler interface + Registry
├── handler_echo.go # echo handler
├── telegram.go # Telegram Bot API client
├── telegram_types.go # Update / Message structs
├── config.go # YAML routing config + per-bot env merge
├── setwebhook.go # CLI subcommands (setwebhook / deletewebhook)
├── chart/ # Helm chart
└── .gitea/workflows/ # CI: docker build → gitea registry
Description
Languages
Go
96.2%
Smarty
1.9%
Makefile
1.4%
Dockerfile
0.5%