Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
<?php
define('BOT_TOKEN', 'XXXXXXXX:XXXXXXXXXXXXXXXXXXXXXXXX'); // place bot token of your bot here
function checkTelegramAuthorization($auth_data) {
$check_hash = $auth_data['hash'];
unset($auth_data['hash']);
$data_check_arr = [];
foreach ($auth_data as $key => $value) {
$data_check_arr[] = $key . '=' . $value;
}
sort($data_check_arr);
$data_check_string = implode("\n", $data_check_arr);
$secret_key = hash('sha256', BOT_TOKEN, true);
$hash = hash_hmac('sha256', $data_check_string, $secret_key);
if (strcmp($hash, $check_hash) !== 0) {
throw new Exception('Data is NOT from Telegram');
}
if ((time() - $auth_data['auth_date']) > 86400) {
throw new Exception('Data is outdated');
}
return $auth_data;
}
function saveTelegramUserData($auth_data) {
$auth_data_json = json_encode($auth_data);
setcookie('tg_user', $auth_data_json);
}
try {
$auth_data = checkTelegramAuthorization($_GET);
saveTelegramUserData($auth_data);
} catch (Exception $e) {
die ($e->getMessage());
}
header('Location: login_example.php');
?>
<?php
define('BOT_USERNAME', 'XXXXXXXXXX'); // place username of your bot here
function getTelegramUserData() {
if (isset($_COOKIE['tg_user'])) {
$auth_data_json = urldecode($_COOKIE['tg_user']);
$auth_data = json_decode($auth_data_json, true);
return $auth_data;
}
return false;
}
if ($_GET['logout']) {
setcookie('tg_user', '');
header('Location: login_example.php');
}
$tg_user = getTelegramUserData();
if ($tg_user !== false) {
$first_name = htmlspecialchars($tg_user['first_name']);
$last_name = htmlspecialchars($tg_user['last_name']);
if (isset($tg_user['username'])) {
$username = htmlspecialchars($tg_user['username']);
$html = "<h1>Hello, <a href=\"https://t.me/{$username}\">{$first_name} {$last_name}</a>!</h1>";
} else {
$html = "<h1>Hello, {$first_name} {$last_name}!</h1>";
}
if (isset($tg_user['photo_url'])) {
$photo_url = htmlspecialchars($tg_user['photo_url']);
$html .= "<img src=\"{$photo_url}\">";
}
$html .= "<p><a href=\"?logout=1\">Log out</a></p>";
} else {
$bot_username = BOT_USERNAME;
$html = <<<HTML
<h1>Hello, anonymous!</h1>
<script async src="https://telegram.org/js/telegram-widget.js?2" data-telegram-login="{$bot_username}" data-size="large" data-auth-url="check_authorization.php"></script>
HTML;
}
echo <<<HTML
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Login Widget Example</title>
</head>
<body><center>{$html}</center></body>
</html>
HTML;
?>
@ximik777

This comment has been minimized.

Copy link

ximik777 commented Feb 7, 2018

Does not work. =(

@ximik777

This comment has been minimized.

Copy link

ximik777 commented Feb 7, 2018

Already working! =)

@ingria

This comment has been minimized.

Copy link

ingria commented Feb 7, 2018

Doesn't work in Firefox

Error: NOT_ALLOWED

@Alisummer

This comment has been minimized.

Copy link

Alisummer commented Feb 7, 2018

Good!

@jumong

This comment has been minimized.

Copy link

jumong commented Feb 7, 2018

Bot domain empty ? Why ?

@kapter

This comment has been minimized.

Copy link

kapter commented Feb 7, 2018

"Bot domain empty"??

@jumong

This comment has been minimized.

Copy link

jumong commented Feb 7, 2018

Bot domain empty error

@ruslanmedia

This comment has been minimized.

Copy link

ruslanmedia commented Feb 7, 2018

@jumong, you should set domain by @Botfather

@ivanfmartinez

This comment has been minimized.

Copy link

ivanfmartinez commented Feb 7, 2018

Does not work on firefox, it returns Error: NOT_ALLOWED (in response payload), and does not redirect to data-auth-url.
No visible information for user in browser.

@kapter

This comment has been minimized.

Copy link

kapter commented Feb 7, 2018

@ruslanmedia, i send /setdomain command, choose my bot but have error "Bot domain empty". What's wrong?

@jumong

This comment has been minimized.

Copy link

