GPT API 기반 뉴스레터 자동화 실험기 (2편) — 프롬프트 설계, 비용 최적화, 클린 코드 리팩토링

GPT API 기반 뉴스레터 자동화 실험기 (2편) — 프롬프트 설계, 비용 최적화, 클린 코드 리팩토링

지난 1편에서는 네이버 뉴스 크롤링의 한계를 겪고 구조가 안정적인 해외 뉴스 플랫폼으로 방향을 전환한 과정을 정리했다. 이번 편에서는 그 파이프라인이 더 안정적이고 실용적으로 쓰일 수 있도록 다듬는 과정을 다룬다.

요약이 아니라 "편집"이 되는 프롬프트

내가 원한 건 '뉴스 기사 문장 몇 개 줄인 요약'이 아니라 브리핑이었다. 그래서 처음부터 프롬프트를 '편집자의 작업 지시서'처럼 설계했다.

  1. 기사 단위 구조 고정
    "제목 → 날짜 → 요약 → 업계 영향(왜 중요한가)" 순서로 쓰게 했다. 블로그에 붙일 때 섹션마다 CSS를 입히거나 템플릿으로 돌리려면 포맷이 고정돼 있어야 편하기 때문에 여기에 공을 들였다. 날짜를 넣게 한 건 데이터 최신성을 드러내기 위함이었다. '업계 영향'은 단순 사실 요약과 인사이트를 분리하기 위한 장치다.
  2. 문장 난이도는 쉽게
    우리가 보는 뉴스 대부분은 청소년도 이해하기 쉬운 표현들로 이루어져 있다. "고등학생도 이해할 만큼 쉽게"라는 가이드를 설정했는데, 이는 단순한 친절함이 아니라 품질 가이드였다. 난이도를 낮추면 모델이 자연스럽게 전문 용어에 쉬운 설명을 달고 단문으로 작성해준다. 난해한 문장보다 이해하기 쉽고 짧은 문장이 뇌리에 더 잘 남고 사용자 친화적이다.
  3. 가독성 저해하는 반복 표현 억제
    LLM 모델은 '또한, 그리고, 한편' 같은 접속어를 자주 반복한다. 읽는 리듬이 자주 깨져서 가독성이 좋지 않기에 금지 패턴으로 적었다. "같은 접속어가 두 번 이상 반복되면 다른 어휘로 바꾸기", "문장 길이가 길어지면 중간에 끊기" 등의 행동 규칙을 프롬프트에 명시했다.
  4. 마무리 섹션은 공통 인사이트
    마지막 섹션에는 선별된 기사들의 공통 시사점을 요약하도록 지시했다. 이 마감 섹션이 글의 '가치'를 끌어 올린다. 토큰이 더 들더라도 이 파트 때문에 글의 밀도가 생기기에 챙겨두었다.


비용을 고려한 모델 선택

강의 촬영 시점이 최근이 아닌지라 Legacy models인 gpt-3.5-turbo를 기준으로 예시로 진행되었다. 나는 테스트 삼아 비용이 비교적 높은 최신 모델을 써봤다. 품질은 만족스러웠지만 토큰 단가 때문에 테스트 예산으로 설정했던 5달러가 금방 소진됐다. 매일 자동으로 도는 워크플로우라면 단가 × 빈도가 누적 비용을 결정한다. 그래서 ​모델은 경제적인 것을 선택하고 '좋은 프롬프트 + 후처리'로 품질을 보정하는 전략을 택했다.

적정 범위 지정

  • temperature 0.6~1.0: 기본 설정은 1.0이며 나는 0.7을 사용했다. (너무 낮으면 로봇 같고 너무 높으면 내용이 중구난방이거나 톤이 튄다)
  • top_p(탑-피) 0.5~1.0: 템퍼러처를 설정했다면 이건 조절 안해도 될 것. top_p 또한 무작위성을 제어하는 값이기 때문이다. 이 또한 높을수록 다양성이 증가한다.
  • max_tokens 제한: 출력값에 따른 토큰 사용량 관리에 직결된다.
  • 크롤링 기사 수량을 제한하고 프롬프트도 간략화해서 인풋 토큰도 줄였다.

템퍼러쳐는 높을수록 창의적이고 다양한 내용이 나오고 낮을수록 일관적인 예측값이 나온다. 정보성 콘텐츠의 경우 온도를 적당히 낮춰서 사용하면 좋다.


Ai 출력 → 워드프레스 업로드까지

파이프라인은 GPT 출력 → HTML 변환 → WordPress API 업로드 순서다. 간단해 보이지만 이 구간에서 꽤나 시간을 썼다.

1) GPT 응답 중단

글의 구성에 제약을 충분히 주지 않으면 모델이 에러를 낸다. 실제로 테스트할 때 중간에 글이 잘리거나 마무리 섹션을 통으로 날리는 케이스가 여러 번 발생했다. 아래 두 가지 방법으로 이를 해결하고자 했다.

  • 크롤링 기사 수량 제한, 추천 포인트, 문장 분량 지정 등 숫자 제약이 강력
  • max_tokens=4000으로 지정

이때 숫자로 제약하는 방법도 먹혔지만 max_tokens가 관건이었다. 3000으로 잡아놨더니 중간에 계속 잘렸던 것..! 아무리 프롬프트를 강화해도 안되던 콘텐츠 잘림 및 중단 이슈가 출력 토큰수를 늘리니 바로 해결됐다. 너무 높게 잡아도 에러 메시지를 뱉으니 모델마다 권장되는 토큰값을 미리 알아보고 설정하는 게 좋다.

