スクレピングで画像を自動ダウンロード


お疲れ様です。@ibusanです。
今回はタイトルの通り、スクレイピングで画像を自動ダウンロードするプログラムを実装しました。
忘れたときに振り返れるよう備忘録的に記事に残しておこうと思います。

概要

単にスクレイピングと言っても、その対象は様々ですが、今回は、私が絶賛どハマり中のゲーム「プリンセスコネクト!Re:Dive」のファンキットを自動収集したいと思います。
手作業でやるには量が多いんですよね〜

準備

まず、スクレイピングをするための環境を整えます。
今回、構築した環境は以下の通りです。

  1. Anaconda
  2. ChromDriver

Anacondaはデータサイエンス向けのPythonパッケージなどを提供するプラットフォームです。
上記リンクからインストールできます。
ChromDriverはChromをプログラムで自動操作するために必要なドライバです。
Anacondaがインストールされていれば、

pip install chromedriver-binary=='ドライバのバージョン'

でインストールできます。ChromDriverのインストールは下記サイトが参考になると思います。
ChromDriverインストール手順

使用するライブラリについは、以下の通り。全てpipでインストールできます。

  1. selenium
  2. BeutifulSoup
  3. requests
  4. os
  5. time

方針

今回は以下の手順で実装を進めていきます。
1.ファンキットページの全ページ(よくある1ページ、2ページやつ)のURLを取得
2.各ページのファンキットのURLを全て取得
3.2で取得したURL先に遷移しファンキットをダウンロード

コーディング

方針が決まったのでコーディングに取り掛かります。

from selenium import webdriver
import time
import os
from bs4 import BeautifulSoup
import requests

まずは、ライブラリのインポートからです。準備で挙げた5つのライブラリをインポートします。

# GoogleChromを起動
browser = webdriver.Chrome("/Users/ibuki_sakata/opt/anaconda3/lib/python3.7/site-packages/chromedriver_binary/chromedriver")
browser.implicitly_wait(3)

次に、ChromDriverとseleniumを使って、Chromを起動します。2行目が起動するための記述になります。
カッコ内のパスはChromDriverのパスです。
3行目の記述は、ブラウザが起動するまで次の処理に進まないように、プログラムを一時停止するための記述です。

# URL先に移動
url_pricone = "https://priconne-redive.jp/fankit02/"
browser.get(url_pricone)
time.sleep(3)

1行目でファンキットのトップページのURLを指定し、2行目で指定したURL先に遷移しています。
browserのgetメソッドはhttp通信のgetメソッドと同様のものです。

# ファンキットの全WebページのURLを取得
current_url = browser.current_url
html = requests.get(current_url)
bs = BeautifulSoup(html.text, "html.parser")
fankitPage = bs.find("ul", class_="page-nav").find_all("li")
page = []

for li_tag in fankitPage:
    a_tag = li_tag.find("a")
    if(a_tag.get('class')):
        page.append(current_url)
    else:
        page.append(a_tag.get("href"))

ここで、1ページ目、2ページ目などの全ページのURLを取得します。
URLの取得にはBeautifulSoupを使用します。BeautifulSoupの使い方は、詳しく解説しているサイトがたくさんあるのでここでは説明しません。

# ファンキットのダウンロード
for p in page:
    html = requests.get(p)
    browser.get(p)
    time.sleep(1)
    bs = BeautifulSoup(html.text, "html.parser")
    ul_fankit_list = bs.find("ul", class_="fankit-list")
    li_fankit_list = ul_fankit_list.find_all("li")
    fankit_url = []
    for li_tab in li_fankit_list:
        a_tab = li_tab.find("a")
        fankit_url.append(a_tab.get("href"))

    for url in fankit_url:
        browser.get(url)
        time.sleep(1)
        html_fankit = requests.get(url)
        bs_fankit = BeautifulSoup(html_fankit.text, "html.parser")
        h3_tag = bs_fankit.find("h3")
        title = h3_tag.text
        os.makedirs(title, exist_ok=True)
        ul_dl_btns = bs_fankit.find_all("ul", class_="dl-btns")
        for i,ul_tag in enumerate(ul_dl_btns, start=0):
            li_tag = ul_tag.find("li")
            a_tag = li_tag.find("a")
            img_url = a_tag.get("href")
            browser.get(img_url)
            time.sleep(1)
            print(img_url)
            img = requests.get(img_url)
            with open(title + "/{}.jpg".format(i), "wb") as f:
                f.write(img.content)
        browser.back()

ここでファンキットのダウンロードを行います。基本はさっきと同じです。
requestsでhtmlのソースを取得し、それをBeautifulSoupで解析、欲しいタグを取得するという流れです。
画像のダウンロードはバイナリモードでファイルをオープンし、requestsで取得した画像データを書き込むことで行います。

実行結果

この様に、画像が各ファンキットごとにダウンロードされています。