jumong commented Feb 7, 2018

@ruslanmedia Рахмат котта!

@kricha

This comment has been minimized.

Copy link

kricha commented Feb 7, 2018

i also have error Bot domain empty

@jumong

This comment has been minimized.

Copy link

jumong commented Feb 7, 2018

Who know? How to set own button name ?

@diseks

This comment has been minimized.

Copy link

diseks commented Feb 7, 2018

Hi. Does anyone known how to use custom button (without text, only custom image)?

@lensws

This comment has been minimized.

Copy link

lensws commented Feb 7, 2018

Waiting wordpress login

@juananpe

This comment has been minimized.

Copy link

juananpe commented Feb 7, 2018

Same "Bot domain empty" problem here.

@ximik777

This comment has been minimized.

Copy link

ximik777 commented Feb 7, 2018

++

Doesn't work in Firefox
Error: NOT_ALLOWED

@9kopb

This comment has been minimized.

Copy link

9kopb commented Feb 7, 2018

you need to link your domain to the bot first

@juananpe

This comment has been minimized.

Copy link

juananpe commented Feb 7, 2018

Ah! Thanks @9kopb... I was going to answer that I've already done that but then I tried again and this time it worked! For the record:

Start a conversation with the BotFather. Type "/mybots". Select your bot. Select "Bot settings". Select "Domain". Then type your domain name. You'll get a feedback message from BotFather like this: "Success! Domain updated. /help"

@akkez

This comment has been minimized.

Copy link

akkez commented Feb 7, 2018

Дуров верни дуровдурова

@lifeact

This comment has been minimized.

Copy link

lifeact commented Feb 7, 2018

How about asp mvc?

@Serdg

This comment has been minimized.

Copy link

Serdg commented Feb 7, 2018

How about iOS and Android login with Telegram?

@t4hor3

This comment has been minimized.

Copy link

t4hor3 commented Feb 7, 2018

It does not work, error 500. What version of PHP is necessary?

@oxmix

This comment has been minimized.

Copy link

oxmix commented Feb 7, 2018

FF 58.0.1
bug! return string get -> "...username=Oxmix&photo_url=**https:/**t.me/i/userpic/320/Oxmix.jpg&auth_date=151..."
below a temporary fix
$data_check_arr[] = $key . '=' . str_replace('https:/t', 'https://t', $value);
without this fix, hash_hmac checking fail

@amirrammari

This comment has been minimized.

Copy link

amirrammari commented Feb 7, 2018

Working good :)

@madl-ash

This comment has been minimized.

Copy link

madl-ash commented Feb 7, 2018

im trying to port this to python but hash_hmac fails.
docs says Data-check-string is a concatenation of all received fields, sorted in alphabetical order
now all fields are id, first_name, last_name, username, photo_url, auth_date and hash;
which fields should i include and in what order exactly?

@roxblnfk

This comment has been minimized.

Copy link

roxblnfk commented Feb 8, 2018

Does anyone know how to force a telegram to redirect a user to my page (without using a widget)?
Need a workflow similar to OAuth2

I just send the user to https://oauth.telegram.org/bot_id=****

After confirming the user redirects to https://oauth.telegram.org/close

I tried to find the GET param as redirect_uri - unsuccessfully.

Also it would be good to receive POST data

@m0cmc

This comment has been minimized.

Copy link

m0cmc commented Feb 8, 2018

Great feature!
But returns "Bot domain invalid" for a ".LIVE" domain (which is set on the bot using BotFather). What's wrong ?

@andre-web

This comment has been minimized.

Copy link

andre-web commented Feb 8, 2018

How I can send message to user if allow access to send messages?

@ImTheDeveloper

This comment has been minimized.

Copy link

ImTheDeveloper commented Feb 8, 2018

Any easy way to set a local development environment domain?

http://localhost:1337 for example would not register as a domain

@6o6p1k

This comment has been minimized.

Copy link

6o6p1k commented Feb 9, 2018

How set localhost as domain??
BotFather return: "The message should contain one domain name."

@6o6p1k

This comment has been minimized.

Copy link

6o6p1k commented Feb 9, 2018

PS Use http://127.0.0.1:youPort/ if you need localhost

@parsibox

This comment has been minimized.

Copy link

parsibox commented Feb 10, 2018

you most limit GET key to only your key
your key is 'username' , 'auth_date' ,'first_name', 'last_name' ,'photo_url' ,'id'
please fix this
it is correct

