日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程语言 > python >内容正文

python

python公众号留言功能_Python 爬取公众号文章、评论

發(fā)布時間:2023/12/20 python 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 python公众号留言功能_Python 爬取公众号文章、评论 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

前段時間有個爬取公眾號評論小需求,花了幾天查了不少資料,實(shí)現(xiàn)方案有好幾種,最后其中一種得以實(shí)現(xiàn)。參考 【Python爬蟲】微信公眾號歷史文章和文章評論API分析 。

本人是 Python 小白,會忽略比較多的具體說明,只記錄關(guān)鍵的幾點(diǎn),以便能快速實(shí)現(xiàn) 。給同樣有興趣的童鞋提供個淺顯的參考。

也建議正在嘗試的童鞋靜下心來,一步步嘗試下去,畢竟我這個小白都成功了呢。當(dāng)然有錯誤的地方也歡迎指正。

使用環(huán)境:

Mac 、 Anaconda、MySQL 和 MySQL workbench。

很多博客里使用的 Windows 安裝的 Python。但是 Mac 也沒關(guān)系,Anaconda 傳送門, MySQL傳送門, MySQL workbench 傳送門。

Anaconda 中的 Spyder 用來運(yùn)行 Python 代碼;

MySQL 是連接 Python 運(yùn)行結(jié)果和數(shù)據(jù)庫的橋梁 (這個有個坑點(diǎn):安裝 MySQL 只是作為一個橋梁,并不能作為數(shù)據(jù)庫使用,所以要創(chuàng)建數(shù)據(jù)庫,否則會報(bào)錯);

MySQL workbench 用來創(chuàng)建、查看數(shù)據(jù)庫,并可以到處 csv 格式的文件。

準(zhǔn)備工作

首先需要提供公眾號文章列表鏈接和評論鏈接,用于分析修改 Python 代碼(具體的 Python 代碼實(shí)現(xiàn),我只看懂了流程,但是不會寫)。那么就需要抓包了,有一些博客是使用 Fiddler,不過我使用 Charles 也完全足夠了。只要能拿到接口相關(guān)數(shù)據(jù)即可。(不會抓包的請自行查閱資料)

公眾號文章列表流程:打開要爬取的公眾號 - 點(diǎn)擊右上角的 '人物' 圖標(biāo) - 點(diǎn)擊 '消息'底部的 '全部消息'

嘗試了幾次,剛打開文章列表,并沒有文章列表的接口,可以上拉刷新一下。

文章列表抓包截圖

文章列表抓包示意圖.png

文章評論抓包截圖

評論抓包示意圖 1.png

評論數(shù)據(jù)示意圖.png

我需要的就是 elected_comment 列表中每個 Object 中的 content 內(nèi)容。Python 代碼已實(shí)現(xiàn)獲取邏輯。

Python 代碼中需要提供接口中的幾個參數(shù):__biz、pass_ticket、app_msg_token、wap_sid2 和 cookie。具體作用可參頂部博客的說明。

正式爬數(shù)據(jù)

提供代碼中所需的幾個字段后,可以在 Anaconda 中的 Spyder 運(yùn)行 Python 代碼(代碼在文末),然后替換其中的字段。即下面的幾個字

biz = 'MzIwNTc4NTEwOQ==' # "碼農(nóng)有道公眾號" mnyd_article mnyd_comment

pass_ticket = 'ZS3nqLX1df5GhZ+zf/t0FYyf7Nfp52yUJ+PuyJUKvQtyln78R3QzBU21Xo528IE+'

app_msg_token = '986_G0Sy%252FL2pNlAGA9PIXcqTRipxsKaGLurexidEyg~~' # 歷史文章

wap_sid2 = 'CL3qgfIFElxMOFBzZ2dZOHQ1WTcxamRQLXUyMGFiU0tvNkZzUEJmRURhZmtJTkhLcEtYWU9rNm5WYmUtd29qd3Q3UmVqbmpZXzFxS21GMG13amVjM1NEaUVPajZNZG9EQUFBfjDH8K3gBTgNQAE='

