0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Webスクレイピング+PandasによるCSV出力の必要性と課題

Posted at

導入:Webスクレイピング+PandasによるCSV出力の必要性と課題

実務経験1〜3年目のエンジニアの皆さん、Web上からデータを自動で収集し、Pandasを使って解析・保存するフローは、日常業務やデータ活用に非常に役立ちます。しかし、HTML構造の変化によるエラー複数ページの処理漏れ、大量アクセスによるスクレイピング禁止リスクなど、実装時に注意すべき課題も多くあります。

背景:関連技術とトレンド

  • 昨今はPython+BeautifulSoup/Selenium+Pandasで、Webデータの取得→加工→保存の流れが一般的。
  • 特に、pandas.read_html() によるtable抽出は頻出ニーズ(公式ドキュメントにあるが詳細不足)
  • Seleniumを組み合わせた動的ページ対応も増加傾向

過去Qiitaで人気のコード例

  • BeautifulSoup + tableタグ抽出後→CSV出力(tr/tdループ)
  • Selenium+pandas.to_csv()による複数ページデータの取得自動化

技術的課題&エラー・パターン

  • table構造が変更されると、BeautifulSoupのセレクタが一致せずnull取得。
  • 多ページ取得でrequestsがタイムアウト、robots.txt非遵守によるアクセス禁止。
  • Seleniumのheadlessブラウザ起動時にドライバ不整合エラー。

公式ドキュメントの要点/ギャップ

  • Pandas公式では read_html() を推奨しているが、jsレンダリング非対応・ページ内tableが複数ある場合の対応が記載不足。
  • to_csv()はエンコーディングやインデックス制御が可能だが、実運用の細かい設定例が不足

実務で役立つTips/失敗例

  • requestsにタイムアウトやUser‑Agent指定を追加し、失敗時リトライ処理を入れる。
  • robots.txt確認&アクセス間隔にtime.sleep()挿入でAPI規約違反を回避。
  • CSV出力後、index=Falseを必ず指定し、列名や文字化けも確認。

具体的構成:Web→Pandas→CSV自動出力プログラム

ステップ1:必要ライブラリ・環境準備

pip install requests beautifulsoup4 pandas lxml selenium # 必要に応じて

※動的ページには Selenium、静的HTMLなら requests + BeautifulSoup + pandas でOK。

ステップ2:HTML取得と解析

import requests
from bs4 import BeautifulSoup
import pandas as pd
def fetch_static(url):
resp = requests.get(url, timeout=10, headers={'User-Agent':'Mozilla/5.0'})
resp.raise_for_status()
return resp.text
def parse_table(html):
soup = BeautifulSoup(html, 'lxml')
table = soup.find('table', {'class':'target-table'})
rows = []
for tr in table.find_all('tr'):
cols = [td.get_text(strip=True) for td in tr.find_all(['th','td'])]
if cols:
rows.append(cols)
df = pd.DataFrame(rows[1:], columns=rows[0])
return df

ステップ3:CSV出力まで

def save_csv(df, filename):
    df.to_csv(filename, index=False, encoding='utf-8-sig')
    print(f"✅ Saved {filename}")
def main():
url = 'https://example.com/data'
html = fetch_static(url)
df = parse_table(html)
save_csv(df, 'output.csv')
if name == 'main':
main()

ステップ4:複数ページ/JS対応

from selenium import webdriver
from bs4 import BeautifulSoup
def fetch_dynamic(url):
options = webdriver.ChromeOptions()
options.add_argument('--headless')
driver = webdriver.Chrome(options=options)
driver.get(url)
html = driver.page_source
driver.quit()
return html

必要に応じて fetch_static → fetch_dynamic に切り替えて利用。

ステップ5:マルチページ処理とエラー対策

import time
def multi_page(base_url, pages=5):
dfs = []
for p in range(1, pages+1):
url = f"{base_url}?page={p}"
html = fetch_static(url)
df = parse_table(html)
dfs.append(df)
time.sleep(1)  # アクセス間隔
return pd.concat(dfs, ignore_index=True)

ステップ6:出力プログラムまとめ

def run_all():
    base_url = 'https://example.com/list'
    df = multi_page(base_url, pages=10)
    save_csv(df, 'multi_output.csv')

ベストプラクティス・運用上の注意

  • 例外処理:requests.get()やSelenium起動はtry/exceptで囲む。
  • ログ出力:進行状況やエラーをログに残す。
  • robots.txt確認:リクエスト前に規約確認し、アクセス頻度を調整。
  • ファイル命名:日付やタイムスタンプを含めると管理しやすい。
  • エンコーディング:UTF‑8‑SIGでBOM付き出力し、Excel互換性を確保。

まとめと今後の展望

ここまで、Webスクレイピング→Pandasのデータフレーム化→CSVファイルに自動出力するまでの一連フローを、静的・動的サイト対応、マルチページ処理、運用上のガード(例外・ログ・robots.txt)までカバーしました。

今後は以下のような発展的取組がおすすめです:
・API取得→JSON→Pandas →CSV(公式APIがある場合)
・大規模データを扱う場合、分散処理やDaskによる高速化
・取得データの可視化やBI連携(例:Power BI、Tableau)

この構成をベースに、実務現場でのデータ自動収集・活用をぜひ進めてください。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?