爬蟲必備:Python 執行 JS 代碼 —— PyExecJS、PyV八、Js2Py

在使用爬蟲中,常常會遇到網頁請求數據是通過 JS 處理的,特別是模擬登陸時可能有加密請求。而目前絕大部分前端 JS 代碼都是通過混淆的,可讀性極低,想理解代碼邏輯須要花費大量時間。這時不要着急使用 Selenium 暴力解決,畢竟 Selenium 嚴重拖慢爬蟲效率,咱們能夠嘗試使用一些第三方庫,來直接執行前端 JS 代碼獲得處理事後的結果。前端

PyExecJS

這個庫主要是將 JS 代碼運行在本地的 JS 環境中,優勢是咱們有多種 JS 環境的選擇,官方推薦了 PyV八、Node.js、PhantomJS、Nashorn 四種,固然缺點是必須安裝一種環境致使不是很輕量,並且調用時有一個啓動環境過程,仍是有明顯緩慢的。node

安裝方式

先解決 JS 環境,這裏推薦安裝 Node.js ,安裝方便,執行效率也高。
而後 pip install PyExecJS 就能夠了。python

使用例子

>>> import execjs
>>> execjs.get().name  # 查看調用的環境
'Node.js (V8)'
>>> ctx = execjs.compile("""  # 執行 JS 語句
...     function add(x, y) {
...         return x + y;
...     }
... """)
>>> ctx.call("add", 1, 2)
3
>>> with open('./test.js') as f:  # 執行 JS 文件
...     ctx = execjs.compile(f.read())
...     ctx.call('add', 1, 2)

PyV8

這是 Google 官方將 Chrome V8 引擎用 Python 封裝的庫,和 PyExecJS 相比,這個庫很輕量,不須要額外裝 JS 環境,由於 V8 自己就是環境,同時也由於不須要啓動外部環境,執行速度很快。git

安裝方式

Python3 安裝不要使用pip,由於官方只支持 Python2,須要在這裏下載對應系統的二進制文件:https://github.com/emmetio/pyv8-binaries
而後解壓後將 PyV8.py 與 _PyV8.so (如so不是這個名字須要改爲這樣) 兩文件複製到 Python 的 site-packages 目錄下,如 /usr/local/lib/python3.6/site-packages程序員

使用例子

>>> import PyV8  # 注意大小寫
>>> with PyV8.JSContext() as ctx:
...     ctx.eval("""
...         function add(x, y) {
...             return x + y;
...         }
...     """)
...     ctx.locals.add(1, 2)

Js2Py

最後這個庫,做用是將 JS 代碼直接轉譯成 Python 代碼,這種方式能夠擺脫調用 JS 環境的瓶頸,但遺憾的是若是用於很長的混淆 JS 代碼,轉譯過來的大機率會報錯… 因此只建議先嚐試一下,若是報錯及時更換上面的庫。github

安裝方式

pip install js2py編程

使用例子

>>> import js2py
>>> add = js2py.eval_js("""
...     function add(x, y) {
...         return x + y;
...     }
... """)
>>> add  # 能夠看到大括號裏已被轉譯
'function add(x, y) { [python code] }'
>>> add(1, 2)
3
>>> # 使用下邊這個方法能夠輸出轉譯後的代碼
>>> # 能夠保存到文件裏,下次不須要再次轉譯
>>> print(js2py.translate_js('var x = 1'))
from js2py.pyjs import *
# setting scope
var = Scope( JS_BUILTINS )
set_global_object(var)

# Code follows:
var.registers(['x'])
var.put('x', Js(1.0))

實戰技巧

當選擇完合適的庫後,若是你還不明白在瀏覽器裏進行 Debug 的方法,那須要去搜索關鍵詞先學習一下。
接下來就是定位目標網頁須要調用的 JS 函數,這裏實在沒法詳述,由於每一個網站的寫法都大不相同。
不過只要你經過 Debug ,查看數據從請求開始,每一步都通過了哪些 JS 函數,又輸出成什麼樣的數據,就能夠順藤摸瓜找到一些可疑的函數,而後將這些方法逐一複製出來,經過上面的庫傳入參數執行,看是否和目標網頁處理後的數據一致,就能夠找到目標函數。瀏覽器


最後,關注個人微信公衆號:面向人生編程

不管什麼樣的編程思想,都不應只存留在代碼之中,更應伴隨於整我的生旅途,這個公衆號不僅聊技術,還會聊產品/互聯網/經濟學等普遍話題,因此也歡迎非程序員關注。微信

相關文章
相關標籤/搜索