mcpgraph
TeamSparkAI/mcpGraph
데이터 변환 및 조건부 논리를 활용하여 다른 MCP 도구를 조합하고 조정하는 도구를 통해 노코드 MCP 서버를 구축하세요.
...모든 것을 확장하십시오소개 mcpgraph
mcpgraph 스킬을 사용하면 여러 MCP 도구를 오케스트레이션하고 조합하는 노코드(no-code) Model Context Protocol(MCP) 서버를 생성할 수 있습니다. 이 스킬을 통해 사용자는 노드의 유향 그래프를 나타내는 YAML 파일을 사용하여 선언적인 방식으로 도구 시퀀스를 정의할 수 있습니다. 이러한 구성을 통해 임베디드 코드 없이도 다양한 MCP 도구, 데이터 변환 및 조건부 논리를 원활하게 통합할 수 있습니다. 이 스킬은 표준화되고 쉽게 구성할 수 있는 접근 방식을 제공함으로써, 코딩 전문 지식이 없는 사용자도 활용할 수 있도록 하여 복잡하고 수동적인 도구 오케스트레이션 문제를 해결합니다.
자주 묻는 질문
내 환경에서 mcpgraph 를 어떻게 구성하나요?
mcpgraph 를 사용하려면 이를 설치하고 MCP 클라이언트에서 구성해야 합니다. 예를 들어, Claude Desktop의 경우 적절한 명령어와 YAML 구성 경로를 사용하여 `claude_desktop_config.json` 파일에 mcpgraph 서버를 추가하십시오.
mcpgraph 는 어떤 종류의 서버와 상호작용할 수 있나요?
mcpgraph 명령줄 도구를 실행하는 stdio 서버와 HTTP 요청을 통해 도구를 제공하는 스트리밍 가능한 HTTP 서버 모두와 상호작용할 수 있습니다.
mcpgraph 를 사용하려면 코드를 작성해야 하나요?
아니요, mcpgraph 는 코딩이 필요 없는 환경을 위해 설계되었습니다. YAML 구성 파일과 JSONata, JSON Logic과 같은 표준 표현 언어를 사용하여 로직과 변환을 정의합니다.
mcpgraph 를 사용하기 위한 시스템 요구 사항은 무엇인가요?
mcpgraph MCP 클라이언트에 액세스할 수 있는 로컬 환경이 필요합니다. mcpgraph 명령을 사용할 수 있어야 하며, 유효한 YAML 구성 파일이 있어야 합니다.
mcpgraph 는 조건부 로직을 처리할 수 있나요?
네, mcpgraph 는 JSON Logic을 활용한 조건부 라우팅을 지원하여, 데이터를 기반으로 한 복잡한 의사 결정 프로세스를 가능하게 합니다.
Building mcpGraphs
This skill teaches you how to build mcpGraph configurations - declarative YAML files that define MCP tools as directed graphs of nodes.
What is an mcpGraph?
An mcpGraph is a declarative YAML configuration file that defines MCP (Model Context Protocol) tools as directed graphs. Each tool executes a sequence of nodes that can:
- Call other MCP tools (on internal or external MCP servers)
- Transform data using JSONata expressions
- Make routing decisions using JSON Logic
When to use mcpGraph:
- You need to orchestrate multiple MCP tool calls in sequence
- You want to transform data between tool calls
- You need conditional routing based on data
- You want declarative, observable configurations (no embedded code)
- You need to compose complex workflows from simpler MCP tools
Why use mcpGraph:
- Declarative: All logic expressed in YAML using standard expression languages
- Observable: Every transformation and decision is traceable
- No Embedded Code: Uses JSONata and JSON Logic instead of full programming languages
- Standard-Based: Built on MCP, JSONata, and JSON Logic standards
- Composable: Build complex tools from simpler MCP tools
How to Use mcpGraph
This skill assumes mcpGraph is installed in your local environment and available as the mcpgraph command.
To use mcpGraph as an MCP server (e.g., in Claude Desktop), add it to your MCP client configuration:
Claude Desktop (~/Library/Application Support/Claude/claude_desktop_config.json on macOS):
{ "mcpServers": { "mcpgraph": { "command": "mcpgraph", "args": ["-g", "/path/to/your/config.yaml"] } }}The -g (or --graph) flag specifies the path to your YAML configuration file.
File Structure
An mcpGraph configuration file is a YAML file with the following structure:
version: "1.0"# MCP Server Metadataserver: name: "serverName" # Required: unique identifier version: "1.0.0" # Required: server version title: "Display Name" # Optional: display name (defaults to name) instructions: "..." # Optional: server usage instructions# MCP Servers used by the graphmcpServers: serverName: command: "command" # For stdio servers args: ["arg1", "arg2"] # Command arguments # OR for HTTP servers: # httpServer: # type: "streamableHttp" # url: "https://api.example.com/mcp" # headers: # Authorization: "Bearer token"# Tool Definitions for tools implemented by this graph and available as part of this MCP servertools: - name: "toolName" description: "Tool description" inputSchema: type: "object" properties: paramName: type: "string" description: "Parameter description" required: - paramName outputSchema: type: "object" properties: result: type: "string" description: "Result description" nodes: # Node definitions here
MCP Server Metadata
The server section defines metadata for the MCP server that will expose these tools:
name(required): Unique identifier for the serverversion(required): Server version (semantic versioning)title(optional): Display name (defaults tonameif not provided)instructions(optional): Instructions for using this server
MCP Servers
The mcpServers section defines the MCP servers that the graph will call. Each server can be:
- stdio server: Uses
commandandargsto run a command-line program - streamableHttp server: Uses
type: "streamableHttp",url, and optionalheaders
Tools
The tools array defines the MCP tools exposed by this server. Each tool has:
name: Tool identifierdescription: Tool descriptioninputSchema: JSON Schema defining input parameters (standard MCP tool schema)outputSchema: JSON Schema defining output structurenodes: Array of node definitions that form the execution graph
Graph Structure and Flow
A graph is a directed sequence of nodes that execute in order. Execution flow:
- Starts at the entry node (receives tool arguments)
- Executes nodes sequentially based on
nextfields - switch nodes can conditionally route to different nodes
- Continues until the exit node is reached
- Exit node returns the final result
Node Connections
Nodes are connected using the next field, which specifies the ID of the next node to execute:
- id: "node1" type: "transform" next: "node2" # Executes node2 after node1
Switch nodes use conditions with next fields (each condition specifies its own next node), plus a top-level next field as the default:
- id: "switch_node" type: "switch" conditions: - rule: { ">": [{ var: "entry.value" }, 10] } next: "high_path" next: "default_path" # Default case if no conditions match
Execution Context
During execution, each node's output is stored in the execution context. You can access node outputs using JSONata expressions:
$.node_id- Accesses the latest output of a node with IDnode_id$.entry.paramName- Accesses a parameter from the entry node
The context is a flat structure: { "node_id": output, ... }
Node Types
Entry Node
The entry point for a tool's graph execution. Receives tool arguments.
Properties:
id: Node identifier (typically "entry")type:"entry"next: ID of the next node to execute
Output: The tool input arguments (passed through as-is)
Example:
- id: "entry" type: "entry" next: "process_node"
MCP Node
Calls an MCP tool on an internal or external MCP server.
Properties:
id: Node identifiertype:"mcp"server: Name of the MCP server (frommcpServerssection)tool: Name of the tool to call on that serverargs: Arguments to pass to the tool (can use JSONata expressions)next: ID of the next node to execute
Output: The MCP tool's response (parsed from the tool's content)
Example:
- id: "list_directory_node" type: "mcp" server: "filesystem" tool: "list_directory" args: path: expr: "$.entry.directory" # JSONata expression accessing entry node output next: "count_files_node"
Transform Node
Applies JSONata expressions to transform data between nodes.
Properties:
id: Node identifiertype:"transform"transform.expr: JSONata expression (string)next: ID of the next node to execute
Output: The result of evaluating the JSONata expression
Expression Format:
- Use single-quoted strings for simple expressions:
expr: '{ "result": "value" }' - Use block scalars (
|) for complex multi-line expressions to improve readability
Example (simple):
- id: "count_files_node" type: "transform" transform: expr: '{ "count": $count($split($.list_directory_node.content, "")) }' next: "exit"
Example (complex):
- id: "increment_node" type: "transform" transform: expr: | $executionCount("increment_node") = 0 ? { "counter": 1, "sum": 1, "target": $.entry_sum.n } : { "counter": $nodeExecution("increment_node", -1).counter + 1, ... } next: "check_condition"
Switch Node
Uses JSON Logic to conditionally route to different nodes based on data.
Properties:
id: Node identifiertype:"switch"conditions: Array of condition rulesrule: JSON Logic expression (required - all conditions must have rules)next: ID of the node to route to if this condition matches
next: ID of the default next node (used if no conditions match)
Output: The node ID of the next node that was routed to (string)
Important: var operations in JSON Logic rules are evaluated using JSONata, allowing full JSONata expression support (including history functions).
Example:
- id: "switch_node" type: "switch" conditions: - rule: ">": [{ var: "entry.value" }, 10] next: "high_path" - rule: ">": [{ var: "entry.value" }, 0] next: "low_path" next: "zero_path" # Default case if no conditions match
Advanced Example with JSONata:
- id: "check_condition" type: "switch" conditions: - rule: "<": [ { var: "$.increment_node.counter" }, { var: "$.increment_node.target" } ] next: "increment_node" # Loop back next: "exit_sum" # Default: exit loop when counter >= target
Exit Node
Exit point that returns the final result to the MCP tool caller.
Properties:
id: Node identifier (typically "exit")type:"exit"- Note: No
nextfield - execution ends here
Output: The output from the previous node in the execution history
Example:
- id: "exit" type: "exit"
JSONata Expressions
JSONata is used in three places in mcpGraph for data transformation and access:
- Transform node expressions - Transform data between nodes
- JSON Logic
varoperations - Access context data in switch node conditions - MCP tool node arguments - Objects with
{ "expr": "..." }are evaluated as JSONata expressions (recursively)
Basic Syntax
- Object construction:
{ "key": value } - Property access:
$.node_id.property - Functions:
$count(array),$split(string, delimiter), etc. - Conditional:
condition ? trueValue : falseValue
Where JSONata is Used
1. Transform Nodes:Transform nodes use JSONata expressions in the transform.expr field to transform data:
transform: expr: '{ "count": $count($split($.list_directory_node.content, "")) }'
2. MCP Tool Node Arguments:To use a JSONata expression in an MCP node argument, wrap it in an object with an expr property:
args: path: expr: "$.entry.directory" # JSONata expression accessing entry node output static: "literal/path" # Literal value (not evaluated) count: expr: "$count($.previous_node.items)" # JSONata expression with function
Complex nested args:
args: path: expr: "'downloads/' & $.entry.filename" # String concatenation options: recursive: true # Literal value filter: expr: "$.entry.filterPattern" # Nested expression
Important:
- Objects with only an
exprproperty are evaluated as JSONata - Objects with
exprand other properties are invalid (error) - All other values (strings, numbers, arrays, objects without
expr) are passed as literals - Arrays and objects are recursively evaluated
3. JSON Logic var Operations:In switch node conditions, var operations are evaluated using JSONata:
rule: ">": [{ var: "$.increment_node.counter" }, 10]
Accessing Node Outputs
$.node_id- Latest output of a node$.node_id.property- Property from node output$.entry.paramName- Parameter from entry node
History Functions
For loops and accessing execution history:
$previousNode()- Get the previous node's output$previousNode(index)- Get the node that executed N steps before current$executionCount(nodeName)- Count how many times a node executed$nodeExecution(nodeName, index)- Get a specific execution (0 = first, -1 = last)$nodeExecutions(nodeName)- Get all executions as an array
Example:
transform: expr: | $executionCount("increment_node") = 0 ? { "counter": 1, "sum": 1, "target": $.entry_sum.n } : { "counter": $nodeExecution("increment_node", -1).counter + 1, "sum": $nodeExecution("increment_node", -1).sum + $nodeExecution("increment_node", -1).counter + 1, "target": $.entry_sum.n }
Expression Format in YAML
Simple expressions: Use single-quoted strings
expr: '{ "count": $count($split($.list_directory_node.content, "")) }'
Complex expressions: Use block scalars (
|) for readabilityexpr: | $executionCount("increment_node") = 0 ? { "counter": 1 } : { "counter": $nodeExecution("increment_node", -1).counter + 1 }
JSON Logic
JSON Logic is used in switch nodes for conditional routing. It allows complex rules as pure JSON objects.
Basic Syntax
- Comparison:
{ ">": [a, b] },{ "<": [a, b] },{ "==": [a, b] }, etc. - Logical:
{ "and": [rule1, rule2] },{ "or": [rule1, rule2] },{ "!": rule } - Variable access:
{ "var": "path" }or{ "var": "$.node_id.property" }
Important: var operations are evaluated using JSONata, so you can use full JSONata expressions:
{ "var": "entry.value" }- Simple property access{ "var": "$.increment_node.counter" }- JSONata expression{ "var": "$previousNode().count" }- JSONata with history function
Examples
Simple comparison:
rule: ">": [{ var: "entry.value" }, 10]
Complex condition:
rule: and: - ">": [{ var: "entry.price" }, 100] - "==": [{ var: "entry.status" }, "active"]
With JSONata:
rule: "<": [ { var: "$.increment_node.counter" }, { var: "$.increment_node.target" } ]
Complete Example
Here's a complete example that counts files in a directory:
version: "1.0"server: name: "fileUtils" version: "1.0.0" title: "File utilities" instructions: "This server provides file utility tools for counting files and calculating total file sizes in directories."mcpServers: filesystem: command: "npx" args: - "-y" - "@modelcontextprotocol/server-filesystem" - "./tests/counting"tools: - name: "count_files" description: "Counts the number of files in a directory" inputSchema: type: "object" properties: directory: type: "string" description: "The directory path to count files in" required: - directory outputSchema: type: "object" properties: count: type: "number" description: "The number of files in the directory" nodes: # Entry node: Receives tool arguments - id: "entry" type: "entry" next: "list_directory_node" # List directory contents - id: "list_directory_node" type: "mcp" server: "filesystem" tool: "list_directory" args: path: expr: "$.entry.directory" next: "count_files_node" # Transform and count files - id: "count_files_node" type: "transform" transform: expr: '{ "count": $count($split($.list_directory_node.content, "")) }' next: "exit" # Exit node: Returns the count - id: "exit" type: "exit"
This graph:
- Receives a directory path as input
- Calls the filesystem MCP server's
list_directorytool - Transforms the result to count files using JSONata
- Returns the count
Best Practices
- Use descriptive node IDs: Make node IDs clear and meaningful (e.g.,
list_directory_nodenotnode1) - Format complex expressions: Use block scalars (
|) for multi-line JSONata expressions - Document with comments: Add YAML comments to explain complex logic
- Validate schemas: Ensure
inputSchemaandoutputSchemamatch actual data flow - Test incrementally: Build and test graphs node by node
- Use history functions carefully: Understand execution context when nodes execute multiple times
Common Patterns
Sequential Tool Calls
Chain multiple MCP tool calls in sequence:
entry -> mcp_node_1 -> mcp_node_2 -> transform -> exitConditional Routing
Use switch nodes to route based on data:
entry -> switch_node -> [path_a | path_b] -> exitLoops
Use switch nodes to loop back to previous nodes:
entry -> increment_node -> check_condition -> [increment_node | exit]Data Transformation
Transform data between nodes using JSONata:
mcp_node -> transform -> next_nodeResources
- JSONata Documentation: https://jsonata.org/
- JSON Logic Documentation: https://jsonlogic.com/
mcpgraph 설치
스킬 파일을 다운로드하여 .claude/skills/ 디렉터리에 압축을 풀어주세요.
ZIP 다운로드저장소를 클론하고 스킬 파일을 프로젝트에 복사하세요.
git clone https://github.com/TeamSparkAI/mcpGraph/blob/main/skills/mcpgraph/SKILL.md # Copy SKILL.md to your .claude/skills/ directory
복사





집
