mirror of
https://github.com/crewAIInc/crewAI.git
synced 2026-04-30 23:02:50 +00:00
Add Korean translations (#3307)
This commit is contained in:
64
docs/ko/mcp/multiple-servers.mdx
Normal file
64
docs/ko/mcp/multiple-servers.mdx
Normal file
@@ -0,0 +1,64 @@
|
||||
---
|
||||
title: 여러 MCP 서버에 연결하기
|
||||
description: CrewAI에서 MCPServerAdapter를 사용하여 여러 MCP 서버에 동시에 연결하고 해당 도구를 집계하는 방법을 알아봅니다.
|
||||
icon: layer-group
|
||||
---
|
||||
|
||||
## 개요
|
||||
|
||||
`crewai-tools`의 `MCPServerAdapter`는 여러 MCP 서버에 동시에 연결할 수 있게 해줍니다. 이는 에이전트가 서로 다른 서비스나 환경에 분산된 도구에 접근해야 할 때 유용합니다. 어댑터는 지정된 모든 서버에서 도구를 집계하여 CrewAI 에이전트가 사용할 수 있게 합니다.
|
||||
|
||||
## 구성
|
||||
|
||||
여러 서버에 연결하려면 서버 파라미터 딕셔너리의 리스트를 `MCPServerAdapter`에 제공합니다. 리스트에 있는 각 딕셔너리는 하나의 MCP 서버에 대한 파라미터를 정의해야 합니다.
|
||||
|
||||
각 서버에 대해 지원되는 transport 타입은 `stdio`, `sse`, 그리고 `streamable-http`입니다.
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
from mcp import StdioServerParameters # Needed for Stdio example
|
||||
|
||||
# 여러 MCP 서버의 파라미터 정의
|
||||
server_params_list = [
|
||||
# Streamable HTTP 서버
|
||||
{
|
||||
"url": "http://localhost:8001/mcp",
|
||||
"transport": "streamable-http"
|
||||
},
|
||||
# SSE 서버
|
||||
{
|
||||
"url": "http://localhost:8000/sse",
|
||||
"transport": "sse"
|
||||
},
|
||||
# StdIO 서버
|
||||
StdioServerParameters(
|
||||
command="python3",
|
||||
args=["servers/your_stdio_server.py"],
|
||||
env={"UV_PYTHON": "3.12", **os.environ},
|
||||
)
|
||||
]
|
||||
|
||||
try:
|
||||
with MCPServerAdapter(server_params_list) as aggregated_tools:
|
||||
print(f"Available aggregated tools: {[tool.name for tool in aggregated_tools]}")
|
||||
|
||||
multi_server_agent = Agent(
|
||||
role="Versatile Assistant",
|
||||
goal="Utilize tools from local Stdio, remote SSE, and remote HTTP MCP servers.",
|
||||
backstory="An AI agent capable of leveraging a diverse set of tools from multiple sources.",
|
||||
tools=aggregated_tools, # All tools are available here
|
||||
verbose=True,
|
||||
)
|
||||
|
||||
... # Your other agent, tasks, and crew code here
|
||||
|
||||
except Exception as e:
|
||||
print(f"Error connecting to or using multiple MCP servers (Managed): {e}")
|
||||
print("Ensure all MCP servers are running and accessible with correct configurations.")
|
||||
|
||||
```
|
||||
|
||||
## 연결 관리
|
||||
|
||||
컨텍스트 매니저(`with` 문)를 사용할 때, `MCPServerAdapter`는 구성된 MCP 서버와의 모든 연결의 라이프사이클(시작 및 종료)을 관리합니다. 이를 통해 리소스 관리를 단순화하고, 컨텍스트를 종료할 때 모든 연결이 적절하게 닫히도록 보장할 수 있습니다.
|
||||
263
docs/ko/mcp/overview.mdx
Normal file
263
docs/ko/mcp/overview.mdx
Normal file
@@ -0,0 +1,263 @@
|
||||
---
|
||||
title: 'CrewAI에서 MCP 서버를 도구로 활용하기'
|
||||
description: '`crewai-tools` 라이브러리를 사용하여 MCP 서버를 CrewAI agent에 도구로 통합하는 방법을 알아봅니다.'
|
||||
icon: plug
|
||||
---
|
||||
|
||||
## 개요
|
||||
|
||||
[Model Context Protocol](https://modelcontextprotocol.io/introduction) (MCP)는 AI 에이전트가 MCP 서버로 알려진 외부 서비스와 통신함으로써 LLM에 컨텍스트를 제공할 수 있도록 표준화된 방식을 제공합니다.
|
||||
`crewai-tools` 라이브러리는 CrewAI의 기능을 확장하여, 이러한 MCP 서버에서 제공하는 툴을 에이전트에 원활하게 통합할 수 있도록 해줍니다.
|
||||
이를 통해 여러분의 crew는 방대한 기능 에코시스템에 접근할 수 있습니다.
|
||||
|
||||
현재 다음과 같은 전송 메커니즘을 지원합니다:
|
||||
|
||||
- **Stdio**: 로컬 서버용 (동일 머신 내 프로세스 간 표준 입력/출력을 통한 통신)
|
||||
- **Server-Sent Events (SSE)**: 원격 서버용 (서버에서 클라이언트로의 일방향, 실시간 데이터 스트리밍, HTTP 기반)
|
||||
- **Streamable HTTP**: 원격 서버용 (유연하며 잠재적으로 양방향 통신이 가능, 주로 SSE를 활용한 서버-클라이언트 스트림 제공, HTTP 기반)
|
||||
|
||||
## 비디오 튜토리얼
|
||||
CrewAI와 MCP 통합에 대한 종합적인 안내를 위해 이 비디오 튜토리얼을 시청하세요:
|
||||
|
||||
<iframe
|
||||
width="100%"
|
||||
height="400"
|
||||
src="https://www.youtube.com/embed/TpQ45lAZh48"
|
||||
title="CrewAI MCP Integration Guide"
|
||||
frameborder="0"
|
||||
style={{ borderRadius: '10px' }}
|
||||
allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture"
|
||||
allowfullscreen
|
||||
></iframe>
|
||||
|
||||
## 설치
|
||||
|
||||
`crewai-tools`와 함께 MCP를 사용하기 전에, 아래 명령어를 통해 `mcp` 추가 `crewai-tools` 종속성을 설치해야 합니다:
|
||||
|
||||
```shell
|
||||
uv pip install 'crewai-tools[mcp]'
|
||||
```
|
||||
|
||||
## 주요 개념 및 시작하기
|
||||
|
||||
`crewai-tools`의 `MCPServerAdapter` 클래스는 MCP 서버에 연결하고 해당 도구들을 CrewAI 에이전트에서 사용할 수 있도록 하는 기본 방법입니다. 다양한 전송 메커니즘을 지원하며 연결 관리를 간소화합니다.
|
||||
|
||||
파이썬 컨텍스트 매니저(`with` 문)를 사용하는 것이 `MCPServerAdapter`를 위한 **권장 방법**입니다. 이를 통해 MCP 서버와의 연결 시작 및 종료가 자동으로 처리됩니다.
|
||||
|
||||
## 연결 구성
|
||||
|
||||
`MCPServerAdapter`는 연결 동작을 맞춤화할 수 있는 여러 구성 옵션을 지원합니다:
|
||||
|
||||
- **`connect_timeout`** (선택 사항): MCP 서버에 연결을 설정하기 위해 대기할 최대 시간(초 단위)입니다. 명시하지 않으면 기본값은 30초입니다. 응답 시간이 가변적인 원격 서버에 특히 유용합니다.
|
||||
|
||||
```python
|
||||
# 사용자 지정 연결 타임아웃 예시
|
||||
with MCPServerAdapter(server_params, connect_timeout=60) as tools:
|
||||
# 60초 이내에 연결이 설정되지 않으면 타임아웃 발생
|
||||
pass
|
||||
```
|
||||
|
||||
```python
|
||||
from crewai import Agent
|
||||
from crewai_tools import MCPServerAdapter
|
||||
from mcp import StdioServerParameters # Stdio 서버용
|
||||
|
||||
# 예시 server_params (서버 유형에 따라 하나 선택):
|
||||
# 1. Stdio 서버:
|
||||
server_params=StdioServerParameters(
|
||||
command="python3",
|
||||
args=["servers/your_server.py"],
|
||||
env={"UV_PYTHON": "3.12", **os.environ},
|
||||
)
|
||||
|
||||
# 2. SSE 서버:
|
||||
server_params = {
|
||||
"url": "http://localhost:8000/sse",
|
||||
"transport": "sse"
|
||||
}
|
||||
|
||||
# 3. 스트림 가능 HTTP 서버:
|
||||
server_params = {
|
||||
"url": "http://localhost:8001/mcp",
|
||||
"transport": "streamable-http"
|
||||
}
|
||||
|
||||
# 예시 사용법 (server_params 설정 후 주석 해제 및 적용):
|
||||
with MCPServerAdapter(server_params, connect_timeout=60) as mcp_tools:
|
||||
print(f"Available tools: {[tool.name for tool in mcp_tools]}")
|
||||
|
||||
my_agent = Agent(
|
||||
role="MCP Tool User",
|
||||
goal="MCP 서버의 도구를 활용합니다.",
|
||||
backstory="나는 MCP 서버에 연결하여 해당 도구를 사용할 수 있습니다.",
|
||||
tools=mcp_tools, # 불러온 도구를 Agent에 전달
|
||||
reasoning=True,
|
||||
verbose=True
|
||||
)
|
||||
# ... 나머지 crew 설정 ...
|
||||
```
|
||||
이 일반적인 패턴은 도구를 통합하는 방법을 보여줍니다. 각 transport에 맞춘 구체적인 예시는 아래의 상세 가이드를 참고하세요.
|
||||
|
||||
## 필터링 도구
|
||||
|
||||
도구를 필터링하는 방법에는 두 가지가 있습니다:
|
||||
|
||||
1. 딕셔너리 스타일의 인덱싱을 사용하여 특정 도구에 접근하기.
|
||||
2. 도구 이름 목록을 `MCPServerAdapter` 생성자에 전달하기.
|
||||
|
||||
### 딕셔너리 스타일 인덱싱을 사용하여 특정 도구에 접근하기
|
||||
|
||||
```python
|
||||
with MCPServerAdapter(server_params, connect_timeout=60) as mcp_tools:
|
||||
print(f"Available tools: {[tool.name for tool in mcp_tools]}")
|
||||
|
||||
my_agent = Agent(
|
||||
role="MCP Tool User",
|
||||
goal="Utilize tools from an MCP server.",
|
||||
backstory="I can connect to MCP servers and use their tools.",
|
||||
tools=[mcp_tools["tool_name"]], # Pass the loaded tools to your agent
|
||||
reasoning=True,
|
||||
verbose=True
|
||||
)
|
||||
# ... rest of your crew setup ...
|
||||
```
|
||||
|
||||
### `MCPServerAdapter` 생성자에 도구 이름의 리스트를 전달하세요.
|
||||
|
||||
```python
|
||||
with MCPServerAdapter(server_params, "tool_name", connect_timeout=60) as mcp_tools:
|
||||
print(f"Available tools: {[tool.name for tool in mcp_tools]}")
|
||||
|
||||
my_agent = Agent(
|
||||
role="MCP Tool User",
|
||||
goal="Utilize tools from an MCP server.",
|
||||
backstory="I can connect to MCP servers and use their tools.",
|
||||
tools=mcp_tools, # Pass the loaded tools to your agent
|
||||
reasoning=True,
|
||||
verbose=True
|
||||
)
|
||||
# ... rest of your crew setup ...
|
||||
```
|
||||
|
||||
## CrewBase와 함께 사용하기
|
||||
|
||||
CrewBase 클래스 내에서 MCPServer 도구를 사용하려면 `mcp_tools` 메서드를 사용하세요. 서버 구성은 mcp_server_params 속성을 통해 제공되어야 합니다. 단일 구성 또는 여러 서버 구성을 리스트 형태로 전달할 수 있습니다.
|
||||
|
||||
```python
|
||||
@CrewBase
|
||||
class CrewWithMCP:
|
||||
# ... 에이전트 및 작업 구성 파일 정의 ...
|
||||
|
||||
mcp_server_params = [
|
||||
# 스트리머블 HTTP 서버
|
||||
{
|
||||
"url": "http://localhost:8001/mcp",
|
||||
"transport": "streamable-http"
|
||||
},
|
||||
# SSE 서버
|
||||
{
|
||||
"url": "http://localhost:8000/sse",
|
||||
"transport": "sse"
|
||||
},
|
||||
# StdIO 서버
|
||||
StdioServerParameters(
|
||||
command="python3",
|
||||
args=["servers/your_stdio_server.py"],
|
||||
env={"UV_PYTHON": "3.12", **os.environ},
|
||||
)
|
||||
]
|
||||
|
||||
@agent
|
||||
def your_agent(self):
|
||||
return Agent(config=self.agents_config["your_agent"], tools=self.get_mcp_tools()) # 모든 사용 가능한 도구 가져오기
|
||||
|
||||
# ... 나머지 crew 설정 ...
|
||||
```
|
||||
|
||||
`get_mcp_tools` 메서드에 도구 이름의 리스트를 전달하여, 에이전트에 제공되는 도구를 필터링할 수 있습니다.
|
||||
|
||||
```python
|
||||
@agent
|
||||
def another_agent(self):
|
||||
return Agent(
|
||||
config=self.agents_config["your_agent"],
|
||||
tools=self.get_mcp_tools("tool_1", "tool_2") # 특정 도구만 가져오기
|
||||
)
|
||||
```
|
||||
|
||||
## MCP 통합 탐색
|
||||
|
||||
<CardGroup cols={2}>
|
||||
<Card
|
||||
title="Stdio 전송"
|
||||
icon="server"
|
||||
href="/ko/mcp/stdio"
|
||||
color="#3B82F6"
|
||||
>
|
||||
표준 입력/출력을 통해 로컬 MCP 서버에 연결합니다. 스크립트와 로컬 실행 파일에 이상적입니다.
|
||||
</Card>
|
||||
<Card
|
||||
title="SSE 전송"
|
||||
icon="wifi"
|
||||
href="/ko/mcp/sse"
|
||||
color="#10B981"
|
||||
>
|
||||
실시간 데이터 스트리밍을 위해 Server-Sent Events를 사용하여 원격 MCP 서버와 통합합니다.
|
||||
</Card>
|
||||
<Card
|
||||
title="스트림 가능한 HTTP 전송"
|
||||
icon="globe"
|
||||
href="/ko/mcp/streamable-http"
|
||||
color="#F59E0B"
|
||||
>
|
||||
유연한 스트림 가능한 HTTP를 활용하여 원격 MCP 서버와 안정적으로 통신할 수 있습니다.
|
||||
</Card>
|
||||
<Card
|
||||
title="다중 서버 연결"
|
||||
icon="layer-group"
|
||||
href="/ko/mcp/multiple-servers"
|
||||
color="#8B5CF6"
|
||||
>
|
||||
하나의 어댑터를 사용하여 여러 MCP 서버의 도구를 동시에 통합할 수 있습니다.
|
||||
</Card>
|
||||
<Card
|
||||
title="보안 고려사항"
|
||||
icon="lock"
|
||||
href="/ko/mcp/security"
|
||||
color="#EF4444"
|
||||
>
|
||||
에이전트를 안전하게 보호하기 위한 MCP 통합의 중요한 보안 모범 사례를 검토하세요.
|
||||
</Card>
|
||||
</CardGroup>
|
||||
|
||||
CrewAI와의 MCP 통합에 대한 전체 데모와 예제를 보려면 이 저장소를 확인하세요! 👇
|
||||
|
||||
<Card
|
||||
title="GitHub 저장소"
|
||||
icon="github"
|
||||
href="https://github.com/tonykipkemboi/crewai-mcp-demo"
|
||||
target="_blank"
|
||||
>
|
||||
CrewAI MCP 데모
|
||||
</Card>
|
||||
|
||||
## MCP와 함께 안전하게 사용하기
|
||||
<Warning>
|
||||
항상 MCP 서버를 사용하기 전에 해당 서버를 신뢰할 수 있는지 확인하세요.
|
||||
</Warning>
|
||||
|
||||
#### 보안 경고: DNS 리바인딩 공격
|
||||
SSE 전송은 적절하게 보안되지 않은 경우 DNS 리바인딩 공격에 취약할 수 있습니다.
|
||||
이를 방지하려면 다음을 수행하세요:
|
||||
|
||||
1. **항상 Origin 헤더를 검증**하여 들어오는 SSE 연결이 예상한 소스에서 오는지 확인합니다.
|
||||
2. **서버를 모든 네트워크 인터페이스**(0.0.0.0)에 바인딩하는 것을 피하고, 로컬에서 실행할 때는 localhost(127.0.0.1)에만 바인딩합니다.
|
||||
3. **모든 SSE 연결에 대해 적절한 인증을 구현**합니다.
|
||||
|
||||
이러한 보호 조치가 없으면 공격자가 원격 웹사이트에서 로컬 MCP 서버와 상호작용하기 위해 DNS 리바인딩을 사용할 수 있습니다.
|
||||
|
||||
자세한 내용은 [Anthropic의 MCP 전송 보안 문서](https://modelcontextprotocol.io/docs/concepts/transports#security-considerations)를 참고하세요.
|
||||
|
||||
### 제한 사항
|
||||
* **지원되는 프리미티브**: 현재 `MCPServerAdapter`는 주로 MCP `tools`를 어댑팅하는 기능을 지원합니다. 다른 MCP 프리미티브(예: `prompts` 또는 `resources`)는 현재 이 어댑터를 통해 CrewAI 컴포넌트로 직접 통합되어 있지 않습니다.
|
||||
* **출력 처리**: 어댑터는 일반적으로 MCP tool의 주요 텍스트 출력(예: `.content[0].text`)을 처리합니다. 복잡하거나 멀티모달 출력의 경우 이 패턴에 맞지 않으면 별도의 커스텀 처리가 필요할 수 있습니다.
|
||||
165
docs/ko/mcp/security.mdx
Normal file
165
docs/ko/mcp/security.mdx
Normal file
@@ -0,0 +1,165 @@
|
||||
---
|
||||
title: MCP 보안 고려사항
|
||||
description: MCP 서버를 CrewAI agent와 통합할 때 중요한 보안 모범 사례에 대해 알아보세요.
|
||||
icon: lock
|
||||
---
|
||||
|
||||
## 개요
|
||||
|
||||
<Warning>
|
||||
MCP 보안에서 가장 중요한 측면은 **신뢰**입니다. 신뢰할 수 있다고 확신하는 MCP 서버에만 CrewAI 에이전트를 **연결해야 합니다**.
|
||||
</Warning>
|
||||
|
||||
CrewAI 에이전트에 MCP(Model Context Protocol) 서버와 같은 외부 서비스를 통합할 때 보안이 가장 중요합니다.
|
||||
MCP 서버는 노출한 도구를 기반으로 코드를 실행하거나 데이터에 접근하거나 다른 시스템과 상호작용할 수 있습니다.
|
||||
응용 프로그램과 데이터를 보호하기 위해 그 영향력을 이해하고 모범 사례를 따르는 것이 매우 중요합니다.
|
||||
|
||||
### 위험
|
||||
|
||||
- 에이전트가 실행 중인 머신에서 임의의 코드를 실행할 수 있습니다(특히 서버가 실행되는 명령어를 제어할 수 있는 `Stdio` 전송 방식을 사용할 경우).
|
||||
- 에이전트나 그 환경에서 민감한 데이터가 노출될 수 있습니다.
|
||||
- 예기치 않은 방식으로 에이전트의 동작이 조작되어, 본인 동의 없이 API 호출이 이루어질 수 있습니다.
|
||||
- 정교한 프롬프트 인젝션 기법(아래 참조)을 통해 에이전트의 reasoning 프로세스가 탈취될 수 있습니다.
|
||||
|
||||
### 1. MCP 서버 신뢰하기
|
||||
|
||||
<Warning>
|
||||
**신뢰할 수 있는 MCP 서버에만 연결하십시오.**
|
||||
</Warning>
|
||||
|
||||
`MCPServerAdapter`를 MCP 서버에 연결하도록 구성하기 전에 다음을 반드시 확인하십시오:
|
||||
- **서버 운영자는 누구입니까?** 신뢰할 수 있는 잘 알려진 서비스이거나 여러분이 직접 제어하는 내부 서버입니까?
|
||||
- **어떤 도구를 노출합니까?** 도구의 기능을 이해해야 합니다. 공격자가 제어권을 얻거나 서버 자체가 악의적이라면 이 도구들이 오용될 수 있습니까?
|
||||
- **어떤 데이터를 접근하거나 처리합니까?** MCP 서버에 전송되거나 처리될 수 있는 민감한 정보가 있는지 반드시 파악하십시오.
|
||||
|
||||
특히 에이전트가 민감한 작업이나 데이터를 처리하는 경우, 알 수 없거나 검증되지 않은 MCP 서버에는 연결하지 마십시오.
|
||||
|
||||
### 2. Tool Metadata를 통한 보안 프롬프트 인젝션: "Model Control Protocol"의 위험성
|
||||
|
||||
중요하면서도 미묘한 위험 중 하나는 툴 메타데이터를 통한 프롬프트 인젝션 가능성입니다. 그 과정은 다음과 같습니다:
|
||||
|
||||
1. CrewAI 에이전트가 MCP 서버에 연결하면, 일반적으로 사용 가능한 툴 목록을 요청합니다.
|
||||
2. MCP 서버는 각 툴에 대한 메타데이터를 이름, 설명, 파라미터 설명과 함께 응답합니다.
|
||||
3. 에이전트의 언더라이잉 Language Model(LLM)은 해당 메타데이터를 활용해 언제, 어떻게 툴을 사용할지 이해합니다. 이 메타데이터는 LLM의 시스템 프롬프트나 컨텍스트에 포함되는 경우가 많습니다.
|
||||
4. 악의적인 MCP 서버는 툴의 메타데이터(이름, 설명 등)에 숨겨진 또는 노골적인 명령어를 삽입할 수 있습니다. 이러한 명령은 프롬프트 인젝션으로 동작하여, LLM에게 특정 방식으로 동작하라고 지시하거나, 민감한 정보를 공개하게 하거나, 악의적인 행동을 수행하게 만들 수 있습니다.
|
||||
|
||||
**중요하게도, 이 공격은 에이전트가 해당 툴을 실제로 *사용*하지 않더라도 단순히 악성 서버에 연결해 툴 목록을 조회하는 것만으로도 발생할 수 있습니다.** 악의적인 메타데이터에 노출되는 것만으로도 에이전트의 행동이 손상될 수 있습니다.
|
||||
|
||||
**완화 방안:**
|
||||
|
||||
* **신뢰되지 않은 서버에 대한 극도의 주의:** 반복합니다. *완전히 신뢰하지 않는 MCP 서버에는 절대 연결하지 마십시오.* 메타데이터 인젝션의 위험성 때문에 이 점이 매우 중요합니다.
|
||||
|
||||
### Stdio 전송 보안
|
||||
|
||||
Stdio(표준 입력/출력) 전송은 일반적으로 CrewAI 애플리케이션과 동일한 머신에서 실행되는 로컬 MCP 서버에 사용됩니다.
|
||||
|
||||
- **프로세스 격리**: 기본적으로 네트워크에 노출되지 않아 일반적으로 더 안전하지만, `StdioServerParameters`로 실행되는 스크립트나 명령어가 신뢰할 수 있는 소스에서 왔으며 적절한 파일 시스템 권한을 가지고 있는지 확인해야 합니다. 악의적인 Stdio 서버 스크립트는 여전히 로컬 시스템에 피해를 줄 수 있습니다.
|
||||
- **입력값 정제**: Stdio 서버 스크립트가 에이전트 상호작용에서 파생된 복잡한 입력을 받는 경우, 스크립트 자체에서 이러한 입력값을 정제하여 명령어 삽입이나 스크립트 논리 내 다른 취약점이 발생하지 않도록 해야 합니다.
|
||||
- **리소스 제한**: 로컬 Stdio 서버 프로세스는 로컬 자원(CPU, 메모리)을 소모하므로, 반드시 정상적으로 동작하는지, 시스템 자원을 소모하지 않는지 주의 깊게 관리해야 합니다.
|
||||
|
||||
### 혼동된 대리인(Confused Deputy) 공격
|
||||
|
||||
[혼동된 대리인 문제(Confused Deputy Problem)](https://en.wikipedia.org/wiki/Confused_deputy_problem)는 고전적인 보안 취약점으로, MCP 통합에서 특히 MCP 서버가 다른 서드파티 서비스(예: Google Calendar, GitHub)와 OAuth 2.0을 통한 인증을 할 때 프록시 역할을 할 경우 나타날 수 있습니다.
|
||||
|
||||
**시나리오:**
|
||||
|
||||
1. MCP 서버(여기서는 `MCP-Proxy`라고 부르겠습니다)가 에이전트가 `ThirdPartyAPI`와 상호작용할 수 있도록 허용합니다.
|
||||
2. `MCP-Proxy`는 `ThirdPartyAPI`의 인증 서버와 통신할 때 자체의 단일 고정 `client_id`를 사용합니다.
|
||||
3. 사용자(즉, 여러분)는 정당하게 `MCP-Proxy`가 여러분을 대신해 `ThirdPartyAPI`에 접근할 수 있도록 승인합니다. 이 과정에서 `ThirdPartyAPI`의 인증 서버는 여러분의 브라우저에 `MCP-Proxy`의 `client_id`에 대한 동의 쿠키를 설정할 수 있습니다.
|
||||
4. 공격자는 악의적인 링크를 만듭니다. 이 링크는 `MCP-Proxy`와의 OAuth 플로우를 시작하지만, `ThirdPartyAPI`의 인증 서버를 속이도록 설계되어 있습니다.
|
||||
5. 여러분이 이 링크를 클릭하고, `ThirdPartyAPI`의 인증 서버가 이미 존재하는 `MCP-Proxy`의 `client_id`에 대한 동의 쿠키를 확인하면, 다시 동의를 묻지 않고 *건너뛰기* 할 수 있습니다.
|
||||
6. 그러면 `MCP-Proxy`가 (공격자에게) 인증 코드를 전달하도록 속거나, 공격자가 여러분을 가장해 `MCP-Proxy`에 사용할 수 있는 MCP 인증 코드를 받게 될 수 있습니다.
|
||||
|
||||
**대응 방안(주로 MCP 서버 개발자용):**
|
||||
|
||||
* 다운스트림 서비스를 위해 정적 client ID를 사용하는 MCP 프록시 서버는 **각 클라이언트 애플리케이션 또는 에이전트별**로 명시적인 사용자 동의를 반드시 받아야 합니다. 이 동의는 서드파티 서비스와의 OAuth 플로우 시작 *이전*에 이루어져야 하며, `MCP-Proxy` 자체가 동의 화면을 표시하도록 해야 합니다.
|
||||
|
||||
**CrewAI 사용자 주의사항:**
|
||||
|
||||
* MCP 서버가 여러 번 OAuth 인증을 위해 리디렉션하는 경우, 특히 예상치 않거나 요청된 권한이 과도하게 넓다면 주의해야 합니다.
|
||||
* 자신과 프록시할 수 있는 서드파티 서비스의 구분을 명확하게 하는 MCP 서버를 선호하는 것이 좋습니다.
|
||||
|
||||
### 원격 전송 보안 (SSE & Streamable HTTP)
|
||||
|
||||
Server-Sent Events(SSE) 또는 Streamable HTTP를 통해 원격 MCP 서버에 연결할 때, 표준 웹 보안 관행이 필수적입니다.
|
||||
|
||||
### SSE 보안 고려사항
|
||||
|
||||
### a. DNS 리바인딩 공격 (특히 SSE의 경우)
|
||||
|
||||
<Critical>
|
||||
**DNS 리바인딩 공격으로부터 보호하세요.**
|
||||
</Critical>
|
||||
|
||||
DNS 리바인딩은 공격자가 제어하는 웹사이트가 동일 출처 정책(same-origin policy)을 우회하여 사용자의 로컬 네트워크(예: `localhost`) 또는 인트라넷에 있는 서버에 요청을 보낼 수 있도록 합니다. 이는 MCP 서버를 로컬(예: 개발용)로 실행하고 브라우저와 유사한 환경에서 agent를 사용하는 경우(일반적인 CrewAI 백엔드 구성에서는 드물지만) 또는 MCP 서버가 내부 네트워크상에 있을 경우 특히 위험할 수 있습니다.
|
||||
|
||||
**MCP 서버 구현자를 위한 대응 전략:**
|
||||
- **`Origin` 및 `Host` 헤더 검증**: MCP 서버(특히 SSE 서버)는 `Origin` 및/또는 `Host` HTTP 헤더를 검증하여 요청이 예상되는 도메인/클라이언트로부터 오는지 확인해야 합니다.
|
||||
- **`localhost`(127.0.0.1)로 바인딩**: 개발을 위해 MCP 서버를 로컬에서 실행할 때는 `0.0.0.0` 대신 `127.0.0.1`로 바인딩하세요. 이를 통해 네트워크의 다른 기기에서 접근하지 못하도록 막을 수 있습니다.
|
||||
- **인증(Authentication)**: MCP 서버가 공개된 익명 접근을 목적으로 하지 않는 한 모든 연결에 대해 인증을 요구하세요.
|
||||
|
||||
### b. HTTPS 사용
|
||||
|
||||
- **전송 중 데이터 암호화**: 원격 MCP 서버의 URL에는 항상 HTTPS(HTTP Secure)를 사용하세요. 이는 CrewAI 애플리케이션과 MCP 서버 간의 통신을 암호화하여 도청 및 중간자 공격으로부터 보호합니다. `MCPServerAdapter`는 URL에 제공된 스킴(`http` 또는 `https`)을 그대로 따릅니다.
|
||||
|
||||
### c. 토큰 패스스루(Token Passthrough) (안티 패턴)
|
||||
|
||||
이 문제는 주로 MCP 서버 개발자들에게 해당되지만, 이를 이해하는 것은 안전한 서버를 선택하는 데 도움이 됩니다.
|
||||
|
||||
"토큰 패스스루"란, MCP 서버가 CrewAI agent로부터 받은 액세스 토큰(예를 들어 `ServiceA`를 위한 토큰일 수도 있음)을 별도의 적절한 검증 없이 다른 하위 API(`ServiceB`)로 그대로 전달하는 것을 의미합니다. 특히, `ServiceB`(또는 MCP 서버 자체)는 명시적으로 *자신들을 위해* 발급된 토큰만 받아야 합니다(즉, 토큰 내의 'audience' 클레임이 해당 서버/서비스와 일치해야 함).
|
||||
|
||||
**위험성:**
|
||||
|
||||
* MCP 서버나 하위 API의 보안 제어(예 : 속도 제한, 세밀한 권한 부여 등)를 우회할 수 있습니다.
|
||||
* 감사 추적 및 책임성을 저해할 수 있습니다.
|
||||
* 탈취된 토큰의 악용을 허용할 수 있습니다.
|
||||
|
||||
**대응 방안 (MCP 서버 개발자용):**
|
||||
|
||||
* MCP 서버는 **명시적으로 자신을 위해 발급된 토큰만** 받아야 합니다. 토큰의 audience 클레임을 반드시 검증해야 합니다.
|
||||
|
||||
**CrewAI 사용자에게 미치는 영향:**
|
||||
|
||||
* 사용자가 직접적으로 제어할 수는 없지만, 보안 모범 사례를 준수하는 잘 설계된 MCP 서버에 연결하는 것이 중요함을 강조합니다.
|
||||
|
||||
#### 인증 및 인가
|
||||
|
||||
- **신원 확인**: MCP 서버가 민감한 도구 또는 비공개 데이터에 대한 액세스를 제공하는 경우, 클라이언트(귀하의 CrewAI 애플리케이션)의 신원을 확인하기 위해 강력한 인증 메커니즘을 반드시 구현해야 합니다. 이는 API 키, OAuth 토큰 또는 기타 표준 방법을 포함할 수 있습니다.
|
||||
- **최소 권한 원칙**: `MCPServerAdapter`에서 사용하는 자격 증명(있는 경우)은 필요한 도구에 접근하는 데 꼭 필요한 권한만 가지고 있도록 해야 합니다.
|
||||
|
||||
### d. 입력 검증 및 정제
|
||||
|
||||
- **입력 검증은 매우 중요합니다**: MCP 서버는 에이전트로부터 받은 모든 입력을 처리하거나 도구에 전달하기 *전에* 철저하게 검증해야 합니다. 이는 많은 일반적인 취약점에 대한 1차 방어선입니다:
|
||||
- **명령어 삽입:** 도구가 입력을 기반으로 셸 명령, SQL 쿼리 또는 기타 해석형 언어 문장을 구성하는 경우, 서버는 악의적 명령어 주입 및 실행을 방지하기 위해 이 입력을 꼼꼼하게 정제해야 합니다.
|
||||
- **경로 탐색:** 도구가 입력 매개변수에 따라 파일에 접근하는 경우, 서버는 미허가 파일 또는 디렉터리에 접근하지 못하도록 이 경로를 검증 및 정제해야 합니다(예: `../` 시퀀스 차단).
|
||||
- **데이터 타입 및 범위 검사:** 서버는 입력 데이터가 기대하는 데이터 타입(예: 문자열, 숫자, 불리언)에 부합하는지, 허용 범위 내에 있거나 정의된 형식(예: URL에 대한 정규식)에 맞는지 확인해야 합니다.
|
||||
- **JSON 스키마 검증:** 모든 도구 매개변수는 정의된 JSON 스키마에 엄격하게 맞춰 검증되어야 합니다. 이를 통해 잘못된 요청을 조기에 차단할 수 있습니다.
|
||||
- **클라이언트 측 인지**: 서버 측 검증이 가장 중요하지만, CrewAI 사용자는 특히 신뢰도가 낮은 또는 새로운 MCP 서버와 상호작용할 때 자신의 에이전트가 MCP 도구에 전달하도록 설계된 데이터에 각별히 유의해야 합니다.
|
||||
|
||||
### e. 속도 제한 및 리소스 관리
|
||||
|
||||
- **오용 방지**: MCP 서버는 악의적(서비스 거부 공격 등)이든 비의도적(예: 잘못 구성된 agent가 과도한 요청을 보내는 경우)이든 오용을 방지하기 위해 속도 제한을 구현해야 합니다.
|
||||
- **클라이언트 측 재시도**: 일시적인 네트워크 문제나 서버의 속도 제한이 예상될 경우, CrewAI 작업에서 합리적인 재시도 로직을 구현하되, 서버 부하를 가중시킬 수 있는 과도한 재시도는 피해야 합니다.
|
||||
|
||||
## 4. 보안 MCP 서버 구현 권장 사항 (개발자용)
|
||||
|
||||
CrewAI 에이전트가 연결할 수 있는 MCP 서버를 개발하고 있다면, 위의 내용에 추가하여 다음과 같은 모범 사례를 고려하세요:
|
||||
|
||||
- **안전한 코딩 관행 준수**: 선택한 언어 및 프레임워크에 대한 표준 안전 코딩 원칙(예: OWASP Top 10)을 준수하세요.
|
||||
- **최소 권한 원칙**: MCP 서버를 실행하는 프로세스(특히 `Stdio`의 경우)는 작업에 필요한 최소 권한만 보유하도록 하세요. 툴 자체도 자신의 기능 수행에 필요한 최소한의 권한만으로 동작해야 합니다.
|
||||
- **종속성 관리**: 운영 체제 패키지, 언어 런타임, 써드파티 라이브러리 등 모든 서버 측 종속성을 최신 상태로 유지하여 알려진 취약점을 패치하세요. 취약한 종속성을 스캔하는 도구를 사용하세요.
|
||||
- **안전한 기본값**: 서버와 그 도구를 기본적으로 안전하게 설계하세요. 예를 들어, 위험할 수 있는 기능은 기본적으로 꺼져 있거나 명확한 경고와 함께 명시적으로 opt-in 하도록 해야 합니다.
|
||||
- **툴에 대한 접근 제어**: 인증 및 권한이 부여된 에이전트 또는 사용자만 특정 툴(특히 강력하거나 민감하거나 비용이 발생하는 툴)에 접근할 수 있도록 강력한 메커니즘을 구현하세요.
|
||||
- **안전한 오류 처리**: 서버는 클라이언트에게 상세한 내부 오류 메시지, 스택 트레이스 또는 디버깅 정보를 노출해서는 안 됩니다. 이러한 정보는 내부 동작이나 잠재적 취약점을 드러낼 수 있습니다. 오류는 서버 측에서 진단을 목적으로 포괄적으로 기록하세요.
|
||||
- **포괄적인 로깅 및 모니터링**: 보안 관련 이벤트(예: 인증 시도, 툴 호출, 오류, 권한 변경)에 대해 상세하게 로깅하세요. 이런 로그를 모니터링하여 의심스러운 활동이나 악용 패턴을 파악하세요.
|
||||
- **MCP 인증 사양 준수**: 인증 및 권한 부여를 구현할 경우, [MCP Authorization specification](https://modelcontextprotocol.io/specification/draft/basic/authorization) 및 관련 [OAuth 2.0 security best practices](https://datatracker.ietf.org/doc/html/rfc9700)를 엄격히 준수하세요.
|
||||
- **정기적인 보안 감사**: MCP 서버가 민감한 데이터를 처리하거나, 중요한 작업을 수행하거나, 대외적으로 노출된 경우 자격을 갖춘 전문가의 정기적인 보안 감사를 고려하세요.
|
||||
|
||||
## 5. 추가 참고 자료
|
||||
|
||||
MCP 보안에 대한 자세한 내용은 공식 문서를 참고하세요:
|
||||
- **[MCP 전송 보안](https://modelcontextprotocol.io/docs/concepts/transports#security-considerations)**
|
||||
|
||||
이러한 보안 고려사항을 이해하고 모범 사례를 구현하면 CrewAI 프로젝트에서 MCP 서버의 강력한 기능을 안전하게 활용할 수 있습니다.
|
||||
여기서 다루는 내용이 모든 것을 포괄하는 것은 아니지만, 가장 일반적이고 중요한 보안 문제들을 포함하고 있습니다.
|
||||
위협은 계속 진화하기 때문에 지속적으로 정보를 확인하고 그에 맞춰 보안 조치를 조정하는 것이 중요합니다.
|
||||
150
docs/ko/mcp/sse.mdx
Normal file
150
docs/ko/mcp/sse.mdx
Normal file
@@ -0,0 +1,150 @@
|
||||
---
|
||||
title: SSE 트랜스포트
|
||||
description: 서버 전송 이벤트(SSE)를 사용하여 CrewAI를 원격 MCP 서버에 연결하여 실시간 통신을 구현하는 방법을 알아보세요.
|
||||
icon: wifi
|
||||
---
|
||||
|
||||
## 개요
|
||||
|
||||
Server-Sent Events(SSE)는 웹 서버가 하나의 장기 실행 HTTP 연결을 통해 클라이언트에 업데이트를 전송할 수 있는 표준 방식을 제공합니다. MCP의 맥락에서 SSE는 원격 서버가 데이터(예: tool 응답)를 실시간으로 CrewAI 애플리케이션에 스트리밍하는 데 사용됩니다.
|
||||
|
||||
## 주요 개념
|
||||
|
||||
- **원격 서버**: SSE는 원격에 호스팅된 MCP 서버에 적합합니다.
|
||||
- **단방향 스트림**: 일반적으로 SSE는 서버에서 클라이언트로의 단방향 통신 채널입니다.
|
||||
- **`MCPServerAdapter` 구성**: SSE의 경우, 서버의 URL을 제공하고 전송 유형을 지정해야 합니다.
|
||||
|
||||
## SSE를 통한 연결
|
||||
|
||||
SSE 기반 MCP 서버에 연결하려면 연결 수명 주기를 관리하는 두 가지 주요 접근 방식을 사용할 수 있습니다.
|
||||
|
||||
### 1. 완전 관리형 연결(권장)
|
||||
|
||||
Python 컨텍스트 매니저(`with` 문)를 사용하는 것이 권장되는 접근 방식입니다. 이 방법은 SSE MCP 서버에 대한 연결의 생성과 종료를 자동으로 처리합니다.
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
|
||||
server_params = {
|
||||
"url": "http://localhost:8000/sse", # Replace with your actual SSE server URL
|
||||
"transport": "sse"
|
||||
}
|
||||
|
||||
# Using MCPServerAdapter with a context manager
|
||||
try:
|
||||
with MCPServerAdapter(server_params) as tools:
|
||||
print(f"Available tools from SSE MCP server: {[tool.name for tool in tools]}")
|
||||
|
||||
# Example: Using a tool from the SSE MCP server
|
||||
sse_agent = Agent(
|
||||
role="Remote Service User",
|
||||
goal="Utilize a tool provided by a remote SSE MCP server.",
|
||||
backstory="An AI agent that connects to external services via SSE.",
|
||||
tools=tools,
|
||||
reasoning=True,
|
||||
verbose=True,
|
||||
)
|
||||
|
||||
sse_task = Task(
|
||||
description="Fetch real-time stock updates for 'AAPL' using an SSE tool.",
|
||||
expected_output="The latest stock price for AAPL.",
|
||||
agent=sse_agent,
|
||||
markdown=True
|
||||
)
|
||||
|
||||
sse_crew = Crew(
|
||||
agents=[sse_agent],
|
||||
tasks=[sse_task],
|
||||
verbose=True,
|
||||
process=Process.sequential
|
||||
)
|
||||
|
||||
if tools: # Only kickoff if tools were loaded
|
||||
result = sse_crew.kickoff() # Add inputs={'stock_symbol': 'AAPL'} if tool requires it
|
||||
print("\nCrew Task Result (SSE - Managed):\n", result)
|
||||
else:
|
||||
print("Skipping crew kickoff as tools were not loaded (check server connection).")
|
||||
|
||||
except Exception as e:
|
||||
print(f"Error connecting to or using SSE MCP server (Managed): {e}")
|
||||
print("Ensure the SSE MCP server is running and accessible at the specified URL.")
|
||||
|
||||
```
|
||||
|
||||
<Note>
|
||||
`"http://localhost:8000/sse"`를 실제 SSE MCP 서버의 URL로 교체하십시오.
|
||||
</Note>
|
||||
|
||||
### 2. 수동 연결 라이프사이클
|
||||
|
||||
더 세밀한 제어가 필요한 경우, `MCPServerAdapter`의 연결 라이프사이클을 수동으로 관리할 수 있습니다.
|
||||
|
||||
<Info>
|
||||
연결이 종료되고 리소스가 해제되도록 반드시 `mcp_server_adapter.stop()`을 호출해야 합니다. `try...finally` 블록을 사용하는 것을 강력히 권장합니다.
|
||||
</Info>
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
|
||||
server_params = {
|
||||
"url": "http://localhost:8000/sse", # Replace with your actual SSE server URL
|
||||
"transport": "sse"
|
||||
}
|
||||
|
||||
mcp_server_adapter = None
|
||||
try:
|
||||
mcp_server_adapter = MCPServerAdapter(server_params)
|
||||
mcp_server_adapter.start()
|
||||
tools = mcp_server_adapter.tools
|
||||
print(f"Available tools (manual SSE): {[tool.name for tool in tools]}")
|
||||
|
||||
manual_sse_agent = Agent(
|
||||
role="Remote Data Analyst",
|
||||
goal="Analyze data fetched from a remote SSE MCP server using manual connection management.",
|
||||
backstory="An AI skilled in handling SSE connections explicitly.",
|
||||
tools=tools,
|
||||
verbose=True
|
||||
)
|
||||
|
||||
analysis_task = Task(
|
||||
description="Fetch and analyze the latest user activity trends from the SSE server.",
|
||||
expected_output="A summary report of user activity trends.",
|
||||
agent=manual_sse_agent
|
||||
)
|
||||
|
||||
analysis_crew = Crew(
|
||||
agents=[manual_sse_agent],
|
||||
tasks=[analysis_task],
|
||||
verbose=True,
|
||||
process=Process.sequential
|
||||
)
|
||||
|
||||
result = analysis_crew.kickoff()
|
||||
print("\nCrew Task Result (SSE - Manual):\n", result)
|
||||
|
||||
except Exception as e:
|
||||
print(f"An error occurred during manual SSE MCP integration: {e}")
|
||||
print("Ensure the SSE MCP server is running and accessible.")
|
||||
finally:
|
||||
if mcp_server_adapter and mcp_server_adapter.is_connected:
|
||||
print("Stopping SSE MCP server connection (manual)...")
|
||||
mcp_server_adapter.stop() # **Crucial: Ensure stop is called**
|
||||
elif mcp_server_adapter:
|
||||
print("SSE MCP server adapter was not connected. No stop needed or start failed.")
|
||||
|
||||
```
|
||||
|
||||
## SSE를 위한 보안 고려사항
|
||||
|
||||
<Warning>
|
||||
**DNS 리바인딩 공격**: SSE 전송 방식은 MCP 서버가 적절하게 보안 조치되지 않은 경우 DNS 리바인딩 공격에 취약할 수 있습니다. 이로 인해 악의적인 웹사이트가 로컬 또는 인트라넷 기반 MCP 서버와 상호 작용할 수 있습니다.
|
||||
</Warning>
|
||||
|
||||
이 위험을 완화하려면:
|
||||
- MCP 서버 구현에서는 들어오는 SSE 연결의 **`Origin` 헤더를 검증**해야 합니다.
|
||||
- 개발 환경에서 로컬 SSE MCP 서버를 실행할 때에는 모든 네트워크 인터페이스(`0.0.0.0`)가 아닌, **`localhost`(`127.0.0.1`)에만 바인딩**해야 합니다.
|
||||
- 민감한 도구나 데이터를 노출하는 SSE 연결에는 **적절한 인증**을 구현해야 합니다.
|
||||
|
||||
보안 모범 사례에 대한 포괄적인 개요는 [보안 고려사항](./security.mdx) 페이지와 공식 [MCP 전송 보안 문서](https://modelcontextprotocol.io/docs/concepts/transports#security-considerations)를 참고하시기 바랍니다.
|
||||
134
docs/ko/mcp/stdio.mdx
Normal file
134
docs/ko/mcp/stdio.mdx
Normal file
@@ -0,0 +1,134 @@
|
||||
---
|
||||
title: Stdio 전송
|
||||
description: Stdio(표준 입력/출력) 전송 메커니즘을 사용하여 CrewAI를 로컬 MCP 서버에 연결하는 방법을 알아보세요.
|
||||
icon: server
|
||||
---
|
||||
|
||||
## 개요
|
||||
|
||||
Stdio(표준 입력/출력) 트랜스포트는 `MCPServerAdapter`를 로컬 MCP 서버에 연결하기 위해 설계되었습니다. 이 MCP 서버는 표준 입력 및 출력 스트림을 통해 통신합니다. 이는 일반적으로 MCP 서버가 CrewAI 애플리케이션과 동일한 머신에서 실행되는 스크립트나 실행 파일일 때 사용됩니다.
|
||||
|
||||
## 주요 개념
|
||||
|
||||
- **로컬 실행**: Stdio 전송은 MCP 서버를 위한 로컬에서 실행 중인 프로세스를 관리합니다.
|
||||
- **`StdioServerParameters`**: `mcp` 라이브러리의 이 클래스는 Stdio 서버를 실행하기 위한 명령어, 인수, 환경 변수를 구성하는 데 사용됩니다.
|
||||
|
||||
## Stdio를 통한 연결
|
||||
|
||||
연결 수명 주기를 관리하기 위한 두 가지 주요 접근 방식으로 Stdio 기반 MCP 서버에 연결할 수 있습니다.
|
||||
|
||||
### 1. 완전 관리형 연결(권장)
|
||||
|
||||
Python 컨텍스트 관리자(`with` 문)를 사용하는 것이 권장되는 방법입니다. 이 방식은 MCP 서버 프로세스의 시작과 컨텍스트 종료 시 자동 종료를 처리합니다.
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
from mcp import StdioServerParameters
|
||||
import os
|
||||
|
||||
# Create a StdioServerParameters object
|
||||
server_params=StdioServerParameters(
|
||||
command="python3",
|
||||
args=["servers/your_stdio_server.py"],
|
||||
env={"UV_PYTHON": "3.12", **os.environ},
|
||||
)
|
||||
|
||||
with MCPServerAdapter(server_params) as tools:
|
||||
print(f"Available tools from Stdio MCP server: {[tool.name for tool in tools]}")
|
||||
|
||||
# Example: Using the tools from the Stdio MCP server in a CrewAI Agent
|
||||
research_agent = Agent(
|
||||
role="Local Data Processor",
|
||||
goal="Process data using a local Stdio-based tool.",
|
||||
backstory="An AI that leverages local scripts via MCP for specialized tasks.",
|
||||
tools=tools,
|
||||
reasoning=True,
|
||||
verbose=True,
|
||||
)
|
||||
|
||||
processing_task = Task(
|
||||
description="Process the input data file 'data.txt' and summarize its contents.",
|
||||
expected_output="A summary of the processed data.",
|
||||
agent=research_agent,
|
||||
markdown=True
|
||||
)
|
||||
|
||||
data_crew = Crew(
|
||||
agents=[research_agent],
|
||||
tasks=[processing_task],
|
||||
verbose=True,
|
||||
process=Process.sequential
|
||||
)
|
||||
|
||||
result = data_crew.kickoff()
|
||||
print("\nCrew Task Result (Stdio - Managed):\n", result)
|
||||
|
||||
```
|
||||
|
||||
### 2. 수동 연결 라이프사이클
|
||||
|
||||
Stdio MCP 서버 프로세스가 시작되고 중지되는 시점을 더 세밀하게 제어해야 하는 경우, `MCPServerAdapter`의 라이프사이클을 수동으로 관리할 수 있습니다.
|
||||
|
||||
<Info>
|
||||
서버 프로세스가 종료되고 자원이 해제되도록 **반드시** `mcp_server_adapter.stop()`을 호출해야 합니다. `try...finally` 블록을 사용하는 것을 강력히 추천합니다.
|
||||
</Info>
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
from mcp import StdioServerParameters
|
||||
import os
|
||||
|
||||
# Create a StdioServerParameters object
|
||||
stdio_params=StdioServerParameters(
|
||||
command="python3",
|
||||
args=["servers/your_stdio_server.py"],
|
||||
env={"UV_PYTHON": "3.12", **os.environ},
|
||||
)
|
||||
|
||||
mcp_server_adapter = MCPServerAdapter(server_params=stdio_params)
|
||||
try:
|
||||
mcp_server_adapter.start() # Manually start the connection and server process
|
||||
tools = mcp_server_adapter.tools
|
||||
print(f"Available tools (manual Stdio): {[tool.name for tool in tools]}")
|
||||
|
||||
# Example: Using the tools with your Agent, Task, Crew setup
|
||||
manual_agent = Agent(
|
||||
role="Local Task Executor",
|
||||
goal="Execute a specific local task using a manually managed Stdio tool.",
|
||||
backstory="An AI proficient in controlling local processes via MCP.",
|
||||
tools=tools,
|
||||
verbose=True
|
||||
)
|
||||
|
||||
manual_task = Task(
|
||||
description="Execute the 'perform_analysis' command via the Stdio tool.",
|
||||
expected_output="Results of the analysis.",
|
||||
agent=manual_agent
|
||||
)
|
||||
|
||||
manual_crew = Crew(
|
||||
agents=[manual_agent],
|
||||
tasks=[manual_task],
|
||||
verbose=True,
|
||||
process=Process.sequential
|
||||
)
|
||||
|
||||
|
||||
result = manual_crew.kickoff() # Actual inputs depend on your tool
|
||||
print("\nCrew Task Result (Stdio - Manual):\n", result)
|
||||
|
||||
except Exception as e:
|
||||
print(f"An error occurred during manual Stdio MCP integration: {e}")
|
||||
finally:
|
||||
if mcp_server_adapter and mcp_server_adapter.is_connected: # Check if connected before stopping
|
||||
print("Stopping Stdio MCP server connection (manual)...")
|
||||
mcp_server_adapter.stop() # **Crucial: Ensure stop is called**
|
||||
elif mcp_server_adapter: # If adapter exists but not connected (e.g. start failed)
|
||||
print("Stdio MCP server adapter was not connected. No stop needed or start failed.")
|
||||
|
||||
```
|
||||
|
||||
플레이스홀더 경로 및 명령어를 실제 Stdio 서버 정보로 교체해야 합니다. `StdioServerParameters`의 `env` 파라미터는
|
||||
서버 프로세스용 환경 변수를 설정할 때 사용할 수 있습니다. 이는 서버의 동작을 구성하거나 필요한 경로(예: `PYTHONPATH`)를 제공하는 데 유용할 수 있습니다.
|
||||
135
docs/ko/mcp/streamable-http.mdx
Normal file
135
docs/ko/mcp/streamable-http.mdx
Normal file
@@ -0,0 +1,135 @@
|
||||
---
|
||||
title: 스트리머블 HTTP 전송
|
||||
description: 유연한 스트리머블 HTTP 전송을 사용하여 CrewAI를 원격 MCP 서버에 연결하는 방법을 알아보세요.
|
||||
icon: globe
|
||||
---
|
||||
|
||||
## 개요
|
||||
|
||||
Streamable HTTP 전송은 원격 MCP 서버에 연결할 수 있는 유연한 방법을 제공합니다. 이는 종종 HTTP를 기반으로 구축되며, 요청-응답 및 스트리밍을 포함한 다양한 통신 패턴을 지원할 수 있습니다. 때때로 더 넓은 HTTP 상호작용 내에서 서버-클라이언트 스트림을 위해 Server-Sent Events(SSE)를 활용하기도 합니다.
|
||||
|
||||
## 주요 개념
|
||||
|
||||
- **원격 서버**: 원격에 호스팅된 MCP 서버용으로 설계되었습니다.
|
||||
- **유연성**: 단순 SSE보다 더 복잡한 상호작용 패턴을 지원할 수 있으며, 서버가 구현한 경우 양방향 통신도 가능할 수 있습니다.
|
||||
- **`MCPServerAdapter` 구성**: MCP 통신을 위한 서버의 기본 URL을 제공하고, 전송 유형으로 `"streamable-http"`를 지정해야 합니다.
|
||||
|
||||
## 스트리머블 HTTP를 통한 연결
|
||||
|
||||
Streamable HTTP MCP 서버와의 연결 라이프사이클을 관리하는 주요 방법에는 두 가지가 있습니다:
|
||||
|
||||
### 1. 완전히 관리되는 연결(추천)
|
||||
|
||||
추천되는 방법은 Python 컨텍스트 매니저(`with` 문)을 사용하는 것으로, 연결의 설정과 해제를 자동으로 처리합니다.
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
|
||||
server_params = {
|
||||
"url": "http://localhost:8001/mcp", # 실제 Streamable HTTP 서버 URL로 교체하세요
|
||||
"transport": "streamable-http"
|
||||
}
|
||||
|
||||
try:
|
||||
with MCPServerAdapter(server_params) as tools:
|
||||
print(f"Available tools from Streamable HTTP MCP server: {[tool.name for tool in tools]}")
|
||||
|
||||
http_agent = Agent(
|
||||
role="HTTP Service Integrator",
|
||||
goal="Utilize tools from a remote MCP server via Streamable HTTP.",
|
||||
backstory="An AI agent adept at interacting with complex web services.",
|
||||
tools=tools,
|
||||
verbose=True,
|
||||
)
|
||||
|
||||
http_task = Task(
|
||||
description="Perform a complex data query using a tool from the Streamable HTTP server.",
|
||||
expected_output="The result of the complex data query.",
|
||||
agent=http_agent,
|
||||
)
|
||||
|
||||
http_crew = Crew(
|
||||
agents=[http_agent],
|
||||
tasks=[http_task],
|
||||
verbose=True,
|
||||
process=Process.sequential
|
||||
)
|
||||
|
||||
result = http_crew.kickoff()
|
||||
print("\nCrew Task Result (Streamable HTTP - Managed):\n", result)
|
||||
|
||||
except Exception as e:
|
||||
print(f"Error connecting to or using Streamable HTTP MCP server (Managed): {e}")
|
||||
print("Ensure the Streamable HTTP MCP server is running and accessible at the specified URL.")
|
||||
|
||||
```
|
||||
**참고:** `"http://localhost:8001/mcp"`은 실제 사용 중인 Streamable HTTP MCP 서버의 URL로 교체해야 합니다.
|
||||
|
||||
### 2. 수동 연결 라이프사이클
|
||||
|
||||
보다 명시적인 제어가 필요한 시나리오에서는 `MCPServerAdapter` 연결을 직접 관리할 수 있습니다.
|
||||
|
||||
<Info>
|
||||
연결을 종료하고 리소스를 해제하려면 작업이 끝난 후 반드시 `mcp_server_adapter.stop()`을 호출하는 것이 **매우 중요**합니다. 이를 보장하는 가장 안전한 방법은 `try...finally` 블록을 사용하는 것입니다.
|
||||
</Info>
|
||||
|
||||
```python
|
||||
from crewai import Agent, Task, Crew, Process
|
||||
from crewai_tools import MCPServerAdapter
|
||||
|
||||
server_params = {
|
||||
"url": "http://localhost:8001/mcp", # Replace with your actual Streamable HTTP server URL
|
||||
"transport": "streamable-http"
|
||||
}
|
||||
|
||||
mcp_server_adapter = None
|
||||
try:
|
||||
mcp_server_adapter = MCPServerAdapter(server_params)
|
||||
mcp_server_adapter.start()
|
||||
tools = mcp_server_adapter.tools
|
||||
print(f"Available tools (manual Streamable HTTP): {[tool.name for tool in tools]}")
|
||||
|
||||
manual_http_agent = Agent(
|
||||
role="Advanced Web Service User",
|
||||
goal="Interact with an MCP server using manually managed Streamable HTTP connections.",
|
||||
backstory="An AI specialist in fine-tuning HTTP-based service integrations.",
|
||||
tools=tools,
|
||||
verbose=True
|
||||
)
|
||||
|
||||
data_processing_task = Task(
|
||||
description="Submit data for processing and retrieve results via Streamable HTTP.",
|
||||
expected_output="Processed data or confirmation.",
|
||||
agent=manual_http_agent
|
||||
)
|
||||
|
||||
data_crew = Crew(
|
||||
agents=[manual_http_agent],
|
||||
tasks=[data_processing_task],
|
||||
verbose=True,
|
||||
process=Process.sequential
|
||||
)
|
||||
|
||||
result = data_crew.kickoff()
|
||||
print("\nCrew Task Result (Streamable HTTP - Manual):\n", result)
|
||||
|
||||
except Exception as e:
|
||||
print(f"An error occurred during manual Streamable HTTP MCP integration: {e}")
|
||||
print("Ensure the Streamable HTTP MCP server is running and accessible.")
|
||||
finally:
|
||||
if mcp_server_adapter and mcp_server_adapter.is_connected:
|
||||
print("Stopping Streamable HTTP MCP server connection (manual)...")
|
||||
mcp_server_adapter.stop() # **Crucial: Ensure stop is called**
|
||||
elif mcp_server_adapter:
|
||||
print("Streamable HTTP MCP server adapter was not connected. No stop needed or start failed.")
|
||||
```
|
||||
|
||||
## 보안 고려사항
|
||||
|
||||
Streamable HTTP 전송을 사용할 때는 일반적인 웹 보안 모범 사례가 매우 중요합니다:
|
||||
- **HTTPS 사용**: 데이터 전송을 암호화하기 위해 항상 MCP 서버 URL에 HTTPS(HTTP Secure)를 사용하는 것이 좋습니다.
|
||||
- **인증**: MCP 서버가 민감한 도구나 데이터를 노출하는 경우 강력한 인증 메커니즘을 구현하세요.
|
||||
- **입력 검증**: MCP 서버가 모든 수신 요청과 매개변수를 반드시 검증하도록 하십시오.
|
||||
|
||||
MCP 통합 보안에 대한 종합적인 안내는 [보안 고려사항](./security.mdx) 페이지와 공식 [MCP 전송 보안 문서](https://modelcontextprotocol.io/docs/concepts/transports#security-considerations)를 참고하시기 바랍니다.
|
||||
Reference in New Issue
Block a user