今天用selenium爬取了我关注的某个博主的所有文章,并保存到本地文件。
思路:自动打开浏览器并搜索网址,找到文章的标题,评论数,阅读量以及链接和下一页的节点,爬取完一页后就自动点击下一页继续爬取,直到爬完,最后关闭浏览器。
过程中遇到的问题:
一,关于找节点:如果节点比较简单的,可以直接copy xpath得到,然后利用find_element_by_xpath()得到相应的节点,进而得到信息(所需的信息可能是该节点的某个属性(get_attribute('xxx'))或者文本内容(.text))。但是如果节点比较复杂,比如某个节点通过copy得到的xpath有这种构造:...div[14]/div[2]/div[4]这种子节点和父节点同名的,在爬取过程中是找不到的,只能自己去分析它的其他的方式。
二,关于“下一页”这个节点的问题,每一页刷新之后,都要重新获取一次这个节点。如果把它放到循环的外面,则在点击下一页的时候,会出现不能跳转的问题,这样爬取的就一直是重复某一页的内容了
三,关于延时等待:第一次爬取的时候,没有做延时等待,爬取结束后发现文件夹里没有东西。然后检查代码,以为是文件写入错误,所以就先把爬取的内容先打印一下,发现结果为空,说明节点没有获取到。调整思路,应该是节点为出现,就跳找节点的过程了,所以我在每次刷新一个网页就停留5秒(有隐式等待和显式等待,但是用显示等待是,获取节点的方法变量一点,不怎么能看懂,就没用那种方法,直接time的sleep(5)方法)
四,关于写入文件:得到的文章的标题,链接,评论数,阅读量都是列表,然后利用pandas库就可以写入了,还有一个问题,就是编码,之前用的是encoding='gb2312',但是出错了(写到一半在某条数据哪儿断了,之后的内容没有写入),之后换成了'gbk',可以的。
放代码:
from selenium import webdriver
import time
import pandas as pd
def get_text(url):
# 自动爬取博主的文章
browser = webdriver.Chrome()
browser.get(url)
# 下一页的按钮next_page
titles = [] # 标题
comments = [] # 评论
links = [] # 链接
reading_nums = [] # 阅读量
time.sleep(10) # 首次加载可能会慢一点,所以延时等待时间久一点
for page in range(1, 15):
time.sleep(5) # 每一页都等待5秒,等待“下一页“的节点出来
next_page = browser.find_element_by_xpath('//a[@class="btn btn-xs btn-default btn-next"]') # 下一页的这个节点在每一页刷新后都重新获取一次
try:
for j in range(1, 11):
try:
title = browser.find_element_by_xpath('//div[@id="divResources"]/div[1]/li[{}]/a'.format(str(j)))
comment = browser.find_element_by_xpath('//div[@id="divResources"]/div[1]/li[{}]/span[1]'.format(str(j)))
reading_num = browser.find_element_by_xpath('//div[@id="divResources"]/div[1]/li[{}]/span[2]'.format(str(j)))
titles.append(title.get_attribute('title')) # 标题
links.append(title.get_attribute('href')) # 链接
comments.append(comment.text) # 评论
reading_nums.append(reading_num.text) # 阅读量
print('第{}页第{}条爬取成功'.format(str(page),str(j)))
except Exception as er:
print('第{}页第{}条爬取失败:{}'.format(str(page),str(j),er))
print('第{}页爬取完成'.format(str(page)))
if next_page:
next_page.click()
else:
print('第{}页的下一页节点没有找到'.format(str(page)))
except Exception as e:
print(e)
browser.close() # 关闭浏览器
return titles, comments, links, reads
def text_to_excel(titles, comments, links, reads):
# 将爬取到的数据写入Excel中
try:
dataframe = pd.DataFrame({'标题':titles, '链接':links, '阅读量':reads, '评论数':comments})
dataframe.to_csv('articles.csv', index = False, encoding = 'gbk')
except Exception as e:
print(e)
if __name__ == '__main__':
url = 'https://my.csdn.net/ohmygirl'
print('开始爬取......')
titles, comments, links, reads = get_text(url)
print('爬取完成\n开始写入文件......')
text_to_excel(titles, comments, links, reads)
print('-----写入文件完成-----')
运行结果: