확인했다1. selenium 라이브러리를 사용할 계획이다. bs4를 사용하려면 '웹 주소'를 알아야만 한다. 그러나 최근에는 사용자가 보는 페이지의 url을 알 수 없는 경우가 많다.
Beautiful Soup만으로 해결할 수 없는 상황
- 접근할 웹 주소를 알 수 없을때
- 자바스크립트를 사용하는 웹페이지의 경우(대부분 아닌가?)
- 웹 브라우저로 접근하지 않으면 안될 때
selenium:
- 웹 브라우저를 원격 조작하는 도구
- 자동으로 URL을 열고 클릭할 수 있음
- 스크롤, 문자의 입력, 화면 캡처 등등
2. selenium을 사용하려면 두 가지 과정을 거쳐야 한다.
1. Python 모듈을 설치하고,
2. Chrome 자체 모듈(확장프로그램)도 받아야 한다.
3. 먼저 사용자의 conda 가상환경에서 selenium을 설치해 주자.
* conda install conda-forge::를 사용하는 이유는 conda-forge커뮤니티에 훨씬 최신화된 버전의 라이브러리들이 업데이트되기 때문이다.
(Windows의 경우) conda install conda-forge::selenium
4. 그 다음 사용자의 chrome버전을 확인해야 한다. 오른쪽 상단의 점 세개 버튼을 누르고 '설정' 에 들어간다.
chrome://settings/
5. 좌하단에 있는 Chrome정보를 보면 자신의 크롬 버전을 알 수 있다.