또한 현재 시점에서 gpt-3.5-turbo-0125와 동일 조건(내 기준 1회당 Input 7,491 tokens, Output 3,139 tokens, 하루 10회, 월 30일)으로 비슷한 비용의 모델을 비교해봤더니 gpt-4o-mini가 경제적이고 성능 면에서도 우위에 있었다. gpt-3.5-turbo-0125의 월 비용(1M per 인풋 $0.5, 아웃풋 $1.5)은 약 $2.54인 반면 gpt-4o-mini(1M per 인풋 $0.4, 아웃풋 $1.6)는 약 $0.9065% 절감을 할 수 있다. 이에 더해 4o-mini는 128k까지 긴 컨텍스트 처리 가능, 추론 정확도가 높고 응답 속도도 빠르다. 비교 결과 단순 비용 절감뿐 아니라 품질 측면에서도 효율적이어서 모델을 바로 변경했다.

2) html 깨짐

워드프레스에 최종 업로드된 글을 보니 HTML 요소에 클래스가 여러 개 적용된 경우 구조가 깨지는 문제가 있었다. 이를 보완하고자 프롬프트에 출력 템플릿을 넣고 html 태그를 타이틀과 영역별로 지정해 최종 출력값을 워드프레스에 업로드하도록 했다.

수동 작업도 필요했다. 설정해두었던 워드프레스 테마 템플릿에서 먹히지 않는 태그도 있었기 때문. 워드프레스에 발행된 글의 코드편집기에 들어가서 이런저런 테스트를 하면서 gpt프롬프트에 적용해줬다.

기타 WordPress REST API 운영 팁
- 워드프레스 업로드 시 카테고리 id를 적용해 업로드하는 것도 가능하다.
- url 슬러그에 글의 제목을 그대로 넣을 수도 있다.


마지막 단계는 클린 코드 리팩토링

하나의 파일에 크롤링, 요약, 발행이 몽땅 들어가 있는 데다 순서가 중간중간 섞이고 예외 처리가 추가되어서 전체 코드가 지저분해졌다. 알아보기 쉽게 정리가 필요해 클린 코드 규칙에 따라 전체 코드 리팩토링을 진행했다.

  • main: 전체 실행 흐름 연결 및 재시도/검증/로그 기록 등 처리
  • models: 기사 데이터 형태(제목/링크/날짜/본문/출처)를 클래스로 정의
  • crawler: 웹페이지 진입, 타이틀과 이미지 및 링크 수집, 본문 파싱
  • summarizer: 프롬프트 빌더 + 모델 호출 + 결과 검증(언어/길이/포맷)
  • publisher: 결과값 콘솔에 출력 후 워드프레스 업로드

이렇게 정리한 뒤에는 코드 길이가 줄었고 "어디서 왜 실패했는지"를 찾아내기가 쉬워졌다. 이제 흐름과 구조는 다 잡아두었으니 이후 n8n으로 옮길 때도 모듈 경계를 노드 경계로만 잘 설정해주면 될듯하다.


마무리하며

크롤링은 재료 수집, GPT는 편집, 워드프레스는 배포 파이프. 이렇게 한번 사이클을 돌고 나니 두 번째는 더 접근이 쉬워서 다른 아이템으로 자동화 프로세스를 하나 더 세팅해두었다. 이번에 배운 것들을 요약하자면 아래와 같다.

  1. 모델을 바꾸는 것보다 프롬프트와 데이터 소스 기준을 바꾸는 게 품질과 비용면에서 효과적이다.
  2. 구조가 안정적인 소스를 고르면 초기 수집 단계의 복잡도가 크게 줄어든다.
  3. 코드도 중요하지만 단계별 소요시간, 수집 기사수, 에러 코드 로그 등도 잘 챙겨둬야 자동화가 수월하다.
  4. "자동 발행"은 기술이 아니라 운영 설계. 실패 , 재시도, 검수의 루틴을 포함해야 비로소 마무리 된다.
최종 구성 요약
항목 구성
정보 출처 구조 안정성 높은 해외 뉴스 (링크/날짜 패턴 명확)
데이터 추출 Playwright(동적 렌더 대기) + BeautifulSoup(정적 파싱)
요약 처리 GPT에 '에디토리얼' 프롬프트 + 반복 방지 규칙
포맷 변환 마크다운을 HTML로 표준화
자동 발행 REST API로 발행, 슬러그 규칙 적용
스케줄 GitHub Actions(크론, cron) 일 1회, 한국 시간 맞춤
보안 Secrets/환경변수 분리, 로컬은 dotenv
비용 가성비 좋은 GPT 4o mini 계열 + 프롬프트 활용

그래서 나온 결과물은.. 소스 추가 확보에 대한 필요성을 느껴서 아직 보완중이다. 안정화되면 글에 추가해둘 예정!

이외에 강의를 통해 Streamlit과 openai Vision, DALL·E, Assistant 생성, 텔레그램 알림도 실습했다. 하지만 이번 작업의 핵심은 '텍스트 소스→편집→발행'이라 시각/음성/대화형 인터랙션은 메인이 아니었다. 나중에 다른 데에 붙일 때 써먹어야겠다.