Изначально значение представленно в виде URl параметров
1. Спарсим initData в объект.
const params: Record<string, string> = {}
const pairs = initData.split('&')
for (const pair of pairs) {
const [key, value] = pair.split('=')
params[key] = value
}{}2. Удаляем ключ hash из объекта
Прежде сохраняем его значение в переменной!
3. Отсортируем объект по ключам в алфавитном порядке.
const sortedParams: Record<string, string> = {}
Object.keys(params)
.sort()
.forEach((key) => {
sortedParams[key] = params[key];
});{}4. Преобразуем отсортированный объект в строку вида - "key1=value1\nkey2=value2\n..."
const dataCheckString = Object.entries(sortedParams)
.map(([key, value]) => `${key}=${value}`)
.join("
")5. Создадим секретный ключ. Хешируем токен бота по ключу "WebAppData" алгоритмом hmacSHA256.
const secretKey = hmacSHA256(botToken, "WebAppData")6. Создаём хеш значения dataCheckString по ключу secretKey алгоритмом hmacSHA256 и преобразуем в строку.
const computedHash = hmacSHA256(dataCheckString, secretKey).toString(Hex)""7. Сравниваем полученный хеш с хешем из параметров initData