Python でクロールするときに、リクエスト ライブラリだけを使用して特定の Web ページを開くと、リクエストの session.cookies に保存される Cookie 情報はほとんどなく、Cookie が空白になることさえあります。しかし、ブラウザで同じウェブページを開くと、Cookie の情報は非常に詳細です. たとえば、ブラウザの Cookie はログイン後もステータス情報を保持します. ログインせずに Python で特定のウェブページにすばやく入るには、そのページをエクスポートする必要があります.最初にブラウザの Web ページ Cookie を読み込み、次に Python でリクエスト ライブラリを使用して Cookie をインポートします。
ステップ 1: ブラウザは cookies.txt をテキスト形式でエクスポートします
ブラウザーのアドレス バーに次の JS コードを入力すると、現在のページの Cookie をテキスト ファイル cookies.txt としてすばやくエクスポートできます。
javascript: (function() { const a = document.createElement('a'); a.href = 'data:text/plain,' + document.cookie; a.download = 'cookies.txt'; a.target = '_blank'; a.style.display = 'none'; document.body.appendChild(a); a.click(); setTimeout(function() { document.body.removeChild(a); }, 100);})();
注: 上記のコードを直接貼り付けることはできません。そうしないと、ブラウザーは先頭の "javascript:" を自動的にブロックします。
正しい姿勢は: 最初に上記のコードをアドレス バーに貼り付け、次にアドレス バーのホーム キーを押してコードの先頭に戻り、手動で javascript: (コロンと半角に注意) と入力して、入力します。これにより、cookies.txt が指定されたディレクトリにエクスポートされます。
ブラウザーがファイルを保存するためのダイアログ ボックスをポップアップ表示しない場合は、ブラウザーが C:\Users\Administrator\Downloads\ などの既定のディレクトリに自動的に保存するように設定されているためです。ファイルを保存するたびにファイルの保存場所をブラウザに尋ねる必要がある場合は、最初にブラウザ設定で次の設定を見つける必要があります。
ステップ 2: Python の requests ライブラリは、cookies.txt を辞書形式としてインポートします
Requests ライブラリのセッションは Cookie をインポートできます。Cookie は辞書形式である必要があります。
上記のブラウザに JS コードを入力してエクスポートした cookies.txt には、次のように 1 行しかありません。
mediav={"_refnf":0};ID=ed5026a06; param={"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)","トークン":""}; cookie_referer=; トークン=検証:トークン
これはデモンストレーションの便宜のための単純な例にすぎません。実際の Cookie 文字列はこれより長くなります。
前任者のアプローチは、文字列をセミコロンで分割し、dict() を使用して辞書形式に変換することです。しかし、この例では user-agent の値にもセミコロンが入っているので、単純にセミコロンで区切ると、区切ってから辞書形式に変換するのは誤りです。
私のアプローチは次のとおりです。等号で割り、余分なセミコロンを削除します。
with open('cookies.txt', encoding = 'utf-8') as f:
cookies = f.read()
'''
载入cookies.txt,假设cookies内容是:'mediav={"_refnf":0};ID=ed5026a06; param={"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)","token":""}; cookie_referer=; token=validation:token'
'''
l1=cookies.split('=')
print(l1)
'''
输出:
['mediav', '{"_refnf":0};ID', 'ed5026a06; param', '{"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)","token":""}; cookie_referer', '; token', 'validation:token']
'''
l1 リストの偶数要素にキーと値が混在していることがわかります. 余分なセミコロンを削除するには, それらを解体する必要があります. 以下は私の改良したコードです:
def cookies_to_dict(cookies):
l1=l2=[]
l1=cookies.split('=')
for i in l1:
if ';' in i:
# 如果字符串存在分号就从后往前找分号来分割
ss = i.rpartition(';')
# rpartition()的作用就是从后往前找,返回三个元素的元组
# 第一个为分隔符左边的子串,第二个为分隔符本身,第三个为分隔符右边的子串
# 因此这里使用extend一次添加ss[0]和ss[2]的子串
l2.extend([ss[0].strip(), ss[2].strip()])
# strip()的作用是清除子串左端和右端的多余的空格
else:
l2.append(i.strip())
c_dict={}
for i in range(0,len(l2),2):
c_dict.update({l2[i]:l2[i+1]})
return c_dict
cookie_dict = cookies_to_dict(cookies)
print(cookie_dict)
'''
输出:
{'mediav': '{"_refnf":0}', 'ID': 'ed5026a06', 'param': '{"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)","token":""}', 'cookie_referer': '', 'token': 'validation:token'}
'''
このように、cookies.txt は辞書としてフォーマットされます。その後、リクエストのセッションにインポートできます。
import requests
se = requests.Session()
se.cookies.clear()
# 先清空Session的cookies,再导入cookies_dict
se.cookies.update(cookies_dict)
2 月 27 日の更新: re ライブラリの正規表現の findall を使用して、完全に解決してください
今日、この記事のコードを何度かデバッグしたところ、Cookie にネストされた情報と「=」が含まれている場合、上記のコードの解析エラーが発生することがわかりました。たとえば、Cookie の内容は次のとおりです。
param={"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)","トークン":"","url":"https://xxxxxxx.com/login/source=xxxxxxx"};
ネストされた辞書形式のクッキー情報です。param の後に等号があり、中括弧内にも等号がネストされています. 上記のコードに従って分割する等号を最初に見つけてから辞書形式を変換すると、エラーが発生します.
私たちの目的は非常に単純で、分割する Cookie 情報で「xxx = xxxxxxxx」を見つけることです。何度もデバッグした結果、re ライブラリの正規表現でしか解決できません。この正規表現は調整が難しく、次のコードにうまく分割できます。
([a-zA-Z0-9_]+)=((?:{[^{}]*}|[^;]*)+)
したがって、コードは次のように更新されます。
import requests
import re
def cookies_to_dict(cookie_str):
matches = re.findall(r'([a-zA-Z0-9_]+)=((?:{[^{}]*}|[^;]*)+)', cookie_str)
result = {}
for i in matches:
result.update({i[0]:i[1]})
return result
if __name__ == '__main__':
# 载入cookies.txt
with open(r'C:\Users\Administrator\Downloads\cookies.txt', 'r', encoding='utf-8') as f:
cookie_str = f.read()
# 把cookies转换为字典格式
cookies_dict = cookies_to_dict(cookie_str)
# 初始化requests的Session
se = requests.Session()
se.cookies.clear()
# 先清空Session的cookies,再导入cookies_dict
se.cookies.update(cookies_dict)
cookies.txt が読み込まれていると仮定すると、cookie_str 文字列の内容は 'mediav={"_refnf":0};ID=ed5026a06; param={"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)", " token":"","url":"https://xxxxxxx.com/login/source=xxxxxxx"}; cookie_referer=; token=validation:token'
上記の改善された cookies_to_dict() 関数が辞書形式に変換されると、cookies_dict の内容は次のようになります。
{
'mediav': '{"_refnf":0}',
'ID': 'ed5026a06',
'param': '{"user_agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64)","token":"","url":"https://xxxxxxx.com/login/source=xxxxxxx"}',
'cookie_referer': '',
'token': 'validation:token'
}