[Python] Selenium 사용법

webdriver 다운로드

Selenium 사용전 사용하는 브라우저에 맞는 webdriver를 다운로드받아서 해당 파일이 있는 곳을 PATH에 추가해두는 것이 좋다. https://pypi.org/project/selenium/ 의 Drivers 섹션을 참고.

특정 페이지를 열기

from selenium import webdriver

driver = webdriver.Firefox()
driver.get("blog.dasomoli.org")

페이지를 열고 난 후 기다리기

어느 페이지를 열고 난 후 동작을 시작하려면 해당 페이지가 열렸을 때 나타나는 element를 기다려서 동작을 시작해야 한다. link text라면 다음과 같은 식으로 기다릴 수 있다. 아래에서 20은 20초를 의미한다. 첫번째 인자가 괄호로 둘러싸여 있음에 유의하라.

from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions as EC

element = WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.LINK_TEXT, "Ult-Build-1")))

다음처럼 어느 태그가 나타나길 기다릴 수도 있다.

from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions as EC

element = WebDriverWait(driver, 10).until(EC.text_to_be_present_in_element((By.TAG_NAME, "h1"), "Project INTEGRATED_BUILD_SYSTEM_TOOL"))

페이지 내의 특정 element 찾기

element = driver.find_element_by_name("userName")

element가 찾기 쉽게 id나, class name 등으로 되어 있다면 find_element_by_id() 혹은 find_element_by_class_name() 등으로 쉽게 찾을 수 있다. 아니라면 tag name 등으로 찾은 후 돌리면서 찾아본다. 함수명이 element가 아닌 elements 임에 유의하라.

import re

ultp = re.compile('^Ult-Build-[12].*')
ult_req = { }

elements = driver.find_elements_by_tag_name("tbody")
for tag in elements:
    if ultp.match(tag.text):
        wordlist = tag.text.split()
        if len(wordlist) >= 2:
            ult_req[wordlist[0]] = wordlist[1]

키 입력이나 클릭하기

찾은 element가 input과 같은 입력이 가능한 element라면 바로 send_keys()로 입력이 가능하다.

from selenium.webdriver.common.keys import Keys

element = driver.find_element_by_id("j_username")
element.send_keys("dasomoli")

element = driver.find_element_by_name("j_password")
element.send_keys("password", Keys.ENTER)

직접 element를 찾기 어렵다면 근처 element를 찾은 후 click한 후 key를 입력할 수도 있다.

from selenium.webdriver.common.action_chains import ActionChains

elements = driver.find_elements_by_class_name("setting-name")
for element in elements:
    if element.text == "P4_Shelve_CLs":
        shelve_element = element

actions = ActionChains(driver)
actions.move_to_element_with_offset(shelve_element, shelve_element.rect['width'] + 5, shelve_element.rect['height'] / 2).click().send_keys("12345678", Keys.ENTER)
actions.perform()

send_keys() 대신 click() 을 이용하면 마우스 클릭이 가능하다. 마우스 클릭 지점을 찾기 힘들 때는 context_click()을 사용하면 우클릭되는데, 이 때 나타나는 context menu로 클릭 지점을 대충 파악할 수 있다.

마우스 클릭 등으로 선택된 element를 얻기

actions = ActionChains(driver)
actions.move_to_element_with_offset(workspace_element, workspace_element.rect['width'] + 23, workspace_element.rect['height'] / 2).click()
actions.perform()
element = driver.switch_to.active_element

select form에서 값 선택

from selenium.webdriver.support.ui import Select

select = Select(element)
if value != "":
    select.select_by_visible_text(value)
else:
    select.select_by_index(0)

참고

  1. Selenium with Python – Read the Docs
  2. Selenium Documentation
  3. Selenium Browser Automation Project (한글 버전도 있다)