2023년 1월 1일
08:00 AM
Buffering ...

최근 글 👑

크롤링 활용(selenium 활용)

2025. 4. 17. 16:37ㆍ개발공부/생성형 AI 기반 개발자 과정
728x90

활용한 사이트(온오프믹스) : https://onoffmix.com/event/main?s=%EC%9D%B8%EA%B3%B5%EC%A7%80%EB%8A%A5%20ai%20chatgpt%20%EC%B1%97gpt

구현 코드

from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
from selenium.common.exceptions import NoSuchElementException
from sqlalchemy import create_engine
import pandas as pd

url = 'https://onoffmix.com/event/main?s=%EC%9D%B8%EA%B3%B5%EC%A7%80%EB%8A%A5%20ai%20chatgpt%20%EC%B1%97gpt'

def crawling(url):
    options = Options()

    #지정한 user-agent로 설정합니다.
    user_agent = "Mozilla/5.0 (Linux; Android 9; SM-G975F) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/71.0.3578.83 Mobile Safari/537.36"
    options.add_argument('user-agent=' + user_agent)
    options.add_argument('--start-maximized') #브라우저가 최대화된 상태로 실행됩니다.
    options.add_argument("headless")

    driver = webdriver.Chrome()
    driver.get(url)
    driver.implicitly_wait(5)   # 페이지 로딩끝나면 다음코드로 넘어감, 인수로 받은 숫자는 최대 딜레이 시간

    page = 1    # 현재 페이지 저장변수

    title = []  # 제목
    date = []   # 일자
    addr = []   # 주소
    img = []    # 이미지경로

    j = 1   # 컨텐츠 제어용 변수
    while(1):  
        try:
            try:
                driver.find_element(By.CSS_SELECTOR, f'#content > div > section.event_main_area > ul > li:nth-child({j}) > article.event_area.event_main > a > div.event_info_area > div.title_area > h5').click()
            except NoSuchElementException as e:
                if(j<20):   # 마지막 컨텐츠 체크용
                    break
                n = 0   # 페이지 제어용 변수
                page += 1
                while(1):
                    try:
                        # 페이징 처리부분
                        # 다음으로 넘어가야할 페이지 번호와 같은 번호 서치
                        if(driver.find_element(By.XPATH, f'//*[@id="content"]/div/section[2]/div[4]/div/a[{n}]').text==str(page)):  
                            j = 1
                            driver.find_element(By.XPATH, f'//*[@id="content"]/div/section[2]/div[4]/div/a[{n}]').click()
                # 페이지 로딩끝나면 다음코드로 넘어감, 인수로 받은 숫자는 최대 딜레이 시간
                            driver.implicitly_wait(5)   

                            driver.find_element(By.CSS_SELECTOR, f'#content > div > section.event_main_area > ul > li:nth-child({j}) > article.event_area.event_main > a > div.event_info_area > div.title_area > h5').click()
                            break
                        elif(n==7): # '다음'버튼으로 넘어가야할때
                            driver.find_element(By.XPATH, '//*[@id="content"]/div/section[2]/div[4]/div/a[7]').click()
                            n = 0
                            continue
                        else:
                            n += 1
                # driver.find_element로 해당 요소를 못 찾을경우
                    except NoSuchElementException as e: 
                        if(n==7):   # 마지막 페이지라 다음 버튼이 비활성 했을때
                            break
                        n += 1
                        continue
            # 새탭으로 제어권 넘어감  
            driver.switch_to.window(driver.window_handles[-1]) 
            driver.implicitly_wait(5)

            # 컨텐츠페이지에서 필요한 데이터 할당부분
            date.append(driver.find_element(By.XPATH, '//*[@id="content"]/div[2]/section[1]/div[3]/ul/li[1]/p').text.strip())
            title.append(driver.find_element(By.XPATH, '//*[contains(concat( " ", @class, " " ), concat( " ", "event_title", " " ))]').text.strip())
            addr.append(driver.find_element(By.XPATH, '//*[@id="content"]/div[2]/section[1]/div[3]/ul/li[2]/p/span').text.strip())
            img.append(driver.find_element(By.XPATH, '//*[@id="content"]/div[2]/section[1]/div[2]/div[1]/img').get_attribute('src'))


            driver.close()  # 탭 닫기
            # 원래탭으로 제어권 돌아감
            driver.switch_to.window(driver.window_handles[0]) 
            j += 1
    # driver.find_element로 해당 요소를 못 찾을경우
        except NoSuchElementException as e: 
            driver.close()  # 탭 닫기
            driver.switch_to.window(driver.window_handles[0])
            j += 1
            continue
        except Exception as e:
            break

    df = pd.DataFrame(data=zip(title, date, addr, img),
                      columns=["title", "date", "addr", "img"]
                      )

    driver.close()

    return df    

if __name__ == '__main__':
    crawling(url)

페이지에 리스트업 되어있는 각 컨텐츠 페이지로 들어가 필요한 데이터를 수집하는 코드. 해당 페이지에 리스트업 되어있는 컨텐츠의 데이터 수집이 끝나면 자동으로 다음페이지로 넘어감

728x90

'개발공부 > 생성형 AI 기반 개발자 과정' 카테고리의 다른 글

공공데이터 크롤링(api 활용)  (0) 2025.04.28
주소록 관리  (0) 2025.04.28
크롤링 기초(api 활용편 - xml)  (0) 2025.04.16
pandas - 7  (0) 2025.04.06
pandas - 6  (0) 2025.04.06