Spring AI MCP 실습: Phase 0~3에서 실제로 터진 오류와 검증 기반 해결 정리
Spring AI MCP 실습 과정에서 Phase 0~3까지 진행 중 실제로 터진 오류를 로그 기반으로 정리했습니다.
Spring AI MCP 실습을 하다 보면, 단순한 “Hello World”를 넘어서 실제 운영 환경에 가까운 구조를 만들 때 예상보다 많은 문제를 만나게 됩니다.
특히 다음과 같은 상황은 문서만 보고는 판단하기 어렵습니다.
- STDIO 방식에서 JSON 파싱 오류가 연쇄적으로 발생하는 경우
- Phase별로 분리했다고 생각했는데, 다른 Phase의 Bean이 섞여 올라오는 문제
- Java 빌드 버전과 런타임 버전 불일치로 인한 즉시 종료
- MCP Inspector에서는 연결되는데 실제 Tool 호출이 실패하는 경우
이 글은 이론 정리나 공식 문서 요약이 아닙니다. 실제 MCP 실습 과정에서 직접 발생한 오류 로그와 그에 대한 검증 결과를 바탕으로, 어디서 왜 막히는지와 어떤 기준으로 다음 Phase로 넘어가야 하는지를 Phase 0부터 Phase 3까지 누락 없이 정리한 기록입니다.
Spring AI MCP 실습 환경 & 전제 (검증 기준)
아래 환경에서 직접 실행해 실패/성공을 재현했습니다.
- 운영체제: Windows 11
- IDE: IntelliJ IDEA
- 빌드 도구: Gradle
- 프레임워크: Spring Boot + Spring AI MCP
- Java 런타임: 기본 PATH는 Java 17, 일부 시점에서 Java 21로 빌드된 Jar 실행 시도
- MCP 테스트 도구: MCP Inspector(UI + Proxy), IntelliJ HTTP Request
중요한 전제
- Phase별 실행은 서로 완전히 독립적이어야 합니다.
- 한 Phase에서 문제가 발생하면 다음 Phase로 진행하지 않는 것이 원칙입니다.
이 기준을 지키지 않으면, 이후 문제의 원인이 현재 Phase인지 이전 Phase 잔재인지 구분할 수 없게 됩니다.
실습 소스 코드 기준
이 글에서 다루는 모든 Phase(0~3)는 실제 실행 및 오류 재현이 가능하도록 구성된 실습 코드를 기준으로 검증되었습니다.
실습 저장소: https://github.com/rexx4314/rex-mcp-lab
추가 자료나 다른 글은 블로그 홈에서 확인하실 수 있습니다: Tech > Guides 전체 보기
해당 저장소에는 Phase별 프로파일 분리 구조, MCP Tool 등록 방식, Streamable HTTP/STDIO 실험 환경, DB/Redis/Sandbox/Git 연계 예제 등이 포함됩니다. 이 글은 저장소의 코드를 그대로 설명하는 문서가 아니라, 실행 과정에서 실제로 발생한 오류와 원인을 로그 기준으로 정리한 기록입니다.
Spring AI MCP 실습 Phase 0 — 최소 MCP 서버 검증 (가장 중요)
목적
- MCP 서버가 정상 기동
- Inspector에서 tools/list 노출
- Tool 호출 시 정상 JSON 응답
여기서 막히면 Phase 1~3은 진행하지 않는 것이 맞습니다. 프로토콜/등록/환경 쪽 문제일 때가 많습니다.
✅ Phase 0 요약 카드
핵심 검증: Inspector 연결 성공 → tools/list에서 echo/health 등 확인 → 각 Tool 호출 시 즉시 JSON 응답
여기서 막히면: Phase 1~3 진행 ❌ (등록/프로토콜/환경 문제 가능성)
이 글은 Spring AI MCP 실습 과정에서 실제로 겪은 실패 지점을 기준으로, 다음 Phase로 넘어가기 전 무엇을 확인해야 하는지에 초점을 둡니다.
Spring AI MCP 실습 실행 및 확인 절차
실행 명령어 (재현용)
# 공통 빌드
./gradlew clean build
# bootJar 생성
./gradlew clean bootJar
# MCP Inspector 실행
npx @modelcontextprotocol/inspector
위 명령어는 재현을 위한 최소 세트이며, 실습의 핵심은 명령 실행 자체보다 Inspector에서 tools/list와 Tool 호출이 성공하는지 여부입니다.
- Gradle로 bootJar 생성
- MCP Inspector 실행


- Transport를 STDIO 또는 Streamable HTTP 중 하나로 선택

- 서버 연결 후 tools/list 확인




