파이썬(Python)/웹스크롤링

셀레늄(Selenium) id, name, xpath, link_text, partial_link_text, tag_name, class_name, css_selector 로 엘리먼트(elements) 찾기 및 실습

끄적끄적아무거나 2021. 1. 23. 21:48
반응형

웹 페이지 element를 찾는 방법은 여러가지가 있다. 사용자는 셀레늄을 사용해서 가장 적절한 방법으로 찾으면 된다.  Selenium 에서는 아래 방법들을 통해 element를 찾을 수 있게 도와 준다.

 

- find_element_by_id
- find_element_by_name
- find_element_by_xpath
- find_element_by_link_text
- find_element_by_partial_link_text
- find_element_by_tag_name
- find_element_by_class_name
- find_element_by_css_selector

 

여러개의 element를 리스트형의 리턴으로 받으려면 아래 방법을 사용하면 된다.

 

- find_element_by_name 
- find_element_by_xpath 
- find_element_by_link_text 
- find_element_by_partial_link_text 
- find_element_by_tag_name 
- find_element_by_class_name 
- find_element_by_css_selector

 

위의 방법과 유사하지만 입력값안에 attribute 타입을 정해서 찾는 방식은 아래 와 같다.

 

- find_element
- find_elements

 

예제>>

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.instagram.com/")
time.sleep(1)
ele = driver.find_element(By.XPATH, '//*[@id="loginForm"]/div/div[3]/button')
print(ele) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="dc62c6afebfafc96d17bb3457076c445", element="c4ecbdb1-80df-49c8-99a6-9570145723bf")>

주석>>

인스타그램에 접속해서 로그인 버튼을 찾는 것이다. time.sleep은 화면이 로딩 되는 시간을 주기위해 주었다. find_element 로 버튼을 찾았다. find_elements 쓰면 여러개를 찾을 수 있다.

 

1. ID로 element 찾기

ID attribute를 이용할때 사용할 수 있다. 여러개 일 경우 첫번째 element가 나온다. 만일 해당 ID 가 없으면 NoSuchElementException 메세지가 뜰 것이다.

 

예제>>

위 그림은 네이버 화면의 소스코드 중 일부이다. 66번째 줄에 id attribute를 볼 수 있다.

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.naver.com/")
time.sleep(3)
ele = driver.find_element_by_id('NM_set_home_btn')
print(ele) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="19a1d0864968bc6bb8f0902128af4717", element="159a5310-f016-4f3e-86cd-1e7ba80b9f95")>

주석>>

id로 네이버 페이지 중 원하는 부분을 가져 올 수 있었다.

 

2. Name으로 element 찾기

name attribute를 이용할때 사용할 수 있다. 여러개 일 경우 첫번째 element가 나온다. 만일 해당 ID 가 없으면 NoSuchElementException 메세지가 뜰 것이다.

 

예제>>

위 그림은 네이버 화면의 소스코드 중 일부이다. 여러개의 name을 볼 수 있다.

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.naver.com/")
time.sleep(3)
ele = driver.find_element_by_name('bid')
print(ele) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="c48bce381ab785bcf42438ffc6d3d076", element="066cc29c-5205-4c49-b167-7ba484a8e18d")>

주석>>

name으로 네이버 페이지 중 원하는 부분을 가져 올 수 있었다.

 

3. XPath로 element 찾기

XPath는 XML 문서의 node 위치를 찾기위해 사용하는 표시등과 같은 것이다. HTML 문서는 XML 문서를 실행한것이므로 셀레늄은 XPath를 이용해서 웹 어플리캐이션에서 위치를 찾을 수 있다.

XPath를 사용하는 가장 큰 이유는 위치를 지정하려고 하는데 해당 element에 적절한 ID나 Name이 없는 경우가 있기 때문이다.  Absolute XPath (Full path)는 elements 까지의 모든 location을 포함하고 있고 그래서 만일 웹 어플리캐이션이 조금 수정되면 위치 찾기에 실패하게 된다. 상대적인 XPath는 찾고자 하는 Xpath와 상대적인 위치의 id나 name attribute를 이용해서 찾기 때문에 웹 어플리캐이션이 조금 바뀌어도 실패할 확율이 Absolute XPath 보다는 적다.

<html>
 <body>
  <form id="loginForm">
   <input name="username" type="text" />
   <input name="password" type="password" />
   <input name="continue" type="submit" value="Login" />
   <input name="continue" type="button" value="Clear" />
  </form>
