├── README.md └── main.py /README.md: -------------------------------------------------------------------------------- 1 | # autobooking_py 2 | 3 | 1. 在你的电脑上安装 python3和requests包 4 | 5 | 2. 使用curl转python网站把网络curl转成python代码 6 | 7 | https://curlconvert.trumanwl.com/python 8 | 9 | 3. 配置你的Email预定成功之后发送Email给你 10 | 11 | 4. 执行python代码。 12 | 13 | 文字教程:https://leftpocket.cn/post/script/py_auto/ 14 | 15 | 视频教程:https://www.youtube.com/watch?v=0cPZ2Udz0_o 16 | 17 | -------------------------------------------------------------------------------- /main.py: -------------------------------------------------------------------------------- 1 | import requests, json, time 2 | import smtplib 3 | from email.mime.text import MIMEText 4 | from email.header import Header 5 | 6 | class Book: 7 | def __init__(self) -> None: 8 | '''headers和cookies从 https://curlconvert.trumanwl.com/python 工具转换''' 9 | self.cookies = { 10 | '_ga': 'GA1.2.1721389846.1649773321', 11 | 'token': 'Bearer%20eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJCQkRDIiwiTlJJQyI6IlM4OTU1OTYzRCIsImV4cCI6MTY3Mzk3MTY2Nn0.-zoev2Cv5rMM7ZTkOh1o5x-0SmSxv6i4SIz-l8YXtOI', 12 | } 13 | 14 | self.headers = { 15 | 'Accept': 'application/json, text/plain, */*', 16 | 'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8', 17 | 'Authorization': 'Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJCQkRDIiwiTlJJQyI6IlM4OTU1OTYzRCIsImV4cCI6MTY3Mzk3MTY2Nn0.-zoev2Cv5rMM7ZTkOh1o5x-0SmSxv6i4SIz-l8YXtOI', 18 | 'Connection': 'keep-alive', 19 | 'Content-Type': 'application/json;charset=UTF-8', 20 | # Requests sorts cookies= alphabetically 21 | # 'Cookie': '_ga=GA1.2.1721389846.1649773321; bbdc-token=Bearer%20eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJCQkRDIiwiTlJJQyI6IlM4OTU1OTYzRCIsImV4cCI6MTY3Mzk3MTY2Nn0.-zoev2Cv5rMM7ZTkOh1o5x-0SmSxv6i4SIz-l8YXtOI', 22 | 'JSESSIONID': 'Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJBQ0NfSUQiOiI5ODY4NDQiLCJpc3MiOiJCQkRDIiwiTlJJQyI6IlM4OTU1OTYzRCIsImV4cCI6MTMwNTIyOTA0MDg2fQ.o46RgxiaXsIW9tW_CCPxIBXPFU-h7I-3KUDpu2F1y98', 23 | 'Origin': 'https://booking.abc.sg', 24 | 'Referer': 'https://booking.abc.sg/', 25 | 'Sec-Fetch-Dest': 'empty', 26 | 'Sec-Fetch-Mode': 'cors', 27 | 'Sec-Fetch-Site': 'same-origin', 28 | 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36', 29 | 'sec-ch-ua': '"Not_A Brand";v="99", "Google Chrome";v="109", "Chromium";v="109"', 30 | 'sec-ch-ua-mobile': '?0', 31 | 'sec-ch-ua-platform': '"macOS"', 32 | } 33 | 34 | def query(self): 35 | '''查询接口''' 36 | json_data = { 37 | 'subStageSubNo': None, 38 | 'insInstructorId': '', 39 | } 40 | 41 | response = requests.post('https://booking.abc.sg/abc-back-service/api/booking/c3practical/listC3PracticalSlotReleased', cookies=self.cookies, headers=self.headers, json=json_data) 42 | return response 43 | 44 | def book(self, slotList): 45 | '''预订接口''' 46 | json_data = { 47 | 'courseType': '123', 48 | 'insInstructorId': '', 49 | 'subVehicleType': None, 50 | 'slotIdList': slotList, 51 | } 52 | response = requests.post('https://booking.abc.sg/abc-back-service/api/booking/c3practical/callBookC3PracticalSlot', cookies=self.cookies, headers=self.headers, json=json_data) 53 | return response 54 | 55 | def getSlotList(self, response): 56 | '''根据返回结果过滤你的条件''' 57 | slotList = [] 58 | 59 | if response == None or response.content == None: 60 | return False 61 | j = json.loads(response.content) 62 | 63 | if 'data' in j and 'releasedSlotListGroupByDay' in j['data'] and j['data']['releasedSlotListGroupByDay'] != None: 64 | for k, v in j['data']['releasedSlotListGroupByDay'].items(): 65 | if len(v) > 0 and v[0]['c3PsrFixGrpNo'] == "G6067": 66 | slotList.append(v[0]['slotId']) 67 | 68 | if len(slotList) == 0: 69 | return False 70 | 71 | return slotList 72 | else: 73 | print("no slot") 74 | return False 75 | 76 | def sendEmail(self): 77 | sender = '12345678@qq.com' # 你的发送方Email地址 78 | receivers = ['codingxiaoma@gmail.com'] # 你的接收方Email地址 79 | 80 | message = MIMEText('预约成功', 'plain', 'utf-8') 81 | message['From'] = Header("预约", 'utf-8') 82 | message['To'] = Header("预约", 'utf-8') 83 | 84 | subject = '预约成功' 85 | message['Subject'] = Header(subject, 'utf-8') 86 | 87 | 88 | try: 89 | smtpObj = smtplib.SMTP() 90 | smtpObj.connect('smtp.qq.com', 587) # SMTP邮件服务器 91 | smtpObj.login(sender,'jejkgpxxotttcacb') # 发送方的邮箱和密码/授权码,腾讯邮箱可以在账户设置里面开启POP3/SMTP服务器并得到一个授权码 92 | smtpObj.sendmail(sender, receivers, message.as_string()) 93 | print ("邮件发送成功") 94 | except smtplib.SMTPException: 95 | print ("Error: 无法发送邮件") 96 | 97 | if __name__ == "__main__": 98 | a = Book() 99 | 100 | while True: 101 | res = a.query() 102 | slotList = a.getSlotList(res) 103 | if slotList == False: 104 | print("no slot, try again") 105 | else: 106 | a.book(slotList) 107 | a.sendEmail() 108 | 109 | time.Sleep(5) --------------------------------------------------------------------------------