麦克表单自动填写提交(pyppeteer完美版)
用途:自动抢川农需要填写表单报名的活动,也可根据实际情况修改为其他用途,配合win10计划任务程序使用效果最佳(使用方法请自行百度)。
特色:
- 用js分析控件,填写更精确,并能处理一定的下拉框,单选框与复选框
- 采用pyppeteer,填写速度更快,省去了安装chromedrive的繁琐步骤
- 能够进行反爬虫(虽然麦克表单用不上)
注意事项:此程序用python编写,需要配置python及安装相应库(所需库见导入模块处),此版本采用pyppeteer模块,无需chromedriver,极大简化了环境的搭建,注意浏览器安装路径改为你的实际安装路径,个人信息填在字典里。如何安装python库请自行百度(实际直接pip install package name即可),pip换源可参考这篇文章:Linux和Windows的pip换源
# encoding=utf8
# 自动填写麦克表单,适用于全是单项填空的表单和简单下拉框,川农登记信息一般为此格式
# 导入所需模块
import time
import asyncio
from pyppeteer import launch
from pyppeteer_stealth import stealth # 反爬虫第三方库
from pyppeteer.errors import PageError # 异常处理
#import os
#from pyzbar import pyzbar
#from PIL import Image
# 识别二维码函数
def decode_qr_code(code_img_path):
if not os.path.exists(code_img_path):
raise FileExistsError(code_img_path)
# Here, set only recognize QR Code and ignore other type of code
return pyzbar.decode(Image.open(code_img_path), symbols=[pyzbar.ZBarSymbol.QRCODE])
async def main(url):
# launch方法会新建一个browser对象,然后赋值给browser
browser = await launch({
# 谷歌浏览器的安装路径
'executablePath': 'C:\\Program Files\\Google\\Chrome\\Application\\chrome.exe',
'headless': False,
# 设置Windows-size和Viewport大小来实现网页完整显示
'args': ['--no-sandbox', '--window-size=1366,850'],
'autoClose': False # 不自动关闭浏览器
})
# 调用 newPage 方法相当于浏览器中新建了一个选项卡,同时新建了一个Page对象
page = await browser.newPage()
await page.setViewport({'width': 1366, 'height': 768})
# 防止页面识别出脚本(反爬虫关键语句)
await stealth(page)
# 调用了Page对象的goto方法就相当于在浏览器中输入问卷的网址,浏览器跳转到了对应的页面进行加载
# 从二维码获取问卷链接
# results = decode_qr_code("s.jpg")
# url = results[0].data.decode("utf-8")
await page.goto(url)
# 需要填的信息从文件录入
# with open("./msg.txt", encoding="utf-8") as file:
# msg = [data.replace("\n", "") for data in file.readlines() if data != "\n"] # 过滤空行并去掉末尾的换行符
# file.close()
# n = len(msg) # 获取需要填写的问题数量
# 以下为录入常见个人信息,个人报名时使用,无需知晓表单具体内容;多人报名时使用上方方法从文件读入,此时需要提前知晓表单内容
msg = {
"姓名": "",
"名字": "",
"性别": "",
"校区": "",
"学号": "",
"班级": "",
"学院": "",
"专业": "",
"联系方式": "",
"手机": "",
"电话": "",
"QQ": "",
"qq": "",
"邮箱": ""
}
# 检查表单是否已开放,还没开放则一直刷新直到开放
while True:
elem = await page.querySelectorAll(".fbi_input")
if not elem:
await page.goto(url)
time.sleep(1.5)
else:
break
start = time.time()
print("开始时间:", time.ctime())
# 用js对所需填写的表单控件进行精确分析,避免了单选框,复选框,下拉框对程序的干扰。
temp = await page.evaluate(pageFunction='''() => {
temp = document.getElementsByClassName("fb_component");
var names = [];
for (var j = 0; j < temp.length; j++) {
i = temp[j].getAttribute("class");
if (i.indexOf("radio") < 0 && i.indexOf("checkbox") < 0 && i.indexOf("dropDown") < 0)
names.push(temp[j].getElementsByTagName("span")[0].textContent);
}
return names;
}''', force_expr=False) # force_expr=False 执行的是函数,True则执行的是语句
n = 0
print("开始自动填写麦克表单信息...")
for name in temp:
for key in msg.keys():
if key in name: # 匹配机制选择以自己的简洁描述去匹配主办方制作的表单描述,如用"姓名"去匹配"你的姓名"或"您的姓名",显然更实用
print(name, msg[key])
await elem[n].type(msg[key])
n += 1
# 处理选择框
choose = '''() => {
var choice = document.getElementsByTagName("span"); var select = document.getElementsByClassName("mg-dropTrigger");
// 将结果返回给python程序
result = [];
// 先点击下拉选择的框,弹出选项
for (var i=0; i<select.length; i++)
select[i].click();
for (var i=0; i<choice.length; i++) {
if (choice[i].innerHTML == "男") {
choice[i].click();
result.push("已选择性别为男");
}
if (choice[i].innerHTML == "是") {
choice[i].click();
result.push("已选择选项为是");
}
} return result;
}'''
result = await page.evaluate(pageFunction=choose, force_expr=False)
# 打印选择框js处理结果
if result:
for i in result:
print(i)
print("填写完毕,提交中...")
sub = "document.getElementsByClassName('fb_submitBtn')[0].click()"
await page.evaluate(sub)
end = time.time()
print("已自动提交!")
print("提交时间:", time.ctime())
print("用时:%.2fs" % (end - start))
if __name__ == "__main__":
url = "" # 活动链接
url = "http://d71ibjcuwhw0zpb2.mikecrm.com/txFEyv2" # 电脑版测试
# url = "https://www.wjx.top/vm/QGHo4eA.aspx" # 手机版测试
asyncio.get_event_loop().run_until_complete(main(url))
若有疑问,请在评论区留言。