키워드 기반 보고서 자동화 모델

Gamchan Kang·2023년 9월 25일
0

딥러닝

목록 보기
6/8

모델을 만들게 된 계기

아는 지인 분과 이야기하다가 크몽에서 대학 과제를 대신 해준다는 이야기가 나왔다. 특정 키워드로 보고서를 작성하는 과제가 많은데, 지인 분은 키워드에 해당하는 뉴스 기사를 모으고 chatGPT를 거쳐 약간의 수정을 통해 만든다고 했다.

이 이야기를 들으며 자동화 아이디어가 떠올랐다. 실제로 내가 딥러닝 모델의 구조를 디자인 할 일은 없으니 금방 걸릴 거라고 생각했다.

Github Repo

전반적인 프로그램 기획

우선 입력받은 키워드를 기반으로 네이버 검색 API에 뉴스 카테고리 데이터 수집으로 시작한다. 수집된 데이터는 cache디렉토리 밑에 json 파일로 저장된다. 수집된 데이터는 해당 기사의 본문 URL을 포함하므로requestbeautifulSoup 모듈로 해당 기사의 본문 텍스트를 파싱한다. 파싱한 텍스트를 konlpyOkt로 형태소 빈도 분석을 한다. 상위 1000개 형태소를 바탕으로 gpt-3.5-turbo-0613 모델에 명령어로 넣어 키워드를 사용하여 보고서를 생성하도록 한다.

코딩

다행히도 네이버 검색 API는 호출이 많지 않다면 무료로 사용할 수 있었다. 네이버 개발자 센터에서 API키를 발급받고 사용해보니 json 데이터를 매우 깔끔하게 얻을 수 있었다.

[
    {
        "cnt": 1,
        "description": "LG<b>스포츠</b> 김인석 대표이사는 &quot;에스알과의 이번 협약을 통해 <b>스포츠</b>팬들이 SRT를 이용하여 더욱 편리하게 전국의 <b>스포츠</b>경기를 관람 할 수 있게 됐다&quot; 라며, &quot;에스알과 협력하는 다양한 <b>마케팅</b> 활동으로 <b>스포츠</b>팬들의... ",
        "link": "https://sports.news.naver.com/news.nhn?oid=477&aid=0000452124",
        "org_link": "https://www.spotvnews.co.kr/news/articleView.html?idxno=633737",
        "pDate": "2023-09-24 18:14:00",
        "title": "야구관람권-SRT 승차권 패키지 상품개발…LG, 에스알과 업무협약"
    },
    {
        "cnt": 2,
        "description": "국제 <b>스포츠</b>계의 큰손으로 부상한 사우디아라비아, 카타르 등 중동 기업들의 후원도 없다. 자국 기업의 후원으로 항저우 아시안게임은 배를 든든하게 불렸다. 천웨이창 항저우 아시안게임 조직위 사무총장은 &quot;<b>마케팅</b>으... ",
        "link": "https://sports.news.naver.com/news.nhn?oid=009&aid=0005191234",
        "org_link": "https://www.mk.co.kr/article/10836940",
        "pDate": "2023-09-24 17:51:00",
        "title": "중국산만 보이는 아시안게임 광고도 후원도 '차이나 온리'"
    },
    ...
  ]

"link"에 해당되는 URL로 request로 접속하고 bs4 모듈로 해당 기사 페이지의 html을 파싱한다. 그리고 div 테그 중 id 값이 contents 혹은 news를 포함하면 전부 긁어온다. 직접 뉴스 기사 페이지에서 html을 뜯어보니 본문에 해당되는 내용은 거의 대부분 contentsnewsid로 설정되어 있었다.

처음 코드를 구상할 때, 이 텍스트를 그대로 모아 text-davinci-002 모델에 넣었다. 하지만 모델이 생성하는 텍스트 길이가 매우 짧았고, 터무니 없는 텍스트를 출력했다.

우선 내가 생각한 첫번째 해결책은 형태소 분석이었다. 뉴스 기사를 형태소 분석을 통해 1글자 미만과 불용어를 제하고 순수 한글 형태소만 저장했다. 여전히 text-davinci-002 모델은 잘 작동하지 않았다. 오히려 더욱 터무니 없는 텍스트를 출력하고 있었다.

그 다음으로 생각한 해결책은 프롬프팅이었다. 프롬프트를 점점 상세하게 설정해가며 코드를 실행해봤다. 프롬프트가 상세해질 수록 텍스트는 더 이상해졌다. 아마 내가 프롬프트 엔지니어링 기법을 활용하지 않고, 내가 스스로 생각한 디테일한 문장으로 명령어를 설정해 그런 문제가 생기지 않았나 싶다.

몇 번의 시도 끝에 gpt-3.5-turbo-0613 모델로 바꿨다. text-davinci-002 모델은 대화형 텍스트 생성 모델이 아닌, 단편 텍스트 요약 및 생성에 초점을 둔 모델인 점을 잊고 있었다. gpt-3.5-turbo-0613으로 바꾸면서 해당 모델에 역할을 부여하고 부연 설명도 더욱 간편하게 줄 수 있었다. 맥락 파악도 이전 모델보다 더 뛰어났다.

messages = [
        {"role": "system", "content": f"너는 {search_keyword} 분야의 전문가로서 조언을 주고 있어"},
        {"role": "user", "content": f"'{search_keyword}'에 관한 주제로 웹 크롤링과 형태소 분석을 통해 얻은 주요 키워드는 {keywords}입니다. 이 키워드들을 바탕으로 보고서를 작성해주세요."}
]
    
