tooh’s diary

半角全角、常体敬体が入り乱れるカオス

Pythonでスクレイピング 1-3,1-4/CSSセレクタ,再帰処理でリンク先を丸ごとダウンロード

1-3

DOM(Document Object Model)の話。正直HTMLとの違いがわかりません......。DOMの要素を引っ張ってくる為の話をしてました。

ブラウザを利用したセレクタの利用例(青空文庫で公開されている夏目漱石の作品一覧を取得するプログラム)

1:「ページのソースを表示」をクリック
f:id:saguh:20190917040750p:plain

2:「要素」をクリック→選択した部分の上で「要素の詳細を表示」をクリック
f:id:saguh:20190917040941p:plain

3:要素のCSSセレクタをコピー
f:id:saguh:20190917041321p:plain

このようにして得られたCSSセレクタの値は
body > ol:nth-child(8) > li:nth-child(1)
となる。これは、「HTMLで上から辿っていくと、<body>→8番目に出てくる<ol>タグ→1番目に出てくる<li>タグが指しているのが、今回の『イズムの功過』なんだよ」という意味。こんな感じで、このページのHTMLの構造を掴んだら、いよいよ作品一覧を取得するプログラムを書く。

from bs4 import BeautifulSoup
import urllib.request as req

url = 'https://www.aozora.gr.jp/index_pages/person148.html'
res = req.urlopen(url)
soup = BeautifulSoup(res, 'html.parser')

#select(セレクタ)はセレクタを複数取り出してリストの形で持つ
li_list = soup.select('ol > li')
for li in li_list: #ここのliは、<li><a href = ~~>(アンカーテキスト)</a>(アンカーテキスト)</li>という形をしている
    a = li.a #aは何も適当に決めたわけではなく、<li>の中の<a href = ~~>(アンカーテキスト)</a>を取ってきたものになる
    if a != None:
        name = a.string #aのアンカーテキストを取ってくる
        href = a.attrs['href'] #URL部分の取得
        print(name, '>', href)

上の例では、セレクタを'ol > li'としていた。これは、「<ol>の直下に<li>がありますよ(そこからliの要素を取ってきてねん)」という意味だった。
CSSセレクタはこの他にも色々な書き方がある。(ここでは割愛)


1-4

相対パス絶対パスの違いの話。
https://webliker.info/78726/

<a>タグのリンク先が外部サイトであれば、絶対パスにしなければならない。(相対パスは、あくまで同じサーバー内での話)というわけで、相対パス絶対パスに直すための工夫をする。

相対パス絶対パスに直すには、urllibのparse.urljoin()を使う。urljoin(基本となるURL,解決したいパス)と入れる。


・リンク先を丸ごとダウンロードするために、途中でぶった切られないようにウェブページを再帰的にダウンロードすることが必要。

(最後に書いてあったコードは長いのでパス。まあそのうち向き合うっしょ!w)



余談:はてな記法で書いてると、<a>とかって書いた時に普通にリンク見たいな感じになってウケる
こんな感じ