82793


Python3とSelenium, openpyxlを使ってExcelのデータを読み込みYahoo! 乗換案内の検索をしています。

各駅を検索したらExcelのD列に処理済みの結果を記載しています。  
WEB上で検索できない場合、  
エラーが表示されたらループを抜けて、次のループに（日暮里）進み  
下記のようにフラグに処理済みのデータを記載したいです。  
エラーした場合処理済みのフラグを記載しないようにしたいです。

Excelデータ（実現内容）

No | 駅 | 駅2 | フラグ  
---|---|---|---  
1 | 東京 | 品川 | 処理済み  
2 | 原宿 | 原宿 |  
3 | 日暮里 | 秋葉原 | 処理済み  
4 | 東京 | 原宿 | 処理済み  
5 | 池袋 | @@@ |  
  
`try`でWEB側でエラーを検知して下記のコードに入れてみましたが、  
実現したい処理と上手く処理できず、  
全てのデータに処理済みと記載されます。  
`if`には検索後にタイトルを取得すれば処理済みのフラグを記載するように組みました。

`elese`のようにエラーしたら処理済みを記載しないようにプログラムを記載  
しましたが何故か全てのデータに処理済みと記載されます。

ご指導をお願いできますでしょうか。

[code]

       try:#タイトルを取得
            message = driver.find_element_by_xpath('//*[@id="cat-pass"]').text
            print(message)
            #Print結果：路線情報トップ > ルート、運賃検索結果
        except:
             print("error")   
    
        if "路線情報トップ > ルート、運賃検索結果"== message:
    
            # 処理済みのでデータをD列へ入力
            df.loc[i,'フラグ']='処理済み'
            print("処理済み・書込み")   
    
            #EXCEL保存 
            df.to_excel("test.xlsx", header=False, index=False)
    
        else:
            print("エクセルへフラグ記載しない")
    
[/code]

Excelデータ（現在の結果）

No | 駅 | 駅2 | フラグ  
---|---|---|---  
1 | 東京 | 品川 | 処理済み  
2 | 原宿 | 原宿 | 処理済み  
3 | 日暮里 | 秋葉原 | 処理済み  
4 | 東京 | 原宿 | 処理済み  
5 | 池袋 | @@@ | 処理済み  
  
code

[code]

    # Excel用ライブラリ読込
    import openpyxl
    from selenium.webdriver.common.keys import Keys
    import time
    from selenium.webdriver.chrome.options import Options
    from selenium.webdriver.support.select import Select  
    from selenium import webdriver
    from selenium.common.exceptions import NoSuchElementException
    import pyautogui
    import pandas as pd
    
    
    # Excelファイルを開く
    v_wb = openpyxl.load_workbook("test.xlsx")
    
    # アクティブなシートを変数へ
    v_ws = v_wb.active
    # シートのロード
    ws = v_wb.worksheets[0]
    
    # convert to pandas dataframe
    df = pd.DataFrame(ws.values)
    print("test")
    print(df)
    
    
    # generate search words 
    # sort=False データソートせずにエクセル順番で行う
    lst = df.iloc[0:,1:].values
    print(lst)
    df['フラグ'] = ''
    
    URL = "https://transit.yahoo.co.jp/"
    
    # ブラウザを開く。 #options=option background 
    options = Options()
    options.add_experimental_option('detach', True)
    driver = webdriver.Chrome(executable_path="C:\\Program Files\\chromedriver_win32\\chromedriver.exe", options=options)
    
    #ループ処理の部分とエクセルへの書き込み処理(行)が合っていないので、
    #row = 1を追加
    
    for i, query in enumerate(lst):
        # Googleの検索TOP画面を開く。
        if i > 0:
          driver.execute_script('window.open()')
        driver.switch_to.window(driver.window_handles[i])
        driver.get(URL)
    
        # 2秒待機
        time.sleep(2)
    
        # from
        fromid = driver.find_element_by_name("from")
        fromid.send_keys(query[0])
    
       # to
        to = driver.find_element_by_name("to")
        to.send_keys(query[1])
    
       #search
        time.sleep(2)
        pyautogui.press(['enter'])
    
     
        try:#タイトルを取得
            message = driver.find_element_by_xpath('//*[@id="cat-pass"]').text
            print(message)
            #Print結果：路線情報トップ > ルート、運賃検索結果
        except:
             print("error")   
    
        if "路線情報トップ > ルート、運賃検索結果"== message:
    
            # 処理済みのでデータをD列へ入力
            df.loc[i,'フラグ']='処理済み'
            print("処理済み・書込み")   
    
            #EXCEL保存 
            df.to_excel("test.xlsx", header=False, index=False)
    
        else:
            print("エクセルへフラグ記載しない")
    
    
