터미널 AI 에이전트 구축 (v33)
개요
터미널에서 동작하는 AI 에이전트는 개발자에게 코드 생성, 분석, 리팩토링을 위한 실시간 도우미를 제공합니다. 이 가이드에서는 오픈소스 AI 에이전트를 구축하고 최적화하는 실전 방법을 소개합니다.
1. CLI AI 에이전트 생태계
현재 CLI AI 에이전트는 다음과 같은 주요 도구들로 구성되어 있습니다:
Aider
가장 인기 있는 오픈소스 도구로, 실시간 코드 수정을 지원합니다:
pip install aider
aider --help
aider --model llama3
Continue.dev
VSCode 확장으로 시작했지만 CLI에서도 사용 가능:
npm install -g @continue/core
continue start
OpenCode
특정 언어에 최적화된 에이전트:
pip install opencode-agent
opencode --language python
사용자 정의 스크립트
다음과 같은 간단한 스크립트로 시작할 수 있습니다:
# aider-like script
import openai
import subprocess
def get_code_context(file_path):
return subprocess.run(['git', 'show', f'HEAD:{file_path}'],
capture_output=True, text=True)
def ai_assistant(prompt, context=""):
client = openai.OpenAI(api_key="your-key")
response = client.chat.completions.create(
model="gpt-4",
messages=[
{"role": "system", "content": context},
{"role": "user", "content": prompt}
]
)
return response.choices[0].message.content
2. 로컬 LLM API 엔드포인트 설정
LocalAI 설치
# Docker로 설치
docker run -p 1234:1234 --name localai \
-v /path/to/models:/models \
localai/localai:latest
# 또는 직접 설치
git clone https://github.com/go-skynet/LocalAI
cd LocalAI
make build
./local-ai --models-path /models
모델 다운로드
# Qwen 모델 다운로드
mkdir -p /models
curl -L -o /models/qwen-7b-chat.bin \
https://huggingface.co/Qwen/Qwen-7B-Chat/resolve/main/qwen-7b-chat.bin
# LLaMA 모델 다운로드
wget -O /models/llama2-7b.gguf \
https://huggingface.co/TheBloke/Llama-2-7B-GGUF/resolve/main/llama-2-7b.Q4_K_M.gguf
API 테스트
# 로컬 API 테스트
curl -X POST http://localhost:1234/v1/chat/completions \
-H "Content-Type: application/json" \
-d '{
"model": "qwen-7b-chat",
"messages": [{"role": "user", "content": "Hello"}]
}'
3. 간단한 Python CLI 에이전트 구축
#!/usr/bin/env python3
# terminal_agent.py
import argparse
import json
import os
import subprocess
import sys
from typing import List, Dict, Any
import openai
class TerminalAgent:
def __init__(self, model="qwen-7b-chat"):
self.model = model
self.client = openai.OpenAI(
base_url="http://localhost:1234/v1/",
api_key="localai"
)
def run_command(self, command: str) -> str:
"""터미널 명령어 실행"""
try:
result = subprocess.run(
command,
shell=True,
capture_output=True,
text=True
)
return result.stdout + result.stderr
except Exception as e:
return f"Error: {str(e)}"
def get_context(self, files: List[str]) -> str:
"""파일 컨텍스트 수집"""
context = []
for file_path in files:
if os.path.exists(file_path):
with open(file_path, 'r') as f:
content = f.read()
context.append(f"File: {file_path}\n{content}")
return "\n\n".join(context)
def execute_function_call(self, function_call: Dict[str, Any]) -> str:
"""함수 호출 실행"""
name = function_call.get("name")
arguments = function_call.get("arguments", {})
if name == "run_command":
return self.run_command(arguments.get("command", ""))
elif name == "search_code":
return self.search_code(arguments.get("pattern", ""))
else:
return f"Unknown function: {name}"
def search_code(self, pattern: str) -> str:
"""코드 검색"""
try:
result = subprocess.run([
"grep", "-r", pattern, ".", "--exclude-dir=.git"
], capture_output=True, text=True)
return result.stdout
except Exception as e:
return f"Search error: {str(e)}"
def chat(self, message: str, context_files: List[str] = None) -> str:
"""채팅 메시지 처리"""
context = self.get_context(context_files) if context_files else ""
try:
response = self.client.chat.completions.create(
model=self.model,
messages=[
{"role": "system", "content": f"Context:\n{context}"},
{"role": "user", "content": message}
]
)
return response.choices[0].message.content
except Exception as e:
return f"AI Error: {str(e)}"
def main():
parser = argparse.ArgumentParser()
parser.add_argument("--message", "-m", required=True)
parser.add_argument("--files", "-f", nargs="*", default=[])
parser.add_argument("--model", "-M", default="qwen-7b-chat")
args = parser.parse_args()
agent = TerminalAgent(model=args.model)
result = agent.chat(args.message, args.files)
print(result)
if __name__ == "__main__":
main()
사용 방법:
# 기본 사용
python terminal_agent.py -m "Write a Python function to reverse a string"
# 파일 컨텍스트 포함
python terminal_agent.py -m "Explain this function" -f "src/main.py"
# 사용자 정의 모델 사용
python terminal_agent.py -m "Optimize this code" -M "llama2-7b"
4. tmux/터미널 멀티플렉서 통합
tmux 스크립트 생성
# ~/.tmux/ai-session.sh
#!/bin/bash
tmux new-session -d -s ai-agent
tmux split-window -h
tmux send-keys -t ai-agent:0 'python terminal_agent.py' Enter
tmux send-keys -t ai-agent:1 'watch -n 1 git status' Enter
tmux attach -t ai-agent
tmux 키 바인딩 설정
# ~/.tmux.conf
bind-key C-a run-shell 'tmux new-session -d -s ai-agent'
bind-key C-b run-shell 'tmux send-keys -t ai-agent:0 "python terminal_agent.py" Enter'
5. 사용자 정의 도구 개발
파일 검색 도구
# tools/file_search.py
import os
import subprocess
from typing import List
class FileSearchTool:
@staticmethod
def search_files(pattern: str, root_dir: str = ".") -> List[str]:
"""파일 검색"""
try:
result = subprocess.run([
"find", root_dir, "-name", f"*{pattern}*"
], capture_output=True, text=True)
return result.stdout.strip().split('\n')
except Exception as e:
return [f"Error: {str(e)}"]
@staticmethod
def search_in_files(pattern: str, file_extensions: List[str] = None) -> str:
"""파일 내부 검색"""
if file_extensions:
extensions = " -o ".join([f"-name '*.{ext}'" for ext in file_extensions])
cmd = f"find . -type f \\( {extensions} \\) -exec grep -l '{pattern}' {{}} \\;"
else:
cmd = f"grep -r '{pattern}' ."
try:
result = subprocess.run(cmd, shell=True, capture_output=True, text=True)
return result.stdout
except Exception as e:
return f"Error: {str(e)}"
Git 통합 도구
python
# tools/git_tool.py
import subprocess
import json
class GitTool:
@staticmethod
def get_staged_files() -> List[str]:
"""스테이징된 파일 목록"""
try:
result = subprocess.run(
['git', 'diff', '--cached', '--name-only'],
---
📥 **Get the full guide on Gumroad**: https://gumroad.com/l/auto ($5)
Top comments (0)