Home Streamlining API Client Generation with Kiota and Koalesce
Post
Cancel

Streamlining API Client Generation with Kiota and Koalesce

After publishing a six-part series about my EcommerceDDD project, I’m dedicating this post to highlight a major improvement: automated API client generation.

This enhancement significantly simplifies API consumption across frontend and backend layers, replacing verbose, manual HttpClient requests with strongly typed, SDK-style clients.

I’ll walk through the rationale behind this shift, the choice of tools (Kiota and Koalesce), and how together they solve real-world integration challenges in distributed systems.

Why Generating API clients?


Manually invoking HTTP endpoints with HttpClient, string-based URIs, and handcrafted request/response models always felt error-prone and redundant, especially when both ends of the wire are within my control.

Leveraging existing OpenAPI definitions, I wanted a maintainable, safer, less redundant, and more expressive approach. Code generation provides exactly that.

Why Kiota?

Kiota helps by:

  • Eliminate boilerplate HttpClient calls.
  • Ensuring compile-time safety for routes, parameters, and data models.
  • Reducing redundant DTOs, ViewModels, and manual object matching.
  • Align SDK usage with your domain naming and semantics.
  • Enhancing developer experience via IntelliSense and clean APIs.

With Kiota, consuming an endpoint like PUT /quotes/{quoteId}/items in TypeScript becomes a clean and intuitive one-liner:

Frontend (Angular/Typescript)
1
await quotesClient.api.quotes.byQuoteId(quoteId).items.put(request);
Backend (C#)
1
await _quotesClient.Api.Quotes[quoteId].Items.PutAsync(request);

No longer worrying about paths, headers, serialization, or model mismatches, is bliss!

Why Koalesce? 🐨

Kiota requires a single OpenAPI definition for client generation. But EcommerceDDD’s microservice architecture means multiple individual APIs, each with its own spec. Without a single merged spec, I’d have to generate multiple separate API clients.

At the same time, the frontend SPA (Single Page Application) interacts with the backend only through a unified API Gateway, unaware of the distributed backend architecture.

That’s where the development challenge began. As we saw previously in the Part 5 - Wrapping up infrastructure (Docker, API gateway, IdentityServer, Kafka), Ocelot aggregates microservices into a single entry point but doesn’t merge or expose a unified OpenAPI definition.

But what if we could do it, and give a single OpenAPI definition to Kiota generate a single client all at once?

That’s precisely the problem Koalesce solves. After looking for merging tools but not finding any that could do it seamlessly with .NET, I created Koalesce, a lightweight open-source .NET library designed to merge multiple OpenAPI documents into one.

 Putting It All Together

  • Each microservice holds its own OpenAPI definition.
  • Koalesce merges them into a single spec based on the API Gateway (only services we expose to the outside world, North-South).
  • Kiota generates TypeScript (frontend) and C# (backend) SDK clients from the merged spec.
  • Backend leverage Kiota for service-to-service calls (no Gateway here, East-West).
  • Frontend views directly consume API endpoints via the Gateway’s Kiota clients.


Hands-on


Generating a Single OpenAPI Definition with Koalesce

According to its README file, Koalesce simply needs URIs for OpenAPI specs, typically configured in appsettings.json:


With Koalesce, you can merge OpenAPI definitions in two ways:

Middleware approach (dynamic merge)

Add the Koalesce middleware to your .NET application pipeline (e.g., Program.cs) to expose a merged document on-the-fly at runtime.

✅ Pros

  • Always up-to-date; changes reflect immediately.
  • Speeds development; no manual regen or CI/CD needed.

❌ Cons

  • Dependent on live services; failure in a microservice skips its definition.
  • Can slow startup and Swagger load times.
  • Misalignments between microservice specs (e.g. incompatible OpenAPI versions) can cause runtime errors.
CLI (Command Line Interface) approach

Use the Koalesce.OpenAPI.CLI tool to output a .json or .yaml file containing the merged spec on the hard drive.

✅ Pros

  • Because you run it manually, and when you know the services are available, the risk of runtime merging failure is reduced.
  • Once merged, the single spec can be served without depending on microservices being online (great for CI/CD or sandbox environments).

❌ Cons

  • Requires explicit regeneration on API changes.
  • Risk of stale specs without automation.


My Approach to the EcommerceDDD project

I always tested endpoints before having a UI, either relying on Swagger UI/or using Postman. While developing the EcommerceDDD, I used Koalesce to merge the API Gateway endpoints I wanted to expose for front-end consumption. Also, having these services displayed and accessible from a single Swagger UI proved really handy. I let the API Gateway leverage hosting the single definition through using the Middleware approach by installing the Koalesce.OpenAPI nuget package in the EcommerceDDD.ApiGateway itself, and adding Koalesce to its execution pipeline in Program.cs like this:

Middleware (for API Gateway in active development):
1
2
3
4
5
6
7
8
9
10
11
12
// Register Koalesce
services.AddKoalesce(builder.Configuration)
 .ForOpenAPI();
 ...
 // Enable Koalesce before Swagger Middleware
app.UseKoalesce();
...
// Enable Swagger UI
app.UseSwaggerUI(c =>
{
   c.SwaggerEndpoint(koalesceOptions.MergedOpenApiPath, koalesceOptions.Title);
});

Then, the ApiGateway now exposes a Swagger UI at http://localhost:5000/swagger/index.html like this:

Pretty cool, right? And since the frontend only knows the Gateway server URI, generating frontend Kiota typescript clients in the SPA itself was a one-liner command:

Install Kiota as .NET tool
1
dotnet tool install --global Microsoft.OpenApi.Kiota
Generate Kiota client from the API Gateway OpenAPI definition
1
kiota generate --openapi http://localhost:5000/swagger/v2/apigateway.yaml --language TypeScript --output ./src/app/clients


Final Thoughts


Automated API clients using Kiota provide clear maintainability, reliability, and developer experience benefits. Though relatively new, Kiota elegantly solves API consumption with an opinionated, focused approach, reducing complexity and enhancing community adoption.

As for Koalesce, merging multiple OpenAPI definitions into a monolithic-style client—as I’ve done—only makes sense depending on your project’s complexity, scale, and CI/CD pipeline. It’s not a one-size-fits-all solution, but for EcommerceDDD, it proved to be a great fit.

I’m still experimenting with this approach, and Koalesce remains under active development. That said, it’s already been valuable in streamlining my workflow, and I hope it proves useful to others as well. The project is open to feedback and contributions.

If you’re interested, you can find both projects here:

Thanks for reading — see you in the next post!




This post is licensed under CC BY 4.0 by the author.