├── README.md
└── nyan.py
/README.md:
--------------------------------------------------------------------------------
1 | # NyanHeroes
2 | nyanheroes项目批量刷邀请+自动完成任务
3 |
4 | 用法:
5 | 修改nyan.py中的邀请码,将tw_token.txt放在脚本同目录,一行一个token。
6 |
7 | python3 nyan.py
8 |
--------------------------------------------------------------------------------
/nyan.py:
--------------------------------------------------------------------------------
1 | import asyncio
2 | import sys
3 | import time
4 | from datetime import datetime
5 | import base58
6 | import httpx
7 | from loguru import logger
8 | from urllib.parse import urlparse, parse_qs
9 | from solathon import Keypair
10 |
11 | g_success, g_fail = 0, 0
12 |
13 | logger.remove()
14 | logger.add(sys.stdout, colorize=True,
15 | format="{time:HH:mm:ss:SSS} | {extra[fail]}-{extra[success]} | {message}")
16 | logger = logger.patch(lambda record: record["extra"].update(fail=g_fail, success=g_success))
17 |
18 |
19 | proxies = {
20 | 'http://': 'http://127.0.0.1:7890',
21 | 'https://': 'http://127.0.0.1:7890',
22 | }
23 |
24 |
25 | class Nyan:
26 | def __init__(self, auth_token, referral):
27 | self.http = httpx.AsyncClient(proxies=proxies, verify=False)
28 | self.http.headers = {
29 | 'Accept-Language': 'en-US,en;q=0.8',
30 | 'Authority': 'twitter.com',
31 | 'Origin': 'https://twitter.com',
32 | 'Referer': 'https://twitter.com/',
33 | 'Sec-Ch-Ua': '"Google Chrome";v="117", "Not;A=Brand";v="8", "Chromium";v="117"',
34 | 'Sec-Ch-Ua-Mobile': '?0',
35 | 'Sec-Ch-Ua-Platform': "Windows",
36 | 'Sec-Fetch-Dest': 'empty',
37 | 'Sec-Fetch-Mode': 'cors',
38 | 'Sec-Fetch-Site': 'same-origin',
39 | 'Sec-Gpc': '1',
40 | 'User-Agent': 'Mozilla/5.0 (Windows NT 11.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/'
41 | }
42 |
43 | self.Twitter = httpx.AsyncClient(proxies=proxies, verify=False)
44 | self.Twitter.headers = {
45 | 'Accept-Language': 'zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2',
46 | 'Accept': 'application/json, text/plain, */*',
47 | 'Origin': 'https://missions.nyanheroes.com',
48 | 'Sec-Fetch-Dest': 'empty',
49 | 'Sec-Fetch-Mode': 'cors',
50 | 'Sec-Fetch-Site': 'same-origin',
51 | 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:123.0) Gecko/20100101 Firefox/123.0'
52 | }
53 | self.Twitter.cookies.update({'auth_token': auth_token})
54 | self.oauth_token, self.authenticity_token, self.oauth_verifier, self.token = None, None, None, None
55 | self.referral = referral
56 | self.auth_token = auth_token
57 |
58 | async def get_twitter(self):
59 | try:
60 | response = await self.http.get(
61 | 'https://api.nyanheroes.com/Login/Authorize?callbackUrl=https://missions.nyanheroes.com/')
62 | if 'oauth_token' in response.text:
63 | parsed_url = urlparse(response.text)
64 | query_params = parse_qs(parsed_url.query)
65 | self.oauth_token = query_params.get('oauth_token', [None])[0]
66 | return True
67 | logger.error(f'{self.auth_token} 获取oauth_token失败')
68 | return False
69 | except Exception as e:
70 | logger.error(e)
71 | return False
72 |
73 | async def get_twitter_token(self):
74 | try:
75 | if not await self.get_twitter():
76 | return False
77 | response = await self.Twitter.get(f'https://api.twitter.com/oauth/authorize?oauth_token={self.oauth_token}')
78 | if 'authenticity_token' in response.text:
79 | self.authenticity_token = response.text.split('authenticity_token" value="')[1].split('"')[0]
80 | return True
81 | logger.error(f'{self.auth_token} 获取authenticity_token失败')
82 | return False
83 | except Exception as e:
84 | logger.error(e)
85 | return False
86 |
87 | async def twitter_authorize(self):
88 | try:
89 | if not await self.get_twitter_token():
90 | return False
91 | data = {
92 | 'authenticity_token': self.authenticity_token,
93 | 'redirect_after_login': f'https://api.twitter.com/oauth/authorize?oauth_token={self.oauth_token}',
94 | 'oauth_token': self.oauth_token
95 | }
96 | response = await self.Twitter.post('https://api.twitter.com/oauth/authorize', data=data)
97 | if 'oauth_verifier' in response.text:
98 | self.oauth_verifier = response.text.split('oauth_verifier=')[1].split('"')[0]
99 | return True
100 | logger.error(f'{self.auth_token} 获取oauth_verifier失败')
101 | return False
102 | except Exception as e:
103 | logger.error(e)
104 | return False
105 |
106 | async def twitter_login(self):
107 | try:
108 | if not await self.twitter_authorize():
109 | return False
110 | data = {
111 | 'oauthToken': self.oauth_token,
112 | 'callbackUrl': 'https://missions.nyanheroes.com/',
113 | 'oauthVerifier': self.oauth_verifier
114 | }
115 | response = await self.http.get(f'https://api.nyanheroes.com/Login/Authorize', params=data)
116 | if response.json()['user']['twitterUsername'] is not None:
117 | self.token = response.json()['token']
118 | self.http.headers['Authorization'] = 'Bearer ' + self.token
119 | return True
120 | logger.error(f'{self.auth_token} 登录失败')
121 | return False
122 | except Exception as e:
123 | logger.error(e)
124 | return False
125 |
126 | async def set_referral(self):
127 | try:
128 | response = await self.http.post('https://api.nyanheroes.com/User/addReferral?referralCode=' + self.referral)
129 | if response.json()['result']:
130 | return True
131 | logger.error(f'{self.auth_token} 设置邀请人失败')
132 | return False
133 | except Exception as e:
134 | logger.error(e)
135 | return False
136 |
137 | async def compete_task(self,sol_wallet):
138 | try:
139 | task_id = [5, 6, 7, 8, 3, 31, 1, 4, 32, 65, 2]
140 | for i in task_id:
141 | time.sleep(1)
142 | try:
143 | if i != 2:
144 | response = await self.http.post('https://api.nyanheroes.com/Quest/setQuest', json={'Id': i})
145 | if not response.json()['result']:
146 | logger.error(f'{self.auth_token} 完成任务{i}失败')
147 | continue
148 | else:
149 | now = datetime.utcnow()
150 | iso_format_time = now.strftime("%Y-%m-%dT%H:%M:%S.%fZ")[:23] + 'Z'
151 | message = f'Please sign in to prove the ownership : {str(sol_wallet.public_key)} , Timestamp: {iso_format_time}'
152 | signature = sol_wallet.sign(message)[:64]
153 | signature = base58.b58encode(signature).decode('utf-8')
154 | data = {
155 | 'QuestId': 2,
156 | 'WalletAddress': str(sol_wallet.public_key),
157 | 'Signature':signature,
158 | 'Message':message,
159 | }
160 | response = await self.http.post('https://api.nyanheroes.com/Quest/verifyMessage', json=data)
161 | if not response.json()['result']:
162 | logger.error(f'{self.auth_token} 完成任务{i}失败')
163 | continue
164 | except Exception as e:
165 | logger.error(e)
166 | continue
167 | return True
168 | except Exception as e:
169 | logger.error(e)
170 | return False
171 |
172 |
173 | async def main(referral_code, file_name,task=False):
174 | global g_fail, g_success
175 | with open(file_name, 'r', encoding='UTF-8') as f, open('nyan-success.txt', 'a') as s, open('nyan-error.txt',
176 | 'a') as e: # eth----auth_token
177 | lines = f.readlines()
178 | for k, v in enumerate(lines):
179 | try:
180 | auth_token = v.strip()
181 | mini = Nyan(auth_token, referral_code)
182 | if await mini.twitter_login() and await mini.set_referral():
183 | sol_private = ''
184 | if task:
185 | sol_wallet = Keypair()
186 | sol_private = str(sol_wallet.private_key)
187 | await mini.compete_task(sol_wallet)
188 | g_success += 1
189 | logger.success(f'{auth_token} 成功')
190 | s.write(f'{auth_token}----{sol_private}\n')
191 | else:
192 | g_fail += 1
193 | logger.error(f'{auth_token} 失败')
194 | e.write(f'{auth_token}----{sol_private}\n')
195 | except Exception as ex:
196 | g_fail += 1
197 | logger.error(f'{auth_token} 失败')
198 | e.write(f'{auth_token}----{auth_token}\n')
199 | continue
200 |
201 |
202 | if __name__ == '__main__':
203 | rel_code = '' #替换为你的邀请码
204 | file_name = 'tw_token.txt'
205 | asyncio.run(main(rel_code, file_name,task=True))
206 |
--------------------------------------------------------------------------------