Nadia

Elixir CIModule VersionHex DocsTotal DownloadLicenseLast Updated

Nadia is an Elixir client for the Telegram Bot API and Telegraph API. It combines complete Bot API method coverage with small, explicit helpers for building bots in an OTP application.

Installation

Nadia requires Elixir 1.20 or later and Erlang/OTP 27 or later.

Add :nadia to mix.exs:

def deps do
[
{:nadia, "~> 1.6"}
]
end

Then run:

mix deps.get

Quick Start

Create a bot with @BotFather. Read its token at runtime instead of committing it to application configuration:

# config/runtime.exs
import Config
config :nadia,
token: {:system, "TELEGRAM_BOT_TOKEN"}

Direct Bot API calls return {:ok, result} or {:error, %Nadia.Model.Error{}}:

case Nadia.get_me() do
{:ok, bot} -> IO.puts("Connected as @#{bot.username}")
{:error, error} -> IO.warn("Telegram error: #{inspect(error.reason)}")
end
Nadia.send_message(chat_id, "Hello from Nadia")

For an OTP bot, generate a handler and offline test:

mix nadia.gen.bot MyApp.Bot --polling

Then supervise long polling:

children = [
{Nadia.Polling,
handler: MyApp.Bot,
allowed_updates: ["message"],
timeout: 30}
]

Run the app with the token in its environment:

TELEGRAM_BOT_TOKEN=123:token mix run --no-halt

The Build Your First Bot guide walks through the complete setup.

Learn By Example

The Examples And Learning Paths page connects Nadia's API reference to complete bot-building tasks.

BuildGuide
A generated polling botBuild Your First Bot
Commands and inline buttonsCommands And Inline Keyboards
A multi-step conversationConversation State
Durable conversation statePersistent Session Backends
Media uploads and downloadsMedia And Files
Rich messages and clickable story areasRich Messages And Stories
Bounded Telegram retriesErrors And Rate Limits
An HTTP endpointReceive Webhook Updates
Several bot identitiesRun Multiple Bots
Credential-free testsTest Bot Handlers
A production deploymentProduction Checklist
Telegraph pagesUse The Telegraph API

Tested, copyable handler modules live in the examples directory.

Configuration

The top-level token config is the default client used by calls such as Nadia.get_me/0 and Nadia.send_message/3. Applications with more than one bot can configure named clients:

config :nadia,
bots: [
support: [
token: {:system, "SUPPORT_BOT_TOKEN"},
recv_timeout: 10
],
alerts: [
token: {:system, "ALERTS_BOT_TOKEN"}
]
]
support = Nadia.Client.from_config(:support)
Nadia.send_message(support, support_chat_id, "How can we help?")

See Run Multiple Bots before supervising several pollers; each worker needs a distinct child ID.

Nadia uses Req as its HTTP transport. Optional HTTP or HTTPS proxy settings are passed to Req/Mint:

config :nadia,
proxy: "http://proxy.example.com:8080",
proxy_auth: {"user", "password"},
recv_timeout: 10

Custom Bot API, file, or Telegraph endpoints can be configured with :base_url, :file_base_url, and :graph_base_url. Most applications should use the defaults.

A trusted local Bot API server started in local mode can return absolute file paths instead of remote download paths. Opt into local filesystem copying explicitly:

config :nadia,
base_url: "http://bot-api.internal/bot",
file_mode: :local

The path must be accessible in Nadia's filesystem namespace. Leave file_mode: :remote at its default for Telegram's hosted API and for local servers that still use HTTP file downloads.

Testing

Nadia's normal test suite is offline and credential-free:

mix test

The Test Bot Handlers guide shows how application tests can inject a fake Nadia.HTTPClient and assert outgoing requests.

Optional maintainer smoke tests against Telegram are tagged :telegram_live. They require the two-bot environment documented in .env.live.local.example and are run with:

mix test --only telegram_live

Contributing

See the contributing guide for local checks, changelog expectations, Bot API maintenance notes, and the GitHub Actions release process.

API Coverage

Since Nadia 1.0.0, the wrapper covers all 180 official methods in Telegram Bot API 10.1, published on June 11, 2026. Current releases preserve that complete method coverage. Modeled response fields are parsed into Nadia structs; unknown future fields are ignored until Nadia explicitly models them.

Use the Nadia reference for Elixir signatures and the official Telegram Bot API documentation for Telegram's field semantics.

Typed outgoing-content helpers include Nadia.InputMedia, Nadia.InputPaidMedia, Nadia.InputPollMedia, Nadia.InputPollOption, Nadia.InputProfilePhoto, Nadia.InputRichMessage, Nadia.InputRichMessageContent, Nadia.InputTextMessageContent, Nadia.InputInvoiceMessageContent, Nadia.InputLocationMessageContent, Nadia.InputVenueMessageContent, Nadia.InputContactMessageContent, Nadia.InputStoryContent, Nadia.InputSticker, Nadia.LabeledPrice, Nadia.ReactionType, and Nadia.StoryArea. Their constructors reject locally detectable mistakes; raw maps, keyword lists, structs, mixed lists, and pre-encoded JSON remain available as compatibility escape hatches.

License

Copyright (c) 2015 Yu Zhang

Nadia is released under the MIT License.