51Testing软件测试论坛

 找回密码
 (注-册)加入51Testing

QQ登录

只需一步,快速开始

微信登录,快人一步

手机号码,快捷登录

查看: 1086|回复: 0
打印 上一主题 下一主题

[转贴] Selenium使用简单的方式抓取复杂的页面信息

[复制链接]
  • TA的每日心情
    无聊
    昨天 09:34
  • 签到天数: 1052 天

    连续签到: 2 天

    [LV.10]测试总司令

    跳转到指定楼层
    1#
    发表于 2022-3-7 11:00:32 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
     selenium简介
      网站复杂度增加,爬虫编写的方式也会随着增加。使用Selenium 可以通过简单的方式抓取复杂的网站页面,得到想要的信息。
      Selenium 是操作浏览器进行自动化,例如自动化访问网站,点击按钮,进行信息采集,对比直接使用bs4 抓取信息,Selenium的抓取速度是有很大缺陷,但是如果抓取页面不多,页面复杂时,使用Selenium是个不错的选择。
      本文将会使用Selenium 进行一些简单的抓取。
      Selenium 使用注意
      在使用 Selenium前需要安装 Selenium,使用pip命令,安装如下:
      pip install selenium


      安装完成 Selenium 还需要下载一个驱动。
      谷歌浏览器驱动:驱动版本需要对应浏览器版本,不同的浏览器使用对应不同版本的驱动。
      作者的环境说明如下:
      ·操作系统:Windows7 SP1 64
      · python 版本:3.7.7
      · 浏览器:谷歌浏览器
      · 浏览器版本: 80.0.3987 (64 位)
      下载好驱动后,必须把驱动给配置到系统环境,或者丢到你python的根目录下。
      正式开始
      首先在代码中引入 selenium
      from selenium import webdriver


      可能有些读者没有把驱动配置到环境中,接下来我们可以指定驱动的位置:
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')


      以上代码调用Chrome 方法并且配置驱动地址(??这里使用 executable_path 指定驱动地址??)为“F:\python\dr\chromedriver_win32\chromedriver.exe”,这时就可以指定了驱动位置,也可以不用配置到环境了。
      这时运行一下代码,查看是否会打开一个浏览器。

      这时将会成功打开谷歌浏览器。
      这时 ??driver?? 变量为浏览器对象,通过 ??driver?? 操作浏览器,使用??get??方法可以访问一个网址。这时我们可以访问 [url=]百度[/url]。代码如下:
      from selenium import webdriver
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')
      driver.get("http://baidu.com")



      成功打开百度搜索界面:

      例如我们想搜索爬虫,使用selenium实现自动搜索。首先需要了解的一个函数为 find_element_by_id,该函数可以通过id 找到界面元素。在html中,大部分有特殊作用的元素会赋予一个id,搜索时需要填写的是百度搜索关键字的文本框,将鼠标移动到文本框,对准文本框点击鼠标右键,点击检查可以查看元素。

      点击检查后将会出现一个源码窗口:

      其中input为文本框元素,id的值是 kw。
      这时得知了文本框的id 值为kw,可以使用 find_element_by_id 函数给予id值,找到元素对象,并且可以操作元素对象进行增删操作。由于 find_element_by_id 是浏览器对象的方法,使用浏览器对象调用,代码如下:
      input = driver.find_element_by_id('kw')


      这时还差向该对象输入要搜索的值。使用 send_keys 方法可以自动键入值,编写如下:
      input.send_keys("爬虫")


      其中input是刚刚获取的元素对象。这时运行代码查看效果:

      这时自动键入了要搜索的关键帧“爬虫”。接下来根据之前的步骤,应该找到 百度一下 按钮的id,随后点击即可。通过相同的流程,得到百度一下 按钮的html代码:
      <input type="submit" id="su" value="百度一下" class="bg s_btn">


      得到id为su,使用 find_element_by_id 得到元素对象:
      enter = driver.find_element_by_id('su')


      该元素调用click方法即可进行点击:
      enter.click()


      最终代码如下:
      from selenium import webdriver
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')
      driver.get("https://www.baidu.com/")
      input = driver.find_element_by_id('kw')
      input.send_keys("爬虫")
      enter = driver.find_element_by_id('su')
      enter.click()



      运行结果如下:

      信息获取
      能够进行自动打开了,下一步接下来需要做的就是获取搜索的信息。
      在这里需要介绍一个知识点 xpath,我们可以理解xpath就像 x,y坐标一样的东西,用于html或者说xml语言中的定位,表示一个位置。简单的使用并不需要去学习它如何编写,因为从浏览器中我们可以直接得到。
      如下图,我们右键搜索出来了信息第一个标题,点击检查后会出现源代码。在源代码中右键,选择Copy之后点击Copy XPath,这时我们就把当前这个元素的XPath获取了。

      获取到了XPath后,复制到文本框,查看是如下形式:
      //*[@id="3001"]/div[1]/h3/a


      在这里注意,理论上每一个页面的第一行结果都将会是该XPath,并不需要每一页都去获取,但也有情况不一致的时候,具体情况得具体分析。
      我们简单实用XPath不需要了解过多,接下来可以使用 ??find_element_by_xpath?? 获取到当前元素对象。
      res_element=driver.find_element_by_xpath('//*[@id="3001"]/div[1]/h3/a')


      获取到元素对象后,可以调用该元素对象的text属性获取到当前文本值:
      print(res_element.text)


      完整代码如下:
      from selenium import webdriver
      import time
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')
      driver.get("https://www.baidu.com/")
      input = driver.find_element_by_id('kw')
      input.send_keys("爬虫")
      enter = driver.find_element_by_id('su')
      enter.click()
      time.sleep(2)
      res_element=driver.find_element_by_xpath('//*[@id="3001"]/div[1]/h3/a')
      print(res_element.text)



      以上代码中 time.sleep(2) 是为了等待点击搜索后页面加载数据,不然会获取不到对象。
      结果如下:

      以上省略了浏览器自动打开并搜索内容的过程,直接查看了结果。
      那么我们每一页都获取第一个结果,这时只需要自动点击下一页后获取即可。
      首先得到下一页按钮的元素对象:

      复制XPath值为:
      //*[@id="page"]/div/a[10]


      则获取下一页对象并且点击跳转的代码为:
      nextbtn_element=driver.find_element_by_xpath('//*[@id="page"]/div/a[10]')
      nextbtn_element.click()



      运行后发现成功跳转到第二页,接下来可以继续获取搜索栏的第一个对象,可以使用循环实现这个过程,我们设定去搜索前10页的所有第一个结果值,这时所有代码可以写为:
      from selenium import webdriver
      import time
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')
      driver.get("https://www.baidu.com/")
      input = driver.find_element_by_id('kw')
      input.send_keys("爬虫")
      enter = driver.find_element_by_id('su')
      enter.click()
      time.sleep(2)
      for _ in range(10):
          res_element=driver.find_element_by_xpath('//*[@id="3001"]/div[1]/h3/a')
          print(res_element.text)
          nextbtn_element=driver.find_element_by_xpath('//*[@id="page"]/div/a[10]')
          nextbtn_element.click()
          time.sleep(2)



      for 循环最下面的停止2秒是为了点击下一页后数据进行加载的等待时间。
      运行后,结果发现报错:

      我们的12行为:
      res_element=driver.find_element_by_xpath('//*[@id="3001"]/div[1]/h3/a')


      那么在这里应该是 ??//*[@id="3001"]/div[1]/h3/a?? 定位错误,没有找到该定位的元素。我们查看第一页、第二页、第三页的第一条结果进行对比:
      第一页://*[@id="3001"]/div[1]/h3/a
      第二页://*[@id="11"]/h3/a
      第三页://*[@id="21"]/h3/a
      第四页://*[@id="31"]/h3/a
      第五页://*[@id="41"]/h3/a



      从以上数据得知,只有第一页的XPath 不同,其它的XPath都遵循从11-21-31-41 每一页加10的规律。
      并且发现下一页按钮的 XPath也发生了改变,变成了:
      //*[@id="page"]/div/a[11]


      完整代码如下:
      from selenium import webdriver
      import time
      #请求网页
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')
      driver.get("https://www.baidu.com/")
      #输入并且搜索
      input = driver.find_element_by_id('kw')
      input.send_keys("爬虫")
      enter = driver.find_element_by_id('su')
      enter.click()
      #等待2秒加载
      time.sleep(2)
      #获取第一个结果并且点击下一页
      res_element=driver.find_element_by_xpath('//*[@id="3001"]/div[1]/h3/a')
      print(res_element.text)
      nextbtn_element=driver.find_element_by_xpath('//*[@id="page"]/div/a[10]')
      nextbtn_element.click()
      time.sleep(2)
      #设置一个变量start
      start=1
      #循环点击下一页 并且获取第一条数据
      for _ in range(10):
          start+=10
          xpath_val=r'//*[@id="'+str(start)+r'"]/h3/a' #//*[@id="11"]/h3/a
          res_element=driver.find_element_by_xpath(xpath_val)
          print(res_element.text)
          nextbtn_element=driver.find_element_by_xpath('//*[@id="page"]/div/a[11]')#//*[@id="page"]/div/a[11] //*[@id="page"]/div/a[11]
          nextbtn_element.click()
          time.sleep(2)



      以上代码中:
      from selenium import webdriver
      import time
      #请求网页
      driver = webdriver.Chrome(executable_path=r'F:\python\dr\chromedriver_win32\chromedriver.exe')
      driver.get("https://www.baidu.com/")
      #输入并且搜索
      input = driver.find_element_by_id('kw')
      input.send_keys("爬虫")
      enter = driver.find_element_by_id('su')
      enter.click()
      #等待2秒加载
      time.sleep(2)
      #获取第一个结果并且点击下一页
      res_element=driver.find_element_by_xpath('//*[@id="3001"]/div[1]/h3/a')
      print(res_element.text)
      nextbtn_element=driver.find_element_by_xpath('//*[@id="page"]/div/a[10]')
      nextbtn_element.click()
      time.sleep(2)



      为之前的代码,新增循环为遍历下一页以及获取第一个结果:
      #设置一个变量start
      start=1
      #循环点击下一页 并且获取第一条数据
      for _ in range(10):
          start+=10
          xpath_val=r'//*[@id="'+str(start)+r'"]/h3/a' #//*[@id="11"]/h3/a
          res_element=driver.find_element_by_xpath(xpath_val)
          print(res_element.text)
          nextbtn_element=driver.find_element_by_xpath('//*[@id="page"]/div/a[11]')#//*[@id="page"]/div/a[11] //*[@id="page"]/div/a[11]
          nextbtn_element.click()
          time.sleep(2)



      首先设置一个start,因为第二页是 XPath 中变化的值为11-21-31…,设置一个变量为1,每次加10即可,所以在循环中,第一句为:
      start+=10


      由于XPath的值其它字符串没变化,所以整一条XPath语句可以写为:
      xpath_val=r'//*[@id="'+str(start)+r'"]/h3/a'


      之后传入xpath函数获取元素即可:
      res_element=driver.find_element_by_xpath(xpath_val)


      接下来的语句都没有太大变化,只有按钮的XPath有变化,所以更改了XPath。其它代码均和之前的相似。最终运行结果如下:

      由于有一些其它信息所以打码了,这就是一个简单的selenium爬虫编写方式

    分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
    收藏收藏
    回复

    使用道具 举报

    本版积分规则

    关闭

    站长推荐上一条 /1 下一条

    小黑屋|手机版|Archiver|51Testing软件测试网 ( 沪ICP备05003035号 关于我们

    GMT+8, 2024-11-28 03:52 , Processed in 0.064033 second(s), 23 queries .

    Powered by Discuz! X3.2

    © 2001-2024 Comsenz Inc.

    快速回复 返回顶部 返回列表