function checkTelegramAuthorization($auth_data) {
$allow_key= array('username' , 'auth_date' ,'first_name', 'last_name' ,'photo_url' ,'id');
  $check_hash = $auth_data['hash'];
  unset($auth_data['hash']);
  $data_check_arr = [];
  foreach ($auth_data as $key => $value) {
      if( in_array( $key , $allow_key)){
            $data_check_arr[] = $key . '=' . $value;
      }
  }
  sort($data_check_arr);
  $data_check_string = implode("\n", $data_check_arr);
  $secret_key = hash('sha256', BOT_TOKEN, true);
  $hash = hash_hmac('sha256', $data_check_string, $secret_key);
  if (strcmp($hash, $check_hash) !== 0) {
    throw new Exception('Data is NOT from Telegram');
  }
  if ((time() - $auth_data['auth_date']) > 86400) {
    throw new Exception('Data is outdated');
  }
  return $auth_data;
}
@Aliham

This comment has been minimized.

Copy link

Aliham commented Feb 10, 2018

پاسخ نداد

@emadweb

This comment has been minimized.

Copy link

emadweb commented Feb 11, 2018

$check_hash an $hash will not be the same

@xen

This comment has been minimized.

Copy link

xen commented Feb 12, 2018

In case somebody needs python version https://gist.github.com/xen/e4bea72487d34caa28c762776cf655a3

@tcapb

This comment has been minimized.

Copy link

tcapb commented Feb 13, 2018

Unusable to me. It allows to add only one domain per bot. I couldn't even use it with multiple subdomains. If i set domain.com - i can use authorization from domain.com page, but cannot - from sub.domain.com page.

@recoilme

This comment has been minimized.

Copy link

recoilme commented Feb 14, 2018

GoLang version of checkTelegramAuthorization: https://gist.github.com/recoilme/a1b9059b5d5f12c18a63bae58b3bc659

@recoilme

This comment has been minimized.

Copy link

recoilme commented Feb 14, 2018

@tcapb similar problem. I will redirect login on main domain, set cookie for main domain and subdomains and redirect back. Not finished right now - http://recoilmeblog.tggram.com/

@Pitasi

This comment has been minimized.

@vitalyster

This comment has been minimized.

Copy link

vitalyster commented Feb 15, 2018

Login widget does not work in Safari (iOS) - it opens new page with "Origin required" text

@Stajor

This comment has been minimized.

@bun4uk

This comment has been minimized.

Copy link

bun4uk commented Feb 15, 2018

How is it possible to test on localhost?
I crated a bot and conected a domain to it.
image
image

@vitalyster

This comment has been minimized.

Copy link

vitalyster commented Feb 15, 2018

new page with "Origin required" text

Same issue on Android System Webview

@sajjad-021

This comment has been minimized.

Copy link

sajjad-021 commented Feb 18, 2018

This is corrected and running without problem ;-)

@seyedahmadqolamy

This comment has been minimized.

Copy link

seyedahmadqolamy commented Feb 19, 2018

hi, how to use these files and code in wordpress?
do i insert codes in which ones: theme file? or text widget in sidbar?
i want to write code and dont want to use plugin. thanx.

@jhuesser

This comment has been minimized.

Copy link

jhuesser commented Feb 21, 2018

new page with "Origin required" text

Have this problem to, mostly after I deleted cookies of telegram.org & my page. Still works fine in Chrome on same the same iOS device

@hprobotic

This comment has been minimized.

Copy link

hprobotic commented Feb 22, 2018

Here is sample implement for React: https://github.com/hprobotic/react-telegram-login

@vchaptsev

This comment has been minimized.

Copy link

vchaptsev commented Feb 24, 2018

Here is Vue component, if someone need it :)

@yi

This comment has been minimized.

Copy link

yi commented Feb 27, 2018

web login works on Android Chrome browser. Not working Android webview, nor iOS Safari. Any idea to make it work? please

@MJ-Vakili

This comment has been minimized.

Copy link

MJ-Vakili commented Mar 2, 2018

How I can send message to user if allow access to send messages?
How start a conversation by bot?
I tried a lot but failed.
Tanks.

@m3night

This comment has been minimized.

Copy link

m3night commented Mar 4, 2018

Works on firefox desktop , but don't work on firefox on an android device.

@balashovka

This comment has been minimized.

Copy link