[/code]


CC BY-SA 4.0
2021-09-16T07:38:08.117
82533
2021-10-01T08:56:20.703
2021-09-24T05:23:57.350
18859
18859
question
python python3
Python エラー処理方法とエクセルのデータを追記について


原因は`message`の中に以前に行われた正常な処理結果が残ったままだからですね。

以下のように`try ... except ...`の前に`message`をクリアするか：

[code]

        message = '' #### 空文字列でクリアしておく
        try:#タイトルを取得
            message = driver.find_element_by_xpath('//*[@id="cat-pass"]').text
            print(message)
            #Print結果：路線情報トップ > ルート、運賃検索結果
        except:
            print("error")
    
[/code]

こちらのように`処理済み`の書き込みを`try ... except ...`の中に組み込めば良いでしょう。

[code]

        try:#タイトルを取得
            message = driver.find_element_by_xpath('//*[@id="cat-pass"]').text
            print(message)
            #Print結果：路線情報トップ > ルート、運賃検索結果
            if "路線情報トップ > ルート、運賃検索結果"== message:
                # 処理済みのでデータをD列へ入力
                df.loc[i,'フラグ']='処理済み'
                print("処理済み・書込み")   
            else:
                print("エクセルへフラグ記載しない")
        except:
            print("error")
    
[/code]

* * *

それからいずれにしてもExcelへの書き込みは1件毎に行うのではなく、`for`ループが終了してからまとめて行う方が良いでしょう。

[code]

    #EXCEL保存 
    df.to_excel("test.xlsx", header=False, index=False)
    
[/code]

* * *

ちなみにExcel読み込み時の`v_wb = openpyxl.load_workbook("test.xlsx")`から`df['フラグ'] =
''`までの処理だと`No 駅 駅2
フラグ`のヘッダー行がデータ行の一部として取り込まれたり、そのため`フラグ`が列として認識されず欄がクリアされないので、元のExcelのフラグ列にデータがあるとクリアされなかったり、処理済みが書き込めなかったりしますので見直しておいた方が良いでしょう。

例えば質問の内容だと`OpenPyXL`での処理は不要なので、読み書き両方とも`pandas`で行うとか。  
読み込み：

[code]

    df = pd.read_excel("test.xlsx")
    
[/code]

書き込み

[code]

    df.to_excel("test.xlsx", index=False)
    
[/code]


CC BY-SA 4.0
2021-09-25T05:27:49.830
82679
2021-09-25T05:46:55.597
2021-09-25T05:46:55.597
26370
26370
82533
answer


下記の方法で`「if "路線情報トップ > ルート、運賃検索結果"== message:」`では条件分岐できていないので、そのコードから無くして  
`try`、`except`、`else`の順番に指定して希望の操作でできました。

FOR文からのコード

[code]

    for i, query in enumerate(lst):
        # Googleの検索TOP画面を開く。
        if i > 0:
          driver.execute_script('window.open()')
        driver.switch_to.window(driver.window_handles[i])
        driver.get(URL)
    
        # 2秒待機
        time.sleep(2)
    
        # from
        fromid = driver.find_element_by_name("from")
        fromid.send_keys(query[0])
    
       # to
        to = driver.find_element_by_name("to")
        to.send_keys(query[1])
    
       #search
        time.sleep(2)
        pyautogui.press(['enter'])
    
     
        try:#タイトルを取得
            message = driver.find_element_by_xpath('//*[@id="cat-pass"]').text
            print(message)
            #Print結果：路線情報トップ > ルート、運賃検索結果
        except:
             print("error")   
    
        else:
            print("処理済み・書込み") 
    
            # 処理済みのでデータをD列へ入力
            df.loc[i,'フラグ']='処理済み'
    
            #EXCEL保存 
            df.to_excel("test.xlsx", header=False, index=False)
    
[/code]


CC BY-SA 4.0
2021-10-01T08:40:49.010
82793
2021-10-01T08:56:20.703
2021-10-01T08:56:20.703
3060
18859
82533
answer