cookie = 'wxuin=1581282621; version=2607033b; pass_ticket={}; wap_sid2={}'.format(pass_ticket, wap_sid2)

在開始運(yùn)行代碼后開始遇到問題:

1 ModuleNotFoundError: No module named 'pymysql';

需要安裝數(shù)據(jù)庫,比如安裝 MySQL。

然后在代碼中替換自己的密碼

self.db = pymysql.connect(

host="localhost",

user="root",

password="123456",

port=3306,

use_unicode=True,

#charset="utf8",

database="sunshine")

self.cursor = self.db.cursor()

2 需要創(chuàng)建數(shù)據(jù)庫,比如代碼中數(shù)據(jù)庫名字為 sunshine;

3 代碼中 offset 大部分是 10,不過有些公眾號是 20,但是 10 也可以正常運(yùn)行,不用擔(dān)心;

4 因?yàn)槭悄M手機(jī)接口,爬取完數(shù)據(jù)后可能會出現(xiàn) '操作頻繁,請稍后再試',這個沒有關(guān)系,等下再刷新就正常了。

基本上 Anaconda 等軟件安裝正確,數(shù)據(jù)庫已安裝,抓包數(shù)據(jù)沒錯,替換 biz 等參數(shù),替換數(shù)據(jù)庫配置密碼(或數(shù)據(jù)庫名),是可以正常運(yùn)行并且保存至數(shù)據(jù)庫。

注意

Python 代碼中需要修改的,都以 # ** 提示

當(dāng)時比較緊急,很多錯誤沒有保存,現(xiàn)在回憶也零零散散。有需要的湊合看參考下吧。

發(fā)布文章要既要綁定手機(jī)號又要綁定微信,讓人很不爽 (小聲BB)

代碼示例

作者: cacho_37967865

# -!- coding: utf-8 -!-

'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

#作者:cacho_37967865

#博客:https://blog.csdn.net/sinat_37967865

#文件:wechatArticleList.py

#日期:2018-12-08

#備注:通過Fiddler抓包,獲取微信公眾號歷史文章信息和文章評論信息存儲到mysql數(shù)據(jù)庫表

'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

import requests

import json

import pymysql

from datetime import datetime

import re

class wechatArticle:

def __init__(self,_biz,_pass_ticket,_appmsg_token,_cookie,_offset=0):

self.offset = _offset # 不同公眾號不一樣

self.biz = _biz

self.pass_ticket = _pass_ticket

self.appmsg_token = _appmsg_token

self.headers = {

'cookie':_cookie,

'User-Agent':'Mozilla/5.0 (Linux; Android 8.0; FRD-AL00 Build/HUAWEIFRD-AL00; wv) AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Chrome/57.0.2987.132'

}

self.db = pymysql.connect(

# ** password 需要替換為自己的。數(shù)據(jù)庫名 database 視情況,是否修改看個人需要

host="localhost",

user="root",

password="123456",

port=3306,

use_unicode=True,

#charset="utf8",

database="sunshine")

self.cursor = self.db.cursor()

def get_article_list(self):

offset = self.offset

while True:

api = 'https://mp.weixin.qq.com/mp/profile_ext?action=getmsg&__biz={0}&f=json&offset={1}&count=10&is_ok=1&scene=126&uin=777&key=777&pass_ticket={2}&wxtoken=&appmsg_token={3}&x5=1&f=json'.format(self.biz, offset, self.pass_ticket, self.appmsg_token)

resp = requests.get(api, headers=self.headers).json()

print(type(resp), resp) # 字典類型

ret, status = resp.get('ret'), resp.get('errmsg') # 狀態(tài)信息

if ret == 0 or status == 'ok':

offset = resp['next_offset']

general_msg_list = resp['general_msg_list']

#print(type(general_msg_list),general_msg_list) # json類型

