diff --git a/src/ModelContextProtocol/Server/AIFunctionMcpServerPrompt.cs b/src/ModelContextProtocol/Server/AIFunctionMcpServerPrompt.cs index b1671b906..404038035 100644 --- a/src/ModelContextProtocol/Server/AIFunctionMcpServerPrompt.cs +++ b/src/ModelContextProtocol/Server/AIFunctionMcpServerPrompt.cs @@ -130,6 +130,7 @@ private static AIFunctionFactoryOptions CreateAIFunctionFactoryOptions( return null; } }, + JsonSchemaCreateOptions = options?.SchemaCreateOptions, }; /// Creates an that wraps the specified . diff --git a/src/ModelContextProtocol/Server/AIFunctionMcpServerTool.cs b/src/ModelContextProtocol/Server/AIFunctionMcpServerTool.cs index 562a8476c..658075c41 100644 --- a/src/ModelContextProtocol/Server/AIFunctionMcpServerTool.cs +++ b/src/ModelContextProtocol/Server/AIFunctionMcpServerTool.cs @@ -151,6 +151,7 @@ private static AIFunctionFactoryOptions CreateAIFunctionFactoryOptions( return null; } }, + JsonSchemaCreateOptions = options?.SchemaCreateOptions, }; /// Creates an that wraps the specified . diff --git a/src/ModelContextProtocol/Server/McpServerPromptCreateOptions.cs b/src/ModelContextProtocol/Server/McpServerPromptCreateOptions.cs index 40ef66211..17f6dfd9d 100644 --- a/src/ModelContextProtocol/Server/McpServerPromptCreateOptions.cs +++ b/src/ModelContextProtocol/Server/McpServerPromptCreateOptions.cs @@ -1,3 +1,4 @@ +using Microsoft.Extensions.AI; using ModelContextProtocol.Utils.Json; using System.ComponentModel; using System.Text.Json; @@ -55,6 +56,14 @@ public sealed class McpServerPromptCreateOptions /// public JsonSerializerOptions? SerializerOptions { get; set; } + /// + /// Gets or sets the JSON schema options when creating from a method. + /// + /// + /// Defaults to if left unspecified. + /// + public AIJsonSchemaCreateOptions? SchemaCreateOptions { get; set; } + /// /// Creates a shallow clone of the current instance. /// @@ -65,5 +74,6 @@ internal McpServerPromptCreateOptions Clone() => Name = Name, Description = Description, SerializerOptions = SerializerOptions, + SchemaCreateOptions = SchemaCreateOptions, }; } diff --git a/src/ModelContextProtocol/Server/McpServerToolCreateOptions.cs b/src/ModelContextProtocol/Server/McpServerToolCreateOptions.cs index ed7a49f10..14fcb7cd7 100644 --- a/src/ModelContextProtocol/Server/McpServerToolCreateOptions.cs +++ b/src/ModelContextProtocol/Server/McpServerToolCreateOptions.cs @@ -1,3 +1,4 @@ +using Microsoft.Extensions.AI; using ModelContextProtocol.Utils.Json; using System.ComponentModel; using System.Text.Json; @@ -132,6 +133,14 @@ public sealed class McpServerToolCreateOptions /// public JsonSerializerOptions? SerializerOptions { get; set; } + /// + /// Gets or sets the JSON schema options when creating from a method. + /// + /// + /// Defaults to if left unspecified. + /// + public AIJsonSchemaCreateOptions? SchemaCreateOptions { get; set; } + /// /// Creates a shallow clone of the current instance. /// @@ -147,5 +156,6 @@ internal McpServerToolCreateOptions Clone() => OpenWorld = OpenWorld, ReadOnly = ReadOnly, SerializerOptions = SerializerOptions, + SchemaCreateOptions = SchemaCreateOptions, }; } diff --git a/tests/ModelContextProtocol.Tests/Server/McpServerPromptTests.cs b/tests/ModelContextProtocol.Tests/Server/McpServerPromptTests.cs index 2e251d033..3804cfbf8 100644 --- a/tests/ModelContextProtocol.Tests/Server/McpServerPromptTests.cs +++ b/tests/ModelContextProtocol.Tests/Server/McpServerPromptTests.cs @@ -3,7 +3,9 @@ using ModelContextProtocol.Protocol.Types; using ModelContextProtocol.Server; using Moq; +using System.ComponentModel; using System.Reflection; +using System.Text.Json; namespace ModelContextProtocol.Tests.Server; @@ -316,6 +318,30 @@ await Assert.ThrowsAsync(async () => await prompt.Get TestContext.Current.CancellationToken)); } + [Fact] + public async Task SupportsSchemaCreateOptions() + { + AIJsonSchemaCreateOptions schemaCreateOptions = new() + { + TransformSchemaNode = (context, node) => + { + node["description"] = "1234"; + return node; + } + }; + + McpServerPrompt prompt = McpServerPrompt.Create(([Description("argument1")] int num, [Description("argument2")] string str) => + { + return new ChatMessage(ChatRole.User, "Hello"); + }, new() { SchemaCreateOptions = schemaCreateOptions }); + + Assert.NotNull(prompt.ProtocolPrompt.Arguments); + Assert.All( + prompt.ProtocolPrompt.Arguments, + x => Assert.Equal("1234", x.Description) + ); + } + private sealed class MyService; private class DisposablePromptType : IDisposable diff --git a/tests/ModelContextProtocol.Tests/Server/McpServerToolTests.cs b/tests/ModelContextProtocol.Tests/Server/McpServerToolTests.cs index 4c42ba242..efd5028b2 100644 --- a/tests/ModelContextProtocol.Tests/Server/McpServerToolTests.cs +++ b/tests/ModelContextProtocol.Tests/Server/McpServerToolTests.cs @@ -355,6 +355,29 @@ public async Task CanReturnCallToolResponse() Assert.Equal("image", result.Content[1].Type); } + [Fact] + public async Task SupportsSchemaCreateOptions() + { + AIJsonSchemaCreateOptions schemaCreateOptions = new () + { + TransformSchemaNode = (context, node) => + { + node["text"] = "1234"; + return node; + }, + }; + + McpServerTool tool = McpServerTool.Create((int num, string str) => + { + return "42"; + }, new() { SchemaCreateOptions = schemaCreateOptions }); + + Assert.All( + tool.ProtocolTool.InputSchema.GetProperty("properties").EnumerateObject(), + x => Assert.True(x.Value.TryGetProperty("text", out JsonElement value) && value.ToString() == "1234") + ); + } + private sealed class MyService; private class DisposableToolType : IDisposable