mcp-api-server
Uses OpenAI's CLIP model for generating image embeddings via an external embedding server.
Integrates Ultralytics YOLOv8 for object detection in images.
Click on "Install Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@mcp-api-serverAnalyze this image for objects: /home/user/photo.jpg"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
MCP API 서버
FastAPI 및 FastMCP 기반의 Model Context Protocol (MCP) 서버로, YOLOv8 이미지 분석과 PostgreSQL 데이터베이스 통합을 지원합니다.
프로젝트 개요
이 프로젝트는 Claude와 같은 AI 에이전트가 이미지를 분석하고 결과를 데이터베이스에 저장할 수 있도록 MCP 프로토콜을 통해 제공합니다.
주요 기능:
YOLOv8 이미지 분석 - nano/small/medium 모델 지원 (빠른 추론)
감지된 객체 자동 처리 - 크롭 및 base64 인코딩
PostgreSQL 데이터 저장 - asyncpg 기반 비동기 DB 연결
4-Layer 아키텍처 - Presenter → Service → Core → Utility 레이어 구분
MCP 3가지 전송 방식 - StdIO (Claude Desktop), HTTP/JSON-RPC, WebSocket
Related MCP server: Agent Construct
시스템 요구사항
Python: 3.13.3 이상
패키지 매니저:
uv(설치 가이드)메모리: 2GB 이상 (YOLOv8 모델 로드용)
데이터베이스: PostgreSQL 12+ (pgvector 확장 필수)
빠른 시작
1단계: 의존성 설치
# 프로젝트 루트에서 실행
uv sync2단계: 데이터베이스 설정
PostgreSQL 데이터베이스를 생성하고 .env 파일에 접속 정보를 설정합니다:
# .env 파일 생성
cat > .env << EOF
# PostgreSQL 데이터베이스 설정
DB_HOST=localhost
DB_PORT=5432
DB_NAME=mcp_db
DB_USER=postgres
DB_PASSWORD=your_password
# YOLOv8 모델 설정
YOLO_MODEL=yolov8n.pt
YOLO_HOME=./src/mcp_server/models
YOLO_CONF_THRESHOLD=0.5
# MCP 서버 설정
MCP_SERVER_NAME=mcp-api-server
LOG_LEVEL=INFO
EOF설정 항목 설명:
항목 | 기본값 | 설명 |
|
| PostgreSQL 호스트 |
|
| PostgreSQL 포트 |
|
| 데이터베이스명 |
|
| DB 사용자명 |
| - | DB 암호 |
|
| YOLOv8 모델 (nano/s/m/l/x) |
|
| 모델 다운로드 디렉토리 |
|
| 감지 신뢰도 임계값 (0~1) |
|
| MCP 서버 이름 |
|
| 로그 레벨 (DEBUG/INFO/WARNING) |
YOLOv8 모델 선택 가이드:
모델 | 추론시간 | 메모리 | 정확도 | 추천 상황 |
yolov8n.pt | ~3ms | <100MB | 낮음 | 빠른 응답 필요 |
yolov8s.pt | ~10ms | 200MB | 중간 | ✅ 권장 |
yolov8m.pt | ~20ms | 400MB | 높음 | 정확도 중시 |
3단계: 서버 실행
MCP StdIO 서버 (Claude Desktop 연결용):
# FastMCP 방식 (권장, 간단함)
uv run python -m mcp_server
# 또는 MCP SDK 방식 (더 많은 기능)
MCP_SERVER_TYPE=sdk uv run python -m mcp_serverFastAPI HTTP/WebSocket 서버 (원격 클라이언트용):
# 개발 모드 (자동 리로드 활성화)
uv run uvicorn src.mcp_server.main:app --reload
# 프로덕션 모드 (4개 워커)
uv run uvicorn src.mcp_server.main:app --workers 4서버 시작 확인:
FastMCP StdIO: 터미널에서 "Starting FastMCP server" 로그 메시지 확인
FastAPI HTTP: 브라우저에서
http://localhost:8000/health접속 →{"status": "ok"}
프로젝트 구조
mcp-api-server/
│
├── .git/ # Git 저장소
├── .python-version # Python 3.13.3
├── .env.example # 환경변수 템플릿
├── .gitignore
│
├── pyproject.toml # uv 프로젝트 설정
├── uv.lock # 의존성 잠금 파일
│
├── README.md # 이 파일
├── CLAUDE.md # 개발 규약
├── NOTION_USAGE_GUIDE.md # Notion 작업 문서 규칙
├── ARCHITECTURE.md # 아키텍처 설명
│
├── src/
│ └── mcp_server/ # 메인 패키지
│ ├── __main__.py # MCP StdIO 진입점
│ ├── main.py # FastAPI HTTP/WS 진입점
│ ├── fastmcp_server.py # FastMCP 서버 구현
│ ├── server.py # MCP 서버 인스턴스 (SDK용)
│ │
│ ├── commons/ # 공유 유틸리티 (infrastructure)
│ │ ├── config.py # Pydantic Settings (환경변수)
│ │ ├── database.py # SQLAlchemy AsyncEngine + asyncpg
│ │ ├── logging.py # 로깅 설정
│ │ └── exceptions.py # 커스텀 예외
│ │
│ ├── core/ # 도메인 모델 (domain layer)
│ │ ├── yolo_model.py # YOLOv8 lazy loading (스레드 안전)
│ │ └── embedding_client.py # 외부 API 클라이언트
│ │
│ ├── schemas/ # 데이터 모델 (Pydantic)
│ │ ├── response.py # 응답 모델 (Detection, AnalysisResult, ImageRecordResponse)
│ │ └── img_model.py # DB ORM 모델 (ImageRecord)
│ │
│ ├── services/ # 비즈니스 로직 (service layer)
│ │ ├── image_analyzer_service.py # YOLOv8 분석 로직
│ │ ├── image_query_service.py # DB 조회 로직
│ │ └── repository.py # DB 저장 로직
│ │
│ ├── tools/ # MCP Tool 구현 (presenter layer)
│ │ ├── __init__.py
│ │ └── image_analysis.py # analyze_image tool
│ │
│ ├── resources/ # MCP Resource (선택)
│ │ └── __init__.py
│ │
│ ├── prompts/ # MCP Prompt (선택)
│ │ └── __init__.py
│ │
│ └── utils/ # 공유 유틸리티
│ ├── suppress_output.py # 출력 억제 데코레이터
│ └── image_utils.py # 이미지 처리 헬퍼
│
├── tests/ # 테스트 스위트
│ ├── conftest.py # pytest fixtures
│ ├── test_models.py # Pydantic 모델 테스트
│ └── test_*.py # 기능별 테스트
│
└── examples/ (선택) # 클라이언트 예제
├── http_client.py # HTTP JSON-RPC 클라이언트
└── websocket_client.py # WebSocket 클라이언트아키텍처 (4 Layers)
┌──────────────────────────────────────────────────────────┐
│ Presenter Layer (MCP Tools) │
│ - tools/image_analysis.py │
│ - MCP Protocol 변환 (JSON-RPC 2.0) │
└──────────────────┬───────────────────────────────────────┘
│
┌──────────────────▼───────────────────────────────────────┐
│ Service Layer (비즈니스 로직) │
│ - services/image_analyzer_service.py │
│ - services/image_query_service.py │
│ - @atransactional 데코레이터로 DB 트랜잭션 관리 │
└──────────────────┬───────────────────────────────────────┘
│
┌──────────────────▼───────────────────────────────────────┐
│ Core Layer (도메인 모델) │
│ - core/yolo_model.py (double-checked locking) │
│ - core/embedding_client.py │
│ - schemas/img_model.py (SQLAlchemy ORM) │
└──────────────────┬───────────────────────────────────────┘
│
┌──────────────────▼───────────────────────────────────────┐
│ Utility Layer (공유 인프라) │
│ - commons/database.py (AsyncEngine + asyncpg) │
│ - commons/config.py (환경변수) │
│ - utils/suppress_output.py (출력 억제) │
└──────────────────────────────────────────────────────────┘의존성 흐름: Presenter → Service → Core → Utility (역방향 금지)
주요 기능 설명
analyze_image MCP Tool
이미지 파일 경로를 입력받아 YOLOv8로 객체를 감지하고 결과를 저장합니다.
입력 파라미터:
파라미터 | 타입 | 필수 | 설명 |
| string | ✅ | 이미지 파일 절대 경로 |
| float | ❌ | 감지 임계값 (0~1, 기본: 0.5) |
반환 결과 (AnalysisResult):
{
"image_path": "/path/to/image.jpg",
"detections": [
{
"class_name": "person",
"confidence": 0.91,
"bbox": [100.0, 50.0, 200.0, 300.0]
}
],
"total_objects": 1
}처리 흐름:
입력 검증 - 파일 존재 확인
이미지 전처리 - PIL로 로드, RGB 변환, 1024×1024 리사이징
객체 감지 - YOLOv8 추론 (asyncio.to_thread 사용)
DB 저장 - ImageRecord 생성 및 PostgreSQL 저장 (@atransactional)
결과 반환 - Pydantic AnalysisResult 모델
주요 특징:
비동기 처리 - asyncio.to_thread()로 블로킹 작업 분리
자동 리사이징 - 1024×1024으로 일관된 처리 품질 보장
에러 처리 - DB 연결 실패 시 예외 발생, 로그 기록
타입 안정성 - Pydantic 모델로 검증
데이터베이스 구성
PostgreSQL + asyncpg 설정
# PostgreSQL 설치 (Windows)
# https://www.postgresql.org/download/windows/
# 데이터베이스 생성
psql -U postgres -c "CREATE DATABASE mcp_db;"데이터베이스 테이블 (자동 생성)
서버 첫 실행 시 init_async_db() 함수가 아래 테이블을 자동으로 생성합니다:
CREATE TABLE image_records (
id SERIAL PRIMARY KEY,
path VARCHAR NOT NULL UNIQUE,
category VARCHAR NOT NULL,
confidence FLOAT NOT NULL,
description TEXT,
objects JSONB,
created_at TIMESTAMP DEFAULT NOW(),
updated_at TIMESTAMP DEFAULT NOW()
);비동기 데이터베이스 접근
모든 DB 접근은 @atransactional 데코레이터를 사용합니다:
from mcp_server.commons.database import atransactional, AsyncSession
from mcp_server.schemas.response import AnalysisResult
@atransactional
async def save_analysis(result: AnalysisResult, db: AsyncSession):
"""데이터베이스에 분석 결과 저장"""
from mcp_server.schemas.img_model import ImageRecord
record = ImageRecord(
path=result.image_path,
category="detected_object",
confidence=result.detections[0].confidence if result.detections else 0.0,
)
db.add(record)
# 트랜잭션 자동 커밋 (예외 발생 시 자동 롤백)특징:
asyncpg 기반 - PostgreSQL 비동기 드라이버
Lazy initialization - FastMCP 루프에서만 engine 생성
자동 트랜잭션 - 데코레이터로 commit/rollback 자동 관리
세션 주입 - 함수 파라미터에 자동으로 db 제공
API 엔드포인트
헬스 체크 및 서버 정보
# 헬스 체크
GET /health
→ {"status": "ok"}
# 서버 정보
GET /infoMCP HTTP/JSON-RPC (네트워크 기반)
엔드포인트: POST /mcp/messages
import httpx
import asyncio
async def call_tool():
async with httpx.AsyncClient() as client:
response = await client.post(
"http://localhost:8000/mcp/messages",
json={
"jsonrpc": "2.0",
"id": 1,
"method": "tools/call",
"params": {
"name": "analyze_image",
"arguments": {
"image_path": "/absolute/path/to/image.jpg",
"conf_threshold": 0.5
}
}
}
)
print(response.json())
asyncio.run(call_tool())MCP WebSocket 양방향 통신
엔드포인트: WS /mcp/ws
import asyncio
import json
import websockets
async def ws_client():
async with websockets.connect("ws://localhost:8000/mcp/ws") as ws:
await ws.send(json.dumps({
"jsonrpc": "2.0",
"id": 1,
"method": "initialize",
"params": {}
}))
response = await ws.recv()
print(f"Response: {response}")
asyncio.run(ws_client())MCP StdIO (Claude Desktop)
Claude Desktop 설정:
macOS: ~/Library/Application Support/Claude/claude_desktop_config.json
Windows: %APPDATA%\Claude\claude_desktop_config.json
{
"mcpServers": {
"mcp-api-server": {
"command": "uv",
"args": ["run", "python", "-m", "mcp_server"],
"cwd": "/absolute/path/to/mcp-api-server"
}
}
}개발 명령어
테스트 실행
# 모든 테스트 실행
uv run pytest
# 상세 출력
uv run pytest -v
# 특정 테스트 실행
uv run pytest tests/test_models.py -v
# 커버리지 리포트
uv run pytest --cov=src코드 린트 및 포맷팅
# 린트 검사
uv run ruff check .
# 자동 포맷팅
uv run ruff format .
# 린트 + 포맷 함께
uv run ruff check . && uv run ruff format .타입 검사
# VS Code Pylance strict mode 사용 (IDE에서 설정)
# .vscode/settings.json:
{
"python.analysis.typeCheckingMode": "strict"
}트러블슈팅
YOLOv8 모델 자동 다운로드 실패
# 수동 다운로드
uv run python -c "from ultralytics import YOLO; YOLO('yolov8n.pt')"
# 또는 서버 실행 (자동 다운로드)
uv run uvicorn src.mcp_server.main:app모델 저장 위치: ./src/mcp_server/models/ (.gitignore 제외)
PostgreSQL 연결 오류
# DB 접속 가능 확인
psql -h localhost -U postgres -d mcp_db -c "SELECT 1;"
# 방화벽 설정 확인 (Windows)
# → Defender 방화벽에서 PostgreSQL 포트 5432 허용asyncpg 루프 바인딩 에러
에러: 'NoneType' object has no attribute 'send'
원인: asyncpg 커넥션이 다른 event loop에 바인딩됨
해결:
init_async_db()는 별도 loop에서 실행 (스키마만 초기화)실제 engine은 FastMCP/FastAPI loop에서 lazy 생성
자세한 설명은 ARCHITECTURE.md 참고
메모리 부족
# 더 작은 모델 사용
echo "YOLO_MODEL=yolov8n.pt" >> .env
# 또는 명령어로 실행
YOLO_MODEL=yolov8s.pt uv run uvicorn src.mcp_server.main:app개발 규약
모든 개발 규약은 CLAUDE.md에 자세히 기술되어 있습니다.
주요 규약:
언어: Python 3.13.3 이상
타입 힌팅: Pylance strict mode 필수 (모든 함수/파라미터)
코드 스타일: Ruff (line-length: 100)
데이터 모델: Pydantic BaseModel + SQLAlchemy ORM
커밋 메시지: Conventional Commits
테스트: pytest + pytest-asyncio
아키텍처: 4-Layer (Presenter → Service → Core → Utility)
Git 워크플로우
새 기능 추가
git checkout -b feature/기능-이름
# ... 작업 ...
git add .
git commit -m "feat(scope): 기능 설명"
git push -u origin feature/기능-이름버그 수정
git checkout -b fix/버그-이름
# ... 수정 ...
git commit -m "fix(scope): 버그 설명"
git push -u origin fix/버그-이름성능 최적화
YOLOv8 모델 선택
모델 | 추론시간 | 메모리 | 정확도 | 추천 |
yolov8n.pt | ~3ms | <100MB | 낮음 | 빠른 응답 |
yolov8s.pt | ~10ms | 200MB | 중간 | ✅ 권장 |
yolov8m.pt | ~20ms | 400MB | 높음 | 정확도 중시 |
yolov8l.pt | ~40ms | 800MB | 매우높음 | 매우 정확 |
비동기 배치 처리
from mcp_server.services.image_analyzer_service import ImageAnalyzerService
service = ImageAnalyzerService()
# 여러 이미지를 동시에 분석
results = await service.analyze_images_abatch([
"/path/to/image1.jpg",
"/path/to/image2.jpg",
"/path/to/image3.jpg",
])라이선스
MIT License
참고 자료
더 자세한 개발 정보는 CLAUDE.md를 참고하세요.
This server cannot be installed
Maintenance
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Latest Blog Posts
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/istanadodan/img_detect_mcp'
If you have feedback or need assistance with the MCP directory API, please join our Discord server