Switch to MOBILE_WEB Client ID
This commit is contained in:
1 parent
137f540d62
commit
70035cde36
2 files changed
+56
-29
No files matched your search
+47
-5
@@ -1,12 +1,13 @@
|
|||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
import sys
|
import sys
|
||||||
|
import random
|
||||||
import logging
|
import logging
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from copy import deepcopy
|
from copy import deepcopy
|
||||||
from enum import Enum, auto
|
from enum import Enum, auto
|
||||||
from datetime import timedelta
|
from datetime import timedelta
|
||||||
from typing import Any, Dict, Literal, NamedTuple, NewType, TYPE_CHECKING
|
from typing import Any, Dict, Literal, NewType, TYPE_CHECKING
|
||||||
|
|
||||||
from yarl import URL
|
from yarl import URL
|
||||||
|
|
||||||
@@ -97,9 +98,17 @@ FILE_FORMATTER = logging.Formatter(
|
|||||||
OUTPUT_FORMATTER = logging.Formatter("{levelname}: {message}", style='{', datefmt="%H:%M:%S")
|
OUTPUT_FORMATTER = logging.Formatter("{levelname}: {message}", style='{', datefmt="%H:%M:%S")
|
||||||
|
|
||||||
|
|
||||||
class ClientInfo(NamedTuple):
|
class ClientInfo:
|
||||||
CLIENT_ID: str
|
def __init__(self, client_id: str, user_agents: str | list[str]) -> None:
|
||||||
USER_AGENT: str
|
self.CLIENT_ID: str = client_id
|
||||||
|
self.USER_AGENT: str
|
||||||
|
if isinstance(user_agents, list):
|
||||||
|
self.USER_AGENT = random.choice(user_agents)
|
||||||
|
else:
|
||||||
|
self.USER_AGENT = user_agents
|
||||||
|
|
||||||
|
def __iter__(self):
|
||||||
|
return iter((self.CLIENT_ID, self.USER_AGENT))
|
||||||
|
|
||||||
|
|
||||||
class ClientType:
|
class ClientType:
|
||||||
@@ -110,7 +119,40 @@ class ClientType:
|
|||||||
"(KHTML, like Gecko) Chrome/108.0.0.0 Safari/537.36"
|
"(KHTML, like Gecko) Chrome/108.0.0.0 Safari/537.36"
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
ANDROID = ClientInfo(
|
MOBILE_WEB = ClientInfo(
|
||||||
|
"r8s4dac0uhzifbpu9sjdiwzctle17ff",
|
||||||
|
[
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13; SM-A205U) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13; SM-A102U) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13; SM-G960U) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13; SM-N960U) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13; LM-Q720) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"Mozilla/5.0 (Linux; Android 13; LM-X420) AppleWebKit/537.36 "
|
||||||
|
"(KHTML, like Gecko) Chrome/115.0.5790.166 Mobile Safari/537.36"
|
||||||
|
),
|
||||||
|
]
|
||||||
|
)
|
||||||
|
ANDROID_APP = ClientInfo(
|
||||||
"kd1unb4b3q4t58fwlpcbzcbnm76a8fp",
|
"kd1unb4b3q4t58fwlpcbzcbnm76a8fp",
|
||||||
(
|
(
|
||||||
"Dalvik/2.1.0 (Linux; U; Android 7.1.2; SM-G977N Build/LMY48Z) "
|
"Dalvik/2.1.0 (Linux; U; Android 7.1.2; SM-G977N Build/LMY48Z) "
|
||||||
|
|||||||
@@ -3,7 +3,6 @@ from __future__ import annotations
|
|||||||
import re
|
import re
|
||||||
import sys
|
import sys
|
||||||
import json
|
import json
|
||||||
import random
|
|
||||||
import asyncio
|
import asyncio
|
||||||
import logging
|
import logging
|
||||||
from time import time
|
from time import time
|
||||||
@@ -91,7 +90,7 @@ class SkipExtraJsonDecoder(json.JSONDecoder):
|
|||||||
return obj
|
return obj
|
||||||
|
|
||||||
|
|
||||||
CLIENT_ID, USER_AGENT = ClientType.SMARTBOX
|
CLIENT_ID, USER_AGENT = ClientType.MOBILE_WEB
|
||||||
SAFE_LOADS = lambda s: json.loads(s, cls=SkipExtraJsonDecoder)
|
SAFE_LOADS = lambda s: json.loads(s, cls=SkipExtraJsonDecoder)
|
||||||
|
|
||||||
|
|
||||||
@@ -499,8 +498,8 @@ class _AuthState:
|
|||||||
headers["User-Agent"] = user_agent
|
headers["User-Agent"] = user_agent
|
||||||
if hasattr(self, "session_id"):
|
if hasattr(self, "session_id"):
|
||||||
headers["Client-Session-Id"] = self.session_id
|
headers["Client-Session-Id"] = self.session_id
|
||||||
if hasattr(self, "client_version"):
|
# if hasattr(self, "client_version"):
|
||||||
headers["Client-Version"] = self.client_version
|
# headers["Client-Version"] = self.client_version
|
||||||
if hasattr(self, "device_id"):
|
if hasattr(self, "device_id"):
|
||||||
headers["X-Device-Id"] = self.device_id
|
headers["X-Device-Id"] = self.device_id
|
||||||
if gql:
|
if gql:
|
||||||
@@ -526,10 +525,11 @@ class _AuthState:
|
|||||||
"GET", BASE_URL, headers=self.headers()
|
"GET", BASE_URL, headers=self.headers()
|
||||||
) as response:
|
) as response:
|
||||||
page_html = await response.text("utf8")
|
page_html = await response.text("utf8")
|
||||||
match = re.search(r'twilightBuildID="([-a-z0-9]+)"', page_html)
|
assert page_html is not None
|
||||||
if match is None:
|
# match = re.search(r'twilightBuildID="([-a-z0-9]+)"', page_html)
|
||||||
raise MinerException("Unable to extract client_version")
|
# if match is None:
|
||||||
self.client_version = match.group(1)
|
# raise MinerException("Unable to extract client_version")
|
||||||
|
# self.client_version = match.group(1)
|
||||||
# doing the request ends up setting the "unique_id" value in the cookie
|
# doing the request ends up setting the "unique_id" value in the cookie
|
||||||
cookie = jar.filter_cookies(BASE_URL)
|
cookie = jar.filter_cookies(BASE_URL)
|
||||||
self.device_id = cookie["unique_id"].value
|
self.device_id = cookie["unique_id"].value
|
||||||
@@ -639,21 +639,6 @@ class Twitch:
|
|||||||
if session.closed:
|
if session.closed:
|
||||||
raise RuntimeError("Session is closed")
|
raise RuntimeError("Session is closed")
|
||||||
return session
|
return session
|
||||||
# try to obtain the latest Chrome user agent from a Github project
|
|
||||||
try:
|
|
||||||
async with aiohttp.request(
|
|
||||||
"GET",
|
|
||||||
"https://jnrbsn.github.io/user-agents/user-agents.json",
|
|
||||||
proxy=self.settings.proxy or None,
|
|
||||||
) as response:
|
|
||||||
agents = await response.json()
|
|
||||||
if sys.platform == "win32":
|
|
||||||
chrome_agent = random.choice(agents[:3])
|
|
||||||
elif sys.platform == "linux":
|
|
||||||
chrome_agent = random.choice(agents[7:11])
|
|
||||||
except Exception:
|
|
||||||
# looks like we can't rely on 3rd parties too much
|
|
||||||
chrome_agent = ClientType.WEB.USER_AGENT
|
|
||||||
# load in cookies
|
# load in cookies
|
||||||
cookie_jar = aiohttp.CookieJar()
|
cookie_jar = aiohttp.CookieJar()
|
||||||
try:
|
try:
|
||||||
@@ -668,7 +653,7 @@ class Twitch:
|
|||||||
self._session = aiohttp.ClientSession(
|
self._session = aiohttp.ClientSession(
|
||||||
connector=connector,
|
connector=connector,
|
||||||
cookie_jar=cookie_jar,
|
cookie_jar=cookie_jar,
|
||||||
headers={"User-Agent": chrome_agent},
|
headers={"User-Agent": USER_AGENT},
|
||||||
timeout=aiohttp.ClientTimeout(connect=5, total=10),
|
timeout=aiohttp.ClientTimeout(connect=5, total=10),
|
||||||
)
|
)
|
||||||
return self._session
|
return self._session
|
||||||
|
|||||||
Reference in new issue
Block a user