Skip to content

Commit 10b1d9c

Browse files
committed
Add Python script to create account sessions
1 parent a3d341e commit 10b1d9c

File tree

1 file changed

+161
-0
lines changed

1 file changed

+161
-0
lines changed

tools/get_session.py

+161
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,161 @@
1+
#!/usr/bin/env python3
2+
import requests
3+
import json
4+
import sys
5+
import pyotp
6+
7+
# NOTE: pyotp and requests are dependencies
8+
# > pip install pyotp requests
9+
10+
TW_CONSUMER_KEY = '3nVuSoBZnx6U4vzUxf5w'
11+
TW_CONSUMER_SECRET = 'Bcs59EFbbsdF6Sl9Ng71smgStWEGwXXKSjYvPVt7qys'
12+
13+
def auth(username, password, otp_secret):
14+
bearer_token_req = requests.post("https://api.twitter.com/oauth2/token",
15+
auth=(TW_CONSUMER_KEY, TW_CONSUMER_SECRET),
16+
headers={"Content-Type": "application/x-www-form-urlencoded"},
17+
data='grant_type=client_credentials'
18+
).json()
19+
bearer_token = ' '.join(str(x) for x in bearer_token_req.values())
20+
21+
guest_token = requests.post(
22+
"https://api.twitter.com/1.1/guest/activate.json",
23+
headers={'Authorization': bearer_token}
24+
).json().get('guest_token')
25+
26+
if not guest_token:
27+
print("Failed to obtain guest token.")
28+
sys.exit(1)
29+
30+
twitter_header = {
31+
'Authorization': bearer_token,
32+
"Content-Type": "application/json",
33+
"User-Agent": "TwitterAndroid/10.21.0-release.0 (310210000-r-0) ONEPLUS+A3010/9 (OnePlus;ONEPLUS+A3010;OnePlus;OnePlus3;0;;1;2016)",
34+
"X-Twitter-API-Version": '5',
35+
"X-Twitter-Client": "TwitterAndroid",
36+
"X-Twitter-Client-Version": "10.21.0-release.0",
37+
"OS-Version": "28",
38+
"System-User-Agent": "Dalvik/2.1.0 (Linux; U; Android 9; ONEPLUS A3010 Build/PKQ1.181203.001)",
39+
"X-Twitter-Active-User": "yes",
40+
"X-Guest-Token": guest_token,
41+
"X-Twitter-Client-DeviceID": ""
42+
}
43+
44+
session = requests.Session()
45+
session.headers = twitter_header
46+
47+
task1 = session.post(
48+
'https://api.twitter.com/1.1/onboarding/task.json',
49+
params={
50+
'flow_name': 'login',
51+
'api_version': '1',
52+
'known_device_token': '',
53+
'sim_country_code': 'us'
54+
},
55+
json={
56+
"flow_token": None,
57+
"input_flow_data": {
58+
"country_code": None,
59+
"flow_context": {
60+
"referrer_context": {
61+
"referral_details": "utm_source=google-play&utm_medium=organic",
62+
"referrer_url": ""
63+
},
64+
"start_location": {
65+
"location": "deeplink"
66+
}
67+
},
68+
"requested_variant": None,
69+
"target_user_id": 0
70+
}
71+
}
72+
)
73+
74+
session.headers['att'] = task1.headers.get('att')
75+
76+
task2 = session.post(
77+
'https://api.twitter.com/1.1/onboarding/task.json',
78+
json={
79+
"flow_token": task1.json().get('flow_token'),
80+
"subtask_inputs": [{
81+
"enter_text": {
82+
"suggestion_id": None,
83+
"text": username,
84+
"link": "next_link"
85+
},
86+
"subtask_id": "LoginEnterUserIdentifier"
87+
}]
88+
}
89+
)
90+
91+
task3 = session.post(
92+
'https://api.twitter.com/1.1/onboarding/task.json',
93+
json={
94+
"flow_token": task2.json().get('flow_token'),
95+
"subtask_inputs": [{
96+
"enter_password": {
97+
"password": password,
98+
"link": "next_link"
99+
},
100+
"subtask_id": "LoginEnterPassword"
101+
}],
102+
}
103+
)
104+
105+
for t3_subtask in task3.json().get('subtasks', []):
106+
if "open_account" in t3_subtask:
107+
return t3_subtask["open_account"]
108+
elif "enter_text" in t3_subtask:
109+
response_text = t3_subtask["enter_text"]["hint_text"]
110+
totp = pyotp.TOTP(otp_secret)
111+
generated_code = totp.now()
112+
task4resp = session.post(
113+
"https://api.twitter.com/1.1/onboarding/task.json",
114+
json={
115+
"flow_token": task3.json().get("flow_token"),
116+
"subtask_inputs": [
117+
{
118+
"enter_text": {
119+
"suggestion_id": None,
120+
"text": generated_code,
121+
"link": "next_link",
122+
},
123+
"subtask_id": "LoginTwoFactorAuthChallenge",
124+
}
125+
],
126+
}
127+
)
128+
task4 = task4resp.json()
129+
for t4_subtask in task4.get("subtasks", []):
130+
if "open_account" in t4_subtask:
131+
return t4_subtask["open_account"]
132+
133+
return None
134+
135+
if __name__ == "__main__":
136+
if len(sys.argv) != 5:
137+
print("Usage: python3 get_session.py <username> <password> <2fa secret> <path>")
138+
sys.exit(1)
139+
140+
username = sys.argv[1]
141+
password = sys.argv[2]
142+
otp_secret = sys.argv[3]
143+
path = sys.argv[4]
144+
145+
result = auth(username, password, otp_secret)
146+
if result is None:
147+
print("Authentication failed.")
148+
sys.exit(1)
149+
150+
session_entry = {
151+
"oauth_token": result.get("oauth_token"),
152+
"oauth_token_secret": result.get("oauth_token_secret")
153+
}
154+
155+
try:
156+
with open(path, "a") as f:
157+
f.write(json.dumps(session_entry) + "\n")
158+
print("Authentication successful. Session appended to", path)
159+
except Exception as e:
160+
print(f"Failed to write session information: {e}")
161+
sys.exit(1)

0 commit comments

Comments
 (0)