Local Code Assistant 도전기 [2]
Local Code Assistant 구축 과정과 아쉬운 점, 그리고 향후 계획에 대해 자세히 설명해 드립니다.
Contents
읽기전에
1편에서는 어쩌다 제가 LocalLLM 에 대해 관심을 가지게 되었는지에 대해 설명하였습니다. 이번 글에서는 구체적으로 어떻게 Local Code Assistant 를 구축하게 되었는지 정리해 보겠습니다.
Github
이 글에서 설명하고 있는 코드는 이 레포지토리에 정리해 놓았습니다. 프로토타입용으로 코드를 구현해 보았기 때문에, 구체적인 코드 구현보다는 전체적인 구조 위주로 봐주시면 감사하겠습니다.
아키텍처

  Local Code Assistant 의 전체적인 구조는 위와 같습니다. 기본적으로 Copilot, Copilot Chat 과 같은 형태로 사용할 수 있는 Local Code Assistant 서버를 구축하였습니다. ChatGPT, Claude 와 같은 LLM 서비스를 그대로 사용하지 않고, 중간에 RAG Server를 거쳐 관련된 코드 문맥을 Vector Database 에서 검색하여 LLM Model에게 전달하도록 코드를 작성하였습니다. 프로토타입 코드에서는 다음과 같은 기술 스펙을 사용하였습니다.
- Language: Typescript
 - Backend Framework: Nest.js
 - LLM Model: qwen2.5-coder:7b-instruct-q4KM
 - Vector Database: ChromaDB
 
SEED
위의 아키텍처 도식을 살펴보면, RAG Server 에서는 Vector Database 에서 관련된 코드를 검색합니다. 그렇게 하기 위해서는, 먼저 Vector Database 에 관련된 코드를 적재시켜 놓아야 합니다. 평소에 Vector Database에 대해 잘 알지 못했었는데, 이번에 프로토타입을 구현하면서 Vector Database 에 대해 찾아보게 되었습니다. 이번 프로젝트에서는 로컬 Vector Database 로 많이 사용한다는 ChromaDB 를 사용해 보았습니다.
ChromaDB 는 2022년 말, Generative AI와 LLM의 인기가 급격히 증가하면서 등장한 프로젝트입니다. 기존의 Database (RDB, MongoDB 등)로는 임베딩 기반의 데이터 검색이 불가능합니다. ChromaDB 는 텍스트나 이미지 데이터의 유사도를 쉽게 검색할 수 있는 오픈소스 프로젝트입니다.
seed.ts 는 로컬 파일시스템의 디렉토리 명을 입력받아, 해당 디렉토리 하위의 파일들을 읽어 ChromaDB 에 적재합니다. ChromaDB 의 내부 데이터 스토리지로는 SQLite를 사용합니다.
API Endpoints
이제는 실질적으로 Client(Intellij IDEA), LLM Model 과 통신하는 RAG API Endpoint 를 작성해 보도록 하겠습니다. 제가 Github Copilot 에서 자주 사용하는 기능은 다음과 같습니다.
- 코드 자동완성
 - Copilot Chat
 
위의 두 기능을 지원해 주는 API Endpoint 는 다음과 같습니다.
| API Endpoint | 설명 | |-------------------------------------------------------------------------------------------------------------------------------------------|--------------| | /api/chat | 코드 자동완성 | | /api/generate | Copilot Chat |
  각각의 API Endpoint 들에서는 공통적으로 stream 모드를 지원하도록 코드를 작성하였습니다. 최근의 LLM Client 들을 보면, 보통 토큰 단위로 문장이 생성되므로, 동일하게 구현하고 싶었기 때문입니다. 이 프로젝트에서는 SSE 방식으로 구현하여, Client 에서 실시간으로 UI 에 응답 데이터를 업데이트 할 수 있도록 구현하였습니다. (관련 코드)
Jetbrain Plugin
Vector Database, RAG Server 의 구현이 모두 끝났다면, 어떻게 실제로 사용해 볼 수 있을까요 ? 많은 선택지들이 있겠지만, 저는 Jetbrain 의 ProxyAI를 사용하였습니다. 이 플러그인에서는 LocalLLM 을 IDE 와 연동하는 기능을 제공합니다. Jetbrain IDE 에서 다음과 같이 RAG Server 에 대한 설정을 추가합니다.

위와 같이 설정을 완료하면, 마치 Github Copilot 플러그인처럼 동작하는 Local Code Assistant 를 사용할 수 있습니다.
아쉬웠던 점
Local Code Assistant 를 사용해 보니, 몇 가지 아쉬운 점이 있었습니다. 기능은 Github Copilot 과 비슷하게 동작하지만, 품질 면에서 아쉬웠던 점들이 있었습니다.
먼저 RAG Server 의 응답 속도가 만족스럽지 않았습니다. 이는 예상한 결과이기도 했지만 로컬에서 M1 맥북에서 돌리다 보니, 하드웨어의 한계를 많이 느끼게 되었습니다. 특히 16GB 의 램 환경에서 7B 파라미터가 입력된 모델을 돌리다 보니, 발열 문제도 생기기 시작했습니다. 처음으로 그래픽 카드가 가지고 싶다는 생각이 들기도 했습니다.
다음으로, 추천해 주는 코드의 정확도가 생각보다 높지 않습니다. 왜 이런 문제가 발생하는지 디버깅을 해 보았는데, Vector Database 에서 연관된 코드로 검색된 Code Context 의 정확도가 높지 않았습니다. Vector Database 에 적재시킬 때의 embedding 알고리즘을 개선시키는 작업을 해 보아야 할 것 같습니다. 사실 embedding 알고리즘은 Ollama의 기능을 사용하고 있어서, 어째서 정확도가 높지 않은지는 추가적으로 확인해 보아야 할 것 같습니다.
&nbps; 당근마켓의 RAG를 활용한 검색 서비스 만들기를 보고, ChromaDB 대신 ElasticSearch 를 활용해 보아도 좋겠다는 생각이 들었습니다. 벡터 검색 대신, 유사한 파일명을 지닌 파일들을 검색하여 코드 문맥으로 입력해 주는 것도 좋을 것 같습니다.
다음으로
LocalLLM 을 돌리다 보니, 로컬 맥북의 한계를 조금 느꼈습니다. 비싼 그래픽카드로 LocalLLM 돌리는 영상 을 보니 좀 부러웠습니다. LocalLLM 에서의 한계를 보완하기 위해, AWS 의 SageMaker, Bedrock 등의 제품들도 사용해 볼 예정입니다.
참고자료
이것도 읽어보세요