공모전에서 챗봇을 개발하는 파트를 맡아 한국 로컬 위주의 여행 지원 봇을 구축해 보았다. 아직 완성본은 아니기에 현재 완료된 부분과 앞으로 새롭게 추가할 기능, 변경된 부분들을 차분히 기록해보고자 한다.
이 챗봇은 로컬 여행 관련 웹 메인 페이지에 위치해 Java Spring 웹서버와 FastAPI를 활용해 통신한다.
로컬 여행 챗봇으로 사용자에게 필요한 정보를 친숙한 대화 형식의 방식으로 지원해준다. 이 챗봇이 가진 기능은 크게 세가지이다.
여행지 추천
사용자가 여행하고자 하는 지역을 파악한 후 사용자 질문과 관련된 장소를 최대 5곳 추천해준다. 아래의 그림 처럼 장소명, 설명, 장소의 그림과 함께 사용자에게 장소를 추천한다.

여행 계획 생성
여행 지역, 여행 기간을 파악한 후 사용자가 원하는 장소들로 구성된 계획을 생성해준다.



시스템 흐름 설명
챗봇이 작동되면 사용자의 질문이 LangGraph Agent에 전달된다. 질문의 의도를 파악하여 질문과 관련된 외부 도구(= 함수)를 호출할 수 있다.
이 도구가 호출될 경우, 사용자 질문과 관련된 함수가 작동되며 질문을 벡터화 시킨 후 관련된 자료를 검색한다. ( RAG 로직이 여기에 이 부분에서 쓰인다.)
호출된 함수에 지정된 지시사항과 검색 참고 자료를 이용해 자연어 처리 모델이 답변을 생성하고, 알맞은 JSON 형식으로 답변을 후처리 후 사용자에게 전달
로컬 크리에이터 기반의 특수 데이터 제공
로컬 크리에이터는 지역의 자산을 활용해 사업을 하고 계신 분들을 의미하며, 정부에서 지역 활성화 프로젝트로 이들을 지원하기도 한다. 마케팅 역량이 부족한 로컬 크리에이터 위주로 장소를 소개하여 일반 여행자가 알아내기 힘든 장소들 위주로 정보를 제공한다.
여행 가이드봇 제공
챗봇을 통해 정보 접근 편의성을 증대시키며 개인의 관심사와 취향을 실시간으로 반영해 여행 정보를 제공 받을 수 있다.
설문 형태의 데이터 군집화 결과가 아닌 사용자와 소통하는 간단한 방식으로 장소를 추천한다.
장소의 구체적인 정보 체크 가능
강원도 로컬 크리에이터 위주로 설문조사를 진행하여 장소의 예약 가능 여부, 반려동물 동반 가능, 분위기, 휠체어 접근 가능 여부 등 디테일한 정보들을 제공함.
다른 여행 사이트에서 제공하지 않는 정보들을 제공하며 챗봇과의 대화와 메인페이지의 장소 검색 기능을 통해 이러한 정보를 손쉽게 얻을 수 있다.
왜 LangGraph 라이브러리를 사용했는지에 대한 답변도 포함한다.
프로그램에 사용되는 LLM은..
1. 이전 대화 내용을 기억할 수 있어야 한다.
자연어 처리 모델를 이용해 대화를 하다 보면 대화 내용이 쌓이게 되는데, 앞선 대화 속에 사용자의 요구사항을 모델이 기억하고 알맞은 답변을 하기 위해서는 대화 내용을 기억할 수 있어야 한다.
2. 도구를 호출할 수 있어야 한다.
사용자의 다양한 요구에 맞는 능동적인 답변을 생성하기 위해서 사용자의 질문과 관련된 함수를 작동시킬 수 있도록 구성하였다. 따라서 위에서 설명한 여행지 추천, 여행 계획 생성, 특정 장소 검색 기능은 각각 다른 함수들로 구성되어 있고, 사용자 질문의 의도를 파악한 후 모델이 관련 함수를 호출한 후 답변을 생성한다.
EX. 사용자 질문: 강릉에서 아이와 함께 갈 수 있는 장소 알려줄래?
-> 모델은 여행지 추천 함수를 작동 후 작동 결과를 다음 단계로 전달
3. 항상 JSON 형식으로 답변을 생성해야 한다.
LLM의 답변을 JSON 형식으로 만들어 웹 서버로 전달해야 하며 FastAPI를 사용한다. 웹 서버에서는 JSON을 받아 필요한 값을 추출해 질문에 가장 효과적인 방식으로 답변을 재구성한다. JSON의 key는 answer와 place가 존재한다.
4. 상황에 따라 생성해야 하는 JSON 값이 다르다.
간단하게 예를 들어 설명하면,
answer 값으로 짧은 추천의 말과, place에는 장소의 정보가 전달된다. {
"answer" : "AI의 짧은 추천의 말",
"place" :
[
{
"place_name" : "장소 이름",
"description" : "장소 설명",
"redirection_url" : "장소의 상세페이지 이동 경로"
},
...
]
}
answer 키의 값으로 들어가고, place 값은 null로 된다. {
"answer" : "1박 2일의 긴 여행 계획 내용",
"place" : null
}
웹 메인 페이지에서 여러 사용자들이 챗봇을 각각 이용할 수 있어야 한다.
현재 병렬적으로 작동하지 않아 한 사용자가 답변을 받은 후 다른 사용자가 이용할 수 있다.
사용자의 여행 취향을 파악할 수 있는 조금 더 효율적인 방법이 필요하다.
사용자와의 대화를 통해 취향에 맞는 장소를 대부분 알려주지만 안정성과 속도 측면에서 좋은 편은 아니라고 판단된다. (가끔 취향과 맞지 않는 장소를 추천해줄 때도 있다)
대화를 시작하기 전 사용자의 여행 유형을 전달하여 이를 기반으로 답변을 생성하는 방식으로 재구성해 보고 싶다.
Self-RAG / Corrective-RAG 방식을 적용해 답변의 검색 정확도와 완성도를 높이는 방법으로 구성하고 싶다.
다음 게시물은 왜 LangGraph 라이브러리를 사용했는지에 대한 구체적인 내용과 구현 내용을 적어볼 것이다 😉