response_texts = []
    
for idx in tqdm(range(max_attempts), desc="Generating report", ncols=100):
    try:
        response = openai.ChatCompletion.create(
            model="gpt-3.5-turbo-0613",
            messages=messages
        )
        res = response['choices'][0]['message']['content']
        response_texts.append(res)
        messages.append({"role": "user", "content": "계속해서 보고서를 완성해주세요."})
    except Exception as e:
        print(f"{COLOR_RED}Error during attempt {idx + 1}: {e}{COLOR_RESET}")

messages.append()로 이전 보고서 맥락을 바탕으로 이후 텍스트를 생성하도록 했다.

모델 추가 기능

이전까지 tqdm 모듈이 있는 건 알았지만, 직접 사용해야겠다 생각한 적은 없었다. 코드를 실행하니 1000개 URL를 크롤링하는데 시간이 5~7분 정도 소요됐다. 1000개 URL이 전부 크롤링을 잘 수행하지 않아 가끔 에러를 던졌지만, 전반적인 진행 상태를 알기 불편했다. tqdm 모듈로 코드 진행 상황을 보니 갑갑한 부분을 조금이나마 해결해줬다.

warnings.simplefilter(action='ignore', category=Warning)로 가벼운 경고를 무시하고 싶었지만 어째서 인지 잘 작동하지 않았다. bs4에서 파싱할 때와 형태소 빈도수 분석을 할때 인코딩에서

Some characters could not be decoded, and were replaced with REPLACEMENT CHARACTER.

와 같은 경고가 계속 발생했는데, main.py 파일에 제일 처음에 위 경고 무시 스크립트를 넣어도 똑같았다. (현재는 잘 동작한다.)

결과

GPT가 키워드를 전부 활용해서 나름 독특한 보고서를 생성하도록 만드는 걸 목표로 했다. 하지만 아무래도 특수 키워드, 특히 이전까지는 거의 접근하지 않다가 요즘에 관련 기사가 많이 생성된 키워드에 관련해서는 불리한 점을 많이 보였다. 예를 들어, 우크라이나-러시아 전쟁 키워드를 넣었을 때 다음과 같이 출력했다.

  1. 주요 키워드 분석
    다음은 웹 크롤링과 형태소 분석을 통해 얻은 우크라이나 러시아 전쟁 분야의 주요 키워드이다:

3.1. 우크라이나

  • 동쪽 국가
  • 키예프
  • 동방 교황청

3.2. 러시아

  • 서쪽 국가
  • 모스크바
  • 크렘린

3.3. 전쟁

  • 군사 충돌
  • 군대
  • 무력 충돌

다른 보고서 부분에서도 키워드 제시를 제외한 나머지 결과는 이상하게 출력됐다.
반면, '기후 변화와 에너지 고갈' 키워드는 다음과 같은 결과를 출력했다.

참고문헌

이 문서는 웹 크롤링과 형태소 분석을 통해 얻은 주요 키워드를 기반으로  작성되었습니다. 따라서 아래의 자료를 참고하여 추가적인 정보를 확보하고 문헌 목록을 작성하시길 권장합니다.

1. IPCC (Intergovernmental Panel on Climate Change). (2018). Global Warming of 1.5°C. Retrieved from https://www.ipcc.ch/sr15/
2. International Energy Agency. (2019). World Energy Outlook 2019. Retrieved from https://www.iea.org/reports/world-energy-outlook-2019
3. United Nations Framework Convention on Climate Change. (n.d.). Retrieved from https://unfccc.int/
4. Renewable Energy Policy Network for the 21st Century. (2019). Renewables 2019 Global Status Report. Retrieved from https://www.ren21.net/gsr/
5. International Renewable Energy Agency. (2020). Renewable Capacity Statistics 2020. Retrieved from https://www.irena.org/-/media/Files/IRENA/Agency/Publication/2020/Jun/IRENA_Renewable_Capacity_Statistics_2020.ashx[보고서 제목]

물론 다른 부분에서는 너무 뻔한 내용의 보고서가 생성됐다.

그리고 세부 키워드 출력 기능은 다음과 같이 동작했다. (입력은 'AI가 사회구조에 미치는 영향')

  1. 인공지능 (AI)
  2. 사회구조
  3. 기술 발전
  4. 자동화
  5. 일자리
  6. 경제
  7. 교육
  8. 사회 평등
  9. 개인 정보 보호
  10. 윤리적 고려 사항
  11. 인간-기계 상호작용
  12. 권력 분포

추가 사항

만약 기회가 주어진다면 키워드 별 연관 관계를 시각화할 수 있는 모델로 발전시키고 싶다. 내가 사용하지 않지만 옵시디언에서 문서와 문서의 연관성을 그래프로 나타낸 것에 착안했는데, 키워드 별 연관/종속성을 그림으로 표현하면 텍스트보다 더욱 좋은 개념 도식화 도구가 될 것 같다.

새로 알게 된 점

  • konlpy는 JVM 기반 Jython으로 동작한다. → 많은 에러가 JVM과 연관이 있어 찾아봤더니 konlpy가 Jython으로 동작한다는 걸 알게 됐다.
  • 생각보다 프롬프트 엔지니어링은 영향이 크지 않을 수 있다.
  • 대부분의 한글자 형태소는 내용을 축약하지 못 할 가능성이 크다. 혹은 한글자 형태소를 배재하더라도 한글 특성 상 무난하게 구문 분석이 가능하다.
profile
Someday, the dream will come true

0개의 댓글