概要
Pythonの鉄板ライブラリ requests を作成した kennethreitzさんが requests-html
というライブラリを公開されています。
requests
と同じく xxxx for Humans
シリーズなライブラリ。やっぱり使いやすいライブラリでした。
markdownに変換できる機能が素晴らしいです。
Readmeみたら、大体の使い方がわかってしまうのですが、とりあえず自分でも使ってみたメモを残しておきます。
インストール
私の環境は、まだpipenv
ではなくて、conda
です。
一旦、存在するかどうか探してみる。
⟩ conda search requests-html Loading channels: done PackagesNotFoundError: The following packages are not available from current channels: - requests-html Current channels: - https://repo.continuum.io/pkgs/main/osx-64 - https://repo.continuum.io/pkgs/main/noarch - https://repo.continuum.io/pkgs/free/osx-64 - https://repo.continuum.io/pkgs/free/noarch - https://repo.continuum.io/pkgs/r/osx-64 - https://repo.continuum.io/pkgs/r/noarch - https://repo.continuum.io/pkgs/pro/osx-64 - https://repo.continuum.io/pkgs/pro/noarch - https://conda.anaconda.org/conda-forge/osx-64 - https://conda.anaconda.org/conda-forge/noarch
無い。ってことで、pipから入れます。
⟩ conda create -n requests-html ipython Solving environment: done ## Package Plan ## environment location: /Users/xxxx/anaconda3/envs/requests-html added / updated specs: - ipython The following NEW packages will be INSTALLED: appnope: 0.1.0-py36hf537a9a_0 ca-certificates: 2017.08.26-ha1e5d58_0 certifi: 2018.1.18-py36_0 decorator: 4.2.1-py36_0 ipython: 6.2.1-py36h3dda519_1 ipython_genutils: 0.2.0-py36h241746c_0 jedi: 0.11.1-py36_0 libcxx: 4.0.1-h579ed51_0 libcxxabi: 4.0.1-hebd6815_0 libedit: 3.1-hb4e282d_0 libffi: 3.2.1-h475c297_4 ncurses: 6.0-hd04f020_2 openssl: 1.0.2n-hdbc3d79_0 parso: 0.1.1-py36hc90e01c_0 pexpect: 4.4.0-py36_0 pickleshare: 0.7.4-py36hf512f8e_0 pip: 9.0.1-py36h1555ced_4 prompt_toolkit: 1.0.15-py36haeda067_0 ptyprocess: 0.5.2-py36he6521c3_0 pygments: 2.2.0-py36h240cd3f_0 python: 3.6.4-hc167b69_1 readline: 7.0-hc1231fa_4 setuptools: 38.5.1-py36_0 simplegeneric: 0.8.1-py36_2 six: 1.11.0-py36h0e22d5e_1 sqlite: 3.22.0-h3efe00b_0 tk: 8.6.7-h35a86e2_3 traitlets: 4.3.2-py36h65bd3ce_0 wcwidth: 0.1.7-py36h8c6ec74_0 wheel: 0.30.0-py36h5eb2c71_1 xz: 5.2.3-h0278029_2 zlib: 1.2.11-hf3cbc9b_2 Proceed ([y]/n)? y Preparing transaction: done Verifying transaction: done Executing transaction: done # # To activate this environment, use # # $ conda activate requests-html # # To deactivate an active environment, use # # $ conda deactivate
一旦、conda で仮想環境作った後で、pipで入れます。
$ conda activate requests-html
一応、pip上にあるかどうかを検索
$ pip search requests-html | grep requests-html requests-html (0.1.1) - HTML Parsing for Humans.
オケ。てことで、インストール。
⟩ pip install -U requests-html (requests-html) Collecting requests-html Downloading requests_html-0.1.1-py2.py3-none-any.whl Collecting pyquery (from requests-html) Downloading pyquery-1.4.0-py2.py3-none-any.whl Collecting html2text (from requests-html) Downloading html2text-2018.1.9-py3-none-any.whl Collecting parse (from requests-html) Downloading parse-1.8.2.tar.gz Collecting requests (from requests-html) Downloading requests-2.18.4-py2.py3-none-any.whl (88kB) 100% |████████████████████████████████| 92kB 2.0MB/s Collecting fake-useragent (from requests-html) Downloading fake-useragent-0.1.10.tar.gz Collecting bs4 (from requests-html) Downloading bs4-0.0.1.tar.gz Collecting lxml>=2.1 (from pyquery->requests-html) Downloading lxml-4.1.1-cp36-cp36m-macosx_10_6_intel.macosx_10_9_intel.macosx_10_9_x86_64.macosx_10_10_intel.macosx_10_10_x86_64.whl (8.7MB) 100% |████████████████████████████████| 8.7MB 171kB/s Collecting cssselect>0.7.9 (from pyquery->requests-html) Downloading cssselect-1.0.3-py2.py3-none-any.whl Collecting chardet<3.1.0,>=3.0.2 (from requests->requests-html) Downloading chardet-3.0.4-py2.py3-none-any.whl (133kB) 100% |████████████████████████████████| 143kB 5.5MB/s Collecting urllib3<1.23,>=1.21.1 (from requests->requests-html) Downloading urllib3-1.22-py2.py3-none-any.whl (132kB) 100% |████████████████████████████████| 133kB 5.3MB/s Requirement already up-to-date: certifi>=2017.4.17 in /Users/xxxx/anaconda3/envs/requests-html/lib/python3.6/site-packages (from requests->requests-html) Collecting idna<2.7,>=2.5 (from requests->requests-html) Downloading idna-2.6-py2.py3-none-any.whl (56kB) 100% |████████████████████████████████| 61kB 5.1MB/s Collecting beautifulsoup4 (from bs4->requests-html) Downloading beautifulsoup4-4.6.0-py3-none-any.whl (86kB) 100% |████████████████████████████████| 92kB 4.8MB/s Building wheels for collected packages: parse, fake-useragent, bs4 Running setup.py bdist_wheel for parse ... done Stored in directory: /Users/xxxx/Library/Caches/pip/wheels/b0/3b/37/4ab694a0d331a3cc487923ff9c3645d0f103e9cd4762065f77 Running setup.py bdist_wheel for fake-useragent ... done Stored in directory: /Users/xxxx/Library/Caches/pip/wheels/07/04/1d/bbd8ba7d692add504b44552504b7df239bddf56aa3387cee2b Running setup.py bdist_wheel for bs4 ... done Stored in directory: /Users/xxxx/Library/Caches/pip/wheels/84/67/d4/9e09d9d5adede2ee1c7b7e8775ba3fbb04d07c4f946f0e4f11 Successfully built parse fake-useragent bs4 Installing collected packages: lxml, cssselect, pyquery, html2text, parse, chardet, urllib3, idna, requests, fake-useragent, beautifulsoup4, bs4, requests-html Successfully installed beautifulsoup4-4.6.0 bs4-0.0.1 chardet-3.0.4 cssselect-1.0.3 fake-useragent-0.1.10 html2text-2018.1.9 idna-2.6 lxml-4.1.1 parse-1.8.2 pyquery-1.4.0 requests-2.18.4 requests-html-0.1.1 urllib3-1.22
結構いっぱい入りますね。
- beautifulsoup4
- pyquery
- cssselect
たちが実行時に裏側で頑張っていると予想。
これでインストールは完了です。
軽く使ってみる
最初にimport
from requests_html import session
処理はこのsession
を起点に行うので、これだけimportしていれば基本使えます。
情報取得
次は、対象となる情報の取得です。今回は自分のブログの情報をちょこっと取得して遊んでみます。
r = session.get('http://devlights.hatenablog.com/')
html属性からリンク取得
session.get()
で取得したオブジェクトのhtml属性からいろいろ取得できます。
Readmeにあるみたいに、リンクを取得してみます。
リンクの取得は、r.html.links
とすれば全部取得できます。
そのままやると、ちょっと件数が多いので3件のみ表示。
ちなみに、r.html.links
の結果はset
オブジェクトとなっています。
list(r.html.links)[:3] ['https://stackoverflow.com/questions/16869024/what-is-pycache', 'https://docs.python.jp/3/using/cmdline.html#id1', 'http://zetcode.com/lang/java/']
こんな感じ。楽ですね。
jqueryチックに要素を取得
pyquery
みたいに、 jquery なセレクタが使えます。
今回は、自分のブログの最近のエントリのリンクを抽出しようと思います。
Chromeのデベロッパーツール使うと、最近のリンクの部分には
recent-entries-title-link
という class が設定されている模様。
セレクタを指定して取得する場合は、r.html.find()
を利用します。
print(r.html.find('.recent-entries-title-link', first=True))
結果はこんな感じ。ちょっと数が多いので、先頭のみ。
ちなみに、取得する際に first=True
と指定すると最初の要素のみ返してくれます。
<Element 'a' href='http://devlights.hatenablog.com/entry/2018/02/25/212126' class='urllist-title-link recent-entries-title-link urllist-title recent-entries-title'>
ちゃんと取得できましたね。
markdownに変換してもらう。
個人的に便利と思った機能。素晴らしい。
取得した要素に対して、markdown
属性を指定すると、markdown形式にしてくれます。
recent_entries = [elem.markdown for elem in r.html.find('.recent-entries-title-link')] for entry in recent_entries: print(entry, end='')
結果は以下のようになります。
[Pythonメモ-67 (JupyterLab試してみた) (JupyterLab is Ready for Users, conda, jupyterlab, PhosphorJS)](http://devlights.hatenablog.com/entry/2018/02/25/212126) [Pythonメモ-66 (pycファイルの生成が行われないようにする) (PYTHONDONTWRITEBYTECODE,sys.dont_write_bytecode, __pycache__,pyc)](http://devlights.hatenablog.com/entry/2018/02/23/124719) [zetcode さんのチュートリアルシリーズ (ZetCode turorials,沢山チュートリアルがあるサイト)](http://devlights.hatenablog.com/entry/2018/02/22/150217) [C#のサンプルコードが沢山あるサイト (1000 C# Programs With Example Code andOutput)](http://devlights.hatenablog.com/entry/2018/02/22/133515) [polacode (指定したソースコードを画像にしてくれる VS Code 拡張機能)(polanoid for your code, visualstudio code)](http://devlights.hatenablog.com/entry/2018/02/21/123728) [carbon(ソースコードをキレイなハイライト状態で画像にしてくれるサイト)](http://devlights.hatenablog.com/entry/2018/02/20/122639) [Pythonメモ-65 (send2trash) (ファイルをゴミ箱に捨ててくれるライブラリ,クロスプラットフォーム)](http://devlights.hatenablog.com/entry/2018/02/20/005539) [Pythonメモ-64 (contextlib.redirect_stdout) (stdoutの矛先を一時的に変更する,redirect_stderr)](http://devlights.hatenablog.com/entry/2018/02/20/001449) [いろいろな言語をREPLで試せるサイト (repl.it, C#, python, java, C++, Go,Ruby)](http://devlights.hatenablog.com/entry/2018/02/19/234327) [Pythonメモ-63 (vscodeのpython拡張でlinterが選択可能になった) (visual studio code, selectlinter, Jan 2018 Release)](http://devlights.hatenablog.com/entry/2018/02/15/152401)
すばらしい。
サンプル
以下サンプルソースです。
""" requests-html のサンプルです。 """ from requests_html import session def go(): # セッション開いて、情報取得 r = session.get('http://devlights.hatenablog.com/') # ページ内のリンク取得 print(r.html.links.pop()) # セレクタを指定して、jqueryチックに要素取得 selector = '.recent-entries-title-link' entries = r.html.find(selector) # markdownに変換 for entry in entries: print(entry.markdown, end='') if __name__ == '__main__': go()
ほかにも、XPathなども普通に使えるみたいなので、今まではpyquery使ってたけど、当面 requests-html で良さそう。
kennethreitzさん、素晴らしいライブラリを公開してくれてありがとうございます。
過去の記事については、以下のページからご参照下さい。
- いろいろ備忘録日記まとめ
サンプルコードは、以下の場所で公開しています。
- いろいろ備忘録日記サンプルソース置き場