This is an automated email from the ASF dual-hosted git repository.

terrymanu pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/shardingsphere.git


The following commit(s) were added to refs/heads/master by this push:
     new 12e9129f148 Strengthen MCP next action example validation (#39001)
12e9129f148 is described below

commit 12e9129f148fb30b943dfb671d616f68d991fced
Author: Liang Zhang <[email protected]>
AuthorDate: Sun Jul 5 10:46:15 2026 +0800

    Strengthen MCP next action example validation (#39001)
---
 .../support/descriptor/MCPToolOutputSchemaValidator.java  | 15 +++++++++++++++
 .../descriptor/MCPDescriptorCatalogValidatorTest.java     |  9 +++++++++
 .../mcp-descriptors/mcp-descriptor-test-planning.yaml     |  2 ++
 3 files changed, 26 insertions(+)

diff --git 
a/mcp/support/src/main/java/org/apache/shardingsphere/mcp/support/descriptor/MCPToolOutputSchemaValidator.java
 
b/mcp/support/src/main/java/org/apache/shardingsphere/mcp/support/descriptor/MCPToolOutputSchemaValidator.java
index f70177f19e6..cdd38749f76 100644
--- 
a/mcp/support/src/main/java/org/apache/shardingsphere/mcp/support/descriptor/MCPToolOutputSchemaValidator.java
+++ 
b/mcp/support/src/main/java/org/apache/shardingsphere/mcp/support/descriptor/MCPToolOutputSchemaValidator.java
@@ -40,6 +40,8 @@ public final class MCPToolOutputSchemaValidator {
     
     private static final Map<String, Collection<String>> 
NEXT_ACTION_ALLOWED_FIELDS = createNextActionAllowedFields();
     
+    private static final Map<String, Collection<String>> 
NEXT_ACTION_REQUIRED_FIELDS = createNextActionRequiredFields();
+    
     private static final Collection<String> NEXT_ACTION_SCHEMA_ALLOWED_FIELDS 
= createNextActionSchemaAllowedFields();
     
     private static final Collection<String> MODEL_CRITICAL_HINT_FIELDS = 
List.of(
@@ -64,6 +66,15 @@ public final class MCPToolOutputSchemaValidator {
                 "terminal", Set.of("order", "type", "title", "reason", 
"depends_on"));
     }
     
+    private static Map<String, Collection<String>> 
createNextActionRequiredFields() {
+        return Map.of(
+                "resource_read", Set.of("order", "type", "title", 
"resource_uri"),
+                "tool_call", Set.of("order", "type", "title", "tool_name", 
"arguments"),
+                "completion", Set.of("order", "type", "title", "ref", 
"argument"),
+                "ask_user", Set.of("order", "type", "title", "question"),
+                "terminal", Set.of("order", "type", "title"));
+    }
+    
     private static Collection<String> createNextActionSchemaAllowedFields() {
         Set<String> result = new HashSet<>();
         for (Collection<String> each : NEXT_ACTION_ALLOWED_FIELDS.values()) {
@@ -199,6 +210,10 @@ public final class MCPToolOutputSchemaValidator {
         Collection<String> allowedFields = 
NEXT_ACTION_ALLOWED_FIELDS.get(type);
         ShardingSpherePreconditions.checkState(null != allowedFields,
                 () -> new IllegalStateException(String.format("Tool `%s` 
next_actions example uses unknown type `%s`.", descriptor.getName(), type)));
+        for (String each : NEXT_ACTION_REQUIRED_FIELDS.get(type)) {
+            ShardingSpherePreconditions.checkState(action.containsKey(each),
+                    () -> new IllegalStateException(String.format("Tool `%s` 
next_actions example `%s` must contain `%s`.", descriptor.getName(), type, 
each)));
+        }
         for (Object each : action.keySet()) {
             String fieldName = String.valueOf(each);
             
ShardingSpherePreconditions.checkState(allowedFields.contains(fieldName),
diff --git 
a/mcp/support/src/test/java/org/apache/shardingsphere/mcp/support/descriptor/MCPDescriptorCatalogValidatorTest.java
 
b/mcp/support/src/test/java/org/apache/shardingsphere/mcp/support/descriptor/MCPDescriptorCatalogValidatorTest.java
index 6d8ee4833af..dccc391cfe2 100644
--- 
a/mcp/support/src/test/java/org/apache/shardingsphere/mcp/support/descriptor/MCPDescriptorCatalogValidatorTest.java
+++ 
b/mcp/support/src/test/java/org/apache/shardingsphere/mcp/support/descriptor/MCPDescriptorCatalogValidatorTest.java
@@ -136,6 +136,15 @@ class MCPDescriptorCatalogValidatorTest {
                 "Tool `database_gateway_test_tool` next_actions example 
`tool_call` contains unsupported field `extra_context`.");
     }
     
+    @Test
+    void assertValidateRejectsMissingNextActionExampleField() {
+        assertValidationError(createCatalog(List.of(), 
List.of(createToolDescriptor(
+                "database_gateway_test_tool", new MCPToolAnnotations("Test 
Tool", true, false, true, true),
+                createOutputSchema(Map.of("next_actions", 
createNextActionsSchema()), List.of(Map.of("next_actions", List.of(
+                        Map.of("order", 1, "type", "tool_call", "title", 
"Retry", "tool_name", "database_gateway_test_tool")))))))),
+                "Tool `database_gateway_test_tool` next_actions example 
`tool_call` must contain `arguments`.");
+    }
+    
     @Test
     void 
assertValidateAcceptsFeatureOwnedToolDescriptorWithoutExtensionMarker() {
         assertDoesNotThrow(() -> 
MCPDescriptorCatalogValidator.validate(createCatalog(List.of(), 
List.of(createToolDescriptor(
diff --git 
a/mcp/support/src/test/resources/META-INF/shardingsphere-mcp/mcp-descriptors/mcp-descriptor-test-planning.yaml
 
b/mcp/support/src/test/resources/META-INF/shardingsphere-mcp/mcp-descriptors/mcp-descriptor-test-planning.yaml
index 24cb18c83b3..7a70c2e7334 100644
--- 
a/mcp/support/src/test/resources/META-INF/shardingsphere-mcp/mcp-descriptors/mcp-descriptor-test-planning.yaml
+++ 
b/mcp/support/src/test/resources/META-INF/shardingsphere-mcp/mcp-descriptors/mcp-descriptor-test-planning.yaml
@@ -195,6 +195,8 @@ tools:
             - order: 1
               type: tool_call
               title: Call database_gateway_apply_workflow
+              tool_name: database_gateway_apply_workflow
+              arguments: {}
               reason: Preview generated workflow artifacts.
     annotations:
       title: Plan Encrypt Rule

Reply via email to