
노출된 AI 에이전트 인프라를 위한 인터넷 규모 탐지 및 보안 테스트 플랫폼.
AIMap은 공개적으로 노출된 AI 엔드포인트(MCP 서버, Ollama 인스턴스, vLLM/LiteLLM 프록시, LangServe 체인, Gradio 앱, ComfyUI 노드 등)를 찾고, 지문을 식별하며, 보안 테스트를 수행합니다. Shodan과 유사하지만, AI 에이전트 공격 표면에 특화되어 있습니다.
Bishop Fox에서 제작했습니다.
경고 이 도구는 공인된 침투 테스트 및 보안 연구 목적으로만 사용해야 합니다. 소유권이 있거나 명시적인 서면 허가를 받은 시스템에 대해서만 AIMap을 사용해야 합니다. 무단 컴퓨터 시스템 접근은 불법입니다. Bishop Fox는 이 도구로 인한 오용이나 손해에 대해 책임을 지지 않습니다. 책임감 있게 사용하십시오.
┌─────────────┐ ┌──────────────┐ ┌───────────┐
│ React SPA │────▶│ FastAPI │────▶│ MongoDB │
│ (Vite) │ WS │ Backend │ │ │
└─────────────┘ └──────┬───────┘ └───────────┘
│
┌────────────┼────────────┐
▼ ▼ ▼
┌──────────┐ ┌──────────┐ ┌──────────┐
│ Shodan │ │ Nuclei │ │ Redis │
│ API │ │ Scanner │ │ Streams │
└──────────┘ └──────────┘ └──────────┘
백엔드 — Python/FastAPI, 비동기 MongoDB(Motor), Redis Streams(공격 로그 스트리밍), Shodan 쿼리 → httpx 활성 검사 → Nuclei 템플릿 스캔 → 보강 파이프라인을 오케스트레이션하는 발견 엔진.
프론트엔드 — React 18 + TypeScript + Tailwind CSS + shadcn/ui. 3D 지구본(globe.gl), WebSocket을 통한 실시간 공격 스트리밍, Shodan 스타일 검색 인터페이스 제공.
스캐닝 — MCP 서버 감지, MCP 도구 열거, OpenAI 호환 API 감지, LangServe 감지, 프롬프트 유출 테스트를 위한 5개의 맞춤형 Nuclei YAML 템플릿.
각 엔드포인트는 다음 요소로부터 0~10점의 위험 점수를 받습니다:
# 클론
git clone [email protected]:BishopFox/aimap.git
cd aimap
# 설정
cp .env.example .env
# .env 편집 — 최소한 SHODAN_API_KEY를 설정하세요
# 실행
docker compose up --build
이 명령은 4개의 서비스를 시작합니다:
http://localhost를 열어 UI에 접속하세요.
# 백엔드
cd backend
python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
uvicorn app.main:app --reload --port 8000
# 프론트엔드 (별도 터미널)
cd frontend
npm install
npm run dev # http://localhost:5173에서 시작
MongoDB가 로컬에서 포트 27017로 실행 중인지 확인하세요. Redis는 선택 사항입니다. Redis를 사용할 수 없으면 백엔드가 인메모리 버퍼로 대체됩니다.
프로젝트 루트에 .env 파일을 만드세요:
# 필수
SHODAN_API_KEY=your_shodan_api_key
# 선택 사항 — 추가 발견 소스로 Censys 사용
CENSYS_API_ID=
CENSYS_API_SECRET=
# 선택 사항 — AI 기반 공격 분석 활성화
ANTHROPIC_API_KEY=
# MongoDB (로컬 개발 시 기본값 사용)
MONGODB_URI=mongodb://localhost:27017
MONGODB_DB=aimap
# Redis (로컬 개발 시 기본값 사용, 선택 사항)
REDIS_URL=redis://localhost:6379/0
# CORS (기본값은 모든 출처 허용)
CORS_ORIGINS=*
# Modal 서버리스 (스캔/공격을 Modal 컨테이너로 전달)
MODAL_ENABLED=false
# Clerk 인증 — 아래 참조
CLERK_ISSUER=
AIMap은 인증에 Clerk를 사용합니다. 활성화하려면:
# .env (프로젝트 루트)
CLERK_ISSUER=https://your-app.clerk.accounts.dev
# frontend/.env.local
VITE_CLERK_PUBLISHABLE_KEY=pk_test_...
인증 비활성화 (로컬 개발, 데모): CLERK_ISSUER를 비워두거나 설정하지 마세요. 백엔드는 합성 local 사용자 ID로 모든 요청을 수락합니다.
ollama, mcp_protocol, vllm)을 선택하거나 사용자 지정 Shodan 쿼리를 입력합니다.net:<cidr>을 추가합니다).Shodan 스타일 쿼리 구문을 사용하여 검색창을 활용하세요:
protocol:mcp # MCP 서버
auth:none # 인증 없음
risk:critical # 위험 점수 9.0 이상
risk:high # 위험 점수 7.0 – 8.9
risk:medium # 위험 점수 4.0 – 6.9
risk:low # 위험 점수 1.0 – 3.9
tool:query_db # 특정 도구를 노출하는 엔드포인트
country:US # 국가 코드별
port:11434 # 포트 번호별
org:"Amazon AWS" # 호스팅 조직별 (여러 단어는 따옴표)
has:system_prompt # 유출된 시스템 프롬프트가 있는 엔드포인트
필터를 자유롭게 결합하세요:
protocol:mcp auth:none country:US # 미국 내 인증 없는 MCP 서버
risk:critical tool:exec_code # 코드 실행 도구가 있는 위험도 높은 엔드포인트
protocol:ollama port:11434 # 기본 포트의 Ollama
key:value 패턴과 일치하지 않는 모든 텍스트는 모든 인덱싱된 필드에 대한 자유 텍스트 검색으로 처리됩니다.
랜딩 페이지에는 발견된 모든 엔드포인트를 보여주는 대화형 3D 지구본이 있습니다:
templates/ 디렉토리의 사용자 지정 템플릿:
모든 엔드포인트는 /api/ 접두사로 시작합니다.
aimap/
├── backend/
│ ├── app/
│ │ ├── main.py # FastAPI 앱, 수명 주기, CORS, 라우터
│ │ ├── config.py # Pydantic 설정 (환경 변수)
│ │ ├── auth.py # Clerk JWT 검증 (CLERK_ISSUER가 비어 있으면 우회)
│ │ ├── database.py # 비동기 MongoDB (Motor) 연결
│ │ ├── limiter.py # SlowAPI 속도 제한
│ │ ├── routes/
│ │ │ ├── endpoints.py # CRUD + 검색 + 지구본 + 보강
│ │ │ ├── scans.py # 스캔 수명 주기 + 실행 + WebSocket
│ │ │ └── attack.py # 공격 전달 + Redis Streams + WebSocket
│ │ ├── discovery/
│ │ │ ├── orchestrator.py # 스캔 파이프라인: Shodan → httpx → Nuclei → 수집
│ │ │ ├── shodan_adapter.py # 32개의 큐레이팅된 Shodan 쿼리 + 결과 정규화
│ │ │ ├── nuclei_runner.py # Nuclei 서브프로세스 실행기 + 결과 파서
│ │ │ └── base.py # SourceAdapter 추상 기본 클래스
│ │ └── services/
│ │ ├── attack_mcp.py # MCP 프로토콜 공격 엔진
│ │ ├── attack_ollama.py # Ollama 공격 엔진
│ │ ├── attack_openclaw.py # OpenClaw/Clawdbot 공격 엔진
│ │ ├── enrichment.py # Shodan/Nuclei 보강 + 위험 점수
│ │ ├── live_probe.py # 모델/도구 열거를 위한 HTTP 프로빙
│ │ ├── search.py # Shodan 스타일 쿼리 파서 → MongoDB 필터
│ │ ├── redis_client.py # 비동기 Redis 싱글톤 (대체 지원)
│ │ └── concurrency.py # 세마포어 + Redis 기반 슬롯 제한
│ ├── Dockerfile
│ └── requirements.txt
├── frontend/
│ ├── src/
│ │ ├── App.tsx # 라우트 + Clerk 인증 래퍼
│ │ ├── pages/
│ │ │ ├── Marketing.tsx # 3D 지구본이 있는 공개 랜딩 페이지
│ │ │ ├── Landing.tsx # 인증된 대시보드 (지구본 포함)
│ │ │ ├── Search.tsx # 쿼리 구문을 사용한 엔드포인트 검색
│ │ │ ├── Explore.tsx # 모든 엔드포인트 탐색/필터
│ │ │ ├── AgentDetail.tsx # 단일 엔드포인트 심층 분석
│ │ │ ├── TestAgent.tsx # 공격 테스트 실행기
│ │ │ ├── Scans.tsx # 스캔 관리
│ │ │ └── Ranges.tsx # CIDR 범위 관리
│ │ ├── components/
│ │ │ ├── GlobeVisualization.tsx # globe.gl 3D 지구본 + 범례
│ │ │ ├── Layout.tsx # 앱 셸 (사이드바 + 내비바)
│ │ │ └── ui/ # shadcn/ui 컴포넌트
│ │ ├── hooks/useApi.ts # 모든 API 엔드포인트용 SWR 훅
│ │ └── lib/api-client.ts # Clerk 토큰 주입이 포함된 Fetch 래퍼
│ ├── Dockerfile
│ ├── nginx.conf
│ └── tailwind.config.js
├── templates/ # Nuclei YAML 템플릿
├── docs/ # GitHub Pages 정적 사이트
├── docker-compose.yml
├── .env.example
└── README.md
플랫폼은 남용을 방지하기 위해 전역 동시성 제한을 시행합니다:
Docker Compose 사용 시 이러한 제한은 Redis 카운터(컨테이너 간)를 통해 적용됩니다. 로컬 개발 모드에서는 asyncio.Semaphore(단일 프로세스)로 대체됩니다.
무거운 스캔 작업의 경우 스캔과 공격을 Modal 컨테이너로 전달할 수 있습니다:
MODAL_ENABLED=true
활성화되면 POST /scans/{id}/run 및 POST /attack은 로컬에서 실행하는 대신 modal.Function.from_name("aimap", "run_scan_task") / run_attack_task를 호출합니다. Modal 전달이 실패하면 로컬 실행으로 대체됩니다.
MIT 라이선스. 자세한 내용은 LICENSE를 참조하세요.
이 프로젝트는 Bishop Fox에서 유지 관리합니다.
| 프로토콜 | 탐지 방법 | Shodan 쿼리 수 |
|---|
| MCP (Model Context Protocol) | SSE 전송, JSON-RPC, /mcp/sse 경로 | 4개 |
| Ollama | 기본 포트 11434, 제품 지문 | 3개 |
| vLLM / LiteLLM / LocalAI | /v1/models, /v1/chat/completions 엔드포인트 | 4개 |
| LangServe / LangChain | Playground 엔드포인트, langserve 마커 | 2개 |
| OpenClaw / Clawdbot | 제어 대시보드, 포트 18789 | 3개 |
| Open WebUI / LibreChat | 제목 기반 탐지 | 2개 |
| Gradio | 제목, 하단 워터마크, favicon 해시 | 3개 |
| Streamlit | 제목, favicon 해시 | 2개 |
| ComfyUI / Stable Diffusion | 제목, 포트 기반 탐지 | 4개 |
| HuggingFace TGI | HTML 마커 | 1개 |
| 일반 추론 | /api/generate, /api/tags 경로 | 2개 |
| 요소 | 점수 영향 |
|---|
| 인증 없음 | +4.0 |
| 알 수 없는 인증 상태 | +1.0 |
| 10개 이상의 도구 노출 | +2.0 |
| 5개 이상의 도구 노출 | +1.0 |
위험도가 높은 도구(예: exec_code, run_shell) | 각 +1.0 |
고위험 도구(예: query_db, file_read) | 각 +0.5 |
열린 CORS (*) | +1.0 |
| TLS 미사용 | +0.5 |
| 시스템 프롬프트 유출 | +0.5 |
| 모델 노출 | +1.0 |
| 검열되지 않은 모델 감지 | +2.0 |
| 가입 활성화 (초대 불필요) | +1.5 |
| 위험한 조합 (예: 인증 없음 + 코드 실행 도구) | 각 +1.0 |
| 템플릿 | 목적 |
|---|
mcp-server-detect.yaml | SSE 전송 및 JSON-RPC 기능 응답을 통해 MCP 서버 감지 |
mcp-tool-enum.yaml | MCP 서버가 노출하는 도구(이름, 설명, 입력 스키마) 열거 |
openai-compat-detect.yaml | /v1/models를 통해 OpenAI 호환 엔드포인트 감지 |
langserve-detect.yaml | 노출된 playground가 있는 LangServe 배포 감지 |
prompt-leak.yaml | 일반적인 인젝션 기법을 통해 시스템 프롬프트 추출 시도 |
| 메서드 | 경로 | 설명 |
|---|
GET | /health | 상태 확인 |
GET | /endpoints | 엔드포인트 목록 (페이지네이션, 필터 가능) |
POST | /endpoints/search | 쿼리 구문을 사용한 고급 검색 |
GET | /endpoints/globe | 3D 지구본용 지리 데이터 |
GET | /endpoints/stats | 집계 통계 |
GET | /endpoints/{id} | 엔드포인트 상세 |
POST | /endpoints/{id}/enrich | 단일 엔드포인트에 대한 보강 트리거 |
POST | /endpoints/enrich-all | 일괄 보강 |
GET | /scans | 스캔 목록 |
POST | /scans | 스캔 생성 |
POST | /scans/{id}/run | 스캔 실행 |
GET | /scans/query-presets | 사용 가능한 Shodan 쿼리 프리셋 |
WS | /scans/{id}/progress | 실시간 스캔 진행 상황 |
POST | /attack | 공격 테스트 실행 |
WS | /attack/{id}/stream | 실시간 공격 로그 스트림 |
GET | /attack/{id}/status | 공격 상태 |