</body>
<html>
login_form = driver.find_element_by_xpath("/html/body/form[1]")
login_form = driver.find_element_by_xpath("//form[1]")
login_form = driver.find_element_by_xpath("//form[@id='loginForm']")

위와 같은 웹페이지가 있다고 하면 절대적인 Xpath는 "/html/body/form[1]" 이다. 이때 form[0]이 아니라 form[1]이 첫번째 form문을 가르키니 실수 하지 말자. 상대적인 XPath는 "//form[1]"에서<html><body>를//로 표현한 것이다.

<> 구문이 3번 나오면 ///로 표현 해도 된다. 

만일 여러개의 form이 있다고 하면 form[1] 과 같이 번호로 구분지어도 되고 아니면 [@id='loginForm'] 와 같이 attribute 를 []안에 넣어서 특정하면 된다.

 

예제>>

 

원하는 xpath를 위와 같이 찾았다. 그리고 아래 코드를 통해 해당 element를 찾는다.

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.naver.com/")
time.sleep(3)
ele = driver.find_element_by_xpath('//*[@id="header"]/div[1]/div/div[1]/h1/a')
print(ele) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="8e2e6db2e7a000ca24d98c5bb8b1aeac", element="1548b809-0a71-4622-8125-7c108cfa12f3")>

주석>>

xpath를 통해 해당 element를 찾았다.

 

4. Link Text로 Hyperlinks element 찾기

link text attribute를 이용할때 사용할 수 있다. 여러개 일 경우 첫번째 element가 나온다. 만일 해당 ID 가 없으면 NoSuchElementException 메세지가 뜰 것이다.

 

예제>>

위 그림은 네이버 화면의 소스코드 중 일부이다. "뉴스스탠드"의 hyperlink를 찾아보겠다.

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.naver.com/")
time.sleep(3)
ele = driver.find_element_by_link_text('뉴스스탠드')
ele1 = driver.find_element_by_partial_link_text('뉴스스')
print(ele) 
print(ele1) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="af55697bd17adcd518f5aa02d38cf208", element="fcb32592-3b70-48cf-840c-fb40d3713e4a")>
<selenium.webdriver.remote.webelement.WebElement (session="af55697bd17adcd518f5aa02d38cf208", element="fcb32592-3b70-48cf-840c-fb40d3713e4a")>

주석>>

동일한 결과값을 리턴하였다. 

 

5. Tag Name으로 element 찾기

tag attribute를 이용할때 사용할 수 있다. 여러개 일 경우 첫번째 element가 나온다. 만일 해당 ID 가 없으면 NoSuchElementException 메세지가 뜰 것이다.

 

예제>>

위 그림은 네이버 화면의 소스코드 중 일부이다. _3h-N8T9V 클래스 element를 찾아보겠다.

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.naver.com/")
time.sleep(3)
ele = driver.find_element_by_class_name('div')
print(ele) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="5ca21e919b87bdbd4cb5d70812b86b8a", element="5dcdef50-3e47-487c-a383-334cbfb7cc76")>

주석>>

class를 통해 해당 element를 찾았다.

 

6. CSS Selector 로 element 찾기

css attribute를 이용할때 사용할 수 있다. 여러개 일 경우 첫번째 element가 나온다. 만일 해당 ID 가 없으면 NoSuchElementException 메세지가 뜰 것이다.

 

예제>>

5번의 _3h-N8T9V 클래스의 예제를 CSS Selector에도 적용해보겠다.

from selenium import webdriver
from selenium.webdriver.common.by import By
import time

options = webdriver.ChromeOptions() 
# options.headless = True
options.add_experimental_option("excludeSwitches", ["enable-logging"])
options.add_argument("user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64)/AppleWebKit/537.36 \
    (KHTML, like Gecko) Chrome/87.0.4280.66 Safari/537.36")
driver = webdriver.Chrome(options=options)
driver.get("https://www.naver.com/")
time.sleep(3)
ele = driver.find_element_by_class_name('_3h-N8T9V')
ele1 = driver.find_element_by_css_selector('a._3h-N8T9V')
print(ele) 
print(ele1) 

결과>>

<selenium.webdriver.remote.webelement.WebElement (session="2f44c80477212496267d76ad5e724268", element="1f4304a0-831d-4522-ab65-8881d0d2c766")>
<selenium.webdriver.remote.webelement.WebElement (session="2f44c80477212496267d76ad5e724268", element="1f4304a0-831d-4522-ab65-8881d0d2c766")>

주석>>

위와 같이 동일한 값을 리턴해주었다. 

 

 

 

 

 

 

 

반응형