Note
Access to this page requires authorization. You can try signing in or changing directories.
Access to this page requires authorization. You can try changing directories.
Cloud-native apps often require various types of scalable caching solutions to improve performance. Aspire integrations simplify the process of connecting to popular caching services such as Redis. In this article, you'll learn how to:
- Create a basic ASP.NET core app that is set up to use Aspire.
- Add Aspire integrations to connect to Redis and implement caching.
- Configure the Aspire integrations to meet specific requirements.
This article explores how to use two different types of ASP.NET Core caching using Aspire and Redis:
- Output caching: A configurable, extensible caching method for storing entire HTTP responses for future requests.
- Distributed caching: A cache shared by multiple app servers that allows you to cache specific pieces of data. A distributed cache is typically maintained as an external service to the app servers that access it and can improve the performance and scalability of an ASP.NET Core app.
Prerequisites
To work with Aspire, you need the following installed locally:
- .NET 8.0 or .NET 9.0.
- Starting with Aspire 9.4, .NET 10 Preview 5 or later is supported.
- An OCI compliant container runtime, such as:
- Docker Desktop or Podman. For more information, see Container runtime.
- An Integrated Developer Environment (IDE) or code editor, such as:
- Visual Studio 2022 version 17.9 or higher (Optional)
- Visual Studio Code (Optional)
- C# Dev Kit: Extension (Optional)
- JetBrains Rider with Aspire plugin (Optional)
For more information, see Aspire setup and tooling, and Aspire SDK.
Create the project
- At the top of Visual Studio, navigate to File > New > Project....
- In the dialog window, enter Aspire into the project template search box and select Aspire Starter Application. Choose Next.
- On the Configure your new project screen:
- Enter a Project name of AspireRedis.
- Leave the rest of the values at their defaults and select Next.
- On the Additional information screen:
- Make sure .NET 9.0 is selected.
- Uncheck Use Redis for caching. You will implement your own caching setup.
- Select Create.
Visual Studio creates a new Aspire solution that consists of the following projects:
- AspireRedis.Web - A Blazor UI project with default Aspire configurations.
- AspireRedis.ApiService - A Minimal API with default Aspire configurations that provides the frontend with data.
- AspireRedis.AppHost - An orchestrator project designed to connect and configure the different projects and services of your app.
- AspireRedis.ServiceDefaults - A Aspire shared project to manage configurations that are reused across the projects in your solution related to resilience, service discovery, and telemetry.
Configure the AppHost project
Add the 📦 Aspire.Hosting.Redis NuGet package to the
AspireRedis.AppHostproject:dotnet add package Aspire.Hosting.RedisFor more information, see dotnet add package or Manage package dependencies in .NET applications.
Update the Program.cs file of the
AspireRedis.AppHostproject to match the following code:var builder = DistributedApplication.CreateBuilder(args); var redis = builder.AddRedis("cache"); var apiservice = builder.AddProject<Projects.AspireRedis_ApiService>("apiservice") .WithReference(redis); builder.AddProject<Projects.AspireRedis_Web>("webfrontend") .WithExternalHttpEndpoints() .WithReference(apiservice) .WithReference(redis); builder.Build().Run();
The preceding code creates a local Redis container instance and configures the UI and API to use the instance automatically for both output and distributed caching. The code also configures communication between the frontend UI and the backend API using service discovery. With Aspire's implicit service discovery, setting up and managing service connections is streamlined for developer productivity. In the context of this tutorial, the feature simplifies how you connect to Redis.
Traditionally, you'd manually specify the Redis connection string in each project's appsettings.json file:
{
"ConnectionStrings": {
"cache": "localhost:6379"
}
}
Configuring connection string with this method, while functional, requires duplicating the connection string across multiple projects, which can be cumbersome and error-prone.
Configure the UI with output caching
Add the Aspire Stack Exchange Redis output caching integration packages to your
AspireRedis.Webapp:dotnet add package Aspire.StackExchange.Redis.OutputCachingIn the Program.cs file of the
AspireRedis.WebBlazor project, immediately after the linevar builder = WebApplication.CreateBuilder(args);, add a call to the AddRedisOutputCache extension method:builder.AddRedisOutputCache("cache");This method accomplishes the following tasks:
- Configures ASP.NET Core output caching to use a Redis instance with the specified connection name.
- Automatically enables corresponding health checks, logging, and telemetry.
Replace the contents of the Home.razor file of the
AspireRedis.WebBlazor project with the following:@page "/" @attribute [OutputCache(Duration = 10)] <PageTitle>Home</PageTitle> <h1>Hello, world!</h1> Welcome to your new app on @DateTime.NowThe integration include the
[OutputCache]attribute, which caches the entire rendered response. The page also include a call to@DateTime.Nowto help verify that the response is cached.
Configure the API with distributed caching
Add the Aspire Stack Exchange Redis distributed caching integration packages to your
AspireRedis.ApiServiceapp:dotnet add package Aspire.StackExchange.Redis.DistributedCachingTowards the top of the Program.cs file, add a call to AddRedisDistributedCache:
builder.AddRedisDistributedCache("cache");In the Program.cs file, add the following
usingstatements:using System.Text; using System.Text.Json; using Microsoft.Extensions.Caching.Distributed;In the Program.cs file, replace the existing
/weatherforecastendpoint code with the following:app.MapGet("/weatherforecast", async (IDistributedCache cache) => { var cachedForecast = await cache.GetAsync("forecast"); if (cachedForecast is null) { var summaries = new[] { "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching" }; var forecast = Enumerable.Range(1, 5).Select(index => new WeatherForecast ( DateOnly.FromDateTime(DateTime.Now.AddDays(index)), Random.Shared.Next(-20, 55), summaries[Random.Shared.Next(summaries.Length)] )) .ToArray(); await cache.SetAsync("forecast", Encoding.UTF8.GetBytes(JsonSerializer.Serialize(forecast)), new () { AbsoluteExpiration = DateTime.Now.AddSeconds(10) }); return forecast; } return JsonSerializer.Deserialize<IEnumerable<WeatherForecast>>(cachedForecast); }) .WithName("GetWeatherForecast");
Test the app locally
Test the caching behavior of your app using the following steps:
- Run the app using Visual Studio by pressing F5.
- If the Start Docker Desktop dialog appears, select Yes to start the service.
- The Aspire Dashboard loads in the browser and lists the UI and API projects.
Test the output cache:
- On the projects page, in the webfrontend row, click the
localhostlink in the Endpoints column to open the UI of your app. - The application will display the current time on the home page.
- Refresh the browser every few seconds to see the same page returned by output caching. After 10 seconds the cache expires and the page reloads with an updated time.
Test the distributed cache:
- Navigate to the Weather page on the Blazor UI to load a table of randomized weather data.
- Refresh the browser every few seconds to see the same weather data returned by output caching. After 10 seconds the cache expires and the page reloads with updated weather data.
Congratulations! You configured a ASP.NET Core app to use output and distributed caching with Aspire.