ログアウト中 ログイン

【Python】BeautifulSoup版スクレイピングツール開発講座 第4章4.2節「完全版アプリの作成」




現在の見出し:4.2節:完全版アプリの作成

見出し一覧

  • 4.2節:完全版アプリの作成
  • - os.path.exists()による重複保存防止機能の実装
  • - print()による処理状況表示機能の追加

【PR】『Python』を学べる企業・個人向けのプログラミングコース

os.path.exists()による重複保存防止機能の実装

前節(第4章 4.1節)で作成したコードを基盤として、os.path.exists()による既存ファイルの存在確認と重複保存防止機能を追加します。現在のプログラムプログラムはコンピュータに対して何をすべきかを指示する一連の命令です。では、CSVファイルを追記モードで開いているため、プログラムを再実行するたびにデータが蓄積され、ヘッダー行が重複する問題があります。

os.path.exists()関数関数は一定の処理をまとめたプログラムの塊です。は、指定したファイルパスファイルパスはコンピュータ上でファイルを特定するための指示書のようなものです。が存在するかを確認する標準的な方法です。この関数を使用することで、プログラム開始時にCSVファイルの存在を確認し、適切な処理分岐を実行できます。既存ファイルがある場合は上書き確認を行い、ない場合は新規作成することでデータの整合性を保てます。

ファイル状態 ユーザー選択 実行される処理 結果
ファイルが存在しない - 新規ファイル作成 scraped_data.csvを作成
ファイルが存在する 上書き(y) 既存ファイル削除・新規作成 scraped_data.csvを上書き
ファイルが存在する 保持(n) 連番付き新規ファイル作成 scraped_data_1.csvを作成

また、新しいファイル名の生成機能も重要な要素です。ユーザーが上書きを拒否した場合、連番付きの新しいファイル名を自動生成することで、既存データを保護しながら新しいデータを保存できます。この機能により、データの誤った上書きを防止し、安全なファイル管理を実現します。

# コード
import requests
from bs4 import BeautifulSoup
import csv
import os

# 重複保存防止機能を追加
filename = "scraped_data.csv"

if os.path.exists(filename):
    overwrite = input(f"{filename}が既に存在します。上書きしますか? (y/n): ")
    if overwrite.lower() == 'y':
        # 既存ファイルを削除して新規作成
        os.remove(filename)
        print("既存ファイルを削除しました")
    else:
        # 新しいファイル名を生成
        counter = 1
        while os.path.exists(f"scraped_data_{counter}.csv"):
            counter += 1
        filename = f"scraped_data_{counter}.csv"
        print(f"新しいファイル名: {filename}")

# CSVヘッダー作成
file = open(filename, 'w', newline='', encoding='utf-8')
writer = csv.writer(file)
writer.writerow(['見出し', 'URL'])
file.close()

# 継続実行機能
while True:
    # URL取得機能
    user_url = input("スクレイピングするURLを入力してください: ")
    print(f"入力されたURL: {user_url}")

    # HTTP接続エラー処理機能
    try:
        # HTMLデータを取得
        response = requests.get(user_url)
        
        # 通信状態確認機能
        if response.status_code == 200:
            print("接続成功")
            print(f"データサイズ: {len(response.text)}文字")

            # HTML解析機能
            soup = BeautifulSoup(response.text, 'html.parser')
            print("HTML解析完了")
            print(f"解析結果タイプ: {type(soup)}")

            # 特定タグ抽出機能
            title_element = soup.find('title')
            print("タイトルタグ抽出完了")
            print(f"抽出要素: {title_element}")

            # 文字データ取得機能
            if title_element:
                title_text = title_element.text
                print("文字データ取得完了")
                print(f"タイトル: {title_text}")
            else:
                print("タイトルタグが見つかりません")
                title_text = "タイトル不明"

            # 複数要素抽出機能
            h2_elements = soup.find_all('h2')
            print(f"h2タグ抽出完了: {len(h2_elements)}個")

            # 繰り返し処理機能(修正)
            file = open(filename, 'a', newline='', encoding='utf-8')
            writer = csv.writer(file)
            
            for element in h2_elements:
                h2_text = element.text.strip()
                writer.writerow([h2_text, user_url])
                
            file.close()
            print("複数データ保存完了")
        else:
            print(f"HTTPエラー: ステータスコード {response.status_code}")
            continue
            
    except requests.exceptions.RequestException as e:
        print(f"接続エラーが発生しました: {e}")
        print("別のURLを試してください")
        continue
    
    # 処理分岐機能
    choice = input("続けますか? (y/n/q): ")
    
    if choice.lower() == 'y':
        print("次のURLを入力してください")
        continue
    elif choice.lower() == 'n':
        print("一時停止します")
        continue
    else:
        print("プログラムを終了します")
        break

