貢獻人:李金原
如果喜歡這里的內(nèi)容,你能夠給我最大的幫助就是轉(zhuǎn)發(fā),告訴你的朋友,鼓勵他們一起來學習。
If you like the content here, the greatest help you can give me is forwarding, so tell your friends and encourage them to learn together.
每次在公眾號中搜索文章都很繁瑣,把自己關(guān)注的公眾號文章下載到本地就是我們需要解決的一個需求了。本篇圖文就是介紹這方面的內(nèi)容:如何利用Python爬取感興趣的公眾號文章 。
本次爬取需要的工具如下:
在 2017 年 6 月左右,微信官方發(fā)布一篇文章 https://mp.weixin.qq.com/s/67sk-uKz9Ct4niT-f4u1KA, 大致意思就是以后發(fā)布文章的時候可以插入其它公眾號的文章。由此,我們即可獲得采集文章的接口。
一、登陸微信公眾號 在這里,我們使用 selenium + chromedriver(chrome 的 webdriver) 的方式來獲取登陸的 cookie,這樣,以后爬取文章時只需要載入 cookie 即可登陸。首先我們打開微信公眾平臺 https://mp.weixin.qq.com/ 進行賬號登陸:
1 我們用 insepect
檢查獲取登陸的賬號、密碼元素所在位置,來實現(xiàn)自動化登陸的目的 。
2 轉(zhuǎn)化成代碼如下:
# 用webdriver啟動谷歌瀏覽器 print ("啟動瀏覽器,打開微信公眾號登錄界面" ) driver = webdriver.Chrome(executable_path='/usr/bin/chromedriver' ) # 此處 webdriver 根據(jù)自己的環(huán)境更改 # 打開微信公眾號登錄頁面 driver.get('https://mp.weixin.qq.com/' )# 等待5秒鐘 time.sleep(5)print ("正在輸入微信公眾號登錄賬號和密碼......" )#清空賬號框中的內(nèi)容 driver.find_element_by_name("account" ).clear()#自動填入登錄用戶名 driver.find_element_by_name("account" ).send_keys("輸入你的公眾號賬號" )#清空密碼框中的內(nèi)容 driver.find_element_by_name("password" ).clear()#自動填入登錄密碼 driver.find_element_by_name("password" ).send_keys("輸入公眾號密碼" )# 在自動輸完密碼之后需要手動點一下記住我 print ("請在登錄界面點擊:記住賬號" ) time.sleep(5)#自動點擊登錄按鈕進行登錄 driver.find_element_by_class_name("btn_login" ).click()# 拿手機掃二維碼! print ("請拿手機掃碼二維碼登錄公眾號" ) time.sleep(20)print ("登錄成功" )
之后,我們需要重新登陸一次,保存 cookie
,以后則載入 cookie
即可,不需要再掃碼登陸。代碼如下:
# 定義一個空的字典,存放cookies內(nèi)容 post = {} driver.get('https://mp.weixin.qq.com/' )# 獲取cookies cookie_items = driver.get_cookies()# 獲取到的cookies是列表形式,將cookies轉(zhuǎn)成json形式并存入本地名為cookie的文本中 for cookie_item in cookie_items: post[cookie_item['name' ]] = cookie_item['value' ] cookie_str = json.dumps(post)with open('cookie.txt' , 'w+' , encoding='utf-8' ) as f: f.write(cookie_str) print("cookies信息已保存到本地" )
之后我們開始文章的爬取。
二、爬取文章 根據(jù)官方描述,接口應(yīng)該藏在新建圖文素材中的插入超鏈接中,和之前爬取幣乎一樣,我們用 F12-Network-XHR 來跟蹤這幾個頁面來獲取我們需要配置的請求:
3 4 5 接下來,我們來配置請求參數(shù):
#公眾號主頁 url = 'https://mp.weixin.qq.com' #設(shè)置headers header = { "HOST" : "mp.weixin.qq.com" , "User-Agent" : "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:53.0) Gecko/20100101 Firefox/53.0" }#讀取上一步獲取到的cookies with open('cookie.txt' , 'r' , encoding='utf-8' ) as f: cookie = f.read() cookies = json.loads(cookie)#登錄之后的微信公眾號首頁url變化為:https://mp.weixin.qq.com/cgi-bin/home?t=home/index&lang=zh_CN&token=1086424384,從這里獲取token信息 response = requests.get(url=url, cookies=cookies) token = re.findall(r'token=(\d+)' , str(response.url))[0 ]#搜索微信公眾號的接口地址 search_url = 'https://mp.weixin.qq.com/cgi-bin/searchbiz?' #搜索微信公眾號接口需要傳入的參數(shù),有三個變量:微信公眾號token、隨機數(shù)random、搜索的微信公眾號名字query query_id = { 'action' : 'search_biz' , 'token' : token, 'lang' : 'zh_CN' , 'f' : 'json' , 'ajax' : '1' , 'random' : random.random(), 'query' : query, 'begin' : '0' , 'count' : '5' }#打開搜索微信公眾號接口地址,需要傳入相關(guān)參數(shù)信息如:cookies、params、headers search_response = requests.get(search_url, cookies=cookies, headers=header, params=query_id)#取搜索結(jié)果中的第一個公眾號 lists = search_response.json().get('list' )[0 ]#獲取這個公眾號的fakeid,后面爬取公眾號文章需要此字段 fakeid = lists.get('fakeid' )#微信公眾號文章接口地址 appmsg_url = 'https://mp.weixin.qq.com/cgi-bin/appmsg?' #搜索文章需要傳入幾個參數(shù):登錄的公眾號token、要爬取文章的公眾號fakeid、隨機數(shù)random query_id_data = { 'token' : token, 'lang' : 'zh_CN' , 'f' : 'json' , 'ajax' : '1' , 'random' : random.random(), 'action' : 'list_ex' , 'begin' : '0' ,#不同頁,此參數(shù)變化,變化規(guī)則為每頁加5 'count' : '5' , 'query' : '' , 'fakeid' : fakeid, 'type' : '9' }#打開搜索的微信公眾號文章列表頁 appmsg_response = requests.get(appmsg_url, cookies=cookies, headers=header, params=query_id_data)
6 接下來,我們選擇要爬取的公眾號,進入文章列表界面:
7 8 9 分析第一頁、第二頁、…、第四百頁,我們可以知道頁碼數(shù)由 begin
參數(shù)決定,且每一頁 +5,初始頁為 0。這樣,我們可以通過對 begin
進行循環(huán)來爬取多個頁數(shù)。
接下來,我們來查看每篇文章的信息藏在哪里:
10 點擊右側(cè)的 Preview
,可以找出 app_msg_list
即可獲取每篇文章的詳細信息,接下來,我們就可以提取我們需要的信息,這里筆者提取了 title
、link
、update_time
方便之后存入數(shù)據(jù)庫。
# 起始頁 begin 參數(shù),往后每頁加 5 begin = 0 while begin <= 1995 : query_id_data = { 'token' : token, 'lang' : 'zh_CN' , 'f' : 'json' , 'ajax' : '1' , 'random' : random.random(), 'action' : 'list_ex' , 'begin' : '{}' .format(str (begin )), 'count' : '5' , 'query' : '' , 'fakeid' : fakeid, 'type' : '9' } print('正在翻頁:--------------' ,begin ) # 獲取每一頁文章的標題和鏈接地址,并寫入本地文本中 query_fakeid_response = requests.get(appmsg_url, cookies=cookies, headers=header, params=query_id_data) fakeid_list = query_fakeid_response.json().get('app_msg_list' ) for item in fakeid_list: content_link=item.get('link' ) content_title=item.get('title' ) content_time=item.get('update_time' ) fileName=query +'.txt' with open (fileName,'a' ,encoding ='utf-8' ) as fh: fh.write(content_title+":\n" +content_link+"\n" ) begin = int (begin ) begin += 5 time.sleep(20 )
至此,我們就可以將所爬取的公眾號文章存入相應(yīng)的 txt 文件,文本每三行為一篇文章,分別是標題、鏈接、發(fā)表時間。
最后,整合代碼如下: