每日分享:
没有一朵花,从一开始就是花
目录
前言(思考过程):
自己之前写过刷赞,刷评论,刷阅读量,最近也是实现了刷收藏,写篇文章记录一下,感觉csdn快被自己玩坏了(手动狗头)
最开始我的想法是,先把博主所有的文章url爬取下来,放到txt文件,然后用selenium控制浏览器对每个网址(文章)点击收藏。
如何爬取所有文章的网址呢?
我当时一看,这不就是爬取全站数据吗,不犹豫,直接用crawlspider框架专门来对付全站数据,开始还想按以前的思路,把主页转成旧版,但是没找到,就只能再对新版主页想办法了(旧版文章是分页展示,而新版是每次显示20个,滑到下面会再显示出20个...)。然后我发现博主的主页里有分类专栏,可以在crawlspider中写三个规则提取器,第一个提取主页每个专栏网址,再对每个专栏提取每一页的网址,最后再对每一页的网址提取每个文章的网址。然后不出意外的话就要出意外了
这是每一页的标签,啊?这里面怎么没有网址?(这我怎么用正则匹配......)罢了罢了,那就用selenium来实现吧:
我想的是,用selenium控制浏览器一直往下滑,来让它加载出所有的文章,之后再用xpath得到所有文章的网址即可。(实现了,下面会放代码)
然后就到下一个问题了,控制浏览器点击收藏
实现点击操作并不难,但出现了一个问题,每次用selenium控制的浏览器是未登录的状态,我想,这还不简单吗,我直接携带着cookie不就解决了吗?之后加了cookie,但是不管用(当时不知道为什么,现在感觉应该是被检测出来了);既然加cookie不行,那我就用selenium控制输入账号密码去登录呗,结果又出意外了,点击操作不难,你多次登录它让你滑动滑块来验证,这也不算难,滑动之后他就说失败,让重新滑动,估计就是被检测出来了,尝试了网上很多selenium规避检测的方法,都不管用(开始我是感觉可能是自己代码滑块滑动的不好,就优化了一下还是不行,为什么我认为是被检测出来了,因为我在selenium打开的浏览器中验证的时候试了一下,手动滑动的也是失败,然后你手动打开浏览器,登录就没问题),自己在这一块卡了很长时间,后来是用接管浏览器解决了问题(接管浏览器进行登录也不行,没有解决被检测出来的问题)。
转换思路,利用接管浏览器,可以手动登录,代码里面一直用这个浏览器即可,也会保持登录状态,然后就get每个网址,点击收藏即可(其实在这之前,我想的思路是用selenium登录一次【因为当时发现,一段时间,你第一次登录不会让你进行滑动验证】,再点击文章,点击收藏,关闭当前标签页,点击下一个文章,再结合着下滑操作来实现的,但代码写的有点问题,后面又接触到了接管这种方法,就放弃了;怎么说呢,这种思路可能不是很好,如果主页的每个文章高度不一样,后面有可能会出现问题,也就是点击不到,不过这也算一种思路)
一、需要注意的点
1. 每次下滑让其加载的时候分两次下滑
一次下滑到底有时会加载不出来,从而导致爬不到数据
下面是获取网址的代码:
from selenium import webdriver
import time
url = "主页的网址"
options = webdriver.ChromeOptions()
# # 配置对象添加开启无界面浏览器的命令
options.add_argument('--headless')
driver = webdriver.Chrome()
driver.get(url)
time.sleep(4)
# 循环的次数取决于文章的总量,一次20,自己算出来即可
for i in range(58):
# 不要直接执行js每次滑到最下面,会出错,有时候页面不更新新的文章,所以我让它下滑两次,确保刷新出来
driver.execute_script("window.scrollTo(0,document.body.scrollHeight / 2)")
driver.execute_script("window.scrollTo(document.body.scrollHeight / 2,document.body.scrollHeight)")
time.sleep(1)
# 获取每个文章的网址(准确来说不是网址,下面get_attribute才是网址)
url_list = driver.find_elements('xpath', '//article[@class="blog-list-box"]/a')
f = open('urls.txt', 'a+', encoding='utf8')
for i in url_list:
i = i.get_attribute('href')
print(i)
f.write(i + '\n')
f.close()
driver.close()
2. get网址前判断是否已经点过收藏了
最开始没有判断,运行一段时间后,它会去到已经点过收藏的文字再去点(会导致取消收藏),到现在也不知道是为什么,总之加上就对了
下面是点击收藏的代码:
from selenium.webdriver import Chrome
from selenium import webdriver
import time
from selenium.webdriver.chrome.options import Options
# 接管浏览器,发送get
def get_chrome_proxy(url):
options = Options()
options.add_experimental_option("debuggerAddress", "127.0.0.1:端口号")
driver = Chrome(options=options)
driver.get(url)
driver.implicitly_wait(15)
return driver
# 实现点击操作
def manage(url):
try:
driver = get_chrome_proxy(url)
# 点击收藏
driver.find_element('xpath', '//*[@id="toolBarBox"]/div/div[2]/ul/li[4]').click()
time.sleep(2)
# 点击默认文件夹的收藏
driver.find_element('xpath', '//*[@id="csdn-collection"]/div/div[2]/ul/li/span[2]').click()
except Exception as e:
print()
if __name__ == '__main__':
# 把访问过的放到列表里
finish = []
with open('urls.txt', 'r') as f:
urls = f.readlines()
# 判断是否访问过
for i in urls:
if i not in finish:
manage(i)
finish.append(i)
不过效率确实有点低