python: 使用万能钥匙 Selenium 搞定一切登录

2019-05-21| |来自: 互联网

Selenium, 大名鼎鼎的Web自动化测试工具,可以跨越Linux、Windows、macOS等平台使用,支持Java、Python、C#、Ruby等多种语言编程,为Web系统自动化测试带来强大支持。通过WebDriver方便操作浏览器,这也给爬虫界带来十分的便利。它可以被称为爬虫登录的万能钥匙,可以横扫一切网站的登录。

如果说,完全用Python代码模拟登录是我们智力的体现,那么选择 Selenium 就是我们的智慧所在。没办法,用它就是一个字儿:倍儿爽!

1. Selenium 登录获取cookies的流程

利用这把万能钥匙的流程大致如下:

  1. 使用Selenium WebDriver 打开浏览器;
  2. 如果没有验证码,可以通过代码输入用户名和密码并点击登录按钮;如果需要人工输入变态的验证码,就让WebDriver sleep一定时间,等待人工输入完成;
  3. 登录后获取cookies,并保存到文件或数据库。

如果上述过程是不需要人工输入验证码的,可以使用 Headless Chrome ,它能在无桌面环境下运行,比如Linux 服务器上一般是没有安装桌面环境的。

获取cookies以后,我们可以继续用webdriver抓取数据页面,这适合于异步加载的页面的抓取;或者把cookies导入到requests的session,利用requests抓取数据页面,这适合于非异步加载的页面。

2. Selenium 登录的实现

按照上面的思路,我们实现两个登录的过程,一个需要验证码,一个不需要验证码。

不需要人工输入验证码的登录:

def login_auto(login_url, username, password,
username_xpath, password_xpath,
submit_xpath, cookies_file, browser=None):
if browser is None:
options = webdriver.ChromeOptions()
# chrome在系统PATH时,可以不指定 binary_location
# options.binary_location = ‘/usr/bin/google-chrome’
options.add_argument('headless')
options.add_argument('window-size=1200x600')
browser = webdriver.Chrome(chrome_options=options)
browser.maximize_window()
browser.get(login_url)
time.sleep(9) # 等登录加载完成
browser.find_element_by_xpath(username_xpath).send_keys(username)
browser.find_element_by_xpath(password_xpath).send_keys(password)
browser.find_element_by_xpath(submit_xpath).send_keys(Keys.ENTER)
time.sleep(9) # 等登录加载完成
cookies = browser.get_cookies()
print(cookies)
save_cookies(cookies, cookies_file)

这个login_auto()函数,使用了headless的chrome,最大化窗口的目的是让整个页面都显示出来,如果默认大小,微博登录页面就不显示登录输入框,自动填写用户名时会保存。

sleep的目的是等待加载登录页面完成,还是微博,它的登录跳转比较费时间,不能一下子加载完成,必须等待。

登录完成我们就可以得到cookies了。通过webdriver的get_cookies()得到的cookies是一个列表,每个元素是一个字典,包含了domain, expiry, name, value等等字段。

最后我们把得到的cookies保存为文件,这里用pickle直接序列化到硬盘,这个cookies就可以被爬虫使用抓取数据了。

需要人工输入验证码的登录

def login_manually(login_url, cookies_file, browser=None):
# 既然是手动,这里就不自动填写用户名和密码了
if browser is None:
browser = webdriver.Chrome()
browser.get(login_url)
time.sleep(30) # 给自己多了点时间输入用户名、密码、验证码
cookies = browser.get_cookies()
print(cookies)
save_cookies(cookies, cookies_file)

需要人工介入的登录,就是让程序自动打开一个浏览器,然后人工输入登录信息完成登录,最后程序保存cookies的过程。

这里可不能用headless的Chrome哦,不然你看不到浏览器窗口无法输入,哈哈哈~

当然,你也可以让程序自动填写用户名、密码,类似login_auto()那样实现,小猿们有兴趣的话可以添加这部分功能。

3. Selenium 登录后的cookies的使用

def load_to_browser(cookies_file, browser=None):
with open(cookies_file, 'rb') as f:
cookies = pickle.load(f)
if browser is None:
browser = webdriver.Chrome()
for cookie in cookies:
browser.add_cookie(cookie)
return browser

保存时用的是pickle序列化到硬盘,读取到内存时同样使用pickle, 把cookies放入WebDriver很简单,把cookies逐个用add_cookie()放入即可。

加载cookies到requests的session

requests的cookies是用RequestsCookieJar这个类管理的,它的结构和WebDriver 的cookies不太一样,它只需要name, value即可,所以加载到requests有些不同:

def load_to_requests(cookies_file, session=None):
with open(cookies_file, 'rb') as f:
cookies = pickle.load(f)
if session is None:
session = requests.Session()
for cookie in cookies:
session.cookies.set(cookie['name'], cookie['value'])

4. Selenium 登录实战: 微博、哔哩哔哩、知乎的登录

微博有时候是不需要输入验证码的,此时就可以自动化登录。幸运的是,我的账号在我机器上就不需要输入验证码,省的我费劲去找一个不需要验证码的网站(现如今真的很难找啊~)

好了,看代码:

login_url = 'https://weibo.com/'
username_xpath = '//input[@id="loginname"]'
password_xpath = '//input[@name="password"]'
submit_xpath = '//a[@action-type="btn_submit"]'
username = 'your-username'
password = 'your-password'
login_auto(login_url, username, password, username_xpath, password_xpath, submit_xpath, 'z-weibo.cookies')
```
而哔哩哔哩、知乎都需要手动解锁验证码,那我们就用人工介入的模式登录:
```python
login_url = 'https://passport.bilibili.com/login'
login_manually(login_url, 'z-bilibili.cookies')

借用login_manually()函数是不是非常的简单,同样的知乎的也很简单:

login_url = 'https://passport.bilibili.com/login'
login_manually(login_url, 'z-zhihu.cookies')

出乎意料的是,登录知乎出现了问题,报了一个错误:Missing argument grant_type。网上有人说是Chrome版本问题,降低版本后就可以了。


标签: cookies 登录 browser login WebDriver xpath 验证 输入 27 password
出处: https://www.toutiao.com/a6692893036520669699/

文明发言,请先登录

文明上网理性发言,请遵守国家法律法规。

最新评论

Hackbase Administrator

©2003- 黑基网 黑名单存档手机版网站地图免责条款法律声明隐私保护