teidesu-scripts/scripts/misc/yamusic-token.ts
2025-09-14 21:52:13 +00:00

87 lines
2.7 KiB
TypeScript

import { randomBytes } from 'node:crypto'
import { faker } from '@faker-js/faker'
import { question } from 'zx'
import { ffetch } from '../../utils/fetch.ts'
// log in with your yandex account in the browser, then go to music.yandex.ru and open devtools
// find long ass string in "Cookie" header from the requests to music.yandex.ru, it must contain "Session_id" cookie.
// make sure to copy it completely (on firefox this requires toggling "Raw")
// looks something like: is_gdpr=0; is_gdpr=0; is_gdpr_b=COnCMBCR0wIoAg==; _yasc=ctfv6IPUcb+Lk+jqYr0thW1STKmQC5yB4IJUM5Gn....
const cookies = await question('music.yandex.ru cookies > ')
const parsed = new Map(cookies.split('; ').map((cookie) => {
const [name, value] = cookie.split('=')
return [name, value]
}))
if (!parsed.has('Session_id')) {
throw new Error('Session_id cookie not found')
}
const deviceId = randomBytes(16).toString('hex')
const uuid = randomBytes(16).toString('hex')
const genRequestId = () => `${uuid}${Math.floor(Date.now())}`
const query = {
manufacturer: 'Google',
model: 'Pixel 9 Pro XL',
app_platform: 'Android 16 (REL)',
am_version_name: '7.46.0(746003972)',
app_id: 'ru.yandex.music',
app_version_name: '2025.09.2 #114gpr',
am_app: 'ru.yandex.music 2025.09.2 #114gpr',
deviceid: deviceId,
device_id: deviceId,
uuid,
}
const res = await ffetch('https://mobileproxy.passport.yandex.net/1/bundle/oauth/token_by_sessionid', {
query: {
...query,
request_id: genRequestId(),
},
form: {
client_id: 'c0ebe342af7d48fbbbfcf2d2eedb8f9e',
client_secret: 'ad0a908f0aa341a182a37ecd75bc319e',
grant_type: 'sessionid',
host: 'yandex.ru',
},
headers: {
'Accept': '*/*',
'User-Agent': 'com.yandex.mobile.auth.sdk/7.46.0.746003972 (Google Pixel 9 Pro XL; Android 16) PassportSDK/7.46.0.746003972',
'Accept-Language': 'en-RU;q=1, ru-RU;q=0.9',
'Ya-Client-Host': 'passport.yandex.ru',
'Ya-Client-Cookie': cookies,
},
}).json() as any
if (res.status !== 'ok') {
console.error('Unexpected response:', res)
process.exit(1)
}
console.log('res', res)
const res2 = await ffetch('https://mobileproxy.passport.yandex.net/1/token', {
query: {
...query,
request_id: genRequestId(),
},
form: {
access_token: res.access_token,
client_id: '23cabbbdc6cd418abb4b39c32c41195d',
client_secret: '53bc75238f0c4d08a118e51fe9203300',
grant_type: 'x-token',
},
}).json() as any
if (!res2.access_token) {
console.error('Unexpected response:', res2)
process.exit(1)
}
console.log('res2', res2)
console.log('')
console.log('Your auth token is:')
console.log(res2.access_token)
console.log('Expires at:', new Date(Date.now() + res.expires_in * 1000).toLocaleString('ru-RU'))