Aangepaste resource-opdrachten in .NET.NET Aspire
Elke resource in het .NET.NET Aspireapp-model wordt weergegeven als een IResource en wanneer deze wordt toegevoegd aan de gedistribueerde toepassingsbouwer, is dit de algemene parameter van de IResourceBuilder<T>-interface. U gebruikt de hulpbronbouwer API om aanroepen te koppelen, de onderliggende hulpbron te configureren, en in sommige situaties wilt u misschien aangepaste opdrachten toevoegen aan de hulpbron. Sommige veelvoorkomende scenario's voor het maken van een aangepaste opdracht kunnen databasemigraties uitvoeren of een database seeden/opnieuw instellen. In dit artikel leert u hoe u een aangepaste opdracht toevoegt aan een Redis resource waarmee de cache wordt gewist.
Belangrijk
Deze .NET.NET Aspire dashboard opdrachten zijn alleen beschikbaar wanneer het dashboard lokaal wordt uitgevoerd. Ze zijn niet beschikbaar bij het uitvoeren van het dashboard in Azure Container Apps.
Aangepaste opdrachten toevoegen aan een resource
Begin met het maken van een nieuwe .NET.NET Aspire Starter-app op basis van de beschikbare sjablonen. Als u de oplossing op basis van deze sjabloon wilt maken, volgt u de Quickstart: Uw eerste .NET.NET Aspire-oplossing bouwen. Nadat u deze oplossing hebt gemaakt, voegt u een nieuwe klasse met de naam RedisResourceBuilderExtensions.cs toe aan het app-hostproject. Vervang de inhoud van het bestand door de volgende code:
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Diagnostics.HealthChecks;
using Microsoft.Extensions.Logging;
using StackExchange.Redis;
namespace Aspire.Hosting;
internal static class RedisResourceBuilderExtensions
{
public static IResourceBuilder<RedisResource> WithClearCommand(
this IResourceBuilder<RedisResource> builder)
{
builder.WithCommand(
name: "clear-cache",
displayName: "Clear Cache",
executeCommand: context => OnRunClearCacheCommandAsync(builder, context),
updateState: OnUpdateResourceState,
iconName: "AnimalRabbitOff",
iconVariant: IconVariant.Filled);
return builder;
}
private static async Task<ExecuteCommandResult> OnRunClearCacheCommandAsync(
IResourceBuilder<RedisResource> builder,
ExecuteCommandContext context)
{
var connectionString = await builder.Resource.GetConnectionStringAsync() ??
throw new InvalidOperationException(
$"Unable to get the '{context.ResourceName}' connection string.");
await using var connection = ConnectionMultiplexer.Connect(connectionString);
var database = connection.GetDatabase();
await database.ExecuteAsync("FLUSHALL");
return CommandResults.Success();
}
private static ResourceCommandState OnUpdateResourceState(
UpdateCommandStateContext context)
{
var logger = context.ServiceProvider.GetRequiredService<ILogger<Program>>();
if (logger.IsEnabled(LogLevel.Information))
{
logger.LogInformation(
"Updating resource state: {ResourceSnapshot}",
context.ResourceSnapshot);
}
return context.ResourceSnapshot.HealthStatus is HealthStatus.Healthy
? ResourceCommandState.Enabled
: ResourceCommandState.Disabled;
}
}
De voorgaande code:
- Deelt de Aspire.Hosting naamruimte zodat deze zichtbaar is voor het app-hostproject.
- Is een
static class
zodat hij uitbreidingsmethoden kan bevatten. - Hiermee definieert u één extensiemethode met de naam
WithClearCommand
, waarmee deIResourceBuilder<RedisResource>
-interface wordt uitgebreid. - De methode
WithClearCommand
registreert een opdracht met de naamclear-cache
waarmee de cache van de Redis-resource wordt gewist. - De methode
WithClearCommand
geeft hetIResourceBuilder<RedisResource>
exemplaar terug, waardoor methodenketting mogelijk is.
De WithCommand
-API voegt de juiste aantekeningen toe aan de resource, die worden gebruikt in het .NET.NET Aspire dashboard. Het dashboard gebruikt deze aantekeningen om de opdracht weer te geven in de gebruikersinterface. Voordat u deze details te ver gaat, moet u ervoor zorgen dat u eerst de parameters van de methode WithCommand
begrijpt:
-
name
: de naam van de opdracht die moet worden aangeroepen. -
displayName
: de naam van de opdracht die moet worden weergegeven in het dashboard. -
executeCommand
: deFunc<ExecuteCommandContext, Task<ExecuteCommandResult>>
die moet worden uitgevoerd wanneer de opdracht wordt aangeroepen, waar de opdrachtlogica wordt geïmplementeerd. -
updateState
: deFunc<UpdateCommandStateContext, ResourceCommandState>
callback wordt aangeroepen om de status Ingeschakeld van de opdracht te bepalen, die wordt gebruikt om de opdracht in of uit te schakelen in het dashboard. -
iconName
: de naam van het pictogram dat moet worden weergegeven in het dashboard. Het pictogram is optioneel, maar wanneer u het opgeeft, moet het een geldige Fluent UI zijn Blazor pictogramnaam. -
iconVariant
: de variant van het pictogram dat in het dashboard moet worden weergegeven, zijn geldige optiesRegular
(standaard) ofFilled
.
Opdrachtlogica uitvoeren
De executeCommand
delegate is waar de commando-logica wordt geïmplementeerd. Deze parameter wordt gedefinieerd als een Func<ExecuteCommandContext, Task<ExecuteCommandResult>>
. De ExecuteCommandContext
biedt de volgende eigenschappen:
-
ExecuteCommandContext.ServiceProvider
: hetIServiceProvider
exemplaar dat wordt gebruikt om services op te lossen. -
ExecuteCommandContext.ResourceName
: de naam van het resource-exemplaar waarop de opdracht wordt uitgevoerd. -
ExecuteCommandContext.CancellationToken
: de CancellationToken die wordt gebruikt om de uitvoering van de opdracht te annuleren.
In het vorige voorbeeld wordt de executeCommand
delegate geïmplementeerd als een async
methode waarmee de cache van de Redis bron wordt gewist. Het delegeert naar een privé-functie binnen de klasse met de naam OnRunClearCacheCommandAsync
om de werkelijke cache-opruiming uit te voeren. Houd rekening met de volgende code:
private static async Task<ExecuteCommandResult> OnRunClearCacheCommandAsync(
IResourceBuilder<RedisResource> builder,
ExecuteCommandContext context)
{
var connectionString = await builder.Resource.GetConnectionStringAsync() ??
throw new InvalidOperationException(
$"Unable to get the '{context.ResourceName}' connection string.");
await using var connection = ConnectionMultiplexer.Connect(connectionString);
var database = connection.GetDatabase();
await database.ExecuteAsync("FLUSHALL");
return CommandResults.Success();
}
De voorgaande code:
- Haalt de verbindingsreeks op uit de Redis resource.
- Maakt verbinding met het Redis-exemplaar.
- Hiermee haalt u het database-exemplaar op.
- Hiermee wordt de opdracht
FLUSHALL
uitgevoerd om de cache te wissen. - Retourneert een
CommandResults.Success()
exemplaar om aan te geven dat de opdracht is geslaagd.
Opdrachtstatuslogica bijwerken
De updateState
-delegaat is de plaats waar de opdrachtstatus wordt bepaald. Deze parameter wordt gedefinieerd als een Func<UpdateCommandStateContext, ResourceCommandState>
. De UpdateCommandStateContext
biedt de volgende eigenschappen:
-
UpdateCommandStateContext.ServiceProvider
: hetIServiceProvider
exemplaar dat wordt gebruikt om services op te lossen. -
UpdateCommandStateContext.ResourceSnapshot
: de momentopname van het resource-exemplaar waarop de opdracht wordt uitgevoerd.
De onveranderbare momentopname is een exemplaar van CustomResourceSnapshot
, waarmee allerlei waardevolle details over het resource-exemplaar worden weergegeven. Houd rekening met de volgende code:
private static ResourceCommandState OnUpdateResourceState(
UpdateCommandStateContext context)
{
var logger = context.ServiceProvider.GetRequiredService<ILogger<Program>>();
if (logger.IsEnabled(LogLevel.Information))
{
logger.LogInformation(
"Updating resource state: {ResourceSnapshot}",
context.ResourceSnapshot);
}
return context.ResourceSnapshot.HealthStatus is HealthStatus.Healthy
? ResourceCommandState.Enabled
: ResourceCommandState.Disabled;
}
De voorgaande code:
- Haalt de logger-instantie van de serviceprovider op.
- Registreert de details van de momentopname van de resource.
- Retourneert
ResourceCommandState.Enabled
als de resource in orde is; anders wordtResourceCommandState.Disabled
geretourneerd.
De aangepaste opdracht testen
Als u de aangepaste opdracht wilt testen, werkt u het Program.cs-bestand van uw app-hostproject bij met de volgende code:
var builder = DistributedApplication.CreateBuilder(args);
var cache = builder.AddRedis("cache")
.WithClearCommand();
var apiService = builder.AddProject<Projects.AspireApp_ApiService>("apiservice");
builder.AddProject<Projects.AspireApp_Web>("webfrontend")
.WithExternalHttpEndpoints()
.WithReference(cache)
.WaitFor(cache)
.WithReference(apiService)
.WaitFor(apiService);
builder.Build().Run();
Met de voorgaande code wordt de WithClearCommand
-extensiemethode aangeroepen om de aangepaste opdracht toe te voegen aan de Redis resource. Voer de app uit en navigeer naar het .NET.NET Aspire dashboard. De aangepaste opdracht wordt weergegeven onder de Redis resource. Selecteer op de pagina Resources van het dashboard het beletselteken onder de kolom Acties:
In de voorgaande afbeelding ziet u de opdracht Cache wissen die is toegevoegd aan de Redis-resource. Het pictogram toont een doorgekruist konijn, wat aangeeft dat de snelheid van de afhankelijke bron wordt gewist.
Selecteer de opdracht Cache wissen om de cache van het Redis hulpmiddel te wissen. De opdracht moet worden uitgevoerd en de cache moet worden gewist: