【Python】Seleniumをヘッドレス(画面なし)で動かす方法・注意点

Python

今回は、Python×Seleniumで、ヘッドレスモード(画面なし)で実行する方法について紹介します。

ヘッドレスモードとは?

Seleniumのヘッドレスモードとは、ブラウザ画面を表示せずに実行するモードのことです。通常、Seleniumを実行するとブラウザが起動します。

しかし、ヘッドレスモードではブラウザは起動せず、中身の処理だけが行われます。

ヘッドレスのしくみ

Webページは、レンダリングエンジンというプログラムによって表示されます。レンダリングエンジンでは、画面上に表示するために文字や画像などの配置を計算し、その結果を表示しています。

通常モードではこの計算結果を描画するのに対し、ヘッドレスモードでは描画までは行いません。ただ、内部ではレンダリングエンジンにより生成されたWebページの構造を持っているため、これをもとにブラウザを操作できます。

ヘッドレスモードのメリット・デメリット

Seleniumのヘッドレスモードのメリット・デメリットについてまとめます。

メリット

ヘッドレスモードのメリット
  • 画面描画がないぶん、ページの読み込みを高速化できる
  • 画面描画がないぶん、CPUやGPUなどのリソース消費量が少ない

通常モードに比べて高速化・軽量化できる点がメリットとなっています。

デメリット

ヘッドレスモードのデメリット
  • ヘッドレスモード時のみエラーになる処理がある
  • ヘッドレスモードではアクセス拒否される場合がある

通常モードだとエラーにならないのに、ヘッドレスモードだとエラーになる場合があります。また、スクレイピング対策でヘッドレスモードだとアクセスを拒否されることがあります。オプションにユーザーエージェントを指定することで対策は一応可能です。

ヘッドレスモードで実行する方法

Seleniumをヘッドレスモードで実行するには、オプションにheadlessを指定します。

以下のコードは、Yahoo!JAPANのトップページから「ショッピング」メニューの要素を取得して、テキストを出力するという内容です。

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.chrome.options import Options

options = Options()
options.headless = True

# ブラウザを起動
driver = webdriver.Chrome(options = options)

# Googleを開く
driver.get('https://www.yahoo.co.jp/')

# 「ショッピング」の要素を取得
elem = driver.find_element(By.XPATH, '//*[@id="ToolList"]/ul/li[1]/div/a/p/span[1]/span')
print(elem.text)

# ブラウザを閉じる
driver.quit()

実行するとブラウザは表示されず、実行結果に要素のテキストが出力されます。

ヘッドレスモードは通常モードより遅いって本当?

ヘッドレスモードについて調べていると、「ヘッドレスモード 遅い」「通常よりヘッドレスのほうが遅い」という検索結果が出てきました。そこで、通常モードとヘッドレスモードで速度の差を確かめてみることにしました。

先ほどのコードを、通常モード・ヘッドレスモードそれぞれで10回実行し、かかる時間を計測します。計測処理については、ChatGPTに書いてもらいました。

通常モード(画面あり)headlessモード(画面なし)
9.18秒8.39秒

ヘッドレスのほうがやや速いという結果になりました。単純なコードすぎたかなと思い、画面遷移、入力、スクロールなどSeleniumの操作を一通り盛り込んだコードで比較してみても、やはりヘッドレスモードのほうが速い結果となりました。

なので、ヘッドレスモードで動かす際、速度に関してそこまで気にすることはないのかなと思います。

ヘッドレスモードでより早く実行するには、オプションにUser-Agentを設定するとよいという情報もありました。実際に試してみたところ、若干ですが処理時間が短縮されました。

ヘッドレスモード実行時の注意点

ヘッドレスモードでseleniumを実行するうえでの注意点をまとめます。

通常モードで成功していた処理が動かなくなる場合がある

ヘッドレスモードは、画面描画がないぶん通常モードよりも処理が早いです。そのため、取得したい要素がまだ出ていないのに取得処理が走ってしまいエラーになるケースがあります。

もしエラーが発生した場合は、以下のように待機処理を入れることが有効です。

# 5秒待機
import time
time.sleep(5)
# 要素が見つかるまで最大10秒待機(見つかったら処理が進む)
driver.implicitly_wait(10)

Selenium3までと書き方が異なる

Selenium4では、Selenium3までとオプション指定方法が異なります。

# Selenium3まで

options = Options()
options.add_argument('--headless')
# Selenium4

options = Options()
options.headless = True

Selenium3の書き方でも動きますが、将来のバージョンで削除されたり非推奨になる可能性があるので、新しい指定方法を使うようにしてください。

バグに気づきにくい

画面を表示している場合、「画面表示が小さいからクリックできないんだな」「まだ読み込めてないから失敗してるだな」とエラーの原因が目に見えて分かりやすいです。いっぽう、ヘッドレスモードだとエラーが発生した場合に、エラーメッセージのみで判断しなければなりません。

開発段階では通常モードで動かし、ある程度完成したらヘッドレスモードに切り替えると良いかと思います。

まとめ

今回は、Seleniumをヘッドレスモードで動かす方法について解説しました。

テストやスクレイピングなどで複数のブラウザを同時に何個も起動する際、通常モードだとたくさんウインドウが増えて、自分が使っているウインドウが埋もれてしまうことがあります。ヘッドレスモードにするとバックグラウンドで動かしつつ、開いているウインドウは自分が使っているものだけにできるので操作性も高まります。

当ブログでは、Python×Seleniumについての記事を他にも投稿していますので、是非参考にしてみてください。

chaso

文系出身、数字が苦手な平凡主婦。塾講師、大手企業SE、不動産事務、Webライター、結婚後はパートタイムでエンジニアをしています。機械音痴だけど効率化や自動化をこよなく愛しています!お仕事の依頼・ご相談は問い合わせよりお願いいたします♪

chasoをフォローする

コメント

タイトルとURLをコピーしました