웹 스크래핑 (1)

Junho_Mun·2025년 9월 6일

웹 데이터를 수집하는 기술인 웹 스크래핑(Web Scraping)은 파이썬의 requestsBeautifulSoup4(bs4)를 활용할 수 있다.

1. 웹 스크래핑과 크롤링

웹 스크래핑은 특정 웹 페이지에서 원하는 데이터만 골라내어 추출하는 기법이다.
그와 비슷한 용어로 웹 크롤링(Web Crawling)은 인터넷을 이것 저곳 탐색하며 직접 필요한 정보를 추출하는 것이다.
이 글은 웹 스크래핑을 파이썬으로 해보는 것에 초점이 맞추어져 있다.

2. Requsts 라이브러리

requests 라이브러리는 파이썬으로 HTTP 요청을 보내 웹 페이지의 전체 HTML 소스 코드를 가져오는 역할을 한다.

import requests

url = "https://weather.naver.com/today/06170105"

# 해당 url로 get 요청 보내기
response = requests.get(url)

print("status code : ", response.status_code)

url_html = response.text
print(url_html)
>>>
status code :  200
<!doctype html>
<html lang="ko" data-platform="pc" data-useragent="python-requests/2.32.5" class="">
    <head>
        <meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
... 이하 계속

위와 같이 requests.get() 으로 해당 url로 요청을 보내어 HTML 소스 코드를 통째로 가져올 수 있다.
또, request.status_code 를 사용하여 해당 메서드가 성공적으로 데이터를 가져왔는지 확인도 할 수 있다 !!

3. beautiful soup4 라이브러리

beautifulSoup4(bs4) 라이브러리는 requests 가 가져온 HTML 소스 코드의 태그 구조를 분석하여 파싱하여 원하는 데이터를 편리하게 추출하도록 도와준다.

BeautifulSoup(html,'html.parser') 를 활용하여 HTML 소스 코드를 분석 가능한 객체로 변환하며,

  • soup.find(’태그명’) : 조건에 맞는 첫 번째 태그를 탐색한다.
  • soup.find_all('태그명') : 조건에 맞는 모든 태그를 리스트 형태로 저장한다.
  • soup.select('CSS 선택자') : CSS 선택자를 사용해 원하는 태그를 더 정교하게 탐색한다.

먼저 웹 페이지의 HTML에서 필요한 데이터가 무엇인지 찾는다.
https://github.com/Door-Juno 의 html 을 가져와 보았다.

https://github.com/Door-Juno의 html 중
...
<title>Door-Juno (Junho Moon) · GitHub</title>
...
<article class="markdown-body entry-content container-lg f5" itemprop="text"><div class="markdown-heading" dir="auto"><h1 class="heading-element" dir="auto">Door-Juno 문준호의 profile</h1><a id="user-content-door-juno-문준호의-profile" class="anchor" aria-label="Permalink: Door-Juno 문준호의 profile" href="#door-juno-문준호의-profile"><svg class="octicon octicon-link" viewBox="0 0 16 16" version="1.1" width="16" height="16" aria-hidden="true"><path d="m7.775 3.275 1.25-1.25a3.5 3.5 0 1 1 4.95 4.95l-2.5 2.5a3.5 3.5 0 0 1-4.95 0 .751.751 0 0 1 .018-1.042.751.751 0 0 1 1.042-.018 1.998 1.998 0 0 0 2.83 0l2.5-2.5a2.002 2.002 0 0 0-2.83-2.83l-1.25 1.25a.751.751 0 0 1-1.042-.018.751.751 0 0 1-.018-1.042Zm-4.69 9.64a1.998 1.998 0 0 0 2.83 0l1.25-1.25a.751.751 0 0 1 1.042.018.751.751 0 0 1 .018 1.042l-1.25 1.25a3.5 3.5 0 1 1-4.95-4.95l2.5-2.5a3.5 3.5 0 0 1 4.95 0 .751.751 0 0 1-.018 1.042.751.751 0 0 1-1.042.018 1.998 1.998 0 0 0-2.83 0l-2.5 2.5a1.998 1.998 0 0 0 0 2.83Z"></path></svg></a></div>
<ul dir="auto">
<li>
<p dir="auto">경북대학교 식품공학부 식품응용공학전공 재학중 (2022 ~)</p>
</li>
<li>
<p dir="auto">경북대학교 컴퓨터학부 인공지능컴퓨팅 복수전공</p>
</li>
<li>
<p dir="auto">Velog link : [<a href="https://velog.io/@door_jono/posts" rel="nofollow">https://velog.io/@door_jono/posts</a>]</p>
</li>
</ul>
</article>
  </div>
</div>
...

저 정보들을 파싱하여 가져와보자 !

import requests
from bs4 import BeautifulSoup

url = "https://github.com/Door-Juno"

# HTML 가져오기
response = requests.get(url)
html_text = response.text

# HTML 파싱하기
soup = BeautifulSoup(html_text,'html.parser')

title = soup.select_one('title').text
list_data = soup.select('li p[dir="auto"]')

# 출력하기
print(f"제목 : {title}")
print(f"정보 리스트 : {list_data}")
제목 : Door-Juno (Junho Moon) · GitHub
정보 리스트 : [
	<p dir="auto">경북대학교 식품공학부 식품응용공학전공 재학중 (2022 ~)</p>, 
	<p dir="auto">경북대학교 컴퓨터학부 인공지능컴퓨팅 복수전공</p>,
	<p dir="auto">Velog link : [<a href="https://velog.io/@door_jono/posts" rel="nofollow">https://velog.io/@door_jono/posts</a>]</p>
	]

결과를 보면 .text 가 없었기 때문에 전체 태그를 다 가져온 것을 볼 수 있다.
soup.select('li p[dir="auto"]') 는 조건에 맞는 모든 태그를 찾아 리스트 형식으로 반환하기 때문에 , 이 리스트인 list_data 에는 .text 라는 속성이 없다. 그러므로 리스트의 요소들을 하나씩 거내서 .text 을 추출하여야 한다.

import requests
from bs4 import BeautifulSoup

url = "https://github.com/Door-Juno"

# HTML 가져오기
response = requests.get(url)
html_text = response.text

# HTML 파싱하기
soup = BeautifulSoup(html_text,'html.parser')

title = soup.select_one('title').text
list_data = soup.select('li p[dir="auto"]')

# List Comprehension (.text 추출) 
list_text = [tag.text.strip() for tag in list_data]

# 출력하기
print(f"제목 : {title}")
print(f"정보 리스트 : {list_text}")
제목 : Door-Juno (Junho Moon) · GitHub
정보 리스트 : [
	'경북대학교 식품공학부 식품응용공학전공 재학중 (2022 ~)', 
	'경북대학교 컴퓨터학부 인공지능컴퓨팅 복수전공', 
	'Velog link : [https://velog.io/@door_jono/posts]'
	]

이제 원하는 정보가 잘 담긴 것을 볼 수 있다 :)

지금은 웹페이지에 원하는 정보가 HTML 파일에 담겨있는 경우를 보았지만 , 동적 웹 페이지(JavaScript 로딩)의 경우 requests 로 가져온 HTML 파일은 자바스크립트가 실행되기 전인 텅 빈 뼈대 HTML 만을 가져오게 된다.

이런 동적 웹 페이지를 스크래핑 하기 위해 Selenium 라이브러리를 다음 글에서 공부해보겠다 :>

profile
Bioinformatics and Data science

0개의 댓글