以某科研基金信息平台为例,写了一个基于selenium的web自动化爬虫。不带验证码防反爬以及代理ip池,是最基础的自动化工具爬虫。
一、首先,此平台需要登录后才能正常访问,否则数据不全,因此需要登录后获取cookie,以便selenium能够以登录状态运行
1.F12打开开发者工具,找到network(网络),在登录后其有一个刷新的请求
可以看到该网站仅刷新了这一个请求
2.点击“cookie”选项卡,进入cookie截面(其实selenium自带了自动保存cookie的方法,但我希望尝试一下手动输入的流程)
3.可以看到cookie的信息分为“name”和“value”两部分,为了让cookie能够注入selenium,需要将其全部整理为[{'name':'xxx','value':'xxx'}]的形式,如下:
这便是一个完整的手动版cookie格式
二、在获取到cookie之后,第二步是需要分析页面找规律,找出我需要获取的信息
1.依旧是打开开发者工具,点开“元素”选项卡,可以看到整个网页的元素结构。将光标放到元素上,页面上就会显示该元素内具体包含了什么
经过查找,发现我需要的内容被包含在一个大元素中,下面分多个子元素,子元素下面又分多个子元素,
虽然关系很复杂,但是实际上,我们可以发现,我们需要的内容的class是一致的,
我需要的内容可以被这样找到:
父元素→遍历其中的子元素→找到子元素中特定class的元素
有了这样的逻辑,我就可以轻松地在代码中定位我需要的数据
为了实际定位,我使用XPATH作为定位的方法
例如我想先找到父元素,也就是<div class="home-content-container">
其XPATH即可以被写为 './/div[@class="home-content-container"]' 即可与find_element配合来获取此元素
三、在以上两步都完成后,我就可以开始编写代码来获取我需要的数据
# coding:utf-8 import time import random from time import sleep from csv import writer from selenium import webdriver from selenium.webdriver.common.by import By#初始化webdriver实例 driver = webdriver.Chrome()#定义函数 def get_information(search_name): #打开某名字下的网站driver.get("https://www.xxxxx.cn/pro/sonE-stwE08?psnname={}".format(search_name))time.sleep(6)#手动添加cookiecookies = [{'name': 'HMACCOUNT', 'value': 'xxx'},{'name': 'Hm_lpvt_0449d831efe3131221f6d2f2b6c91897', 'value': 'xxx'},{'name': 'Hm_lvt_0449d831efe3131221f6d2f2b6c91897', 'value': 'xxx'},{'name': '_c_WBKFRo', 'value': 'xxx'},{'name': '_nb_ioWEgULi', 'value': ''},{'name': 'acw_tc', 'value': 'xxx'},{'name': 'counter', 'value': 'xxx'},{'name': 'gzr_session', 'value': 'xxx'},{'name': 'userId', 'value': 'xxx'},{'name': 'uuid', 'value': 'xxx'},] #加载cookie模拟登陆for cookie in cookies:driver.add_cookie(cookie)time.sleep(5)driver.refresh()time.sleep(random.randrange(5,10))#定位需要爬取的元素(这里我进一步简化了定位的路径,请见谅)#获取我需要的主元素,由于有好几个,所以使用find_elementsparent_element=driver.find_elements(By.XPATH,'.//div[@class="item-box layui-card "]')#遍历每一个主元素for child_element in parent_element:#主元素中的数据元素,也是有多个text_element=child_element.find_elements(By.XPATH,'.//div[@class="layui-col-xs4"]')info=''#对于每个数据元素,使用.text取出数据for n in text_element:info+=n.textinfo+=','print(info)#储存到csv里list_data=[name,info]with open("信息.csv", "a", newline="") as f_object:writer_object = writer(f_object)writer_object.writerow(list_data)time.sleep(5)list_name=[xxxxx] #主程序 for name in list_name:get_information(name)time.sleep(random.randrange(10,30))