balashovka commented Mar 7, 2018

hi. logIN is work. anybody know how to logOUT authorized user?

@mohammadhoseinpari

This comment has been minimized.

Copy link

mohammadhoseinpari commented Mar 19, 2018

Tanks

@nadernmds

This comment has been minimized.

Copy link

nadernmds commented Mar 22, 2018

any one can translate this to c#????
just auth part is enough

@akicreative

This comment has been minimized.

Copy link

akicreative commented Apr 2, 2018

I have been trying to integrate this with my web sites. But sometimes.... not all the time I get this issue: Invalid 'X-Frame-Options' header encountered when loading

So the widget loads and then when you click it won't do anything. It is a pain, and not very reliable. This is in Safari.

@t1maccapp

This comment has been minimized.

Copy link

t1maccapp commented Apr 10, 2018

You can use 127.0.0.1 with port 80 to test it locally.

@matinbeigi97

This comment has been minimized.

Copy link

matinbeigi97 commented Apr 10, 2018

working file in login_example.php

@matinbeigi97

This comment has been minimized.

Copy link

matinbeigi97 commented Apr 10, 2018

but not work check_authorization.php
recive message Data is NOT from Telegram

@AlexR1712

This comment has been minimized.

Copy link

AlexR1712 commented May 7, 2018

is working fine

@edu2004eu

This comment has been minimized.

Copy link

edu2004eu commented May 9, 2018

For anyone who set their domain and still receiving a domain-related errors, note that you can't use ports inside domain names. BotFather will accept it, but the widget will not load. You need to use port 80.

@90K2

This comment has been minimized.

@jehan96

This comment has been minimized.

Copy link

jehan96 commented May 27, 2018

anyone know how to allow only specific user can login using the widget?

@Vitalicus

This comment has been minimized.

Copy link

Vitalicus commented May 27, 2018

How to get also phone number on login?

@prutya

This comment has been minimized.

Copy link

prutya commented Jun 5, 2018

@Stajor Thank you a lot!

@ha93715

This comment has been minimized.

Copy link

ha93715 commented Jun 7, 2018

Thank you a lot

@DKorablin

This comment has been minimized.

Copy link

DKorablin commented Jun 25, 2018

C#

private static Boolean ValidateHash(String secretKey, String telegramUrl)
{
	String urlHash = null;
	IEnumerable<String> datas = telegramUrl
		.Split(new Char[] { '&', '?', }, StringSplitOptions.RemoveEmptyEntries)
		.Where(p => { if(p.StartsWith("hash=")) { urlHash = p.Substring("hash=".Length); return false; } else return true; })
		.OrderBy(p => p);

	String dataCheckString = String.Join("\n", datas);

	using(SHA256 sha256 = SHA256Managed.Create("sha256"))
	{
		Byte[] bSecretKey = sha256.ComputeHash(Encoding.UTF8.GetBytes(secretKey));
		using(HMACSHA256 hmacsha256 = new HMACSHA256(bSecretKey))
		{
			Byte[] hash = hmacsha256.ComputeHash(Encoding.UTF8.GetBytes(dataCheckString));
			String strHash = String.Join(String.Empty, hash.Select(p => p.ToString("x2")));
			return strHash == urlHash;
		}
	}
}
@sgyyz

This comment has been minimized.

Copy link

sgyyz commented Jul 5, 2018

login widget is not working in Telegram in App browser on iOS 10 and below. Did there anyone meet this issue?

@monoplasty

This comment has been minimized.

Copy link

monoplasty commented Jul 6, 2018

There are no 'photo_url' and 'username' fields in the parameters of the callback function. Did there anyone meet this issue?

@wukexiu

This comment has been minimized.

Copy link

wukexiu commented Aug 21, 2018

Object-C check_authorization

/**
 Telegram @return to check hash
 
 @param plaintext: already sorted and not contain 'hash' parameters
                   e.g @"auth_date=<auth_date>\nfirst_name=<first_name>\nid=<id>\n...".
 @param token: BOT_TOKEN e.g @"XXXXXXXX:XXXXXXXXXXXXXXXXXXXXXXXX"
 @return Hash value calculated by myself
 */
