使用selenium和chromedriver实现12306抢票
前段时间由于12306增加了候补功能,暴力去抢票意义不是很大,但在车票刚放出时前几分钟运行还是有些用处的,姑且就当成一个实验吧。
该程序需要刚开始去扫码登录,如果账号密码肯定需要验证码就比较麻烦了,所以一开始扫码登录,后续就交给程序跑就好了
from selenium import webdriver
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import Select
from selenium.common.exceptions import NoSuchElementException,ElementNotVisibleException
import csv# 为什么需要把driver放在外面?
# 因为如果放在里面,那么driver将会随着对象的销毁而被销毁
# 而我们的TrainSpider的对象是放在main函数中执行的,
# 只要main函数运行完成后,里面所有的变量都不会被销毁,
# 也就说spider也会被销毁,那么spider里面的driver也会被销毁。
driver = webdriver.Chrome(executable_path="D:\ProgramApp\chromedriver\chromedriver73.exe")# 9:商务座,M:一等座,O:二等座,3:硬卧,4:软卧,1:硬座class TrainSpider(object):login_url = "https://kyfw.12306.cn/otn/resources/login.html"personal_url = "https://kyfw.12306.cn/otn/view/index.html"left_ticket_url = "https://kyfw.12306.cn/otn/leftTicket/init?linktypeid=dc"confirm_passenger_url = "https://kyfw.12306.cn/otn/confirmPassenger/initDc"def __init__(self,from_station,to_station,train_date,trains,passengers):""":param from_station: 起始站:param to_station: 目的站:param train_date: 出发日期:param trains: 需要购买的车次。{"G529":["M","O"],"G403":["M","O"]}:param passengers: 乘客的姓名,需要为一个列表"""self.from_station = from_stationself.to_station = to_stationself.train_date = train_dateself.trains = trainsself.passengers = passengersself.selected_number = Noneself.selected_seat = None# 初始化站点所对应的代号self.station_codes = {}self.init_station_code()def init_station_code(self):with open("stations.csv", 'r', encoding='utf-8') as fp:reader = csv.DictReader(fp)for line in reader:name = line["name"]code = line['code']self.station_codes[name] = codedef login(self):driver.get(self.login_url)# 等待url是否变成个人中心的url,来判断是否登录成功WebDriverWait(driver,1000).until(EC.url_contains(self.personal_url))print("登录成功!")def search_left_ticket(self):driver.get(self.left_ticket_url)# 起始站的代号设置from_station_input = driver.find_element_by_id("fromStation")from_station_code = self.station_codes[self.from_station]driver.execute_script("arguments[0].value='%s'"%from_station_code,from_station_input)# 终点站的代号设置to_station_input = driver.find_element_by_id("toStation")to_station_code = self.station_codes[self.to_station]driver.execute_script("arguments[0].value='%s'" % to_station_code, to_station_input)# 时间设置train_date_input = driver.find_element_by_id("train_date")driver.execute_script("arguments[0].value='%s'" % self.train_date, train_date_input)# 执行查询操作search_btn = driver.find_element_by_id("query_ticket")search_btn.click()# 解析车次信息WebDriverWait(driver,1000).until(EC.presence_of_element_located((By.XPATH,"//tbody[@id='queryLeftTable']/tr")))train_trs = driver.find_elements_by_xpath("//tbody[@id='queryLeftTable']/tr[not(@datatran)]")is_searched = Falsewhile True:for train_tr in train_trs:infos = train_tr.text.replace("\n", " ").split(" ")number = infos[0]if number in self.trains:seat_types = self.trains[number]for seat_type in seat_types:if seat_type == "O":# 二等座count = infos[9]if count.isdigit() or count == '有':is_searched = Truebreakelif seat_type == 'M':# 一等座count = infos[8]if count.isdigit() or count == '有':is_searched = Truebreakif is_searched:self.selected_number = numberorder_btn = train_tr.find_element_by_xpath(".//a[@class='btn72']")order_btn.click()returndef confirm_passengers(self):WebDriverWait(driver,1000).until(EC.url_contains(self.confirm_passenger_url))# 先等待一下乘客标签显示出来了WebDriverWait(driver,1000).until(EC.presence_of_element_located((By.XPATH,"//ul[@id='normal_passenger_id']/li/label")))# 确认需要购买车票的乘客passenger_labels = driver.find_elements_by_xpath("//ul[@id='normal_passenger_id']/li/label")for passenger_label in passenger_labels:name = passenger_label.textif name in self.passengers:passenger_label.click()# 确认需要购买的席位信息seat_select = Select(driver.find_element_by_id("seatType_1"))seat_types = self.trains[self.selected_number]for seat_type in seat_types:try:self.selected_seat = seat_typeseat_select.select_by_value(seat_type)except NoSuchElementException:continueelse:break# 等待提交订单按钮可以被点击WebDriverWait(driver,1000).until(EC.element_to_be_clickable((By.ID,"submitOrder_id")))submit_btn = driver.find_element_by_id("submitOrder_id")submit_btn.click()# 判断模态对话框出现并且确认按钮可以点击了WebDriverWait(driver,1000).until(EC.presence_of_element_located((By.CLASS_NAME,"dhtmlx_window_active")))WebDriverWait(driver,1000).until(EC.element_to_be_clickable((By.ID,"qr_submit_id")))submit_btn = driver.find_element_by_id("qr_submit_id")while submit_btn:try:submit_btn.click()submit_btn = driver.find_element_by_id("qr_submit_id")except ElementNotVisibleException:breakprint("恭喜!%s车次%s抢票成功!"%(self.selected_number,self.selected_seat))def run(self):# 1. 登录self.login()# 2. 车次余票查询self.search_left_ticket()# 3. 确认乘客和车次信息self.confirm_passengers()def main():from_station = input("请输入出发地:")to_station = input("请输入目的地:")spider = TrainSpider(from_station,to_station,"2020-08-01",{"G529":["O","M"],"G111":["M"]},['杨靖智'])spider.run()if __name__ == '__main__':main()
使用selenium和chromedriver实现12306抢票相关推荐
- python实战 selenium+chrome玩转12306抢票
文章目录 一.目标网站分析 1.1购票流程逐步分析 1.2网站细节分析 1.2.1 输入出发地和目标地的注意点 1.2.2 跳转页面的时候要加入显示等待 1.2.3 被淘汰的语法应该被替换掉 二.代码 ...
- 12306 抢票 python + selenium + chrome (二) 基础准备的软件和材料
我使用的 vmware 14 + ubuntu 16 + PyCharm 开发环境 12306抢票 python+selenium+chrome 实现一 12306抢票 python+selen ...
- python3+selenium实现12306抢票脚本
文章目录 一. 环境配置 windows环境 mac.linux环境 二. 实现思路及代码 1. 查询票数 2. 登录 关于自动登录 3. 提交订单 4. 邮件提醒 5. 短信提醒 三.总结与分析 一 ...
- python+selenium实现12306抢票
python+selenium实现12306抢票 一.准备工作 1.要先下载相关的包,selenium.interval.最好使用国内清华源 pip install (which package) - ...
- python编程实践(3):python+selenium实现12306抢票脚本
又到了一年一度的春运时节,抢个票? 1.设计思路 如果我们要买一张火车票,我们会怎么做?打开12306,登陆,输入出发地和目的地,选择出行日期,然后点击查询,有余票的话就下单购买,没有票就点刷新或者等 ...
- Python selenium+pyautogui写的一个12306抢票
用selenium+pyautogui写的一个12306抢票 `` 最近处于找工作阶段,在家里闲着无聊,写了一个12306的抢票,还很简陋,也是第一次写文发帖,大佬勿喷. 首先导入模块部分.有些外部库 ...
- 爬虫实战篇---12306抢票爬虫
12306抢票爬虫 先直接上一下效果图吧: 图片上信息是抢票成功后的界面 1.技术路线 selenium + chromedriver 2.思路分析 (1).模拟浏览器登录抢票界面,手动进行登录 (2 ...
- python抢票web端_python+Splinter实现12306抢票功能
本文实例为大家分享了python实现12306抢票功能的具体代码,供大家参考,具体内容如下 源码记录如下: #!/usr/bin/env python # _*_ coding:utf-8 _*_ # ...
- 通过python实现12306抢票
铁路12306抢票系统 #!/usr/bin/env python # -*- coding: utf-8 -*- """ 通过splinter刷12306火车票 进 ...
- python爬虫抢火车票_如何用python写一个简单的12306抢票软件|python 爬火车票 教程...
python 如果抓取验证码图片 类似12306的登录验证码图片 这个以前做次.最大的麻烦是码的识别算法的识别率太低.12306那种网站登陆错3次就限制你20分钟.所以除非你有33%以上的识别率否则不 ...
最新文章
- thinkphp5的目录结构和命名规范
- composer 更新国内镜像地址
- Apollo后台配置:添加部门
- Java 8 Lambda演练
- Ubuntu开发环境配置--- 安装chrome浏览器
- Vijos P1786 质因数分解【质因数分解】
- sublime3中文乱码解决包ConvertToUTF8.zip
- 介绍下Javascript原型和原型链的特点?
- HashSet、TreeSet、LinkedHashSet的区别
- 开源微信小程序源码+小程序游戏代码附搭建框架教程
- 信息安全管理体系(ISMS)
- wordpress设置首页为特定页
- 创建一个新用户身份为计算机管理员,以Guest账户身份创建一个管理员
- python将字典按行或按列写入csv文件
- RL(Chapter 3): Finite Markov Decision Processes (有限马尔可夫决策过程)
- Arcgis使用教程(十)ARCGIS地图制图之经纬网格添加
- greenplum数据库的使用
- Android设备唯一标识符ID
- Mysql字段类型转换
- JQuery DataGrid 中文文档
热门文章
- 动态拨号主机多IP随机分配拨号自动分配
- Zabbix5.0监控CenterOS(RPM版)
- 【已解决】更新到MacOS Catalina 10.15后,VMware Fusion 虚拟机黑屏以及无法添加辅助功能的问题
- MacOS获取辅助功能权限控制鼠标点击事件
- 小程序中 icon 颜色自定义解决方案
- 七夕表白攻略:教你用自己的专业说情话,成功率100%,我只能帮你们到这里了啊~(程序员系列)
- 内容公链Contentos首席科学家不建议刚毕业的年轻人直接从事区块链开发
- 3D迷宫(DirextX9)
- 转载 测试开发岗--高频知识整理
- 爬虫入门 手写一个Java爬虫