- 파이썬의 다양한 크롤링 라이브러리를 배워보고 있다. 이번시간에는 beautifulsoup, selenium 다음으로 scrapy를 한 번 사용해보고자 한다.
0. 준비하기
- pip install scrapy로 라이브러리를 먼저 설치해주고, 프로젝트를 생성해보자(밑줄 친 부분은 임의 변경 가능)
scrapy start project scrapy_practice 명령어 실행
- 다음과 같이 여러 파일들이 추가된 구조를 확인할 수 있다.
1. 본격 크롤링
- 목표로 하는 크롤링 url 주소는 이것이다. : https://www.worldometers.info/world-population/population-by-country/
- 다음과 같이 명령어를 실행하자(위치 : spiders 폴더로 이동 후 명령어 실행)
- 명령어의 결과로 worldometer.py 파일이 생성된다.
- 해당 파일에 코드가 이미 작성되어있는데, 아래와 같이 코드를 수정해주자.
import scrapy
class WorldometerSpider(scrapy.Spider):
name = "worldometer"
allowed_domains = ["www.worldometers.info/"]
start_urls = ["http://www.worldometers.info/world-population/population-by-country"]
def parse(self, response):
title = response.xpath('//h1/text()').get()
countries = response.xpath('//td/a/text()').getall()
yield {
'titles' : title,
'countries' : countries,
}
- 이제 이 코드를 worldometer.py 가 있는 폴더에서 실행해보자. 명령어는 scrapy crawl worldometer 이며, 결과는 아래 이미지 처럼 출력될 것이다.
2. Multiple links 가져오기
- 이번에는 다음 코드를 이용하여 해당 웹사이트 내의 다양한 링크를 가져와보도록 하자.
import scrapy
class WorldometerSpider(scrapy.Spider):
name = "worldometer"
allowed_domains = ["www.worldometers.info/"]
start_urls = ["http://www.worldometers.info/world-population/population-by-country"]
################################# 상 동 #################################
def parse(self, response):
countries = response.xpath('//td/a')
for country in countries:
country_name = country.xpath(".//text()").get()
link = country.xpath(".//@href").get()
yield {
'country_name' : country_name,
'link' : link
}
- 이번 코드는 국가 이름과 해당 국가 페이지의 링크를 추출하는 기능을 구현한 코드이다.
countries = response.xpath('//td/a'): 페이지에서 모든 <td> 요소 내부의 <a> 요소를 선택하여 countries 변수에 저장함으로써 각 국가의 정보가 포함된 요소를 가져올 수 있다.
country_name = country.xpath(".//text()").get(): 현재 국가 요소에서 텍스트를 추출하여 country_name 변수에 저장함.
link = country.xpath(".//@href").get(): 현재 국가 요소의 href 속성 값을 추출하여 link 변수에 저장함.
* //@href는 모든 요소의 href 속성을 선택한다.
yield: 추출한 국가 이름과 링크를 딕셔너리 형태로 정리하여 반환함.
- 이제 이 코드를 worldometer.py 가 있는 폴더에서 실행해보자. 명령어는 scrapy crawl worldometer 이며, 결과는 아래 이미지 처럼 출력될 것이다.
3. Multiple links 데이터를 추출하기
- 데이터 추출을 위해 먼저 XPath를 확인하자.
- 위 화면에서 Ctrl + F를 입력 후 다음과 같이 입력 후 검색한다.
(//table[@class="table table-striped table-bordered table-hover table-condensed table-list"])[1]
- 다음은 tr 태그에 접근하기 위해 다음과 같이 검색해보자.
(//table[@class="table table-striped table-bordered table-hover table-condensed table-list"])[1]/tbody/tr
- 노란색 표시가 되어있는 부분들을 클릭하다보면, 해당 하는 행이 선택되는 걸 확인할 수 있다.
- 이러한 정보를 조합한 결과 전체 코드는 다음과 같다. ★
import scrapy
class WorldometersSpider(scrapy.Spider):
name = 'worldometer'
allowed_domains = ['www.worldometers.info']
start_urls = ['https://www.worldometers.info/world-population/population-by-country/']
def parse(self, response):
# a 요소 확인
countries = response.xpath('//td/a')
# 반복문
for country in countries:
country_name = country.xpath(".//text()").get()
link = country.xpath(".//@href").get()
# 절대경로
# absolute_url = f'https://www.worldometers.info/{link}' # 방법 1
# yield scrapy.Request(url=absolute_url) # sending a request with the absolute url
# 상대경로
yield response.follow(url=link, callback=self.parse_country, meta={'country':country_name})
# Getting data inside the "link" website
def parse_country(self, response):
country = response.request.meta['country']
rows = response.xpath("(//table[contains(@class,'table')])[1]/tbody/tr")
for row in rows:
year = row.xpath(".//td[1]/text()").get()
population = row.xpath(".//td[2]/strong/text()").get()
# Return data extracted
yield {
'country':country,
'year': year,
'population':population,
}
- 다음의 명령어 " scrapy crawl worldometer -o population.json " 를 입력하면, json 파일이 생기게 된다.
* 같은 명령어에서 가장 뒤를 .csv 로 하면 csv 파일로도 저장이 가능하다
- 추가로 만약에 데이터 프레임으로 불러오고 싶다면, 다음의 절차를 따르면 된다.
- .json 파일이 위치한 동일한 디렉토리 경로에 get_df.py(이름 임의로) 파일을 만들고 다음과 같이 코드를 작성해주면 된다.
* scrapy에서 물론 방법이 있겠지만, json파일로 저장한 뒤 불러오는 방식으로 DF를 만드는 것을 대부분 선호한다고 한다.
import pandas as pd
# json 파일 불러오기
def main():
data = pd.read_json("population.json")
data = pd.DataFrame(data)
print(data.head())
if __name__ == "__main__":
main()
- 결과 확인
★ 이 부분이 중요하면서, 꽤나 이해가 어려운 부분이었다. scrapy 사용 전 복습과 재실습이 필요해보인다.
'IT & 개발공부 > 파이썬(Python)' 카테고리의 다른 글
API 인증키를 활용한 웹 크롤링 실습 -2 (공공데이터 포털 feat.xmltodict) (0) | 2023.08.12 |
---|---|
API 인증키를 활용한 웹 크롤링 실습 -1 (한국도로공사 데이터) (0) | 2023.08.11 |
Pandas 기초 개념 공부 (0) | 2023.08.09 |
셀레니움(selenium)을 이용한 웹 크롤링 실습 (0) | 2023.08.08 |
파이썬(beautifulsoup) 크롤링 기초 공부 및 예제를 통해 실습하기 -2 (0) | 2023.08.07 |