11//! Test to verify MCP schema generation for usize fields
22
3- use codanna:: mcp:: { AnalyzeImpactRequest , SearchSymbolsRequest , SemanticSearchRequest } ;
3+ use codanna:: mcp:: {
4+ AnalyzeImpactRequest , GetIndexInfoRequest , SearchSymbolsRequest , SemanticSearchRequest ,
5+ } ;
46
57#[ test]
68fn test_mcp_schema_uint_format ( ) {
@@ -14,7 +16,7 @@ fn test_mcp_schema_uint_format() {
1416 println ! ( "{search_json}" ) ;
1517
1618 if search_json. contains ( r#""format":"uint"# ) {
17- println ! ( "\n ❌ WARNING: SearchSymbolsRequest contains 'uint' format!" ) ;
19+ println ! ( "\n [WARN] SearchSymbolsRequest contains 'uint' format!" ) ;
1820 println ! ( " This may cause issues with MCP clients like Gemini." ) ;
1921 }
2022
@@ -28,7 +30,7 @@ fn test_mcp_schema_uint_format() {
2830 println ! ( "{semantic_json}" ) ;
2931
3032 if semantic_json. contains ( r#""format":"uint"# ) {
31- println ! ( "\n ❌ WARNING: SemanticSearchRequest contains 'uint' format!" ) ;
33+ println ! ( "\n [WARN] SemanticSearchRequest contains 'uint' format!" ) ;
3234 }
3335
3436 println ! ( "\n {}" , "=" . repeat( 50 ) ) ;
@@ -41,7 +43,7 @@ fn test_mcp_schema_uint_format() {
4143 println ! ( "{impact_json}" ) ;
4244
4345 if impact_json. contains ( r#""format":"uint"# ) {
44- println ! ( "\n ❌ WARNING: AnalyzeImpactRequest contains 'uint' format!" ) ;
46+ println ! ( "\n [WARN] AnalyzeImpactRequest contains 'uint' format!" ) ;
4547 }
4648
4749 // Summary
@@ -53,10 +55,38 @@ fn test_mcp_schema_uint_format() {
5355 || impact_json. contains ( r#""format":"uint"# ) ;
5456
5557 if has_uint {
56- println ! ( "❌ Schema contains 'uint' format which is not standard JSON Schema." ) ;
58+ println ! ( "[FAIL] Schema contains 'uint' format which is not standard JSON Schema." ) ;
5759 println ! ( " This causes compatibility issues with MCP clients." ) ;
5860 println ! ( " Fix: Change usize fields to u32 or u64 in MCP request structs." ) ;
5961 } else {
60- println ! ( "✅ No 'uint' format found in schemas." ) ;
62+ println ! ( "[OK] No 'uint' format found in schemas." ) ;
6163 }
6264}
65+
66+ /// Regression test: `get_index_info` is a no-parameter tool whose inputSchema must satisfy
67+ /// both MCP spec (recommends `additionalProperties: false`) and OpenAI's strict
68+ /// function-calling validation (requires `properties` field).
69+ #[ test]
70+ fn test_get_index_info_schema_has_properties ( ) {
71+ let schema = rmcp:: schemars:: schema_for!( GetIndexInfoRequest ) ;
72+ let json = serde_json:: to_string_pretty ( & schema) . unwrap ( ) ;
73+ println ! ( "GetIndexInfoRequest schema:\n {json}" ) ;
74+
75+ let root: serde_json:: Value = serde_json:: from_str ( & json) . unwrap ( ) ;
76+
77+ assert_eq ! (
78+ root. get( "type" ) . and_then( |v| v. as_str( ) ) ,
79+ Some ( "object" ) ,
80+ "schema must have type=object\n Got:\n {json}"
81+ ) ;
82+ assert ! (
83+ root. get( "properties" ) . is_some( ) ,
84+ "schema must contain 'properties' for OpenAI compatibility\n Got:\n {json}"
85+ ) ;
86+ assert_eq ! (
87+ root. get( "additionalProperties" ) . and_then( |v| v. as_bool( ) ) ,
88+ Some ( false ) ,
89+ "schema should set additionalProperties=false per MCP spec\n Got:\n {json}"
90+ ) ;
91+ println ! ( "[OK] GetIndexInfoRequest schema is MCP-spec compliant and OpenAI-compatible." ) ;
92+ }
0 commit comments