SeleniumとPandasを使ったデータ収集の自動化
はじめに
要はスクレイピングです。
その方法として、SeleniumとPandasのコンビネーションがとても心地よかったのでまとめます。
Seleniumってブラウザテストに使われることが多いと思うんですが、こんなに安定したスクレイピング用のアプリってないよね、ってくらい使いやすい印象でした。webブラウザ上の作業を自動化するならとてもオススメしたいです。
では早速使い方のご紹介です。
環境構築
pythonの環境はAnacondaで一気に行いました。そういうところで悩みたくないので。Pandasなどもインストールされるので便利。
Seleniumはちゃちゃまるくんの記事を参考にpipでインストールしました。
実装した処理
とあるwebサイトの一覧画面のURLリストを予めテキストファイルにまとめておいて、
・そのURLを読み込み、
・ログインしてアクセスし、
・表示されたページから必要な情報を抜き出して、
・TSVファイルに纏めて出力する、
といったような処理です。
調べるページが2,3ページなら手でやったほうが早いかもしれませんが、それが100ページ超えてきたら流石に手でやるのは辛いと思います。
コンピュータはそういった反復処理が得意なので、スクリプティングしましょう。
処理の準備
データの読み込みとデータフレームの作成をしておきます。
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
import pandas as pd
from time import sleep
import os
# URLリストをまとめたファイル読み込み
f = open('url_list.txt')
url_data = f.read().splitlines()
# 空のデータフレーム
df = pd.DataFrame(columns=['カラム名1', 'カラム名2'])
必要なライブラリを読み込みます。
WebDriverとキー操作、pandasと動作をウェイトさせるためのsleepと、ファイルを取り扱うためのos。
f.read().splitlines()は、改行ごとに文字列区切って格納してくれます。
DataFrameはPandasの二次元データ構造を持つオブジェクトです。エクセルのような表のデータを格納できます。
ここではカラム名を2つ設定して、データは空っぽの状態です。
WebDriverでchromeを操作
chromeを起動して、サイトにID/PWDを自動入力し、ログインします。ID/PWDを入力する場所の指定はxpathをつかってます。
ID/PWDのxpathは、chromeのデベロッパーツールを立ち上げて、該当箇所をクリックし、右クリックからxpathでコピーするだけです。
driver = webdriver.Chrome()
driver.get("認証画面のURL")
# ID入力エレメント取得して入力
ele = driver.find_element_by_xpath("ID入力するエレメントのxpath")
ele.send_keys("ログインIDを記入")
#PWD入力エレメント取得して入力
ele = driver.find_element_by_xpath("パスワード入力するエレメントのxpath")
ele.send_keys("ログインパスワードを記入")
#Enterキーを押下
ele.send_keys(Keys.ENTER)
# 3秒間待機。
sleep(3)
リストのURLにアクセスし欲しいデータを読み取って保存
pythonの繰り返し文はfor-inとwhileがありますが、ここではfor-inをつかってます。
配列の個数だけ繰り返し処理します。iには配列の値がはいるのでファイルから読み込んだURLが格納されます。
また、アクセスする画面に欲しいデータが空っぽのケースを想定し、xpathで画面にアクセスしてテキストを持ってくる処理をtry-exceptで囲んで処理が止まらないようにします。
exceptionが返って来たらここでは半角スペースを変数に格納して次の処理に流してます。
そのあとに抜いて来たデータをDataframeに保存する処理ですが、一旦SeriesというPandasの一次元データ構造のオブジェクトに取って来たデータを格納して、Dataframeのappendメソッドでデータを追加しています。
# 繰り返し処理
for i in url_data:
#ページロード
driver.get(i)
sleep(3)
#初期化
hoshii_data1=" "
hoshii_data2=" "
# 名前と組織情報を抜き出す保存(try-exceptで囲み、データがないケースに対応する)
try:
hoshii_data1 = driver.find_element_by_xpath("長いので省略").text
except:
hoshii_data1 = " "
try:
hoshii_data2 = driver.find_element_by_xpath("長いので省略").text
except:
hoshii_data2 = " "
# Dataframeにデータ追加
df_add = pd.Series([hoshii_data1, hoshii_data2], index=df.columns)
df = df.append(df_add, ignore_index = True)
sleep(3)
#forループはここまで
データの出力
Dataframeの出力メソッドは充実してて、Excelファイルに出力することもできますが、ここではtsv出力をしてます。
tsv出力専用のメソッドは存在しないので、to_csvメソッドのセパレータをタブにすることで実現しています。
indexをfalseにしてるのは行番号を書き出さないようにするためです。
あとは立ち上げたアプリを終了して処理はおしまいです。
# Dataframe出力
df.to_csv("/保存するローカル環境のパス/ファイル名.tsv",sep="\t",index=False)
#webdriver終了
driver.close()
driver.quit()
#ファイル閉じる
f.close()
終わりに
最初for文でDataframeに1行ずつ追記する処理のところで苦戦してしまいました。
appendはSeriesを引数に取るので、一旦そこにデータを格納する必要があります。
Selenium WebDriverはスクショとかともとれるし、いろんなことができるので、web画面を使った単純作業の自動化にとても有用なソリューションだと思います。
W3C勧告されたようですし知っておいて損はないはず!
この記事が気に入ったらサポートをしてみませんか?