- (NSString *)_hmac256:(NSString *)plaintext withToken:(NSString *)token
{
    NSData *tokenData =  [token dataUsingEncoding:NSUTF8StringEncoding];
    uint8_t digest[CC_SHA256_DIGEST_LENGTH] = {0};
    CC_SHA256(tokenData.bytes, (CC_LONG)tokenData.length, digest);
    NSData *cKey = [NSData dataWithBytes:digest length:CC_SHA256_DIGEST_LENGTH];
    
    NSData *cData = [plaintext dataUsingEncoding:NSUTF8StringEncoding];
    
    unsigned char cHMAC[CC_SHA256_DIGEST_LENGTH];
    CCHmac(kCCHmacAlgSHA256, cKey.bytes, cKey.length, cData.bytes, cData.length, cHMAC);
    NSData *HMACData = [NSData dataWithBytes:cHMAC length:sizeof(cHMAC)];
    const unsigned char *buffer = (const unsigned char *)[HMACData bytes];
    NSMutableString *HMAC = [NSMutableString stringWithCapacity:HMACData.length * 2];
    for (int i = 0; i < HMACData.length; ++i){
        [HMAC appendFormat:@"%02x", buffer[i]];
    }
    return HMAC;
}
@4ibo

This comment has been minimized.

Copy link

4ibo commented Sep 2, 2018

Typescript

function checkTelegramAuth(auth: TelegramAuthenticateDto): boolean {
    const now = Date.now() / 1000;
    const timeDiff = now - auth.auth_date;

    const checkString: string = Object.keys(auth)
      .filter(key => key !== 'hash')
      .map(key => `${key}=${auth[key]}`)
      .sort()
      .join('\n');

    const secret = crypto
      .createHash('sha256')
      .update(constants.telegram.bot.token)
      .digest();

    const hash = crypto
      .createHmac('sha256', secret)
      .update(checkString)
      .digest('hex');

    return auth.hash === hash && timeDiff < constants.telegram.authExpiresIn;
  }
@manzoorwanijk

This comment has been minimized.

Copy link

manzoorwanijk commented Sep 24, 2018

WordPress plugin based on that
https://wordpress.org/plugins/wptelegram-login/

@TheNeikos

This comment has been minimized.

Copy link

TheNeikos commented Oct 22, 2018

A note: You need to have third party cookies enabled for this to work

@sintetico82

This comment has been minimized.

Copy link

sintetico82 commented Oct 30, 2018

Hi,
After an user is logged in with Telegram Widget, it's possibile to use the bot to notify user somethings?

@1019238091

This comment has been minimized.

Copy link

1019238091 commented Nov 7, 2018

++

Doesn't work in Firefox
Error: NOT_ALLOWED

The sample to you. Can someone tell me how to do authroize and get user information in the Android.

@zengxiang1

This comment has been minimized.

Copy link

zengxiang1 commented Nov 28, 2018

There are no 'photo_url' and 'username' fields in the parameters of the callback function. Did there anyone meet this issue?

me too

@paulojp-dev

This comment has been minimized.

Copy link

paulojp-dev commented Nov 28, 2018

It's working!

@AlexanderSysoev

This comment has been minimized.

Copy link

AlexanderSysoev commented Dec 2, 2018

Should photo_url be urlencoded to calculate hash?

@jtfell

This comment has been minimized.

Copy link

jtfell commented Dec 5, 2018

@364578357

This comment has been minimized.

Copy link

364578357 commented Dec 10, 2018

A2YQF8MK

@shayanbjn78

This comment has been minimized.

Copy link

shayanbjn78 commented Dec 26, 2018

can i write a code in c# language for telegram bot ???

@tjkcc

This comment has been minimized.

Copy link

tjkcc commented Feb 22, 2019

Ran into a problem. Or, rather a UX issue.
iOS 12, trying to log in through built-in browser right in Telegram app. User clicks “login with telegram” button, enters the phone number, TG sends a message asking to confirm, but there are no notifications for this message, apart from a sound if it is on. Then a user needs to close the browser, open the chat with Telegram, press Confirm, then go back to the chat with a bot, open the web link again, click “log in with tg” button again, and after I had seen two outcomes. One when a user is asked the phone number again, which leads to the process loop and no ability to log in, unless user opens the web page in a safari tab (not built it safari). And two, when after clicking the login button, the user is actually logged in.
The whole process in telegram app is kind of bad, I think. Any ideas on how to make it better?

@ledzgio

This comment has been minimized.

Copy link

ledzgio commented Apr 15, 2019

Ho do we catch the logout events? users can logout and the system wouldn't recognise it

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.