Python selenium实现全自动购买火车票

这个是实现结果,因为一天只能取消三次,所以最后一步点击确认被我注释了

在这里插入图片描述

1.首先实现使用selenium登陆12306

关于使用selenium实现12306登陆可以看我的另一篇文章
这里实现了使用selenium登陆12306,这次是基于上次的代码进行修改实现全自动购买车票的
实现全自动登陆12306链接

2.根据上面实现登陆后,实现购买火车票还需两步

这里只进行了二等座的查询和购票,想要买其他的自己也可以进行修改
1.进行车票的查询
这里面需要注意的是在输入目的地和起始地时需要先click一下文本框browser.find_element_by_id(‘fromStationText’).click()
不然输入的地址无效
还有将日期的只读属性去掉

def search_railway_ticket(fromstation,tostation,train_date):# 火车票页面查询urlsearch_url = 'https://kyfw.12306.cn/otn/leftTicket/init?linktypeid=dc'# 转到查询车次页面browser.get(search_url)time.sleep(2)#输入出发地WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.ID, 'fromStationText')))#先点击一下browser.find_element_by_id('fromStationText').click()browser.find_element_by_id('fromStationText').send_keys(fromstation)browser.find_element_by_id('fromStationText').send_keys(Keys.ENTER)time.sleep(1)WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.ID, 'toStationText')))#输入目的地browser.find_element_by_id('toStationText').click()browser.find_element_by_id('toStationText').send_keys(tostation)browser.find_element_by_id('toStationText').send_keys(Keys.ENTER)time.sleep(5)#将日期的只读属性去掉js = 'document.getElementById("train_date").removeAttribute("readonly")'browser.execute_script(js)#去掉原本的时间WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.ID, 'train_date')))browser.find_element_by_id("train_date").clear()#输入出发时间browser.find_element_by_id('train_date').send_keys(train_date)# 等待查询按钮是否可用WebDriverWait(browser, 1000).until(EC.element_to_be_clickable((By.ID, 'query_ticket')))searBtn = browser.find_element_by_id('query_ticket')searBtn.click()print('点击按钮')

2.购买火车票
在这个函数中需要注意的是最好把最后一步注释掉
browser.find_element_by_id(‘qr_submit_id’).click()
因为一天只能取消3次订单

def buy_ticket(fromstation,tostation,train_date,train_number,passenger):#查询火车票search_railway_ticket(fromstation,tostation,train_date)time.sleep(5)#获取每一个车次的信息tr_list = browser.find_elements_by_xpath('.//tbody[@id="queryLeftTable"]/tr[not(@datatran)]')for tr in tr_list:#获取车次号number = tr.find_element_by_class_name('number').textif number in  train_number:#获取是否还有票left_ticket = tr.find_element_by_xpath('./td[4]').textif left_ticket =='有'or left_ticket.isdigit:print(f'{number}还有票')#点击预订orderBtn = tr.find_element_by_class_name('btn72')orderBtn.click()time.sleep(5)#获取12306中乘客的信息passenger_list = browser.find_elements_by_xpath('//*[@id="normal_passenger_id"]/li')for li in passenger_list:name = li.find_element_by_xpath('./label').textprint(name)#配对12306人名if name == passenger:li.find_element_by_tag_name('input').click()#提交订单submit = browser.find_element_by_id('submitOrder_id')submit.click()WebDriverWait(browser, 1000).until(EC.element_to_be_clickable((By.ID, 'qr_submit_id')))#一天只能取消3次 所以最好把最后一步注释了browser.find_element_by_id('qr_submit_id').click()print('已经提交订单')break

下面是源代码

测试的时候可以把#click_captcha()这个点击验证码的去掉自己手动点击,这样就不用扣超级鹰的积分(有钱的话当我没说),留下了贫穷的泪水。

