Adding Ithil to Your API
Ithil.Hosting is a NuGet package you add to your existing ASP.NET Web API. It does two things: registers the source-generated tool schema endpoint, and provides the [AgentTool] attribute for decorating controller methods.
Your existing API code, routes, and business logic are unchanged. Ithil is additive only.
Install the package
dotnet add package Ithil.HostingWire up in Program.cs
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddControllers();
builder.Services.AddIthilHosting(); // registers Ithil services
var app = builder.Build();
app.MapControllers();
app.MapIthilSchema(SchemaRegistry.Tools); // exposes GET /ithil/schema
app.Run();SchemaRegistry is a static class emitted by the Ithil source generator at compile time. It contains a Tools collection of all [AgentTool]-decorated methods found in the project.
How the source generator works
At compile time, the Ithil Roslyn source generator:
- Scans every class in the project for
[AgentTool]attributes - For each decorated method, reads the HTTP verb (from
[HttpGet],[HttpPost], etc.) and the route template - Emits a
SchemaRegistryclass with a statically-typedToolscollection containing the full MCP tool schema for each method
No reflection occurs at runtime. The schema is fully resolved at build time, which means startup is fast and there are no surprises if an attribute is misconfigured — the build fails instead.
What MapIthilSchema does
app.MapIthilSchema(SchemaRegistry.Tools) registers a single endpoint:
GET /ithil/schemaThe gateway polls this endpoint at startup to discover which tools are available. The response is a JSON array of tool definitions:
[
{
"name": "GetOrderStatus",
"description": "Returns the current status of an order given its order ID",
"httpMethod": "GET",
"routePattern": "orders/{id}/status",
"inputSchema": {
"type": "object",
"properties": {
"id": { "type": "string" }
},
"required": ["id"]
},
"allowWrite": false,
"maxResponseTokens": 2000
}
]The gateway must be able to reach GET /ithil/schema on your API. Ensure there are no network or firewall rules blocking this path. The endpoint does not require authentication — it is an internal service-to-service call between the gateway and your API.
Verify it worked
After starting your API, confirm the schema endpoint is responding:
curl http://localhost:5200/ithil/schemaYou should see a JSON array containing one entry for every [AgentTool]-decorated method. If the array is empty, check that:
- The source generator ran — rebuild the project with
dotnet build MapIthilSchema(SchemaRegistry.Tools)is called inProgram.cs- At least one method has
[AgentTool]applied
Targeting specific endpoints
[AgentTool] is applied to individual controller action methods:
[AgentTool("Returns inventory count for a SKU")]
[HttpGet("inventory/{sku}")]
public IActionResult GetInventory(string sku) { ... }
[AgentTool("Creates a purchase order", AllowWrite = true)]
[HttpPost("orders")]
public IActionResult CreateOrder([FromBody] OrderRequest req) { ... }See the [AgentTool] Reference for all attribute parameters.