← Blog
Development5 min readBy:

How to Build a Telegram Mini App in 2026: From Prototype to 60,000 Daily Users

A full guide to Telegram Mini App development from The Open Squad's experience. Stack (Next.js, FastAPI, TON SDK), initData auth, Stars and USDT payments, deployment, and scaling.

Telegram Mini Apps have grown from an experimental feature into a real distribution platform: 200 million users open them every month, and they're the fastest-growing way to ship a product inside the messenger. We launched The Open Earn in early 2024 and grew it to 60,000 daily active users and 500,000+ completed tasks over 18 months. This guide is what we did and what we'd tell ourselves on day one.

Mini App vs regular bot: when to pick which

A Telegram Bot is a chat interface over messages. A Telegram Mini App is a full web application that opens inside Telegram and has access to the messenger's API.

A regular bot is enough when:

  • The flow is linear: commands → replies (escrow bot, notification bot)
  • UI complexity is minimal
  • Prototype speed matters

You need a Mini App when:

  • Complex UI with navigation, forms, lists
  • Real-time interactivity
  • Payments via Telegram Payments or Stars
  • Product catalogs, user profiles, feeds

In The Open Earn we run both: a bot for notifications and onboarding, a Mini App for the main interface (balance, withdrawal, stats).

Stack: what we actually use

The production stack of The Open Earn, no marketing fluff:

Frontend (Mini App):

  • Next.js 16 (App Router, SSR) — for fast first paint and SEO on the landing
  • React 19 + TypeScript
  • @twa-dev/sdk — wrapper around the Telegram Web Apps SDK (theme, viewport, events)
  • TonConnect SDK — for connecting the user's TON wallet

Backend:

  • Python 3.12 + FastAPI — API server
  • aiogram 3.x — the bot
  • PostgreSQL 16 — primary store
  • Redis — session cache, rate limiting, pub/sub for workers
  • Celery — background jobs (payouts, task verification)

Infrastructure:

  • One dedicated server (8 GB RAM, 4 vCPU)
  • nginx as reverse proxy
  • PM2 for Node processes, systemd for Python
  • Let's Encrypt for SSL

This handles up to 50–100K DAU. We only had to upgrade when we crossed 60K — we moved Postgres to a managed instance.

Authentication: initData and server-side validation

The most common rookie mistake: trusting Telegram.WebApp.initDataUnsafe. It's spoofable in DevTools.

The correct flow:

  1. The Mini App receives initData (raw string) from Telegram via the JS SDK on launch
  2. It sends that to your backend in Authorization: TelegramInitData ...
  3. The backend validates the signature with HMAC-SHA256 keyed off the bot token
  4. On valid signature — extract user.id and issue a session token

Validation in Python:

import hmac, hashlib
from urllib.parse import parse_qs

def validate_init_data(init_data: str, bot_token: str) -> dict:
    parsed = parse_qs(init_data)
    received_hash = parsed.pop("hash")[0]
    data_check = "\n".join(f"{k}={v[0]}" for k, v in sorted(parsed.items()))
    secret = hmac.new(b"WebAppData", bot_token.encode(), hashlib.sha256).digest()
    expected = hmac.new(secret, data_check.encode(), hashlib.sha256).hexdigest()
    if not hmac.compare_digest(expected, received_hash):
        raise ValueError("Invalid signature")
    return parsed

Also check auth_date — drop sessions older than 24 hours (replay protection).

Payments: Stars, TON, USDT

Three real ways to take money inside the Telegram ecosystem in 2026:

1. Telegram Stars (for digital goods) — via Bot API: sendInvoice with currency: "XTR". Intangible purchases only. Telegram takes ~30%.

2. TON directly — via TonConnect: the user connects a wallet and signs the transaction. Fees are fractions of a cent.

3. USDT on TON (Jetton) — same as TON but as a stablecoin. Useful for B2B and fixed-price billing.

In The Open Earn we pay out earnings in USDT via TonConnect — users see a dollar amount, not a fluctuating TON price. Minimum withdrawal: $1.

Deployment and scaling

The simplest production layout for the first 10K DAU:

[Cloudflare] → [nginx] → [Next.js on :3000] → [FastAPI on :8000] → [Postgres]
                                                  ↓
                                              [Redis]

What broke for us at 30K DAU and how we fixed it:

  • Postgres connection pool ran out — added pgbouncer and split read/write
  • Redis OOM during peaks — bumped maxmemory, switched to allkeys-lru
  • Bot webhook latency — moved heavy checks to Celery
  • Static asset CDN — pushed to Cloudflare R2

The one rule that matters: measure, don't guess. Sentry for errors, Grafana + Prometheus for metrics, day one.

What we'd do differently

If we were starting again on day one:

  1. Split into 2 services from the start — public API (Mini App) and private (admin/workers). Merging is cheaper than splitting later.
  2. Ship feature flags from day one (Unleash, GrowthBook) — would have been useful for A/B tests during growth.
  3. Use Next.js Server Actions instead of a custom REST layer for simple forms. Less code.
  4. Skip the pretty animations on day one — users come for the function, not the polish. Polish makes sense post product-market fit.
  5. Build i18n in from day one — translations across 12 languages 4×'d our traffic, but retrofitting them was painful.

What's next

Mini Apps in 2026 are no longer "Telegram's experiment" — they're a real distribution channel. If your product overlaps with the messenger's active audience, it's worth at least a prototype. The starter stack is small, the risk is lower than a native mobile app.

If you want to see what this looks like in production — open The Open Earn or jump straight into the bot.