3.1-3. 네이버 API 활용한 뉴스 크롤링 실습

1. 네이버 검색 API 설정 및 키 발급

네이버 API 사용을 위한 애플리케이션 등록 및 인증 키를 발급받아야 함.

1. 네이버 개발자 센터 접속

2. '애플리케이션 등록' 메뉴 선택.

애플리케이션 이름 입력 (예: 네이버스터디).
사용 API로 '검색' 선택.
서비스 환경으로 'WEB 설정' 선택.
웹 서비스 URL 입력 (예: http://localhost).
'등록하기' 클릭하여 애플리케이션 등록 완료.
등록 후 발급된 클라이언트 ID와 클라이언트 시크릿 확인 및 보관.
이 두 정보가 API 호출에 필요한 인증 키 (나만의 직통전화 비밀번호 같은 거)

2. 기본 Python 예제 코드 확보 및 이해

네이버 개발자 센터에서 제공하는 파이썬 샘플 코드를 복사하고, API의 기본 구조를 파악

1. 예제 코드 복사

네이버 디벨로퍼의 '서비스 API' > '검색' 페이지 로 이동 > '개발 가이드 보기' 클릭
'뉴스' API 명세 확인.
주요 요청 변수(파라미터) 확인: query(검색어), display(표시 개수), start(검색 시작 위치), sort(정렬).
주요 응답 필드 확인: title, originallink, link, description, pubDate.
뉴스 검색 구현 예제(페이지 맨 하단) > '검색 API 블로그 검색 구현 예제' 클릭
Python 코드를 복사
# 네이버 검색 API 예제 - 뉴스 검색 import os import sys import urllib.request client_id = "YOUR_CLIENT_ID" client_secret = "YOUR_CLIENT_SECRET" encText = urllib.parse.quote("검색할 단어") url = "https://openapi.naver.com/v1/search/news?query=" + encText # JSON 결과 # url = "https://openapi.naver.com/v1/search/news.xml?query=" + encText # XML 결과 request = urllib.request.Request(url) request.add_header("X-Naver-Client-Id",client_id) request.add_header("X-Naver-Client-Secret",client_secret) response = urllib.request.urlopen(request) rescode = response.getcode() if(rescode==200): response_body = response.read() print(response_body.decode('utf-8')) else: print("Error Code:" + rescode)

3. Google Colab에서 기본 코드 실행 및 확인

복사한 코드를 Google Colab에서 실행하여 API가 정상적으로 작동하는지 확인.
💬
Google Colab(코랩)
정의: 웹 브라우저에서 실행되는 파이썬 노트북 환경입니다.
특징
1. 무료: 누구나 Google 계정만 있으면 무료로 사용 가능.
2. 설치 불필요: 로컬 PC에 파이썬이나 라이브러리를 설치할 필요 없음.
3. 클라우드 기반: 코드는 Google 서버에서 실행되며, 노트북은 Google Drive에 저장.
4. 딥러닝이나 데이터 분석에 유용 : GPU/TPU 제공- 복잡한 딥러닝 모델 학습을 위해 무료 GPU(그래픽 처리 장치) 또는 TPU(텐서 처리 장치) 사용 환경을 제공.
Shift + Enter: 현재 셀을 실행하고 다음 셀로 이동. 가장 많이 사용하는 단축키.
Ctrl + Enter: 현재 셀을 실행하고 그대로. 결과를 바로 확인하고 싶을 때 유용.
1.
Google Colab에 접속하여 '새 노트' 생성 완료.
2.
복사한 Python 코드를 코드 셀에 붙여넣기 시행.
3.
코드 내 client_id와 client_secret에 발급받은 본인 키 값으로 대체 입력.
4.
요청 URL이 블로그(blog)로 설정되어 있다면 뉴스 검색용 URL(news)로 수정 완료.
a.
쇼핑(shop), 웹검색(webkr) : 개발자 센터 가이드 참조
5.
검색하고 싶은 키워드 입력하고, 코드 셀 실행
6.
검색 결과 10개가 정상적으로 출력되는지 확인 완료.

4. ChatGPT를 활용하여 코드 업그레이드 (키워드 입력 + 대량 분석 환경 구축)

💬
수정할 사항
검색 결과 default 10개 → Max. 1000개까지 가능
검색량을 입력할 수 있도록 함
검색 키워드 먼저 입력하는 UI 로 수정 작업 진행
—> 대량 데이터 수집 및 분석을 위해 ChatGPT에게 코드 수정 지시를 내려야 함.
1.
Colab 코드를 복사하여 ChatGPT에 전달 완료.
2.
다음 내용으로 코드 수정 요청 지시:
네이버 API를 사용해서 네이버 뉴스를 검색하는 코드야. 이 코드를 아래와 같이 수정해줘. --- 1. 먼저 사용자에게 검색 키워드와 검색량(최대 1000개)을 입력받도록 함 2. 입력한 검색 키워드로 검색하도록 함 3. 입력한 검색량만큼 검색하도록 함 4. 검색 결과를 Pandas DataFrame(Python에서의 엑셀 시트에 해당)에 넣도록 함 5. 최종적으로 DataFrame을 CSV 파일로 다운로드할 수 있게 함 6. CSV는 영문 파일 명으로 함 --- # 네이버 검색 API 예제 - 뉴스 검색 import os import sys import urllib.request client_id = "YOUR_CLIENT_ID" client_secret = "YOUR_CLIENT_SECRET" encText = urllib.parse.quote("검색할 단어") url = "https://openapi.naver.com/v1/search/news?query=" + encText # JSON 결과 # url = "https://openapi.naver.com/v1/search/news.xml?query=" + encText # XML 결과 request = urllib.request.Request(url) request.add_header("X-Naver-Client-Id",client_id) request.add_header("X-Naver-Client-Secret",client_secret) response = urllib.request.urlopen(request) rescode = response.getcode() if(rescode==200): response_body = response.read() print(response_body.decode('utf-8')) else: print("Error Code:" + rescode)
3.
ChatGPT가 수정한 새 Python 코드 확보
💬
gpt
좋아! 아래는 요청하신 6가지를 모두 반영해 완전 동작하는 파이썬 스크립트예요.
실행 시 사용자에게 검색 키워드수집 개수(최대 1000) 를 입력받습니다.
네이버 뉴스 API를 페이지네이션으로 여러 번 호출해 원하는 개수만큼 수집합니다.
결과를 Pandas DataFrame으로 만들고, 영문 파일명으로 CSV 저장("다운로드")합니다.
# -*- coding: utf-8 -*- """ Naver News Search -> Pandas DataFrame -> CSV 저장 스크립트 요구사항: 1) 사용자 입력: 검색 키워드, 검색량(최대 1000) 2) 입력 키워드로 검색 3) 입력 검색량 만큼 수집 (API 페이지네이션) 4) 결과를 Pandas DataFrame으로 5) DataFrame을 CSV로 저장 6) CSV 파일명은 영문(ASCII)으로 생성 """ import os import sys import time import json import re import html import math import urllib.request import urllib.parse from datetime import datetime try: import pandas as pd except ImportError: print("pandas가 필요합니다. `pip install pandas` 로 설치하세요.") sys.exit(1) # --- 여기에 본인 API 키 입력 또는 환경변수 사용 --- CLIENT_ID = os.getenv("NAVER_CLIENT_ID", "YOUR_CLIENT_ID") CLIENT_SECRET = os.getenv("NAVER_CLIENT_SECRET", "YOUR_CLIENT_SECRET") API_URL = "https://openapi.naver.com/v1/search/news.json" # JSON 결과 MAX_TOTAL = 1000 # 네이버 검색 최대 1000개 MAX_PER_REQUEST = 100 # display 최대 100 RATE_SLEEP = 0.1 # 호출 간 살짝 쉬기(레이트 제한 여유) def clean_text(s: str) -> str: """네이버 응답의 <b> 태그 제거 및 HTML 엔티티 디코딩""" if s is None: return "" s = html.unescape(s) s = re.sub(r"<\/?b>", "", s) s = re.sub(r"<[^>]+>", "", s) # 혹시 남은 태그 제거 return s.strip() def slugify_ascii(text: str) -> str: """영문/숫자/밑줄만 남겨 파일명으로 안전하게 변환""" text = text.lower() text = re.sub(r"[^a-z0-9]+", "_", text) text = re.sub(r"_+", "_", text).strip("_") return text or "query" def fetch_naver_news(query: str, total_count: int): """쿼리에 대해 total_count개까지 뉴스 수집하여 list[dict] 반환""" headers = { "X-Naver-Client-Id": CLIENT_ID, "X-Naver-Client-Secret": CLIENT_SECRET, } total_count = max(1, min(int(total_count), MAX_TOTAL)) pages = math.ceil(total_count / MAX_PER_REQUEST) results = [] fetched = 0 for i in range(pages): remaining = total_count - fetched display = min(MAX_PER_REQUEST, remaining) start = fetched + 1 # 네이버 start는 1부터 params = { "query": query, "display": display, "start": start, # 정렬 옵션: sim(정확도), date(날짜). 필요시 변경 가능 "sort": "date", } url = f"{API_URL}?{urllib.parse.urlencode(params)}" req = urllib.request.Request(url, headers=headers) try: with urllib.request.urlopen(req) as resp: if resp.getcode() != 200: print(f"HTTP {resp.getcode()} 오류 발생") break data = json.loads(resp.read().decode("utf-8")) except Exception as e: print(f"요청 중 오류: {e}") break items = data.get("items", []) if not items: # 더 이상 결과가 없으면 중단 break for item in items: results.append({ "title": clean_text(item.get("title")), "originallink": item.get("originallink", ""), "link": item.get("link", ""), "description": clean_text(item.get("description")), "pubDate": item.get("pubDate", ""), }) fetched += 1 if fetched >= total_count: break if fetched >= total_count: break time.sleep(RATE_SLEEP) return results def main(): # --- 사용자 입력 --- query = input("검색 키워드를 입력하세요: ").strip() if not query: print("검색 키워드는 비어 있을 수 없습니다.") sys.exit(1) try: total = int(input("검색량(최대 1000)을 입력하세요: ").strip()) except ValueError: print("검색량은 정수여야 합니다.") sys.exit(1) # --- API 키 검증(기본값 그대로면 경고) --- if CLIENT_ID == "YOUR_CLIENT_ID" or CLIENT_SECRET == "YOUR_CLIENT_SECRET": print("경고: CLIENT_ID/CLIENT_SECRET를 설정하세요. 환경변수 NAVER_CLIENT_ID/NAVER_CLIENT_SECRET 또는 코드 상수로 설정 가능합니다.") print(f"▶ '{query}' 뉴스 {min(total, MAX_TOTAL)}개까지 수집 중...") items = fetch_naver_news(query, total) if not items: print("결과가 없습니다.") sys.exit(0) # --- DataFrame 변환 --- df = pd.DataFrame(items, columns=["title", "originallink", "link", "description", "pubDate"]) print(f"수집 완료: {len(df)}건") # --- CSV 저장(영문 파일명) --- slug = slugify_ascii(query) ts = datetime.now().strftime("%Y%m%d_%H%M%S") filename = f"naver_news_{slug}_{ts}.csv" df.to_csv(filename, index=False, encoding="utf-8-sig") print(f"CSV 저장 완료: {filename}") if __name__ == "__main__": main()

사용 팁

sort"date"로 설정해 최신순 수집하도록 했습니다(정확도 우선이면 "sim"으로 바꾸세요).
대량 호출 시 API 레이트 제한을 고려해 RATE_SLEEP을 조절하세요.
CSV 파일명은 naver_news_<영문슬러그>_<타임스탬프>.csv 형태로 저장됩니다.

5단계: 대량 데이터 크롤링 및 CSV 다운로드

ChatGPT가 수정한 코드를 Colab에 적용하여 데이터를 추출하고 다운로드해야 함.
1.
기존 Colab 코드를 ChatGPT가 제공한 코드로 대체 완료.
a.
코드 내 client_id와 client_secret에 발급받은 본인 키 값으로 대체 입력
2.
코드 실행 후 프롬프트에 원하는 검색어 및 검색량 입력 및 엔터 처리.
a.
정상 작동 후, 좌측 파일에서 CSV 파일 다운로드 가능
3.
오류 발생 시:
발생한 오류 메시지 복사하여 ChatGPT에 다시 전달.
ChatGPT가 수정한 새 코드로 재대체 후 다시 실행.
4.
크롤링 및 파일 생성 완료 메시지 확인 완료.
5.
Colab 왼쪽 패널의 '폴더' 아이콘 클릭.
6.
생성된 CSV 파일 확인 후 로컬 PC로 다운로드하여 분석에 활용.
Contact : azureguy@empal.com / azureguy@cau.ac.kr