.NET Core Microservices - Ocelot API Gateway

In this article, we will examine the open source Ocelot API Gateway library, which takes the responsibility of forwarding the coming request from the client to the relevant services.


r3.PNG

1 - Ocelot creates HttpRequestMessage and HttpRequestMessage objects. The HttpRequest object created as a result of the request is assigned to the HttpRequestMessage object. The HttpRequestMessage object is delivered to the relevant services.


2 - The HttpRequestMessage object returned from the services is assigned to the HttpResponse object. So that in this way, in the pipeline (middleware), the HttpResponse object is returned to the client.



r1.PNG

r2.PNG

Let's create ProductAPI, CustomerAPI and GatewayAPI


- Open Visual Studio 2019 Community


- Create a new project then select the "ASP.NET Core Web Application" option.


- Name the project name as ProductAPI.


r5.PNG

r4.PNG

- Create a new api controller named ProductController


r6.PNG

using Microsoft.AspNetCore.Mvc;
using System.Collections.Generic;

namespace ProductAPI.Controllers
{
    [Route("api/[controller]")]
    [ApiController]
    public class ProductController : ControllerBase
    {
        public IActionResult Get()
        {
            return Ok(new List { "Book", "Notebook", "Pencil", "Pen" });
        }
    }
}

Then since this project will be worked on locally, let's define a suitable port in the launchSettings.json.


"ProductAPI": {
  "commandName": "Project",
  "launchBrowser": true,
  "launchUrl": "weatherforecast",
  "applicationUrl": "https://localhost:5001;http://localhost:5000",
  "environmentVariables": {
    "ASPNETCORE_ENVIRONMENT": "Development"
  }
}

In the same solution, create a new API named CustomerAPI.


r7.PNG

- Create a new api controller named CustomerController


using Microsoft.AspNetCore.Mvc;
using System.Collections.Generic;

namespace CustomerAPI.Controllers
{
    [Route("api/[controller]")]
    [ApiController]
    public class CustomerController : ControllerBase
    {
        public IActionResult Get()
        {
            return Ok(new List { "Mike Anderson", "Rick Wasson", "Tom Donald" });
        }
    }
}

- Define a suitable port in the launchSettings.json.


"CustomerAPI": {
  "commandName": "Project",
  "launchBrowser": true,
  "launchUrl": "weatherforecast",
  "applicationUrl": "https://localhost:5003;http://localhost:5002",
  "environmentVariables": {
    "ASPNETCORE_ENVIRONMENT": "Development"
  }
}

Microservices are ready. Let's implement the api gateway project that will be able to meet the coming requests from the clients and direct them tot the relevant services ( ProductAPI and CustomerAPI ).


- Create a new api controller named GatewayAPI



r8.PNG

- Define a suitable port in the launchSettings.json.


"GatewayAPI": {
  "commandName": "Project",
  "launchBrowser": true,
  "launchUrl": "weatherforecast",
  "applicationUrl": "https://localhost:5005;http://localhost:5004",
  "environmentVariables": {
    "ASPNETCORE_ENVIRONMENT": "Development"
  }
}

Let's install the Ocelot library in the GatewayAPI project as shown below.


r9.PNG

- Create a json file name ocelot.json in the GatewayAPI.


r10.PNG

{
  "Routes": [
    {
      "DownstreamPathTemplate": "/api/customer",
      "DownstreamScheme": "https",
      "DownstreamHostAndPorts": [
        {
          "Host": "localhost",
          "Port": 5003
        }
      ],
      "UpstreamPathTemplate": "/api/gateway/customer",
      "UpstreamHttpMethod": [ "Get" ],
      "DangerousAcceptAnyServerCertificateValidator": true
    },
    {
      "DownstreamPathTemplate": "/api/product",
      "DownstreamScheme": "https",
      "DownstreamHostAndPorts": [
        {
          "Host": "localhost",
          "Port": 5001
        }
      ],
      "UpstreamPathTemplate": "/api/gateway/product",
      "UpstreamHttpMethod": [ "Get" ],
      "DangerousAcceptAnyServerCertificateValidator": true
    }
  ],
  "GlobalConfiguration": {
    "BaseUrl": "https://localhost:5005"
  }
}



As you can see above, GlobalConfiguration > BaseUrl is the base url to access microservices through the Ocelot library.


The Routes array;


- DownstreamPathTemplate : The route of the microservice to be directed. (Ex: CustomerAPI).


- UpstreamPathTemplate : The route to the microservice via API Gateway.


- Set "DangerousAcceptAnyServerCertificateValidator": true, if you want to ignore SSL validation. ( ONLY FOR TEST )




- Modify the Program.cs file in the GatewayAPI project as follows.


public class Program
{
    public static void Main(string[] args)
    {
        CreateHostBuilder(args).Build().Run();
    }

    public static IHostBuilder CreateHostBuilder(string[] args) =>
        Host.CreateDefaultBuilder(args)
            .ConfigureAppConfiguration((hosting, config) =>
            {
                config.AddJsonFile("ocelot.json", false, true);
            })
            .ConfigureWebHostDefaults(webBuilder =>
            {
                webBuilder.UseStartup<Startup>();
            });
}

- Modify the Startup cs file in the GatewayAPI project as follows.


public void ConfigureServices(IServiceCollection services)
{
    services.AddOcelot();
    .
	.
	.
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    app.UseOcelot();

    .
	.
	.
}

Output :


r11.PNG
r12.PNG

Parameter Routing


{
   "DownstreamPathTemplate": "/api/product/{id}",
   "DownstreamScheme": "https",
   "DownstreamHostAndPorts": [
       {
           "Host": "localhost",
           "Port": 5001
       }
   ],
   "UpstreamPathTemplate": "/api/gateway/product/{id}",
   "UpstreamHttpMethod": [ "Get" ]
}

The request to https://localhost:5005/api/gateway/product/1 will be redirected to https://localhost:5001/api/product/1.


Capturing All Requests

{
    "DownstreamPathTemplate": "/{url}",
    "DownstreamScheme": "https",
    "DownstreamHostAndPorts": [
            {
                "Host": "localhost",
                "Port": 5001
            }
        ],
    "UpstreamPathTemplate": "/p/{url}",
    "UpstreamHttpMethod": [ "Get" ]
}

The request to https://localhost:5005/p/api/product will be redirected to https://localhost:5001/api/product.


tags : Ocelot,API Gateway .NET Core

Download the source code.