【Selenium】ドロップダウン/selectタグ選択,取得方法まとめ

- Python -
2024.01.04
Python[パイソン]

Python × Selenium × ChromeDriverで、select/optionタグで構成されるドロップダウン(プルダウン)リストを選択状態にしたり・値を取得する方法をまとめました。

SeleniumのSelectモジュールを使うと簡単に操作できます。

こんなHTMLを前提として書いていきます。

HTML<!DOCTYPE html>
<html>

<select name="test" id="dropdown">
    <option value="1">1番目</option>
    <option value="2">2番目</option>
    <option value="3">3番目</option>
    <option value="4">4番目</option>
    <option value="5">5番目</option>
    <option value="6">6番目</option>
</select>

</html>

この中の特定のoptionを選択状態にしたり、選択状態の選択肢のvalue, textを取得したり、全ての選択肢を取得したりします。

【Python × Selenium】ドロップダウンをSelectモジュールで選択/取得する

準備:Selectモジュール

  1. Selectモジュールのインポート
  2. select要素を find_element_by_xxx で取得する
  3. Selectオブジェクト生成

という手順で準備します。上記1, 2, 3は以下コメント1, 2, 3と照らし合わせてください。

Pythonimport chromedriver_binary
from selenium import webdriver
# ① Selectモジュールをインポート
from selenium.webdriver.support.select import Select
 
driver = webdriver.Chrome()
driver.get('http://127.0.0.1:5500/index.html')
 
dropdown = driver.find_element_by_id('dropdown') # ② select要素を取得
select = Select(dropdown) # ③ Selectオブジェクト生成

これでドロップダウンリストの選択肢をいじくり回す準備が完了です。

Selenium 3.x系と4.x系ではfind_element系メソッドの記法が異なります(上記コード9行目)。

本記事中ではselenium 3.x系で統一していますが、4.x系の場合は以下のように読み替えてください。4.x系の場合Byインポートを忘れずに。

Python# 3.x系
find_element_by_id("id")
find_element_by_name("name")
find_element_by_xpath("xpath")
find_element_by_link_text("link text")
find_element_by_partial_link_text("partial link text")
find_element_by_tag_name("tag name")
find_element_by_class_name("class name")
find_element_by_css_selector("css selector")


# 4.x系
from selenium.webdriver.common.by import By

find_element(By.ID, "id")
find_element(By.NAME, "name")
find_element(By.XPATH, "xpath")
find_element(By.LINK_TEXT, "link text")
find_element(By.PARTIAL_LINK_TEXT, "partial link text")
find_element(By.TAG_NAME, "tag name")
find_element(By.CLASS_NAME, "class name")
find_element(By.CSS_SELECTOR, "css selector")

インデックス指定で選択:select_by_index( )

Selectオブジェクトはselect_by_xxx( )というメソッドを使って特定の選択肢(option)を選択状態にできます。

最初はselect_by_index( )で、インデックス値で指定するパターン(以下4, 5行目)。

Pythondropdown = driver.find_element_by_id('dropdown')
select = Select(dropdown)

select.select_by_index(2)  # 3番目のoptionタグを選択状態に
select.select_by_index(len(select.options)-1)  # 最後のoptionタグを選択状態に

インデックスなので1つ目の選択肢は0からスタート。

5行目のようにSelect.optionsとすると、全てのoptionタグがWebElementのリストで返ってくるのでlen()関数で選択肢の数を数えることができます。

value="x"の値で選択:select_by_value( )

<option value="3">3番目</option>の"3"を指定して選択状態にしたい場合。

Pythondropdown = driver.find_element_by_id('dropdown')
select = Select(dropdown)

select.select_by_value('3') # valueが"3"のoptionタグを選択状態にする

選択肢テキストで選択:select_by_visible_text( )

<option value="3">3番目</option>の"3番目"を指定して選択状態にしたい場合。