from selenium import webdriver
from selenium.webdriver import ActionChains
import time
from PIL import Image
import requests
from hashlib import md5
from selenium.webdriver import ChromeOptions
#验证码识别处理
from selenium.webdriver.common.keys import Keys
from selenium.webdriver.common.by import By
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.support import expected_conditions as ECclass Chaojiying_Client(object):def __init__(self, username, password, soft_id):self.username = usernamepassword =  password.encode('utf8')self.password = md5(password).hexdigest()self.soft_id = soft_idself.base_params = {'user': self.username,'pass2': self.password,'softid': self.soft_id,}self.headers = {'Connection': 'Keep-Alive','User-Agent': 'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 5.1; Trident/4.0)',}def PostPic(self, im, codetype):"""im: 图片字节codetype: 题目类型 参考 http://www.chaojiying.com/price.html"""params = {'codetype': codetype,}params.update(self.base_params)files = {'userfile': ('ccc.jpg', im)}r = requests.post('http://upload.chaojiying.net/Upload/Processing.php', data=params, files=files, headers=self.headers)return r.json()def ReportError(self, im_id):"""im_id:报错题目的图片ID"""params = {'id': im_id,}params.update(self.base_params)r = requests.post('http://upload.chaojiying.net/Upload/ReportError.php', data=params, headers=self.headers)return r.json()def login(username,password):# 填写账号密码browser.find_element_by_id('J-userName').send_keys(username)browser.find_element_by_id('J-password').send_keys(password)# 获取验证码get_captcha()# 填写验证码click_captcha()#点击登录time.sleep(4)browser.find_element_by_id('J-login').click()time.sleep(4)#滑动验证码slider()print('成功登陆')time.sleep(5)def slider():#滑动验证码WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.XPATH, '//*[@id="nc_1_n1z"]')))span = browser.find_element_by_xpath('//*[@id="nc_1_n1z"]')# 对div_tag进行滑动操作action = ActionChains(browser)# 点击长按指定的标签action.click_and_hold(span).perform()action.drag_and_drop_by_offset(span, 400, 0).perform()def click_captcha():# 获取验证码需要的为点击位置chaojiying = Chaojiying_Client('自己的用户名', '密码', '软件id')  # 用户中心>>软件ID 生成一个替换 96001im = open('./captcha.png', 'rb').read()  # 本地图片文件路径 来替换 a.jpg 有时WIN系统须要//location = chaojiying.PostPic(im, 9004)['pic_str']  # 1902 验证码类型  官方网站>>价格体系 3.4+版 print 后要加()print(chaojiying.PostPic(im, 9004))# 将位置进行分割成    [  [  ], [ ], [ ]  ]类型location_list = [i.split(',') for i in location.split('|')]for l in location_list:x = l[0]y = l[1]ActionChains(browser).move_to_element_with_offset(browser.find_element_by_class_name('login-pwd-code'), int(x),int(y)).click().perform()time.sleep(0.5)def get_captcha():# 获取网页的截图allscreen = browser.get_screenshot_as_file('allscreen.png')# 获取captchacaptcha = browser.find_element_by_class_name('login-pwd-code')# 获取captcha的左上角位置location = captcha.location# 获取图片大小size = captcha.size# 裁取captcharangle = (location['x'],location['y'],(location['x']+size['width']),(location['y']+size['height']))i = Image.open('./allscreen.png')captcha_img = './captcha.png'frame = i.crop(rangle)frame.save(captcha_img)def buy_ticket(fromstation,tostation,train_date,train_number,passenger):#查询火车票search_railway_ticket(fromstation,tostation,train_date)time.sleep(5)tr_list = browser.find_elements_by_xpath('.//tbody[@id="queryLeftTable"]/tr[not(@datatran)]')for tr in tr_list:number = tr.find_element_by_class_name('number').textif number in  train_number:left_ticket = tr.find_element_by_xpath('./td[4]').textif left_ticket =='有'or left_ticket.isdigit:print(f'{number}还有票')orderBtn = tr.find_element_by_class_name('btn72')orderBtn.click()time.sleep(5)passenger_list = browser.find_elements_by_xpath('//*[@id="normal_passenger_id"]/li')for li in passenger_list:name = li.find_element_by_xpath('./label').textif name == passenger:li.find_element_by_tag_name('input').click()submit = browser.find_element_by_id('submitOrder_id')submit.click()WebDriverWait(browser, 1000).until(EC.element_to_be_clickable((By.ID, 'qr_submit_id')))#一天只能取消3次 所以把最后一步注释了# browser.find_element_by_id('qr_submit_id').click()print('已经提交订单')breakdef search_railway_ticket(fromstation,tostation,train_date):# 火车票页面查询urlsearch_url = 'https://kyfw.12306.cn/otn/leftTicket/init?linktypeid=dc'# 转到查询车次页面browser.get(search_url)time.sleep(2)#输入出发地WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.ID, 'fromStationText')))#先点击一下browser.find_element_by_id('fromStationText').click()browser.find_element_by_id('fromStationText').send_keys(fromstation)browser.find_element_by_id('fromStationText').send_keys(Keys.ENTER)time.sleep(1)WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.ID, 'toStationText')))#输入目的地browser.find_element_by_id('toStationText').click()browser.find_element_by_id('toStationText').send_keys(tostation)browser.find_element_by_id('toStationText').send_keys(Keys.ENTER)time.sleep(5)#将日期的只读属性去掉js = 'document.getElementById("train_date").removeAttribute("readonly")'browser.execute_script(js)#去掉原本的时间WebDriverWait(browser, 1000).until(EC.presence_of_element_located((By.ID, 'train_date')))browser.find_element_by_id("train_date").clear()#输入出发时间browser.find_element_by_id('train_date').send_keys(train_date)# 等待查询按钮是否可用WebDriverWait(browser, 1000).until(EC.element_to_be_clickable((By.ID, 'query_ticket')))searBtn = browser.find_element_by_id('query_ticket')searBtn.click()print('点击按钮')if __name__ == '__main__':option = ChromeOptions()  # 实例化一个ChromeOptions对象option.add_experimental_option('excludeSwitches', ['enable-automation'])  # 以键值对的形式加入参数option.add_experimental_option('useAutomationExtension', False)browser = webdriver.Chrome(options=option)# 获取响应browser.get('https://kyfw.12306.cn/otn/resources/login.html')script = 'Object.defineProperty(navigator,"webdriver",{get:()=>undefined,});'browser.execute_script(script)browser.maximize_window()time.sleep(1)# 点击账号登陆browser.find_element_by_class_name('login-hd-account').click()#登陆12306的账号密码login('用户名','密码')time.sleep(4)#例buy_ticket('南昌','抚州北','2020-12-15','D2241','xx')buy_ticket('起始地','目的地','出发日期','车次','姓名')

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/1621667.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