6. 해당 정보를 바탕으로 크롬 드라이버를 설치해야 한다. 아래 페이지에 들어가서 instruction에 따라 크롬드라이버를 설치하자.
https://developer.chrome.com/docs/chromedriver/get-started?hl=ko
ChromeDriver 시작하기 | Chrome for Developers
이 페이지는 Cloud Translation API를 통해 번역되었습니다. ChromeDriver 시작하기 컬렉션을 사용해 정리하기 내 환경설정을 기준으로 콘텐츠를 저장하고 분류하세요. 이 페이지에서는 데스크톱 (Windows/M
developer.chrome.com
7. (115버전 이상의 경우) 크롬 115. 이상부터는 버전을 선택할 필요가 없다. 아래 페이지에서 자신의 버전에 호환되는 드라이버를 표시해주고 있다.
https://googlechromelabs.github.io/chrome-for-testing/
Chrome for Testing availability
chrome-headless-shellmac-arm64https://storage.googleapis.com/chrome-for-testing-public/123.0.6312.122/mac-arm64/chrome-headless-shell-mac-arm64.zip200
googlechromelabs.github.io

8. 자신의 버전에 맞는 링크를 복사하여 주소창에 붙여넣기 하면 다운로드가 된다.(웃긴 건 크롬 브라우저 스스로 의심스러운 다운로드라며 차단한다ㅋㅋ) 크롬브라우저의 차단과 윈도우 os의 차단 두 가지를 무시하고 압축파일을 자신이 사용하는 가상환경('data', 'source_code' 폴더를 만들어놓았다)의 'driver'라는 폴더를 만들어 그 안에 넣어 준다.
9. 그러면 셀레늄을 사용할 준비가 다 되었다. 되는지 테스트해보자.

*** 여기서 특이사항!!!! ***
최신화된 셀레늄(4.1버전 이상)부터는 크롬 드라이버가 필요가 없다. 원래는 아래의 코드처럼 사용자의 환경 안에 위에서 다운받은 크롬드라이버 파일을 넣고 그것을 통해 셀레늄을 실행했다고 한다. 그러나 최신 버전 셀레늄에서는 그런 것 없이도 코드를 실행해준다. 아래 이전 코드/최신 코드를 함께 남겨 둔다. 이는 jupyter notebook이나 다른 환경(java 등)에서도 마찬가지다.
# 4.1버전 이하의 경우
driver = webdriver.Chrome('../driver/chromedriver.exe') # 자신의 크롬드라이버 경로
driver.get('https://www.naver.com')
# 4.1버전 이상 최신 selenium의 경우
driver = webdriver.Chrome()
driver.get('https://www.naver.com')

*** 다시 셀레늄으로 돌아오자! ***
10. 셀레늄을 잘 동작시켰다면 이제 가장 기초적인 사용방법을 익혔다. 즉 selenium에서 webdriver모듈을 import하고, .get()명령어에 url을 넣어 페이지를 실행하는 것이다.
11. 스크롤 가능한 높이를 가져와보자. .execute_script명령어로 html에 자바스크립트 명령어를 적용할 수 있다!
last_height = driver.execute_script('return document.body.scrollHeight')
last_height
# 3104
12. 자바스크립트 명령어를 몇 가지 더 이용해보자. 스크롤을 화면 가장 밑으로 내리는 명령어를 실행해보자.
* javascript는 세미콜론(;)으로 코드를 마무리하는 것을 항상 기억하자. 이제 자바스크립트를 활용하므로, 기존 js문법을 이용해야 코드가 정상적으로 인식된다!
driver.execute_script('window.scrollTo(0, document.body.scrollHeight);')

scrollTo기능을 좀 더 잘 활용하려면, 크롬의 개발자 도구에서 xPath를 찾아오면 좋다. 찾은 요소를 클릭하여 해당 부분의 html을 표시하게 한 다음, copy -> copy xPath를 누르면 xPath가 복사된다.

해당 img까지의 xPath는 다음과 같다.
//*[@id="newsstand"]/div[3]/div[1]/ul/li[1]/div/a
*** 최신버전의 selenium은 find_element_by_xpath라는 메소드를 사용하지 않는다. selenium.webdriver.common.by에서 By를 import하여 사용한다. 코드는 다음과 같다.
from selenium.webdriver import ActionChains
from selenium.webdriver.common.by import By
some_tag = driver.find_element(By.XPATH, '//*[@id="newsstand"]/div[3]/div[1]/ul/li[1]/div/a')
action = ActionChains(driver)
action.move_to_element(some_tag).perform()
아래는 find_element의 docstring이다.
Signature: driver.find_element(by='id', value: Union[str, NoneType] = None) -> selenium.webdriver.remote.webelement.WebElement
Docstring:
Find an element given a By strategy and locator.
:Usage:
::
element = driver.find_element(By.ID, 'foo')
:rtype: WebElement
13. 이제 naver 검색창의 xpath를 구한 후 그곳에 검색어를 입력해보는 명령어를 실행해보자.
some_tag = driver.find_element(By.XPATH, '//*[@id="query"]')
some_tag.send_keys('data science')

14. 이번엔 검색 버튼을 찾아야 한다. 검색버튼의 xpath를 구한 다음에 눌러서 검색까지 실행해보자.
some_tag = driver.find_element(By.XPATH, '//*[@id="query"]')
some_tag.send_keys('data science')
xpath_search = '//*[@id="sform"]/fieldset/button'
some_tag = driver.find_element(By.XPATH, xpath_search).click()

15. 그렇다면 이제 바뀐 화면에서(검색결과화면에서) 링크를 검색하려면 어떻게 하면 좋을까? selenium은 강력한 라이브러리이지만, 셀레늄의 find_element명령어로 일일이 필요한 데이터를 검색하기엔 무리가 있다. 그래서 일반적으로 셀레늄을 이용해 검색창에 값 입력/검색버튼 클릭 등의 코드로 검색결과창까지 접근한 후, BeautifulSoup을 이용하는 경우가 많다.
from bs4 import BeautifulSoup
req = driver.page_source
soup = BeautifulSoup(req, 'html.parser')
soup

16. 이제 광고를 제외한 검색결과가 나타나는 태그를 찾거나 검색결과 하나하나를 의미하는 태그를 찾을 수 있다.

17. 이제까지 배운 내용을 바탕으로 유가 정보를 검색하여 분석해보자!
'데이터분석 > 미니프로젝트 03. 유가 분석' 카테고리의 다른 글
| 미니프로젝트 03-01-03. 주유소 가격 정리, 시각화 (2) | 2024.04.19 |
|---|---|
| 미니프로젝트 03-01-02. selenium으로 셀프주유소 데이터 확인 (1) | 2024.04.14 |