msg_list = json.loads(general_msg_list)['list'] # 先轉(zhuǎn)化為字典類型再獲取列表類型

for msg in msg_list:

comm_msg_info = msg['comm_msg_info'] # 字典類型,每次推送的消息(一次三篇)

msg_id = comm_msg_info['id'] # 推送消息的id

post_time = datetime.fromtimestamp(comm_msg_info['datetime']) # 發(fā)布時間

try:

app_msg_ext_info = msg['app_msg_ext_info'] # 字典類型,文章信息(一次三篇)

first_article_id = app_msg_ext_info['fileid']

first_article_title = app_msg_ext_info['title'] # 本次推送的首條文章標(biāo)題

first_article_digest = app_msg_ext_info['digest'] # 本次推送的首條文章摘要

first_article_url = app_msg_ext_info['content_url']

self.get_article_detail(first_article_id,first_article_url)

first_url = first_article_url.replace('amp;', '').split('&chksm')[0]

self.article_to_mysql(msg_id, first_article_id, first_article_title, first_article_digest,first_url, post_time)

multi_app_msg_item_list = app_msg_ext_info.get('multi_app_msg_item_list')

for article in multi_app_msg_item_list:

article_id = article['fileid']

multi_article_title = article['title']

multi_article_digest = article['digest']

multi_article_url = article['content_url']

self.get_article_detail(article_id,multi_article_url)

multi_url = multi_article_url.replace('amp;', '').split('&chksm')[0]

self.article_to_mysql(msg_id, article_id, multi_article_title, multi_article_digest,multi_url, post_time)

except Exception as f:

print(str(f))

def get_article_detail(self,article_id,content_url):

try:

url = content_url.replace('amp;', '').replace('#wechat_redirect', '').replace('http', 'https')

html = requests.get(url, headers=self.headers).text

#print(html)

except:

print('獲取評論失敗' + content_url)

else:

str_comment = re.search(r'var comment_id = "(.*)" \|\| "(.*)" \* 1;', html)

str_msg = re.search(r"var appmsgid = '' \|\| '(.*)'\|\|", html) # 文章的id

str_token = re.search(r'window.appmsg_token = "(.*)";', html)

if str_comment and str_msg and str_token:

comment_id = str_comment.group(1) # 評論id(固定)

app_msg_id = str_msg.group(1) # 票據(jù)id(非固定)

appmsg_token = str_token.group(1) # 票據(jù)token(非固定)

# 缺一不可

if comment_id and app_msg_id and appmsg_token:

print("爬取評論的鏈接:" + url,html)

self.get_article_comments(app_msg_id,comment_id,appmsg_token,article_id)

def get_article_comments(self,app_msg_id,comment_id,appmsg_token,article_id):

api = 'https://mp.weixin.qq.com/mp/appmsg_comment?action=getcomment&scene=0&__biz={0}&appmsgid={1}&idx=2&comment_id={2}&offset=0&limit=100&uin=777&key=777&pass_ticket={3}&wxtoken=777&devicetype=android-26&clientversion=2607033b&appmsg_token={4}&x5=1&f=json'.format(

self.biz, app_msg_id, comment_id, self.pass_ticket, appmsg_token)

resp = requests.get(api, headers=self.headers).json()

ret, status = resp['base_resp']['ret'], resp['base_resp']['errmsg']

if ret =='0' or status == 'ok':

elected_comment = resp['elected_comment']

for comment in elected_comment:

content_id = comment.get('content_id') # 評論ID

nick_name = comment.get('nick_name') # 評論人昵稱

like_num = comment.get('like_num') # 點(diǎn)贊

comment_time = datetime.fromtimestamp(comment.get('create_time')) # 評論時間

content = comment.get('content') # 評論內(nèi)容

#print("評論內(nèi)容文章:",article_id,nick_name)

self.comment_to_mysql(article_id,content_id,comment_time,nick_name,like_num,content)

