質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.35%
Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

selenium

Selenium(セレニウム)は、ブラウザをプログラムで作動させるフレームワークです。この原理を使うことにより、ブラウザのユーザーテストなどを自動化にすることができます。

Q&A

解決済

1回答

2708閲覧

画面に要素が表示されていないのにも関わらす、is_displayed()がtrue判定になる

Sakamotos

総合スコア7

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

selenium

Selenium(セレニウム)は、ブラウザをプログラムで作動させるフレームワークです。この原理を使うことにより、ブラウザのユーザーテストなどを自動化にすることができます。

0グッド

1クリップ

投稿2021/11/20 00:40

編集2021/11/20 00:56

前提・実現したいこと

旅行サイトの一休の口コミをスクレイピングして、CSVファイルにデータ化したい。
※このページをスクレイピングしたい↓↓
https://www.ikyu.com/00001917/#review-modal

動作環境
Python 3.9.2
macOS 12.0.1

該当のソースコード

python

1from selenium import webdriver 2from selenium.webdriver.chrome.options import Options 3from selenium.common.exceptions import NoSuchElementException 4from webdriver_manager.chrome import ChromeDriverManager 5import pandas 6import time 7 8options = Options() 9options.add_argument('--headless') 10options.add_argument("--no-sandbox") 11driver = webdriver.Chrome(ChromeDriverManager().install(), options=options) 12 13url = 'https://www.ikyu.com/00001917/#review-modal' 14driver.get(url) 15 16# 「口コミをもっと見る」のボタンがなくなるまでクリックを続ける 17while True: 18 try: 19 element = driver.find_element_by_css_selector('.WordOfMouth-ikyu__showMore--21ctT') 20 # print(element.is_displayed()) 21 if element.is_displayed(): 22 time.sleep(1) 23 element.click() 24 else: 25 break 26 except NoSuchElementException: 27 break 28 29body = driver.find_elements_by_xpath("//dd[@class='WordOfMouth-ikyu__reviewContentsFusuma--TZ3NI']/p[1]") 30date = driver.find_elements_by_class_name('WordOfMouth-ikyu__postedDate--1YawZ') 31 32l=[] 33for d, b,in zip(date, body): 34 data={} 35 data["口コミ"]=b.text 36 data["投稿日"]=d.text 37 l.append(data) 38 39# ドライバーを終了させる 40driver.quit() 41 42df=pandas.DataFrame(l) 43df.to_csv("一休.csv", encoding='utf_8_sig') 44df

このコードを実行して、Webブラウザを実行してスクレイピングをしているのですが、下の画像のようにページ分「クチコミをもっと見る」をクリックしないと全ての口コミが表示されないようになっております。口コミが全件表示された後はこのボタンの要素はdisplay:none;となり画面からは表示されない仕様となっております。
イメージ説明

そのため、element.is_displayed()で要素が表示されているか判定してクリックを押すようにしているのですが、print(element.is_displayed())で確認してみると全てボタンを全て押し切り、該当の要素がdisplay:none;となった後もtrue判定が返ってきてしまします。そのせいでElementNotInteractableException: Message: element not interactableのエラーが発生しております。

python

1# 「口コミをもっと見る」のボタンがなくなるまでクリックを続ける 2while True: 3 try: 4 element = driver.find_element_by_css_selector('.WordOfMouth-ikyu__showMore--21ctT') 5 print(element.is_displayed()) 6 if element.is_displayed(): 7 time.sleep(1) 8 element.click() 9 else: 10 break 11 except NoSuchElementException: 12 break

発生している問題・エラーメッセージ

True True True True --------------------------------------------------------------------------- ElementNotInteractableException Traceback (most recent call last) /var/folders/cq/jc48y6vj3gj0rp8l7ym9n7tm0000gn/T/ipykernel_77247/2946560853.py in <module> 21 if element.is_displayed(): 22 time.sleep(1) ---> 23 element.click() 24 else: 25 break /usr/local/lib/python3.9/site-packages/selenium/webdriver/remote/webelement.py in click(self) 78 def click(self) -> None: 79 """Clicks the element.""" ---> 80 self._execute(Command.CLICK_ELEMENT) 81 82 def submit(self): /usr/local/lib/python3.9/site-packages/selenium/webdriver/remote/webelement.py in _execute(self, command, params) 691 params = {} 692 params['id'] = self._id --> 693 return self._parent.execute(command, params) 694 695 def find_element(self, by=By.ID, value=None): /usr/local/lib/python3.9/site-packages/selenium/webdriver/remote/webdriver.py in execute(self, driver_command, params) 416 response = self.command_executor.execute(driver_command, params) 417 if response: --> 418 self.error_handler.check_response(response) 419 response['value'] = self._unwrap_value( 420 response.get('value', None)) /usr/local/lib/python3.9/site-packages/selenium/webdriver/remote/errorhandler.py in check_response(self, response) 241 alert_text = value['alert'].get('text') 242 raise exception_class(message, screen, stacktrace, alert_text) # type: ignore[call-arg] # mypy is not smart enough here --> 243 raise exception_class(message, screen, stacktrace) 244 245 def _value_or_default(self, obj: Mapping[_KT, _VT], key: _KT, default: _VT) -> _VT: ElementNotInteractableException: Message: element not interactable

公式ドキュメントも確認してみましたが、画面に表示されているかどうか(display:none;がスタイルに適用されているか)もis_displayed()で判定できるかと思っているのですが、コード上何か間違いがあるのか、
または、display:none;がスタイルに適用されているかを判定する方法が間違っている場合、is_displayed()以外の適切なメソッドがあれば教えていただけましたら幸いです。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

otn

2021/11/20 01:42

間違ってはいないと思うので、is_displayedを見る前にsleepを入れてみてはどうでしょうか。
Sakamotos

2021/11/20 03:01

otn様 ご回答ありがとうございます。is_displayedの前にsleepを入れることで正常に判定され解決できました。m(_ _)m
guest

回答1

0

自己解決

sleepの位置をif element.is_displayed()の前に変更することで解決いたしました。

python

1# 「口コミをもっと見る」のボタンがなくなるまでクリックを続ける 2while True: 3 try: 4 element = driver.find_element_by_css_selector('.WordOfMouth-ikyu__showMore--21ctT') 5 time.sleep(1) 6 if element.is_displayed(): 7 element.click() 8 else: 9 break 10 except NoSuchElementException: 11 break

投稿2021/11/20 05:17

Sakamotos

総合スコア7

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.35%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問