Bye Bye Moore

PoCソルジャーな零細事業主が作業メモを残すブログ

Ubuntu 20.10 on Raspberry Pi 4B にSeleniumの環境を構築してスクレイピング その2:ログインしてページ遷移

shuzo-kino.hateblo.jp
の続き。
今度は、よくあるログインページを経由してトップページに遷移する方法について。

実際のところ

実行環境

スクリプト

ログインページ"LOGINPAGE"に

  • name「userid」がついたユーザー名フォーム
  • name「userpass」がついたパスワードフォーム
  • class「btn-login」がついたログインボタン

があるという想定で、これに入力しトップページ"TOPPAGE"に遷移するスクリプトは以下の通り。

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import time
from selenium import webdriver
from selenium.webdriver.chrome.options import Options

# ブラウザの場所は絶対PATHとして指定
CHROME_BIN    = "/usr/bin/chromium-browser"
CHROME_DRIVER = "/usr/lib/chromium-browser/chromedriver"

# LogIn Info
USER_ID   = 'YOURID'
USER_PASS = 'YOURPASS'

# TargetURL
LOGINPAGE = 'YOURLOGINSPAGE'
TOPPAGE     = 'YOURTOPPAGE'

# 実行オプション
options = Options()
options.binary_location = CHROME_BIN
options.add_argument("--remote-debugging-port=9696")  # sshでやるなら
options.add_argument('--headless')


# 実行インスタンス
print("start\r\n")
driver = webdriver.Chrome(CHROME_DRIVER, options=options)
time.sleep(3)

# URLに接続
print("Connect URL...\r\n")
driver.get(LOGINPAGE)

# 読み込み用の待機。性能に自信があるとかでない限り、やった方が無難。
time.sleep(3)

# ID/PASSを入力
print("Enter ID/PASS\r\n")
id = driver.find_element_by_name("userid")
id.send_keys(USER_ID)
password = driver.find_element_by_name("userpass")
password.send_keys(USER_PASS)

time.sleep(1)

# ログインボタンをクリック
print("Click Button\r\n")
login_button = driver.find_element_by_class_name('btn-login')
login_button.click()

# サイト内で他の画面に遷移させたければ
print("NextPage....\r\n")
driver.get(TOPPAGE)
time.sleep(5)

# 結果を変数に格納
html = driver.page_source

# 何かしら実行。今回はプリントするだけ
print(html)

# インスタンスを片付ける。整理整頓は基本。
driver.quit()

参考もと

qiita.com

RaspberryPi 4B上に組んだSlenium環境にSSHで繋いだらリモートデバッグ扱いになるので適正なオプションをつける

RaspberryPi 4B上に組んだSlemium環境にSSHで繋いだところ、”DevToolsActivePort file doesn't exist”とエラーに。
調べてみたところ、SSH越しではChromeのリモートデバッグという扱いになるようで、Selemiumにも適正なオプションをつけないといけないらしいです。

実際のところ

実行環境

問題のエラー

下のトコだけ切り出すと

selenium.common.exceptions.WebDriverException: Message: unknown error: DevToolsActivePort file doesn't exist

とでて、ポートを設定するファイルがないとかなんとか。
ポートと言われてもね……という感じでしたが、調べてみたところSSH越しではリモートデバッグという扱いになり
リモートデバッグ用のポートを割り付けてあげないといけないそうで。
……なるほどね??
developer.mozilla.org

前回の奴をベースにすると、オプションのところで"--remote-debugging-port=9222"というオプションを追加してあげるよう。

from selenium import webdriver
from selenium.webdriver.chrome.options import Options

# ブラウザの場所は絶対PATHとして指定
CHROME_BIN = '/usr/bin/chromium-browser'
CHROME_DRIVER = '/usr/lib/chromium-browser/chromedriver'

# 実行オプション
options = Options()
options.binary_location = CHROME_BIN
options.add_argument('--headless')
options.add_argument("--remote-debugging-port=9222")  # <= コレ

# 実行インスタンス
driver = webdriver.Chrome(CHROME_DRIVER, options=options)

#...処理

9222は調べたところ、特に有名ドコロと衝突してるわけではなさそうなので都合のいい数字に変更しても大丈夫です。
また、ufwでしっかりルールを決めているときは、それに従いましょう。

参考もと

stackoverflow.com

Ubuntu 20.10 on Raspberry Pi 4B にSeleniumの環境を構築してスクレイピング その1:環境構築とお試し

一日に一度、特定のサイトからファイルをダウンロードして別のサーバーにアップロードするという、実にクリエイティブな仕事が発生しました。

しかも遠くにある機体の内部でやれと……。

一瞬、そいつ用のラックトップPCに環境構築して送り付けようかと思いましたが、もしかしてRaspberryPi 4Bの8Gbyteで。

実際のところ

前提

そこそこ時間がかかるので、注意

pythonの環境

python3系がある状態で

pip install selenium

chromeにバイナリ

chromiumを最新に

$ sudo apt install chromium-browser

chrome-driverの確保(少し苦労

chrome-driverバイナリを確保します。
公式ページにはデスクトップ環境用のものしかなく、arm系のはありません。
仕方がないので、開発リポジトリに潜ります。
launchpad.net
へ行き、今回のターゲットである64bit版Ubuntuに対応したarm64系のビルドを探します。

$ wget https://launchpad.net/~canonical-chromium-builds/+archive/ubuntu/stage/+build/20989279/+files/chromium-chromedriver_88.0.4324.150-0ubuntu0.18.04.1_arm64.deb
$ sudo dpkg -i chromium-chromedriver_88.0.4324.150-0ubuntu0.18.04.1_arm64.deb
$ ls /usr/lib/chromium-browser/chromedriver
/usr/lib/chromium-browser/chromedriver

動作テスト

参考もと様のページそのまんま写経。

#!/usr/bin/env python
# -*- coding: utf-8 -*-
 
import time
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
 
# ブラウザの場所は絶対PATHとして指定
CHROME_BIN = "/usr/bin/chromium-browser"
CHROME_DRIVER = '/usr/lib/chromium-browser/chromedriver'
 
# 実行オプション
options = Options()
options.binary_location = CHROME_BIN
options.add_argument('--headless')
 
# 実行インスタンス
driver = webdriver.Chrome(CHROME_DRIVER, options=options)
 
# URLに接続
driver.get("https://www.google.co.jp")
 
# 読み込み用の待機。性能に自信があるとかでない限り、やった方が無難。
time.sleep(5)
 
# 結果を変数に格納
html = driver.page_source

# 何かしら実行。今回はプリントするだけ
print(html)

# インスタンスを片付ける。整理整頓は基本。
driver.quit()

あとは公式ドキュメントに沿って、写経したり実験したりすれば大抵の事はできるのかな、と。
https://www.selenium.dev/documentation/en/getting_started_with_webdriver/locating_elements/www.selenium.dev

Python3.6から導入されたフォーマット済み文字列リテラル

sprintfみたいなノリで、フォーマットの差し込みができるリテラルが3.6からついた様子。

実際のところ

10進数を文字列として埋め込む

value = 999

f"Value : {str(value)}\r\n"
#>>>'Value : 999\r\n'

print(f"Value : {str(value)}\r\n")
#>> Value : 999

桁やゼロ埋めの設定も可能

shuzo-kino.hateblo.jp
でやったHEX文字列まわりも、元数字を変数に格納して桁だのゼロ埋めの設定ができたり

value = 0x7e38
print(f"Value : {value:#08x}\r\n")
#>> Value : 0x007e38

参考もと

docs.python.org