code-snippets/docs/dotnet/api-key-auth.md
Liam Pietralla a19c3bcff4
All checks were successful
Build, Test & Publish / Build (pull_request) Successful in 56s
Build, Test & Publish / Build and Publish Container Image (pull_request) Has been skipped
Build, Test & Publish / Deploy to Infrastructure (pull_request) Has been skipped
added api key auth docs
2025-02-18 08:52:04 +11:00

136 lines
3.5 KiB
Markdown

# API Key Auth
Simple API Key authentication is a great option when building public facing APIs without strict security requirements, but you would rather not leave open. Think syncs, long running jobs or other non-critical operations.
## Configuration
This example stores the ApiKey in the `appsettings.json` file. You can also store it in a database, environment variable, or any other configuration source.
::: code-group
```json[appsettings.json]
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
}
},
"AllowedHosts": "*",
"ApiKey": "ThisIsMySecretKey",
// ...
}
```
:::
## Filter
The logic for the api key authentication is a simple Authorization filter. It checks the `ApiKey` header against the configured value.
Start by storing the header name in a constants file or similar:
::: code-group
```csharp[Constants.cs]
namespace ApiKeyAuthDemo.Core
{
public static class Constants
{
public const string API_KEY_HEADER_NAME = "X-API-KEY";
}
}
```
:::
Then create the filter:
::: code-group
```csharp[ApiKeyAuthorizeAttribute.cs]
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.Filters;
namespace ApiKeyAuthDemo.Core.Filters
{
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)]
public class ApiKeyAuthorizeAttribute() : Attribute, IAuthorizationFilter
{
public void OnAuthorization(AuthorizationFilterContext context)
{
// Get the API key from the request headers
string? apiKeyValue = context.HttpContext.Request.Headers[Constants.API_KEY_HEADER_NAME];
// Get the API key from the configuration
IConfiguration configuration = context.HttpContext.RequestServices.GetRequiredService<IConfiguration>();
string? apiKey = configuration.GetValue<string>("ApiKey");
// Check if the API key is valid and set
if (apiKeyValue == null || apiKeyValue != apiKey)
{
context.Result = new UnauthorizedResult();
}
}
}
}
```
:::
## Usage
See below for example usage (on the second GET method):
::: code-group
```csharp[WeatherForecastController.cs]
using ApiKeyAuthDemo.Core.Filters;
using Microsoft.AspNetCore.Mvc;
namespace ApiKeyAuthDemo.Controllers;
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
private static readonly string[] Summaries = new[]
{
"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};
private readonly ILogger<WeatherForecastController> _logger;
public WeatherForecastController(ILogger<WeatherForecastController> logger)
{
_logger = logger;
}
[HttpGet]
public IEnumerable<WeatherForecast> Get()
{
return Enumerable.Range(1, 5).Select(index => new WeatherForecast
{
Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
TemperatureC = Random.Shared.Next(-20, 55),
Summary = Summaries[Random.Shared.Next(Summaries.Length)]
})
.ToArray();
}
[ApiKeyAuthorize]
[HttpGet("auth")]
public IEnumerable<WeatherForecast> GetAuth()
{
return Enumerable.Range(1, 5).Select(index => new WeatherForecast
{
Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
TemperatureC = Random.Shared.Next(-20, 55),
Summary = Summaries[Random.Shared.Next(Summaries.Length)]
})
.ToArray();
}
}
```
:::