→コード: v4.1.3 reCAPTCHAでbot検知された場合に自動で再起動する
>Fet-Fe (→コード: v4.1.2) |
>Fet-Fe (→コード: v4.1.3 reCAPTCHAでbot検知された場合に自動で再起動する) |
||
7行目: | 7行目: | ||
"""Twitter自動収集スクリプト | """Twitter自動収集スクリプト | ||
ver4.1. | ver4.1.3 2023/10/22恒心 | ||
当コードは恒心停止してしまった https://rentry.co/7298g の降臨ショーツイート自動収集スクリプトの復刻改善版です | 当コードは恒心停止してしまった https://rentry.co/7298g の降臨ショーツイート自動収集スクリプトの復刻改善版です | ||
78行目: | 78行目: | ||
from bs4.element import NavigableString, ResultSet, Tag | from bs4.element import NavigableString, ResultSet, Tag | ||
from selenium import webdriver | from selenium import webdriver | ||
from selenium.common.exceptions import WebDriverException | from selenium.common.exceptions import (InvalidSwitchToTargetException, | ||
WebDriverException) | |||
from selenium.webdriver.common.by import By | from selenium.webdriver.common.by import By | ||
from selenium.webdriver.firefox.options import Options as FirefoxOptions | from selenium.webdriver.firefox.options import Options as FirefoxOptions | ||
381行目: | 382行目: | ||
def _check_recaptcha(self, url: str) -> None: | def _check_recaptcha(self, url: str) -> None: | ||
"""reCAPTCHAが表示されているかどうか判定して、入力を待機する。 | """reCAPTCHAが表示されているかどうか判定して、入力を待機する。 | ||
botであることが検知された場合、自動でブラウザを再起動する。 | |||
Args: | Args: | ||
388行目: | 391行目: | ||
Raises: | Raises: | ||
ReCaptchaRequiredError: JavaScriptがオフの状態でreCAPTCHAが要求された場合のエラー。 | ReCaptchaRequiredError: JavaScriptがオフの状態でreCAPTCHAが要求された場合のエラー。 | ||
""" | """ | ||
if len(self._driver.find_elements(By.ID, 'g-recaptcha')) > 0: | if len(self._driver.find_elements(By.ID, 'g-recaptcha')) > 0: | ||
396行目: | 396行目: | ||
logger.warning(f'{url} でreCAPTCHAが要求されたナリ') | logger.warning(f'{url} でreCAPTCHAが要求されたナリ') | ||
print('reCAPTCHAを解いてね(笑)、それはできるよね。') | print('reCAPTCHAを解いてね(笑)、それはできるよね。') | ||
print(' | print('botバレしたら自動でブラウザが再起動するナリよ') | ||
self._driver.switch_to.frame( # reCAPTCHAのフレームに遷移する | |||
self._driver, | self._driver.find_element( | ||
self.WAIT_TIME_FOR_RECAPTCHA).until( # type: ignore | By.CSS_SELECTOR, | ||
'iframe[title="recaptcha challenge expires in two minutes"]' | |||
) | |||
self._random_sleep() # DoS対策で待つ | ) | ||
self. | try: | ||
WebDriverWait( | |||
self._driver, | |||
self.WAIT_TIME_FOR_RECAPTCHA).until( # type: ignore | |||
ec.visibility_of_element_located( | |||
# bot検知された場合に現れるクラス | |||
(By.CLASS_NAME, 'rc-doscaptcha-header') | |||
) | |||
) | |||
except InvalidSwitchToTargetException: | |||
# reCAPTCHAのフレームがなくなっていた場合 | |||
logger.info('reCAPTCHAが解かれましたを') | |||
self._driver.switch_to.default_content() | |||
self._random_sleep() # DoS対策で待つ | |||
else: | |||
# waitを普通に抜けた場合 | |||
logger.warn('botバレしたなりを') | |||
# 一回ブラウザを落として起動し直す | |||
self.quit() | |||
self._refresh_browser() | |||
self.get(url) | |||
else: | else: | ||
raise ReCaptchaRequiredError( | raise ReCaptchaRequiredError( | ||
526行目: | 546行目: | ||
except AccessError: | except AccessError: | ||
logger.warning( | logger.warning( | ||
url | url + 'への通信失敗ナリ ' | ||
+ f'{i}/{self.LIMIT_N_REQUESTS}回') | + f'{i}/{self.LIMIT_N_REQUESTS}回') | ||
if i < self.LIMIT_N_REQUESTS: | if i < self.LIMIT_N_REQUESTS: |