def create_article_table(self):

sql1 = 'drop table if exists mnyd_article;'

sql2 = 'create table mnyd_article(No INT(11) NOT NULL AUTO_INCREMENT,msg_id VARCHAR(15),article_id VARCHAR(15),post_time timestamp(2),title VARCHAR(200),digest VARCHAR(200),article_url varchar(300),PRIMARY KEY (No));'

self.cursor.execute(sql1)

self.cursor.execute(sql2)

self.db.commit()

def article_to_mysql(self,msg_id, article_id,title,digest,article_url,post_time):

sql = "insert into mnyd_article(msg_id,article_id,title,digest,article_url,post_time) values('%s','%s','%s','%s','%s','%s')" % (msg_id,article_id,title, digest,article_url,post_time)

try:

# 使用 cursor() 方法創(chuàng)建一個游標(biāo)對象 cursor

self.cursor.execute(sql)

except Exception as e:

# 發(fā)生錯誤時回滾

self.db.rollback()

print(str(e))

else:

self.db.commit() # 事務(wù)提交

print('事務(wù)處理成功')

def create_comment_table(self):

sql1 = 'drop table if exists mnyd_comment;'

sql2 = "create table mnyd_comment(No INT(11) NOT NULL AUTO_INCREMENT,article_id VARCHAR(15),content_id VARCHAR(20),comment_time timestamp(2),nick_name VARCHAR(50),like_num int,content varchar(1000),PRIMARY KEY (No)) COLLATE='utf8mb4_unicode_ci';"

self.cursor.execute(sql1)

self.cursor.execute(sql2)

self.db.commit()

def comment_to_mysql(self,article_id,content_id,comment_time,nick_name,like_num,content):

sql = "insert into mnyd_comment(article_id,content_id,comment_time,nick_name,like_num,content) values('%s','%s','%s','%s','%i','%s')" % (article_id,content_id,comment_time, nick_name,like_num,content)

try:

# 使用 cursor() 方法創(chuàng)建一個游標(biāo)對象 cursor

self.cursor.execute(sql)

except Exception as e:

# 發(fā)生錯誤時回滾

self.db.rollback()

print(str(e))

else:

self.db.commit() # 事務(wù)提交

print('事務(wù)處理成功')

if __name__ == '__main__':

# ** 以下幾個字段需要替換為自己需要的,每個公眾號都是不同的

biz = 'MzIwNTc4NTEwOQ==' # "碼農(nóng)有道公眾號" mnyd_article mnyd_comment

pass_ticket = 'ZS3nqLX1df5GhZ+zf/t0FYyf7Nfp52yUJ+PuyJUKvQtyln78R3QzBU21Xo528IE+'

app_msg_token = '986_G0Sy%252FL2pNlAGA9PIXcqTRipxsKaGLurexidEyg~~' # 歷史文章

wap_sid2 = 'CL3qgfIFElxMOFBzZ2dZOHQ1WTcxamRQLXUyMGFiU0tvNkZzUEJmRURhZmtJTkhLcEtYWU9rNm5WYmUtd29qd3Q3UmVqbmpZXzFxS21GMG13amVjM1NEaUVPajZNZG9EQUFBfjDH8K3gBTgNQAE='

cookie = 'wxuin=1581282621; version=2607033b; pass_ticket={}; wap_sid2={}'.format(pass_ticket, wap_sid2)

# 以上信息不同公眾號每次抓取都需要借助抓包工具做修改

wxarticles = wechatArticle(biz, pass_ticket, app_msg_token, cookie)

wxarticles.create_article_table() # 創(chuàng)建數(shù)據(jù)庫表記錄文章

wxarticles.create_comment_table() # 創(chuàng)建數(shù)據(jù)庫表記錄評論

wxarticles.get_article_list() # 開始爬取文章和評論

總結(jié)

以上是生活随笔為你收集整理的python公众号留言功能_Python 爬取公众号文章、评论的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。