End-to-end analytics for a Telegram bot or channel: from the ad click to the deposit
End-to-end analytics means one unbroken record per person: the ad they clicked, the moment they started the bot or joined the channel, what they wrote and what they paid, with the cost of the ad on one side and the revenue on the other. For a website this is routine. For a Telegram funnel it has to be built differently, because the person leaves the browser at the first tap. This guide explains what the record has to contain, how Tellmetric builds it without guessing, and what you can read from it.
What end-to-end analytics means for a Telegram funnel
The phrase is used loosely, so here is what it has to deliver. For a bot or a channel fed by paid ads, end-to-end analytics answers four questions with one set of data:
Which ad brought each member. Not "how many members came this week" but, for one person, the campaign, ad set and creative that produced them.
What each step cost. Cost per join, cost per retained member and cost per first deposit, per campaign and per creative.
What each step brought in. Deposits and payments tied back to those same rows, so a creative shows its return, not just its click-through rate.
Whether the ad platform knows. The join and the deposit sent back to Meta, TikTok or Google, so the campaign can optimise for depositors rather than clicks.
All four need one identifier, issued at the click, that survives the bot start, the join, days of messages and a deposit weeks later. Lose it at any step and everything after is counted but not attributed.
Why a pixel or UTMs alone cannot do it
Website analytics rests on two tools, and neither reaches into Telegram.
A pixel runs on a page you control. A Telegram group, channel or bot is not such a page. The Meta Pixel cannot fire on a join, and the Telegram Ads Pixel Tag measures websites only, as explained in the Telegram pixel explained.
UTM parameters stop at the redirect. A link can carry utm_campaign as far as the tracking link, but Telegram passes none of it to the bot or the group. Inside, the UTM exists only in the click log, unconnected to the account that joined. See UTM tracking for Telegram ads.
Counting members against clicks is not attribution. It gives one ratio for the whole channel, not a result per ad, and it is wrong whenever people also join from elsewhere.
What Telegram does offer is a bot API: an admin bot is told who joined and through which invite link, any bot is told which start code a person pressed Start with, and a bot receives Stars payments. The missing piece is tying each of those facts to one click.
How Tellmetric follows one person, deterministically
The click. The ad points at a tracking link made on the Links page. The link records a click with its own id (c_…), stores the platform's click identifier when there is one (fbclid, ttclid, gclid, sccid and the others), the campaign parameters, sub1 to sub9, country and device.
The bot start or the join. The visitor goes to the bot as t.me/<bot>?start=<click id>, so the Start press arrives with the click id. For a group or channel, the bot mints a single-use invite link for that one click; with direct join switched on, the visitor is sent straight to it. When the person joins, Telegram tells the bot which invite was used, and that invite belongs to exactly one click. No time window, no IP matching.
Messages. The first message to your bot after a message link is recorded against the click. Messages that arrive without a link are kept as unattributed: counted, never credited to the wrong ad.
The deposit. A broker, payment provider or your own backend sends a postback or an event API call with the click id. If the paying system only knows the customer's Telegram account, the event API accepts the Telegram user id instead, and the deposit is matched to the click that user arrived with. Stars payments received by the bot are recorded as purchases on their own, attributed through the invoice payload's click id or, failing that, the person's join.
What happens afterwards. Leaves and kicks are recorded; after the number of days you set, each join is marked retained or not. Refunds are tied to their purchase and never sent to an ad platform.
Because every step is matched by an identifier, not by timing, a deposit a month after the click is attributed like one the same afternoon. The chain is described step by step in Telegram conversion tracking and Telegram attribution.
What the dashboard shows
The dashboard has four pages behind one tab row, all reading the same records.
Overview. Clicks, joins, messages and deposits day by day, where people drop off between steps (your join rate and deposit rate), the top campaigns and the checks that need attention.
Results. The funnel table by campaign, ad or creative, traffic source, link, country or device and, once the ad URL template is in use, by Meta campaign, ad set and ad id (likewise for TikTok and Google). With spend present, each row carries spend, cost per join, cost per retained member, cost per deposit and ROAS.
Community. Who is still in the group or server after the retention period and, on Pro and Agency, what new members are worth: people grouped by the week they joined and the deposits they made afterwards.
Delivery. What was sent to Meta and the other platforms, how well Meta can recognise your customers (match quality, Pro and Agency), the latest activity, and tracking health, which emails the owner when clicks flow but no joins arrive, the bot loses admin rights, Meta rejects events or match quality falls.
Spend comes from three places. A connected Meta ad account and a connected Google Ads account are imported daily. Telegram Ads has no reporting API, so on the Telegram Ads page under Ad accounts each link gets a t.me address per creative and spend is entered by hand, and the same unit costs appear.
Sending the results back to the ad platforms
End-to-end analytics is not only a report. The join and the deposit go back to the platform that showed the ad, with the original click identifier, so the campaign can be optimised for the step that matters. A join reaches Meta as CompleteRegistration by default, a message as Contact, a deposit as Purchase with value and currency; the mapping can be changed per workspace. Meta receives events on every plan through the Conversions API; TikTok, Snapchat, Reddit, Spotify, X and Google Ads are available on Pro and Agency, and Google Ads receives deposits and purchases only. The delivery side is covered in Meta Conversions API for Telegram.
Building reports elsewhere: exports and webhooks
Teams that report in a Google Sheet, a BI tool or an affiliate tracker have two routes out.
CSV export. Every table on the dashboard can be downloaded with the filters applied, on Pro and Agency.
Outbound webhooks. On Connections you can forward every join, message, deposit, lead and membership change to a URL, either as a GET request built from a template with {clickid}, {status} and {payout} macros, or as a signed JSON POST with an X-Tellmetric-Signature HMAC-SHA256 header and an X-Tellmetric-Event header. A Send a test button fires a sample first.
The GET form suits Keitaro, RedTrack or Binom; the JSON form is what Zapier, Make and a Google Sheets Apps Script expect, with recipes in Telegram to Zapier, Make and Google Sheets.
A worked example
The figures below are illustrative. A trading-signals channel runs two Meta ad sets and one Telegram Ads creative for a week, each with its own "Opens your group" link and direct join on. Deposits arrive by postback from a broker, with the click id carried in an offer link posted in the channel.
Read by cost per join, the Telegram Ads creative wins at €0.49. By cost per retained member the three are close. Read by ROAS, the lookalike ad set earns more than eight times its spend while the Telegram Ads creative returns under two and a half, because its cheap joins leave quickly and rarely deposit. Without the chain from click to deposit, budget would have moved towards the cheapest joins. With it, the 31 lookalike deposits went to Meta as Purchase events with their value, and that ad set can be optimised for depositors.
Setting it up
Connect the bot. Create one with @BotFather, paste its token on Connections, and add it to your group or channel as an admin with the invite-users right. Member only, for groups where you cannot grant admin rights, matches the join to the person's Start tap instead; channels accept bots only as admins.
Connect the ad platforms. Meta's dataset id and Conversions API token, plus the ad account for spend; the other platforms on Pro and Agency.
Make one link per ad set or creative on the Links page, named after it, and use the ad URL template the page proposes so the platform's campaign, ad set and ad ids travel with every click.
Connect deposits with the postback URL or the event API from the developer page; the response to a test postback states whether the click was matched.
Run the setup test on the Setup test page, then check Tracking health after the first day of spend.
Frequently asked
Does end-to-end analytics need a website or a landing page?
No. The ad can point straight at the tracking link, which sends the visitor into Telegram. If you do have a landing page, the one-line tracker.js snippet passes the click identifiers to the links on it.
Does it work for a bot without a group?
Yes. A link of the kind "Opens a chat with your bot" carries the click id in the start parameter, so the start, the first message, any Mini App event and any Stars payment are attributed to the click.
Can the deposit be attributed without the click id?
Through the event API, yes: send the depositor's Telegram user id and the deposit is matched to the click that user arrived with. The postback route needs the click id, which an offer link fills in with its {clickid} macro.
Does Tellmetric track people with my own Telegram account?
No. Joins are recorded by your bot, as an admin or as a member, never by a personal account. Nothing is installed inside Telegram.
Does it also work for Discord?
The same chain exists for a Discord server: the join link runs the visitor through Discord's authorise step and the callback records the join against the click. See Discord conversion tracking.