Google重新发明了搜索, Facebook重新发明了社交, Apple重新发明了手机, Amazon重新发明了书籍...天朝重新发明了局域网

Python + selenium 爬取淘宝中硬盘信息

Python 2017-04-07 浏览量: 1711 字数统计: 1043 最后更新: 2018-10-27 15:57

文章目录[显示]

Python + selenium 爬取淘宝中 硬盘信息

selenium是什么?

用于网站应用的测试自动化,支持多种浏览器,其中包括Chrome,Firefox ,IE(6,7,8),Opera,Safari ,支持多种开发语言,Java,Python,Ruby,C等等

下面就开始用 Python+selenium+chrome爬取淘宝的硬盘信息


安装

pip install selenium

获取页面

首先获取淘宝的页面,最常见的是调用 “get” 方法

webdriver 相当于浏览器的一个驱动,先要声明一个浏览器的驱动

from selenium import webdriver

chrome_driver = "D:\\chromedriver"
browser = webdriver.Chrome()

但是 webdriver 可能不会等待页面的加载,也就是说 webdriver 可能在页面加载完毕前就返回控制,也许是开始加载之前。为了确保健壮性,你需要使用 Explicit and Implicit Waits 等到页面元素可用。


等待

Selenium Webdriver 支持两种类型的等待,explicit & implicit

explicit wait 显式等待 使 WebDriver 等待某个条件进一步发生之前执行

implicit wait 隐式等待 使 WebDriver 调查 DOM等待一定的时间试图找到一个元素。

Explicit Waits

等待10秒钟后在抛出 TimeoutException ,WebDriverWait 默认调用 ExpectedCondition 每500毫秒 , 直到它成功返回

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

chrome_driver = "D:\\chromedriver"
driver = webdriver.Chrome()
driver.get("http://somedomain/url_that_delays_loading")
try:
    element = WebDriverWait(driver, 10).until(
        EC.presence_of_element_located((By.ID, "myDynamicElement"))
    )
finally:
    driver.quit()

Python 提供了 自动化 绑定提供了一些convienence 方法,所以你不需要代码创建expected_condition 类或创建自己的实用程序包。

from selenium.webdriver.support import expected_conditions as EC

wait = WebDriverWait(driver, 10)
element = wait.until(EC.element_to_be_clickable((By.ID, 'someid')))

Implicit Waits

from selenium import webdriver

driver = webdriver.Firefox()
driver.implicitly_wait(10) # seconds
driver.get("http://somedomain/url_that_delays_loading")
myDynamicElement = driver.find_element_by_id("myDynamicElement")

查找 Web 元素

其中 webdriver 的实例可以查找Web元素,查找的 方法使用了一个定位器或者一个叫 “By” 的查询对象。支持的元素主要有 By id,By Class Name,By Tag Name,By Name,By Link Text,By Partial Link Text,By CSS,By XPATH

By id

当你知道一个元素的 id 属性你就可以通过 id 元素获取,这是最高效也是首选的方法,第一个元素的 id 属性值将返回匹配的位置。如果没有匹配元素id属性,将会引发一个NoSuchElementException 异常

HTML

<html>
 <body>
  <form id="loginForm">
   <input name="username" type="text" />
   <input name="password" type="password" />
   <input name="continue" type="submit" value="Login" />
  </form>
 </body>
<html>

Python

from selenium.webdriver.common.by import By
login_form = driver.find_element_by_id('loginForm')

by Name

查找 name 属性匹配的表单元素,同样如果没有匹配元素将会引发一个NoSuchElementException 异常

HTML

<html>
 <body>
  <form id="loginForm">
   <input name="username" type="text" />
   <input name="password" type="password" />
   <input name="continue" type="submit" value="Login" />
  </form>
 </body>
<html>

Python

from selenium.webdriver.common.by import By
username = driver.find_element_by_name('username')
password = driver.find_element_by_name('password')

By XPath

首先 XPath 是什么?

XPath即为XML路径语言,它是一种用来确定XML(标准通用标记语言的子集)文档中某部分位置的语言。XPath基于XML的树状结构,提供在数据结构树中找寻节点的能力。起初 XPath 的提出的初衷是将其作为一个通用的、介于XPointer与XSLT间的语法模型。但是 XPath 很快的被开发者采用来当作小型查询语言。

当我们没有合适的 id 或者name 去匹配元素,于是 XPath 就派上用场了,可以使用XPath在绝对定位元素(不建议)。

HTML

<html>
 <body>
  <form id="loginForm">
   <input name="username" type="text" />
   <input name="password" type="password" />
   <input name="continue" type="submit" value="Login" />
   <input name="continue" type="button" value="Clear" />
  </form>
</body>
<html>

Python