Pythondropdown = driver.find_element_by_id('dropdown')
select = Select(dropdown)

select.select_by_visible_text('3番目') # "3番目"と表示されたoptionタグを選択状態にする

選択中の選択肢を取得:first_selected_option

これまでは「選択状態にするパターン」でしたが、これは「選択されたoption要素を取得して確認に利用するパターン」です。

こんな風↓にselected="selected"で初期値が設定されているとします。

HTML<!DOCTYPE html>
<html>

<select name="test" id="dropdown">
    <option value="1">1番目</option>
    <option value="2">2番目</option>
    <option value="3" selected="selected">3番目</option>
    <option value="4">4番目</option>
    <option value="5">5番目</option>
    <option value="6">6番目</option>
</select>

</html>

以下5行目Select.first_selected_optionとすると、選択状態になっているoption要素(WebElement)が返ってきます。

Pythondropdown = driver.find_element_by_id('dropdown')
select = Select(dropdown)

# 初期設定値を取得する
selected = select.first_selected_option
print(selected)
# -> <selenium.webdriver.remote.webelement.WebElement (session="a9a9ca9cd538a7e343d2f414c4f3c6a1", element="7603f68c-c14b-4a6d-bc98-436c9159ffcf")>
print(selected.text)
# -> 3番目
print(selected.get_attribute('value'))
# -> 3
print(selected.get_attribute('outerHTML'))
# -> <option value="3" selected="selected">3番目</option>

5行目でWebElementが返ってきているので、.text.get_attribute('属性名')などで値を引っこ抜くことができます。

全て/特定のoptionを取得:Select.options

Select.optionsで全てのoptionタグがリストになって返ってきます。

Pythondropdown = driver.find_element_by_id('dropdown')
select = Select(dropdown)

all_options = select.options # 全ての選択肢を取得(list)
for option in all_options:
    print(option.text) # 選択肢のテキスト
    print(option.get_attribute('outerHTML')) # HTMLタグ
    print(option.get_attribute('value')) # value属性の値
    print('----------------------------')

for文で回した6, 7, 8行目の出力はこうなります↓

$ python test.py
1番目
<option value="1">1番目</option>
1
----------------------------
2番目
<option value="2">2番目</option>
2
----------------------------
3番目
<option value="3" selected="selected">3番目</option>
3
----------------------------
4番目
<option value="4">4番目</option>
4
----------------------------
5番目
<option value="5">5番目</option>
5
----------------------------
6番目
<option value="6">6番目</option>
6
----------------------------

選択されている選択肢を全て取得:all_selected_options

<select name="xxx" multiple>とmultiple属性がついたselectタグで2つ以上の同時選択が可能な場合で、選択状態にある選択肢を全て取得したい場合。

Pythondropdown = driver.find_element_by_id('dropdown')
select = Select(dropdown)

select.select_by_index(2)  # 3番目を選択状態に
select.select_by_index(3)  # 4番目を選択状態に
selected = select.all_selected_options # 選択状態にある全ての選択肢を取得
print(selected[0].text)
# -> 3番目
print(selected[1].text)
# -> 4番目

選択を解除する系:deselect_xxx( )

<select name="xxx" multiple>とmultiple属性がついたselectタグで2つ以上の同時選択が可能な場合で、選択状態の選択肢を解除したい時。

1つ目の全て解除以外は、selectをdeselectに変えるだけなので簡単です。

  • .deselect_all()
    → 選択状態を全て解除
  • .deselect_by_index(2)
  • .deselect_by_value(2)
  • .deselect_by_visible_text('3番目')

・・・

以上、PythonのSeleniumでドロップダウンリストを操作する方法でした。

ドキュメントPython Selenium WebDriver API:Select Support

 

▼体型的なスクレイピング学習におすすめ

技術評論社Pythonクローリング&スクレイピング[増補改訂版] -データ収集・解析のための実践開発ガイド
Amazonで見る ≫
↑TOP