【web测试】实战1:去哪儿网购买火车票|优化|po模式

【web测试】实战1:去哪儿网购买火车票|优化|po模式 测试用例设计1.项目计划2.测试用例 项目实战脚本基本代码优化代码重构base_function.pyqunaer_book.pytest_qunaer_book.pydata.xlsx po模式目录base.pyfunction.pybook_ticket_page.pybook_list_page.pybook_orde…

java购买火车票

题目要求:假设从A地到B地的火车票有硬座和硬卧,价格分别为100和190元。根据铁路部门规定,未成年人(18周岁以下)身高不足120cm免票,120(含)-150(不含)cm需半票…

Java购买火车票(初识并发)

初识并发(购买火车票) 购买火车票 发现问题:多个线程操作同一个资源的情况下,线程不安全,数据紊乱。 Code: public class TicketDemo_04 implements Runnable{private int ticketNumber 10; // 票数Overridepubli…

Spring注解之@validated的使用

使用步骤 1.引入依赖 <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-validation</artifactId> </dependency> 2.异常拦截类 /*** 全局异常处理*/ Slf…

电视卡众说纷纭(二):2007年度市面常见电视卡软硬件性能

在查找VISTA MCE插件开发的过程中看到很多的是跟电视卡硬件相关的资料。看到最多的名词就是软压卡、硬压卡。一个好的软件开发人员不只是要了解软件的开发&#xff0c;对硬件的设施也应该有相关的了解。要不然就成了闭塞的书呆子。所以我整理了我看到的关于电视卡比较好帖子和文…

dasBlog-1.8.5223.1中文版

dasBlog-1.8.5223.1中文版 本版本的DasBlog是qihangnet基于dasBlog-1.8.5223.1原版做的本地化版本。安装提示&#xff1a;1、由于本系统是使用Asp.Net开发的&#xff0c;所以在安装前请确保您的服务器或者虚拟主机支持Asp.net&#xff1b;2、请确定您将要安装的目录&#xff0c…

关于Linux下ISE和vivado安装cable usb驱动的问题

由于先前安装Android Studio一直不成功&#xff0c;一气之下&#xff0c;本人重装了系统&#xff0c;导致之前装的驱动什么的都没有了&#xff0c;这时再安装vivado&#xff0c;检测不到驱动&#xff0c;这里介绍怎么安装cable usb的驱动&#xff0c;供参考。 要安装这个驱动&a…

如何用计算机观看电视节目,如何将计算机显示器变成电视以观看节目

2006-11-16 如何在计算机上观看电视&#xff1f;我喜欢NBA&#xff0c;我喜欢 对于初次接触电视卡的用户&#xff0c;安装和接收电视确实不是一件容易的事。为此&#xff0c;我们将以Winfast TV2000电视卡为例来说明此应用程序的具体步骤。实际上&#xff0c;不同品牌的电视卡使…

ElasticSearch(一)数据类型

ElasticSearch&#xff08;一&#xff09;数据类型 1.简述 Es数据类型分为基础数据类型和复杂类型数据&#xff0c;掌握ES数据类型才能进一步使用ES检索数据内容。 <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot…

无人驾驶领域的软件测试该如何开展?

无人驾驶汽车使用自主决策和控制系统&#xff0c;这种系统通常由多个软件和硬件组件组成。软件测试是必要的&#xff0c;因为它可以确保无人驾驶汽车的软件系统达到高度可靠性和安全性&#xff0c;以及提高无人驾驶汽车的性能和可靠性。 因此无人驾驶汽车是一定要进行严格的软件…

手写数字识别之网络结构

目录 手写数字识别之网络结构 数据处理 经典的全连接神经网络 卷积神经网络 手写数字识别之网络结构 无论是牛顿第二定律任务&#xff0c;还是房价预测任务&#xff0c;输入特征和输出预测值之间的关系均可以使用“直线”刻画&#xff08;使用线性方程来表达&#xff09…

[牛客复盘] 牛客周赛 Round 9 20230827

[牛客复盘] 牛客周赛 Round 9 20230827 总结小美的外卖订单编号1. 题目描述2. 思路分析3. 代码实现 小美的加法1. 题目描述2. 思路分析3. 代码实现 小美的01串翻转1. 题目描述2. 思路分析3. 代码实现 小美的数组操作1. 题目描述2. 思路分析3. 代码实现 六、参考链接 总结 又是…

数据分析基础-数据可视化学习笔记03-可视化的符号与表示-图形符号学

概念 图型符号学&#xff08;Cartographic Symbolization&#xff09;是地图学领域中的一个重要概念&#xff0c;涉及到如何使用不同的符号、颜色、图案和标记来在地图上表示地理信息和数据。图型符号学旨在传达地理信息&#xff0c;使得地图能够清晰、有效地传达各种空间数据…

DDT数据驱动测试

简单介绍 ​ DDT&#xff08;Date Driver Test&#xff09;&#xff0c;所谓数据驱动测试&#xff0c;简单来说就是由数据的改变从而驱动自动化测试的执行&#xff0c;最终引起测试结果的改变。通过使用数据驱动测试的方法&#xff0c;可以在需要验证多组数据测试场景中&#…

【80天学习完《深入理解计算机系统》】第十一天 3.5 过程(函数调用)

专注 效率 记忆 预习 笔记 复习 做题 欢迎观看我的博客&#xff0c;如有问题交流&#xff0c;欢迎评论区留言&#xff0c;一定尽快回复&#xff01;&#xff08;大家可以去看我的专栏&#xff0c;是所有文章的目录&#xff09;   文章字体风格&#xff1a; 红色文字表示&#…

模板(二)

目录 非类型模板参数 引入 分类 使用typename的特殊情况 注意点 模板特化 引入 介绍 函数模板特化 使用 ​编辑 优点 类模板特化 全特化 偏特化 部分特化 特殊的特化 使用 分离编译 介绍 问题代码示例 代码 说明 预处理 编译 链接 类模板实例化…

期货量化软件:衡量指标信息

机器学习依靠数据训练来学习市场的一般行为&#xff0c;最终做出相当准确的预测。 所选学习算法必须遍历精心挑选的样本&#xff0c;以便提取有意义的信息。 许多人未能成功应用这些精密工具的原因是&#xff0c;大多数有意义的信息都隐藏在嘈杂的数据当中。 对于许多策略开发人…

期货量化交易软软件:怎样开发可以获利的交易策略

简介 通过技术分析开发成功交易策略的过程可以分为以下几步: ​ 编辑 添加图片注释&#xff0c;不超过 140 字&#xff08;可选&#xff09; 在某个资产价格图表窗口上附加几个技术指标, 并识别出其中信号指标与市场关联的模式. 把上一步相关性分析取得的数据进行公式化. …

免费期货量化交易软件:种群优化算法引力搜索算法(GSA)

1. 概述 ​​​​​​​ 引力搜索算法&#xff08;GSA&#xff09;是由 E. Rashedi 提出的&#xff0c;用于解决优化问题&#xff0c;特别是非线性问题&#xff0c;它遵循牛顿的万有引力定律原理。 在所提议的算法中&#xff0c;粒子被视为物体&#xff0c;并在考虑其质量的情…

免费_期货量化软件:神经网络变得轻松-网络训练和测试

1. 定义问题 在开始创建智能交易系统之前&#xff0c;必须定义将为新神经网络设定的目标。 当然&#xff0c;金融市场上所有智能交易系统的共同目标是获利。 然而&#xff0c;此目的太笼统宽泛。 赫兹期货量化软件需要为神经网络指定更具体的任务。 甚至&#xff0c;我们需要了…