스파르타/웹개발

22.01.28 python 웹스크래핑(크롤링)

h.단디 2022. 2. 2. 09:50

필요한 패키지 - requests / beautiful soup(BS4) 

 

* 크롤링 기본 세팅 코드

import requests                        #import하기
from bs4 import BeautifulSoup

headers = {'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36'}
data = requests.get('URL',headers=headers)              #headers:코드단에서 요청할 때 막아둔 사이트가 많아서, 브라우저에서 한 것 같은 효과를 냄 

soup = BeautifulSoup(data.text, 'html.parser')          # requests로 받아온 데이터를 솎아내기 좋은 형태로!

# 코딩 시작

 

크롤링 : 내가 서버로부터 이미 받아온 것을 가지고 필요한걸 솎아내는 것 

             따라서 브라우저를 켜지 않고 코드단에서 요청을 하는 것(requests)과 가져온 html에서 솎아내는 것(BS4)가 중요함

 

print(soup)            #html 결과를 그대로 가져옴

 

가져 올 데이터 마우스 우클릭 > 검사 > 파랗게 활성화된거 copy selector

 

 

 

 

 

[하나 가져오기] - select_one

import requests
from bs4 import BeautifulSoup

headers = {'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36'}
data = requests.get('https://movie.naver.com/movie/sdb/rank/rmovie.nhn?sel=pnt&date=20200303',headers=headers)

soup = BeautifulSoup(data.text, 'html.parser')

title = soup.select_one('#old_content > table > tbody > tr:nth-child(2) > td.title > div > a')      #copy selector 붙여넣음

print(title)     


# 그 결과->     <a href="/movie/bi/mi/basic.naver?code=171539" title="그린 북">그린 북</a>
                       #태그의 속성 print(title['herf'])          태그의 텍스트-> print(title.text)

 

 

 

 

[왕창 가져오기] - select

전략적으로 접근 ! 

각각의 데이터 2~3개 copy selector 한 후에 비교해봄

#old_content > table > tbody > tr:nth-child(3)

#old_content > table > tbody > tr:nth-child(2)

-> 겹치는 '#old_content > table > tbody > tr'를 활용하면 이거에 해당하는거 다 가져올 수 있음

 

1. select로 모든 tr을 list형태로 전부 불러옴

import requests
from bs4 import BeautifulSoup

headers = {'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36'}
data = requests.get('https://movie.naver.com/movie/sdb/rank/rmovie.nhn?sel=pnt&date=20200303',headers=headers)

soup = BeautifulSoup(data.text, 'html.parser')

trs = soup.select('#old_content > table > tbody > tr')

for tr in trs :
    print(tr)

 

2. select_one으로 tr의 list 중에서 제목(속성&텍스트)만 가져오기

(제목 copy selector해서 'td.title > div > a' 활용할거임)

import requests
from bs4 import BeautifulSoup

headers = {'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36'}
data = requests.get('https://movie.naver.com/movie/sdb/rank/rmovie.nhn?sel=pnt&date=20200303',headers=headers)

soup = BeautifulSoup(data.text, 'html.parser')

trs = soup.select('#old_content > table > tbody > tr')

for tr in trs :
    a_tag = tr.select_one('td.title > div > a')       #tr중에서 제목만 찾아줘
    print(a_tag)

 

3. 제목 텍스트만 가져오기

2의 결과중 none 때문에 에러가 남. -> 조건문 걸어줘야함

import requests
from bs4 import BeautifulSoup

headers = {'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36'}
data = requests.get('https://movie.naver.com/movie/sdb/rank/rmovie.nhn?sel=pnt&date=20200303',headers=headers)

soup = BeautifulSoup(data.text, 'html.parser')

trs = soup.select('#old_content > table > tbody > tr')

for tr in trs :
    a_tag = tr.select_one('td.title > div > a')
    if a_tag is not None :
        title = a_tag.text
        print(title)

 

 

Quiz 크롤링 연습

 

import requests
from bs4 import BeautifulSoup

headers = {'User-Agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Safari/537.36'}
data = requests.get('https://movie.naver.com/movie/sdb/rank/rmovie.nhn?sel=pnt&date=20200303',headers=headers)

soup = BeautifulSoup(data.text, 'html.parser')

trs = soup.select('#old_content > table > tbody > tr')

for tr in trs :
    a_tag = tr.select_one('td.title > div > a')          #전략적으로 한 줄(tr)을 골랐고
    if a_tag is not None :
        rank = tr.select_one('td:nth-child(1) > img')['alt']       #그 줄에서 순위를 찾고
        title = a_tag.text 
        star = tr.select_one('td.point').text                      #그 줄에서 별점을 찾고!
        print(rank, title, star)