# 終了処理
print("スクレイピングツールを終了しました")
# 実行結果
scraped_data.csvが既に存在します。上書きしますか? (y/n): n
新しいファイル名: scraped_data_1.csv
スクレイピングするURLを入力してください: https://httpbin.org/html
入力されたURL: https://httpbin.org/html
接続成功
データサイズ: 3741文字
HTML解析完了
解析結果タイプ: <class 'bs4.BeautifulSoup'>
タイトルタグ抽出完了
抽出要素: <title>Herman Melville - Moby-Dick</title>
文字データ取得完了
タイトル: Herman Melville - Moby-Dick
h2タグ抽出完了: 0個
複数データ保存完了
続けますか? (y/n/q): q
プログラムを終了します
スクレイピングツールを終了しました
行数 種別 コード 解説
5行目 新規 import os ファイルの存在確認と削除を行うためのosライブラリライブラリは再利用可能なソフトウェアの部品です。をインポートします。Pythonの標準ライブラリに含まれているため追加インストール不要です。
8行目 新規 filename = "scraped_data.csv" CSVファイル名を変数変数はデータを一時的に記憶しておく場所です。として定義して、プログラム全体で統一して使用できるようにします。後の処理で再利用するため変数化します。
10行目 新規 if os.path.exists(filename): 指定したCSVファイルが既に存在するかを確認します。ファイルが存在する場合は上書き処理、存在しない場合は新規作成を行います。
11行目 新規 overwrite = input(f"{filename}が既に存在します。上書きしますか? (y/n): ") 既存ファイルの処理方法をユーザーに確認します。データの意図しない上書きを防ぐための重要な確認処理です。
14行目 新規 os.remove(filename) ユーザーが上書きを選択した場合、既存ファイルを削除します。os.remove()関数によりファイルシステムから完全に削除され、新規作成の準備が整います。
18行目 新規 counter = 1 新しいファイル名生成のためのカウンター変数を初期化します。連番付きファイル名の作成に使用する数値を設定します。
19行目 新規 while os.path.exists(f"scraped_data_{counter}.csv"): 連番付きファイル名が既に存在するかを確認するループループは一連の命令を繰り返し実行する構造です。です。存在しないファイル名が見つかるまで連番を増加させます。
21行目 新規 filename = f"scraped_data_{counter}.csv" 存在しない連番でファイル名を確定します。既存データを保護しながら新しいCSVファイルを作成するための名前を生成します。
25行目 新規 file = open(filename, 'w', newline='', encoding='utf-8') プログラム開始時にCSVファイルを新規作成してヘッダー行を事前に書き込みます。while文での重複ヘッダーを防止します。
27行目 新規 writer.writerow(['見出し', 'URL']) CSVファイルの最初の行にヘッダーを書き込みます。プログラム開始時に1回だけ実行することで、ヘッダーの重複を完全に防止します。
70行目 変更 file = open(filename, 'a', newline='', encoding='utf-8') 前節の固定ファイル名「scraped_data.csv」を変数filenameに変更して、動的に決定されたファイル名を使用します。
print()による処理状況表示機能の追加

第4章4.2節「print()による処理状況表示機能の追加」の続きを見る


すべてのカリキュラムを無料登録で学ぶ

プログラミング・マーケティング・AI活用方法を
今すぐ無料登録すると、全てのコンテンツが視聴可能になります。