from selenium.webdriver.common.by import By
login_form = driver.find_element_by_xpath("/html/body/form[1]")
login_form = driver.find_element_by_xpath("//form[1]")
login_form = driver.find_element_by_xpath("//form[@id='loginForm']")

username = driver.find_element_by_xpath("//form[input/@name='username']")
username = driver.find_element_by_xpath("//form[@id='loginForm']/input[1]")
username = driver.find_element_by_xpath("//input[@name='username']")

by CSS Selectors

第一个元素将返回匹配的CSS选择器,如果没有元素匹配,将会引发一个 NoSuchElementException   异常

但是使用 css 选择器不能保证在所有浏览器里都表现一样,有些在某些浏览器里工作良好,在另一些浏览器里可能无法工作。

浏览器中检查选中搜索按钮,右键copy-->copy selector,然后到代码中粘贴

HTML

<html>
 <body>
  <p class="content">Site content goes here.</p>
</body>
<html>

Python

from selenium.webdriver.common.by import By
content = driver.find_element_by_css_selector('p.content')

其他的元素就不一一介绍了,因为官网上都有

地址请见

http://selenium-python.readthedocs.io


抓取

EC.element_to_be_clickable((By.CSS_SELECTOR, '#J_TSearchForm > div.search-button > button')))

好,模拟在淘宝首页输入硬盘,捕获TimeoutException异常

# -*- coding: UTF-8 -*-

from selenium import webdriver
from selenium.common.exceptions import TimeoutException
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC

chrome_driver = "D:\\chromedriver"
browser = webdriver.Chrome(chrome_driver)


def search():
    try:
        browser.get('https://www.taobao.com')
        # 判断是否加载成功 设置等待时间
        input_data = WebDriverWait(browser, 5).until(
            EC.presence_of_element_located((By.CSS_SELECTOR, '#q'))
        )
        # 按钮选择器
        submit_data = WebDriverWait(browser, 5).until(
            EC.element_to_be_clickable((By.CSS_SELECTOR, '#J_TSearchForm > div.search-button > button')))
        # 调用send_keys
        input_data.send_keys(u'硬盘')
        # click点击按钮提交
        submit_data.click()
    except TimeoutException:
       return search()

def main():
    search()


if __name__ == '__main__':
    main()

你会看到弹出Chrome 浏览器跳转到淘宝首页然后自动输入硬盘点击搜索按钮


模拟翻页

返回总页数,页数的显示是共 100 页,的形式,所以需要取出数字100

用正则去除数字

total_pages_num = re.compile('(\d+)').total_pages_data.group(1)
print(total_pages_num)

100
  • 同样处理TimeoutException异常,重新执行请求
  • 判断翻页是否正确,需要判断输入框里面是不是想要输入的数字,所以需要判断当前选择的页码是不是输入的页码,注意判断当前页码是字符串类型,所以需要把page_number转换成str
  • 输入页码的时候需要先清除输入框里面的数字,然后在输入页码,所以需要先clear()send_keys()
def next_page(page_number):
    try:
        input_data = WebDriverWait(browser, 10).until(
            EC.presence_of_element_located((By.CSS_SELECTOR, '#mainsrp-pager > div > div > div > div.form > input'))
        )
        submit_data = WebDriverWait(browser, 10).until(EC.element_to_be_clickable(
            (By.CSS_SELECTOR, '#mainsrp-pager > div > div > div > div.form > span.btn.J_Submit')))
        # 先清除输入框里面的数字,然后在输入页码
        input_data.clear()
        input_data.send_keys(page_number)
        # 点击确定翻页
        submit_data.click()
        '''
        判断翻页是否正确,需要判断输入框里面是不是想要输入的数字,所以需要判断当前选择的页码是不是输入的页码,
        注意判断当前页码是字符串类型,所以需要把page_number转换成str
        '''
        WebDriverWait(browser, 10).until(EC.text_to_be_present_in_element(
            (By.CSS_SELECTOR, '#mainsrp-pager > div > div > div > ul > li.item.active > span'), str(page_number)))
    except TimeoutException:
        return next_page(page_number)

# 调用从第二页翻到第九页
for i in range(2, 10):
    next_page(i)

下次在写解析商品的信息


参考链接:
http://selenium-python.readthedocs.io/
https://www.guru99.com/selenium-python.html

小蜗牛 说:
Freedom is the source from which all meaning and all values spring .


文章版权归 原文作者所有丨本站默认采用CC-BY-NC-SA 4.0协议进行授权| 转载必须包含本声明,并以超链接形式注明原文作者和本文原始地址: https://www.tougetu.com/2017/04/python-selenium-1.html

还不快抢沙发

添加新评论

代码 Pastebin Gist 加粗 删除线 斜体 链接 签到