실제 발생한 오류와 검증된 원인
1) STDIO JSON 파싱 오류 대량 발생
증상: Unexpected token / not valid JSON 오류가 반복 출력
원인(검증됨): STDIO transport는 표준 출력에 MCP JSON만 있어야 하는데, Spring Boot 로그가 stdout으로 섞여 들어가면서 Node MCP SDK가 파싱에 실패합니다.
결론: 실습 단계에서는 Streamable HTTP 방식이 훨씬 안정적입니다. STDIO는 로그 분리/비활성화 등 추가 설정이 없으면 추천하기 어렵습니다.
2) Jar 실행 경로 오류
증상: Unable to access jarfile …
원인: build/libs 경로 누락 또는 상대 경로 기준 혼동
검증 결과: 절대 경로 또는 정확한 build/libs 경로를 사용하면 즉시 해결됩니다.
3) Java 버전 불일치 오류
증상: UnsupportedClassVersionError (예: class file version 65.0 vs runtime 61.0)
원인: Java 21로 빌드된 Jar를 Java 17 런타임으로 실행
해결 선택지: (1) 빌드 버전을 17로 낮추거나 (2) 런타임 Java를 21로 맞춥니다. 실습 속도 기준으로는 Java 17 통일이 가장 빠른 선택인 경우가 많습니다.
Spring AI MCP 실습 Phase 1~3 실행 요약 (공통)
Phase 0이 정상적으로 통과되었다면, 이제 Phase 1~3은 아래 명령어로 각각 실행해 검증할 수 있습니다. 각 Phase는 서로 독립적으로 실행해야 하며, 동시에 띄우지 않는 것이 원칙입니다.
# Phase 1
./gradlew bootRun --args="--spring.profiles.active=phase1"
# Phase 2
./gradlew bootRun --args="--spring.profiles.active=phase2"
# Phase 3
./gradlew bootRun --args="--spring.profiles.active=phase3"
각 Phase 실행 시 서버 포트, 활성 프로파일, Inspector 연결 대상이 서로 일치하는지 반드시 로그로 확인한 뒤 다음 Phase로 넘어가야 합니다.
Spring AI MCP 실습 Phase 1 — 내부 HTTP 호출 Tool 검증
✅ Phase 1 요약 카드
목적: MCP Tool → 내부 HTTP API 호출 구조 검증(정상/지연/실패 전파)
자주 발생: Connection refused(포트 혼선), 404(컨트롤러 없음)
목적: MCP Tool → 내부 HTTP API 호출 구조를 안정적으로 검증하고, 지연/실패/타임아웃 전파가 올바르게 되는지 확인합니다.
Spring AI MCP 실습 Phase 1 실행
공통 요약에서 한 번 실행했다면, Phase 1은 아래 명령으로 단독 실행 중인지 다시 확인합니다.
./gradlew bootRun --args="--spring.profiles.active=phase1"
Spring AI MCP 실습 실행 및 테스트 흐름
- Phase 1 프로파일로 서버 실행
- IntelliJ HTTP Request로 내부 API 직접 호출(정상/지연/실패)

