들어가며
안녕하세요. Game Platform Dev의 류동훈, Zhang Youlu(Michael), Takenaka, 이형중입니다. 저희 조직은 게임 퍼블리싱에 필요한 다양한 기능을 개발하고 운영하는 역할을 맡고 있습니다.
저희는 최근 조직 내 업무 효율을 높이기 위해 다양한 LLM(large language model) 애플리케이션을 개발하고, 이와 연계해 LLMOps 시스템 구축 프로젝트를 진행했습니다. 프로젝트의 주요 목표 중 하나는 진입 장벽이 높은 LLM 애플리케이션 개발을 직군에 상관없이 누구나 쉽게 제작할 수 있는 환경을 구축하는 것이었는데요. 이를 위해 여러 가지를 고민하며 시도하는 과정을 거쳤고, 그 결과 누구나 손쉽게 접근할 수 있는 개발 및 배포 환경을 마련할 수 있었습니다.
이번 글에서는 LLM 애플리케이션의 일반적인 개발 방식과 개발 과정에서 마주하는 어려움을 살펴보고, 이런 문제를 해결할 수 있는 환경을 구성하기 위해 저희가 어떤 고민을 하고 노력을 했는지 공유하고자 합니다. 이 글을 통해 LLM 애플리케이션 개발 과정의 병목 지점을 개선하고 고도화해 접근성을 높일 수 있는 인사이트를 얻으시길 바라며 시작하겠습니다.
LLM 애플리케이션의 개발 과정
프롬프트는 모델이 수행해야 할 작업의 맥락과 방향을 제시하므로 프롬프트를 잘 구조화하면 LLM의 성능을 한층 더 높일 수 있습니다. 또한 프롬프트는 수정하기 쉽기 때문에 비싼 비용을 지불해 모델을 직접 수정하는 것보다 훨씬 저렴하다는 장점도 있습니다. 이런 장점을 이용해 개발자들은 보다 빠르고 경제적으로 모델의 성능을 최적화할 수 있습니다.
하지만 LLM 애플리케이션이 새로운 데이터에 대해 적절히 답변하도록 만드는 문제는 프롬프트 최적화만으로는 해결할 수 없습니다. 그럼 이 문제를 모델을 추가 학습하지 않고 어떻게 해결할 수 있을까요?
일반적으로 이런 문제는 LLM의 몇 가지 기능을 활용해 해결합니다. LLM은 사전 학습된 데이터 외에 프롬프트에 제시된 추가 정보를 통해 즉석에서 정보를 생성할 수 있습니다. 이런 기능을 인 컨텍스트(in-context) 러닝이라고 합니다. 인 컨텍스트 러닝 중 특히 몇 가지 예시 답변을 통해 모델이 패턴을 익히고 더욱 잘 답변하게 만드는 것을 퓨 샷(few-shot) 러닝이라고 하는데요. 이를 이용해 프롬프트에 정보를 주입하면 LLM이 새로운 데이터에 대해 적절히 답변할 수 있게 만들 수 있습니다.
이제 LLM이 새로운 데이터에 대해 답변할 수 있게 됐지만 인 컨텍스트 러닝과 퓨 샷 러닝, 두 가지 기법만으로는 새로운 데이터에 대해 완벽히 대응하기 어렵습니다. 이를 보완하기 위해 외부 데이터베이스의 적절한 추가 정보나 예시 등을 실시간으로 모델에 주입해 결과를 생성하는 방법인 RAG(Retrieval Augmented Generation)를 사용합니다.
RAG의 기본적인 메커니즘은 두 단계로 나눌 수 있습니다. 첫 번째는 모델이 이해할 수 있는 형태로 데이터를 임베딩(embedding)해 벡터로 만들어 데이터베이스에 저장하는 단계이고, 두 번째는 LLM으로 요청할 때 데이터베이스에 질의해 질문과 유사한 데이터를 검색(retrieval)해서 그 결과를 프롬프트에 주입하는 단계입니다. 그 결과 인 컨텍스트 러닝을 통해 새로운 데이터에 대해서도 패턴을 인식해 LLM이 답변할 수 있게 됩니다.