Last active
October 29, 2024 10:12
-
-
Save immmdreza/29415b29106d759371fbab23b67fff20 to your computer and use it in GitHub Desktop.
Validate data from telegram web app (https://core.telegram.org/bots/webapps#validating-data-received-via-the-web-app) in C#.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Parse string initData from telegram. | |
var data = HttpUtility.ParseQueryString(initData); | |
// Put data in a alphabetically sorted dict. | |
var dataDict = new SortedDictionary<string, string>( | |
data.AllKeys.ToDictionary(x => x!, x => data[x]!), | |
StringComparer.Ordinal); | |
// Constant key to genrate secret key. | |
var constantKey = "WebAppData"; | |
// https://core.telegram.org/bots/webapps#validating-data-received-via-the-web-app: | |
// Data-check-string is a chain of all received fields, | |
// sorted alphabetically. | |
// in the format key=<value>. | |
// with a line feed character ('\n', 0x0A) used as separator. | |
// e.g., 'auth_date=<auth_date>\nquery_id=<query_id>\nuser=<user>' | |
var dataCheckString = string.Join( | |
'\n', dataDict.Where(x => x.Key != "hash") // Hash should be removed. | |
.Select(x => $"{x.Key}={x.Value}")); // like auth_date=<auth_date> .. | |
// secrecKey is the HMAC-SHA-256 signature of the bot's token | |
// with the constant string WebAppData used as a key. | |
var secretKey = HMACSHA256.HashData( | |
Encoding.UTF8.GetBytes(constantKey), // WebAppData | |
Encoding.UTF8.GetBytes(_botConfig.BotToken)); // Bot's token | |
var generatedHash = HMACSHA256.HashData( | |
secretKey, | |
Encoding.UTF8.GetBytes(dataCheckString)); // data_check_string | |
// Convert received hash from telegram to a byte array. | |
var actualHash = Convert.FromHexString(dataDict["hash"]); // .NET 5.0 | |
// Compare our hash with the one from telegram. | |
if (actualHash.SequenceEqual(generatedHash)) | |
{ | |
// Data from telegram. | |
} |
There is no way this code can work because you use HMACSHA256 for hashing of token for secret key instead of SHA256.
There is no way this code can work because you use HMACSHA256 for hashing of token for secret key instead of SHA256.
data_check_string = ...
secret_key = HMAC_SHA256(<bot_token>, "WebAppData")
if (hex(HMAC_SHA256(data_check_string, secret_key)) == hash) {
// data is from Telegram
}
Telegram docs noticed that it should be HMAC_SHA256
.
I’m not really sure that it’s working at the moment, but it was.
@immmdreza Man! Thank you very much!
@immmdreza Man! Thank you very much!
🙏
data_check_string = ...
secret_key = SHA256(<bot_token>)
if (hex(HMAC_SHA256(data_check_string, secret_key)) == hash) {
// data is from Telegram
}
Thanks for the code!
Thanks, This really helped
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
For .NET Core 3
You can use
byte[] HmacSHA256(byte[] code, byte[] data) { using (HMACSHA256 hmac = new HMACSHA256(code)) { var hmBytes = hmac.ComputeHash(data); return hmBytes; } }
instead ofHMACSHA256.HashData