- 동일 동작을 MCP Tool로 호출
실제 발생 오류
1) Connection refused
원인: 기본 8080으로 요청했으나 실제 서버 포트는 3001 등으로 설정되어 있었던 케이스
검증: server.port 값과 요청 포트를 일치시키면 즉시 해결됩니다.
2) 404 Not Found
원인: 내부 API 컨트롤러/매핑 자체가 없는 상태
중요한 판단: Phase 1은 Tool만으로 검증하기 어렵고, HTTP 엔드포인트가 반드시 존재해야 IntelliJ HTTP Request로 선검증이 가능합니다.
Spring AI MCP 실습 Phase 2 — DB / Redis 연계 (운영 관점 핵심)
✅ Phase 2 요약 카드
목적: DB/Redis 같은 내부 리소스 접근 + 조회 제한/마스킹 같은 운영 요구사항 반영
핵심 검증: limit 강제, 민감정보 마스킹, redis set/get 일치, 프로파일 완전 분리
목적: “사내 리소스 접근” 단계로 넘어가며 DB/Redis 같은 내부 자원과 연결합니다. 이 단계에서는 기능 구현 자체보다도 결과 제한(예: limit 강제), 마스킹, 운영·보안 요구사항이 포함되는지 확인하는 것이 중요합니다.
주요 검증 포인트
- 검색 결과 limit이 강제로 적용되는지
- 민감 정보가 마스킹되어 노출되는지
- Redis set/get이 기대대로 일치하는지
실제로 가장 많이 막힌 문제
1) Phase 0 실행 시 Phase 2 Bean 로딩
증상: Phase 0으로 실행했는데 Repository bean not found 등으로 종료
원인(확인됨): Phase 2 Bean에 Profile 분리가 적용되지 않아 다른 Phase에서도 생성되는 구조
결론: 모든 Phase 전용 Bean(Tools/Service/Repository/Controller/Config)은 반드시 해당 Phase 프로파일로 묶여야 합니다.
2) data.sql 실행 오류
증상: Table not found
원인: JPA 테이블 생성 이전에 data.sql이 먼저 실행되는 초기화 순서 문제
해결 방향: (1) JPA ddl-auto 이후 실행되도록 설정하거나 (2) schema.sql / data.sql 분리 등으로 초기화 책임을 명확히 분리합니다.
Spring AI MCP 실습 Phase 3 — 위험 도구 통제 검증
✅ Phase 3 요약 카드
목적: 파일/Git 같은 위험 도구를 “안전하게” 노출하고 통제가 올바른지 검증
성공 기준: “작동”이 아니라 “차단”이 기대대로 되는지(화이트리스트/샌드박스/경로 차단)
목적: Phase 3은 “되게 만드는 단계”가 아니라 안전하게 막는 단계입니다. 샌드박스, 화이트리스트, 경로 traversal 차단, 승인(approval) 같은 통제가 핵심입니다.
핵심 검증 케이스
- 디렉터리 traversal(예: ../) 차단
- 허용된 파일만 접근 가능
- 허용 리스트 밖 명령은 무조건 DENY
- Git status는 저장소(.git) 루트가 아니면 명확한 에러를 반환
각 케이스는 가능하면 MCP Inspector에서 직접 호출한 결과 화면을 함께 남겨두면, 나중에 원인 분리가 훨씬 쉬워집니다.
파일이 안 바뀐 것처럼 보이는 경우(혼동 지점)
writeSandbox 같은 호출을 했는데 파일이 안 바뀐 것처럼 보이는 상황은 현업에서도 흔합니다. 이번 실습 흐름 기준으로 가장 가능성이 높은 원인은 다음 3가지였습니다.
- 서버 프로세스가 여러 개 떠 있음 (IDE 실행 + jar 실행 + Inspector 재연결 등)
- Inspector가 다른 포트/다른 프로파일 서버에 붙어 있음
- 내가 보고 있는 파일 경로와 실제 sandbox-dir 경로가 다름
검증 방법: 서버 로그에서 active profile 확인 → 포트 리슨 PID 하나만 남기기 → readSandbox로 “서버가 보는 내용”을 교차검증하면 원인 분리가 쉬워집니다.
Spring AI MCP 실습 공통 트러블슈팅 플로우 (의사결정 기준)
Phase가 올라갈수록 문제가 복잡해지므로, 아래 순서를 고정하면 원인 분리가 매우 쉬워집니다.
- 서버가 뜨는가?
- active profile이 의도한 Phase인가?
- tools/list가 보이는가?
- HTTP로 먼저 검증 가능한가?
- 그 다음 MCP Tool 호출로 동일 결과가 나오는가?
이 순서를 지키면 “현재 Phase 문제인지, 이전 Phase 잔재인지”를 빠르게 분리할 수 있습니다.
마무리
Spring AI MCP 실습에서 가장 크게 느낀 점은 하나였습니다.
MCP는 “되게 만드는 기술”이 아니라, 통제와 분리를 얼마나 정확히 하느냐가 핵심입니다.
이 글이 도움이 되는 분들은 보통 아래 상황에 해당하는 경우가 많습니다.
- MCP / Spring AI를 실제 프로젝트에 쓰려다 막힌 경우
- 로그는 많은데 어디서부터 정리해야 할지 모르는 경우
- 다음 단계로 넘어가도 되는지 판단이 어려운 경우
요약
- Spring AI MCP 실습기(Phase 0~3) 실제 오류 기반 정리
- STDIO vs Streamable HTTP: 실습에서는 HTTP가 안정적인 경향
- 프로파일 분리, Java 버전 불일치, DB 초기화 순서 이슈가 대표적인 장애 포인트
- Phase 3은 “작동”보다 “차단”이 성공 기준
이직·퇴사, 지금 결정해도 되는 단계인지 5분 만에 점검해보세요
감정이 아니라 체크리스트로 현재 상태를 구조화합니다.
결과는 “정답”이 아니라
혼자 판단해도 되는지 / 지금 움직이면 위험한지를 가르는 기준입니다.
체크가 많다면,
다음 단계는 더 고민이 아니라 선택지 정리입니다.
체크리스트부터 할지 고민된다면,
지금 판단해도 되는 단계인지 먼저 확인해보세요