Greptile MCP 서버 [완료]
빠른 실행 명령 치트시트
✅ 프로젝트 상태: 모든 작업 완료(11/11)
완료된 작업 요약은 PROJECT_COMPLETION.md를 참조하고, 사용 지침은 USER_GUIDE.md를 참조하세요.
환경 | 설정 및 설치 | 실행 명령 |
---|
로컬(Python) | python -m venv .venv && source .venv/bin/activate && pip install -e . | python -m src.main |
도커 | docker build -t greptile-mcp . | docker run --rm --env-file .env -p 8050:8050 greptile-mcp |
대장간 | npm install -g smithery | smithery deploy (smithery.yaml 참조) |
.env.example
사용하여 .env
채우고 실행하기 전에 GREPTILE_API_KEY
와 GITHUB_TOKEN
설정합니다.
전체 필수 구성 요소, 고급 에이전트 사용, 통합 및 문제 해결에 대한 자세한 내용은 docs/README.md
에서 전체 설명서를 참조하고 AGENT_USAGE.md 에서 에이전트 세부 정보를 참조하세요.
Greptile API와 통합되어 AI 에이전트에 코드 검색 및 쿼리 기능을 제공하는 MCP(Model Context Protocol) 서버 구현입니다.
특징
이 서버는 AI 에이전트가 코드베이스와 상호 작용할 수 있도록 하는 4가지 필수 Greptile 도구를 제공합니다.
index_repository
: 코드 검색 및 쿼리를 위해 저장소를 인덱싱합니다.- 저장소를 검색 가능하게 처리
- 저장소가 변경되면 기존 인덱스를 업데이트합니다.
- 알림 환경 설정 구성
query_repository
: 코드 참조로 답변을 얻기 위해 저장소를 쿼리합니다.- 코드베이스에 대한 자연어 질문을 하세요
- 특정 코드 위치를 참조하는 자세한 답변을 받으세요
- 세션 ID를 사용한 대화 기록 지원
search_repository
: 전체 답변을 생성하지 않고 관련 파일에 대한 저장소를 검색합니다.- 특정 개념이나 기능과 관련된 파일 찾기
- 관련성 순으로 정렬된 문맥별 일치 항목 가져오기
- 파일 위치만 필요한 경우 전체 쿼리보다 빠릅니다.
get_repository_info
: 인덱스된 저장소에 대한 정보를 가져옵니다.- 인덱싱 상태 및 진행 상황 확인
- 쿼리에 사용할 수 있는 저장소를 확인하세요.
- 인덱싱된 저장소에 대한 메타데이터 가져오기
대장간 배치
Greptile MCP 서버는 Smithery를 통한 배포를 지원합니다. smithery.yaml
구성 파일은 프로젝트 루트에 포함되어 있습니다.
대장간 구성
Smithery 구성은 smithery.yaml
에 정의되어 있으며 다음 옵션을 지원합니다.
지엑스피1
Smithery와 함께 사용
Smithery를 사용하여 배포하려면:
- Smithery 설치:
npm install -g smithery
- 서버 배포:
smithery deploy
- 필요한 API 키로 Smithery 클라이언트를 구성하세요.
추가 문서
AI 에이전트에 대한 자세한 사용 지침은 에이전트 사용 가이드를 참조하세요.
필수 조건
필수 Python 패키지
fastmcp
- MCP 서버 구현httpx
- 비동기 HTTP 클라이언트python-dotenv
- 환경 변수 관리uvicorn
- SSE 전송을 위한 ASGI 서버
설치
pip 사용(개발 또는 로컬 테스트용)
- 이 저장소를 복제하세요:
git clone https://github.com/sosacrazy126/greptile-mcp.git
cd greptile-mcp
- 가상 환경을 만듭니다(권장):
python -m venv .venv
source .venv/bin/activate # On Windows use `.venv\Scripts\activate`
- 종속성 설치:
.env.example
기반으로 .env
파일을 만듭니다..env
파일에서 환경 변수를 구성하세요.GREPTILE_API_KEY=your_api_key_here
GITHUB_TOKEN=your_github_token_here
Docker 사용(배포에 권장)
- 저장소를 복제합니다.
git clone https://github.com/sosacrazy126/greptile-mcp.git
cd greptile-mcp
.env.example
을 기반으로 .env
파일을 만들고 환경 변수를 구성합니다.- Docker 이미지를 빌드합니다.
docker build -t greptile-mcp .
서버 실행
pip 사용하기
SSE 운송(기본값)
.env
파일에서 TRANSPORT=sse
, PORT=8050
(또는 선택한 포트)이 설정되어 있는지 확인하세요.
서버는 http://<HOST>:<PORT>/sse
에서 수신합니다.
Stdio Transport
.env
파일에 TRANSPORT=stdio
설정하세요. stdio를 사용하면 MCP 클라이언트가 일반적으로 MCP 서버 프로세스를 시작합니다.
# Usually invoked by an MCP client, not directly
TRANSPORT=stdio python -m src.main
Docker 사용
SSE 운송(기본값)
# Mounts the .env file for configuration and maps the port
docker run --rm --env-file .env -p 8050:8050 greptile-mcp
서버는 http://localhost:8050/sse
(localhost가 아닌 경우 호스트 IP)에서 수신합니다.
Stdio Transport
TRANSPORT=stdio
로 Docker 컨테이너를 실행하도록 MCP 클라이언트를 구성합니다.
# Example of running with stdio transport
docker run --rm -i --env-file .env -e TRANSPORT=stdio greptile-mcp
MCP 클라이언트와의 통합
SSE 구성 예
MCP 클라이언트 구성에 다음을 추가합니다(예: mcp_config.json
):
{
"mcpServers": {
"greptile": {
"transport": "sse",
"url": "http://localhost:8050/sse"
}
}
}
Stdio 구성을 사용한 Python 예제
명령이 실행되는 환경에서 TRANSPORT=stdio
설정되어 있는지 확인하세요.
{
"mcpServers": {
"greptile": {
"transport": "stdio",
"command": "/path/to/your/greptile-mcp/.venv/bin/python",
"args": ["-m", "src.main"],
"env": {
"TRANSPORT": "stdio",
"GREPTILE_API_KEY": "YOUR-GREPTILE-API-KEY",
"GITHUB_TOKEN": "YOUR-GITHUB-TOKEN",
"GREPTILE_BASE_URL": "https://api.greptile.com/v2"
}
}
}
}
Stdio 구성을 사용한 Docker 예제
{
"mcpServers": {
"greptile": {
"transport": "stdio",
"command": "docker",
"args": [
"run", "--rm", "-i",
"-e", "TRANSPORT=stdio",
"-e", "GREPTILE_API_KEY",
"-e", "GITHUB_TOKEN",
"-e", "GREPTILE_BASE_URL",
"greptile-mcp"
],
"env": {
"GREPTILE_API_KEY": "YOUR-GREPTILE-API-KEY",
"GITHUB_TOKEN": "YOUR-GITHUB-TOKEN",
"GREPTILE_BASE_URL": "https://api.greptile.com/v2"
}
}
}
}
자세한 사용 가이드
코드베이스 분석을 위한 워크플로
index_repository
사용하여 분석하려는 인덱스 저장소get_repository_info
로 인덱싱 상태를 확인 하여 처리가 완료되었는지 확인하세요.query_repository
사용하여 자연어를 사용하여 저장소를 쿼리합니다.search_repository
사용하여 기능이나 개념과 관련된 특정 파일을 찾으세요.
대화 컨텍스트를 위한 세션 관리
모든 클라이언트(Smithery 포함)를 통해 Greptile MCP 서버와 상호 작용할 때 대화 맥락을 유지하기 위해 적절한 세션 관리가 중요합니다.
- 대화 시작 시 고유한 세션 ID 생성
- 관련된 모든 후속 쿼리에 동일한 세션 ID를 재사용합니다.
- 새로운 대화를 시작할 때 새 세션 ID를 만듭니다.
세션 ID 관리 예시:
# Generate a unique session ID
import uuid
session_id = str(uuid.uuid4())
# Initial query
initial_response = query_repository(
query="How is authentication implemented?",
repositories=[{"remote": "github", "repository": "owner/repo", "branch": "main"}],
session_id=session_id # Include the session ID
)
# Follow-up query using the SAME session ID
followup_response = query_repository(
query="Can you provide more details about the JWT verification?",
repositories=[{"remote": "github", "repository": "owner/repo", "branch": "main"}],
session_id=session_id # Reuse the same session ID
)
Smithery 통합 관련 중요 사항 : Smithery를 통해 연결하는 에이전트는 자체 세션 ID를 생성하고 유지해야 합니다. Greptile MCP 서버는 세션 ID를 자동으로 생성하지 않습니다. 세션 ID는 에이전트의 대화 상태에 포함되어야 합니다.
모범 사례
- 인덱싱 성능 : 작은 저장소는 인덱싱 속도가 더 빠릅니다. 대규모 단일 저장소의 경우 특정 브랜치나 태그를 인덱싱하는 것이 좋습니다.
- 쿼리 최적화 : 쿼리를 구체적으로 작성하세요. 더 나은 결과를 위해 관련 기술 용어를 포함하세요.
- 저장소 선택 : 여러 저장소를 쿼리하는 경우 최상의 결과를 얻으려면 관련성 순으로 나열하세요.
- 세션 관리 : 후속 질문에 세션 ID를 사용하여 쿼리 전반의 맥락을 유지합니다.
API 참조
1. 인덱스 저장소
향후 검색 시 검색할 수 있도록 저장소를 인덱싱합니다.
매개변수:
remote
(문자열): 저장소 호스트("github" 또는 "gitlab")repository
(문자열): 소유자/repo 형식의 저장소(예: "greptileai/greptile")branch
(문자열): 인덱싱할 브랜치(예: "main")reload
(부울, 선택 사항): 이전에 인덱싱된 저장소를 강제로 다시 처리할지 여부notify
(부울, 선택 사항): 인덱싱이 완료되면 이메일 알림을 보낼지 여부
예:
// Tool Call: index_repository
{
"remote": "github",
"repository": "greptileai/greptile",
"branch": "main",
"reload": false,
"notify": false
}
응답:
{
"message": "Indexing Job Submitted for: greptileai/greptile",
"statusEndpoint": "https://api.greptile.com/v2/repositories/github:main:greptileai%2Fgreptile"
}
2. 쿼리 저장소
자연어로 저장소를 쿼리하여 코드 참조로 답변을 얻습니다.
매개변수:
query
(문자열): 코드베이스에 대한 자연어 쿼리repositories
(배열): 쿼리할 저장소 목록, 각 저장소의 형식은 다음과 같습니다.{
"remote": "github",
"repository": "owner/repo",
"branch": "main"
}
session_id
(문자열, 선택 사항): 대화를 계속하기 위한 세션 IDstream
(부울, 선택 사항): 응답을 스트리밍할지 여부genius
(부울, 선택 사항): 향상된 쿼리 기능을 사용할지 여부
예:
// Tool Call: query_repository
{
"query": "How is authentication handled in this codebase?",
"repositories": [
{
"remote": "github",
"repository": "greptileai/greptile",
"branch": "main"
}
],
"session_id": null,
"stream": false,
"genius": true
}
응답:
{
"message": "Authentication in this codebase is handled using JWT tokens...",
"sources": [
{
"repository": "greptileai/greptile",
"remote": "github",
"branch": "main",
"filepath": "/src/auth/jwt.js",
"linestart": 14,
"lineend": 35,
"summary": "JWT token validation middleware"
}
]
}
3. 저장소 검색
전체 답변을 생성하지 않고도 관련 파일을 찾기 위해 저장소를 검색합니다.
매개변수:
query
(문자열): 코드베이스에 대한 검색 쿼리repositories
(배열): 검색할 저장소 목록session_id
(문자열, 선택 사항): 대화를 계속하기 위한 세션 IDgenius
(부울, 선택 사항): 향상된 검색 기능을 사용할지 여부
예:
// Tool Call: search_repository
{
"query": "Find files related to authentication middleware",
"repositories": [
{
"remote": "github",
"repository": "greptileai/greptile",
"branch": "main"
}
],
"session_id": null,
"genius": true
}
응답:
{
"sources": [
{
"repository": "greptileai/greptile",
"remote": "github",
"branch": "main",
"filepath": "/src/auth/middleware.js",
"linestart": 1,
"lineend": 45,
"summary": "Authentication middleware implementation"
},
{
"repository": "greptileai/greptile",
"remote": "github",
"branch": "main",
"filepath": "/src/auth/jwt.js",
"linestart": 1,
"lineend": 78,
"summary": "JWT token handling functions"
}
]
}
4. 저장소 정보 가져오기
인덱싱된 특정 저장소에 대한 정보를 가져옵니다.
매개변수:
remote
(문자열): 저장소 호스트("github" 또는 "gitlab")repository
(문자열): 소유자/repo 형식의 저장소branch
(문자열): 인덱싱된 브랜치
예:
// Tool Call: get_repository_info
{
"remote": "github",
"repository": "greptileai/greptile",
"branch": "main"
}
응답:
{
"repository": "greptileai/greptile",
"remote": "github",
"branch": "main",
"private": false,
"status": "COMPLETED",
"filesProcessed": 234,
"numFiles": 234,
"sha": "a1b2c3d4e5f6..."
}
통합 예제
1. Anthropic API를 통한 Claude.ai와의 통합
from anthropic import Anthropic
import json
import requests
# Set up Anthropic client
anthropic = Anthropic(api_key="your_anthropic_key")
# Function to call Greptile MCP
def query_code(question, repositories):
response = requests.post(
"http://localhost:8050/tools/greptile/query_repository",
json={
"query": question,
"repositories": repositories,
"genius": True
}
)
return json.loads(response.text)
# Ask Claude with enhanced code context
def ask_claude_with_code_context(question, repositories):
# Get code context from Greptile
code_context = query_code(question, repositories)
# Format the context for Claude
formatted_context = f"Code Analysis Result:\n{code_context['message']}\n\nRelevant Files:\n"
for source in code_context.get('sources', []):
formatted_context += f"- {source['filepath']} (lines {source['linestart']}-{source['lineend']})\n"
# Send to Claude with context
message = anthropic.messages.create(
model="claude-3-opus-20240229",
max_tokens=1000,
messages=[
{"role": "user", "content": f"Based on this code context:\n\n{formatted_context}\n\nQuestion: {question}"}
]
)
return message.content
# Example usage
answer = ask_claude_with_code_context(
"How does the authentication system work?",
[{"remote": "github", "repository": "greptileai/greptile", "branch": "main"}]
)
print(answer)
2. LLM 기반 챗봇과의 통합
from fastapi import FastAPI, Request
from fastapi.responses import JSONResponse
import httpx
import json
app = FastAPI()
# Greptile MCP endpoint
GREPTILE_MCP_URL = "http://localhost:8050/tools/greptile"
@app.post("/chat")
async def chat_endpoint(request: Request):
data = await request.json()
user_message = data.get("message", "")
# Check if this is a code-related question
if "code" in user_message or "repository" in user_message or "function" in user_message:
# Query the repository through Greptile MCP
async with httpx.AsyncClient() as client:
response = await client.post(
f"{GREPTILE_MCP_URL}/query_repository",
json={
"query": user_message,
"repositories": [
{"remote": "github", "repository": "your-org/your-repo", "branch": "main"}
],
"genius": True
}
)
greptile_result = response.json()
# Process the result and return to the user
answer = greptile_result.get("message", "")
sources = greptile_result.get("sources", [])
return JSONResponse({
"message": answer,
"code_references": sources
})
# For non-code questions, use your regular LLM
return JSONResponse({
"message": "This appears to be a general question. I'll handle it normally."
})
# Run with: uvicorn app:app --reload
3. 명령줄 코드 쿼리 도구
#!/usr/bin/env python3
import argparse
import json
import requests
import sys
def main():
parser = argparse.ArgumentParser(description="Query code repositories using natural language")
parser.add_argument("query", help="The natural language query about the code")
parser.add_argument("--repo", "-r", required=True, help="Repository in format github:owner/repo:branch")
parser.add_argument("--genius", "-g", action="store_true", help="Use enhanced query capabilities")
args = parser.parse_args()
# Parse the repository string
try:
remote, repo_path = args.repo.split(":", 1)
if ":" in repo_path:
repo, branch = repo_path.split(":", 1)
else:
repo = repo_path
branch = "main"
except ValueError:
print("Error: Repository must be in format 'github:owner/repo:branch' or 'github:owner/repo'")
sys.exit(1)
# Prepare the request
payload = {
"query": args.query,
"repositories": [
{
"remote": remote,
"repository": repo,
"branch": branch
}
],
"genius": args.genius
}
# Make the request
try:
response = requests.post(
"http://localhost:8050/tools/greptile/query_repository",
json=payload
)
response.raise_for_status()
except requests.exceptions.RequestException as e:
print(f"Error: {e}")
sys.exit(1)
# Process the response
result = response.json()
# Display the answer
print("\n=== ANSWER ===\n")
print(result.get("message", "No answer found"))
# Display the sources
sources = result.get("sources", [])
if sources:
print("\n=== CODE REFERENCES ===\n")
for i, source in enumerate(sources, 1):
print(f"{i}. {source['filepath']} (lines {source.get('linestart', '?')}-{source.get('lineend', '?')})")
print(f" Repository: {source['repository']} ({source['branch']})")
if 'summary' in source:
print(f" Summary: {source['summary']}")
print()
if __name__ == "__main__":
main()
문제 해결
일반적인 문제
1. 인증 실패
증상 : 401 Unauthorized
또는 Repository not found with configured credentials
오류가 발생합니다.
솔루션 :
- Greptile API 키가 유효하고
.env
파일에 올바르게 설정되었는지 확인하세요. - GitHub/GitLab 토큰이 만료되었는지 확인하세요(일반적으로 일정 기간 후 만료됨)
- GitHub/GitLab 토큰에 저장소에 액세스할 수 있는
repo
범위가 있는지 확인하세요. - GitHub API를 사용하여 GitHub 토큰을 직접 테스트하여 작동하는지 확인하세요.
GitHub 토큰 테스트 :
curl -H "Authorization: token YOUR_GITHUB_TOKEN" https://api.github.com/user
2. 저장소를 찾을 수 없습니다
증상 : API가 404 오류 또는 "저장소를 찾을 수 없습니다" 메시지를 반환합니다.
솔루션 :
- 저장소가 존재하고 GitHub/GitLab 토큰으로 액세스할 수 있는지 확인하세요.
- 저장소 형식을 다시 한 번 확인하세요(
owner/repo
여야 함) - 개인 저장소의 경우 토큰에 적절한 액세스 권한이 있는지 확인하세요.
- 지점 이름이 올바른지 확인하세요
3. 연결 문제
증상 : MCP 서버에 연결할 수 없습니다.
솔루션 :
- 서버가 실행 중인지 확인하세요(
ps aux | grep src.main
) - 다른 애플리케이션에서 포트를 사용하고 있지 않은지 확인하세요.
- 네트워크 설정 및 방화벽 구성을 확인하세요
.env
파일에서 PORT
값을 변경하여 다른 포트를 시도해 보세요.
4. Docker 문제
증상 : Docker 컨테이너가 시작되지 않거나 올바르게 작동하지 않습니다.
솔루션 :
- Docker 로그 확인:
docker logs <container_id>
.env
파일이 올바르게 마운트되었는지 확인하세요.docker run
명령에서 포트 매핑이 올바른지 확인하세요.- Docker 네트워크 구성에서 필요한 연결이 허용되는지 확인하세요.
로그 및 디버깅
더 자세한 로깅을 활성화하려면 다음 환경 변수를 설정하세요.
# Add to your .env file
DEBUG=true
LOG_LEVEL=debug
특정 MCP 상호작용 문제를 해결하려면 MCP 서버 로그를 검사하세요.
# Run with enhanced logging
LOG_LEVEL=debug python -m src.main
고급 구성
환경 변수
변하기 쉬운 | 설명 | 기본 |
---|
TRANSPORT | 전송 방법( sse 또는 stdio ) | sse |
HOST | SSE 전송을 위해 바인딩할 호스트 | 0.0.0.0 |
PORT | SSE 운송 항구 | 8050 |
GREPTILE_API_KEY | Greptile API 키 | (필수의) |
GITHUB_TOKEN | GitHub/GitLab 개인 액세스 토큰 | (필수의) |
GREPTILE_BASE_URL | Greptile API 기본 URL | https://api.greptile.com/v2 |
DEBUG | 디버그 모드 활성화 | false |
LOG_LEVEL | 로깅 레벨 | info |
사용자 정의 API 엔드포인트
사용자 정의 Greptile API 엔드포인트를 사용해야 하는 경우(예: 엔터프라이즈 설치의 경우) GREPTILE_BASE_URL
환경 변수를 수정하세요.
GREPTILE_BASE_URL=https://greptile.your-company.com/api/v2
성능 튜닝
프로덕션 배포의 경우 다음과 같은 성능 최적화를 고려하세요.
- 작업자 구성 : Uvicorn과 함께 SSE 전송을 사용할 때 적절한 작업자 수를 구성하세요.
# For CPU-bound applications: workers = 1-2 × CPU cores
uvicorn src.main:app --workers 4
- 시간 초과 설정 : 대규모 저장소의 시간 초과를 조정합니다.
# Add to .env
GREPTILE_TIMEOUT=120.0 # Default is 60.0 seconds
- 메모리 최적화 : 대규모 배포의 경우 컨테이너 리소스 제한을 고려하세요.
docker run --rm --env-file .env -p 8050:8050 --memory="1g" --cpus="1.0" greptile-mcp
기여하다
기여를 환영합니다! 풀 리퀘스트를 제출해 주세요.
- 저장소를 포크하세요
- 기능 브랜치를 생성합니다(
git checkout -b feature/amazing-feature
) - 변경 사항을 커밋하세요(
git commit -m 'Add some amazing feature'
) - 브랜치에 푸시(
git push origin feature/amazing-feature
) - 풀 리퀘스트 열기
개발 설정
개발을 위해 추가 종속성을 설치하세요.
테스트 실행:
특허
이 프로젝트는 MIT 라이선스에 따라 라이선스가 부여되었습니다. 자세한 내용은 라이선스 파일을 참조하세요.
( https://github.com/sosacrazy126 )에서 빌드됨