Esercizio - Usare una libreria JavaScript in un'app Blazor

Completato

Dopo che un cliente aggiunge una pizza all’ordine, può selezionare l’icona X per rimuovere la pizza dall'ordine senza conferma. Per evitare che i clienti rimuovano accidentalmente le pizze dagli ordini, l'azienda di pizze vuole che si aggiunga una richiesta di conferma per la rimozione degli articoli.

Inoltre, l'azienda di pizza vuole che i clienti vedano in tempo reale l'avanzamento dell’ordine. È necessario aggiornare la pagina dei dettagli dell'ordine per eseguire query sullo stato dell'ordine e fornire ai clienti feedback sullo stato di aggiornamento della pagina.

In questo esercizio, usando l'interoperabilità JS di un componente Blazor per chiamare JavaScript sul lato client estenderemo l'app esistente dell’azienda di pizze a domicilio. Verrà eseguita l’integrazione a una libreria JavaScript di terze parti per migliorare la finestra popup di annullamento e verrà chiamato n metodo Blazor da JavaScript per ottenere lo stato di un ordine del cliente in tempo reale.

Clonare l’app esistente

Per usare Blazor, assicurarsi di avere installato .NET 8.0 SDK. Per altre informazioni, vedere Controllare che tutti gli elementi siano stati installati correttamente.

  1. Aprire Visual Studio Code e aprire un terminale integrato selezionando Terminale>Nuovo terminale nel menu principale.

  2. Nel terminale, passare alla directory in cui si vuole creare il progetto.

  3. Eseguire il seguente comando per clonare l'app da GitHub a una sottodirectory locale.

    git clone https://github.com/MicrosoftDocs/mslearn-build-interactive-components-blazor.git BlazingPizza
    
  4. Nella barra del menu in alto selezionare File>Apri cartella.

  5. Nella finestra di dialogo Apri cartella, passare alla cartella BlazingPizza e selezionare Seleziona cartella.

    Se Visual Studio Code richiede asset che mancano o dipendenze non risolte, selezionare o Ripristina.

  6. Per eseguire l'app e verificare che tutto funzioni correttamente, premere F5 o selezionare Esegui>Avvia debug.

  7. Nell'app Web selezionare delle pizza e aggiungerle all'ordine. Nell'elenco degli ordini, con diverse pizze presenti, selezionare la X accanto a una delle pizze e verificare che l'elemento scompaia senza generare alcuna richiesta.

  8. Premere MAIUSC+F5 o selezionare Esegui>Arresta debug per arrestare l'app.

Effettuare il refactoring del processo di ordine

Per usare l'interoperabilità JS, inserire l'astrazione IJSRuntime.

  1. In Visual Studio Code Esplora risorse, espandere Pages e quindi selezionare Index.razor.

  2. Nel file Index.razor, dopo l’istruzione @inject OrderState OrderState, aggiungere l’inserimento IJSRuntime come indicato di seguito.

    @inject OrderState OrderState
    @inject IJSRuntime JavaScript
    
  3. Al momento, l’evento onclick per la funzionalità di rimozione della pizza chiama il metodo OrderState.RemoveConfiguredPizza(configuredPizza)) direttamente. Sostituire l'intero elemento <a @onclick="@(() => OrderState.RemoveConfiguredPizza(configuredPizza))" class="delete-item">❌</a> con il codice seguente:

    <button type="button" class="close text-danger" aria-label="Close"
         @onclick="@(async () => await RemovePizzaConfirmation(configuredPizza))">
         <span aria-hidden="true">&times;</span>
    </button>
    
  4. Nella direttiva @code alla fine del file, aggiungere un nuovo metodo per chiamare la funzione JavaScript confirm nativa. Se il cliente seleziona OK dal prompt, il metodo chiama OrderState.RemoveConfiguredPizza per rimuovere la pizza dall'ordine. In caso contrario, la pizza rimane nell'ordine.

    async Task RemovePizzaConfirmation(Pizza removePizza)
    {
        if (await JavaScript.InvokeAsync<bool>(
            "confirm",
            $"""Do you want to remove the "{removePizza.Special!.Name}" from your order?"""))
        {
            OrderState.RemoveConfiguredPizza(removePizza);
        }
    }
    

    Il server usa il metodo IJSRuntime.InvokeAsync per chiamare la funzione confirm sul lato client. La risposta dalla chiamata restituisce un valore bool. Se il risultato della finestra di dialogo di conferma è true, la pizza viene rimossa dall'ordine.

  5. Premere F5 o selezionare Esegui>Avvia debug.

  6. Aggiungere delle pizza all'ordine nell’app.

  7. Con alcune pizza nell'ordine, selezionare la X accanto a una delle pizza. Viene visualizzata una finestra di dialogo di conferma standard di JavaScript.

    Screenshot of the default JavaScript confirm dialog.

  8. Selezionare OK e verificare che la pizza venga rimossa dall'ordine. Selezionare X accanto a un'altra pizza, selezionare Annulla nella finestra di dialogo di conferma e verificare che la pizza rimanga nell'ordine.

  9. Premere MAIUSC+F5 o selezionare Esegui>Arresta debug per arrestare l'app.

Aggiungere una libreria JavaScript di terze parti a un'app Blazor

L'azienda di pizze vuole migliorare la chiarezza del testo presente sui pulsanti della finestra di dialogo di conferma. Inoltre, vuole incorporare il proprio marchio distintivo e aderire allo stile aziendale all'interno di questa finestra di dialogo. Dopo aver eseguito alcune ricerche, si è deciso di utilizzare una piccola libreria JavaScript chiamata SweetAlert. Questa opzione si presenta come un valido sostituto della finestra di dialogo standard.

  1. In Visual Studio Code Esplora risorse, espandere Pages e quindi selezionare _Host.cshtml.

  2. Alla fine del file _Host.cshtml, dopo la riga <script src="_framework/blazor.server.js"></script> ma prima della riga </body>, aggiungere l'elemento script seguente per includere la libreria SweetAlert.

    <script src="https://cdn.jsdelivr.net/npm/sweetalert@latest/dist/sweetalert.min.js"></script>
    

    La libreria SweetAlert è ora disponibile per chiamare sul lato client.

  3. Per usare la nuova libreria, aggiornare il metodo RemovePizzaConfirmation nel file Index.razor come indicato di seguito.

    async Task RemovePizzaConfirmation(Pizza removePizza)
    {
        var messageParams = new
        {
            title = "Remove Pizza?",
            text = $"""Do you want to remove the "{removePizza.Special!.Name}" from your order?""",
            icon = "warning",
            buttons = new
            {
                abort = new { text = "No, leave it in my order", value = false },
                confirm = new { text = "Yes, remove pizza", value = true }
            },
            dangerMode = true
        };
    
        if (await JavaScript.InvokeAsync<bool>("swal", messageParams))
        {
            OrderState.RemoveConfiguredPizza(removePizza);
        }
    }
    

    Il nome "swal" è l'identificatore per la funzione JavaScript proveniente dal riferimento sweetalert.js di terze parti. Il codice per chiamare la funzione swal è simile a confirm. La maggior parte dell'aggiornamento riguarda il modo in cui la funzione riceve i parametri. SweetAlert accetta un oggetto JSON che include tutte le impostazioni necessarie.

  4. In Visual Studio Code, premere F5 o selezionare Esegui>Avvia debug.

  5. Verificare che la finestra di dialogo confirm ora abbia due pulsanti che indicano No, lascia nell’ordine e Sì, rimuovi pizza e che funzionino come previsto.

    Screenshot showing the SweetAlert dialog box.

  6. Premere MAIUSC+F5 o selezionare Esegui>Arresta debug per arrestare l'app.

Aggiornare la pagina dell'ordine per mostrare lo stato dell'ordine in tempo reale

Quando un cliente effettua un ordine per una pizza, la pagina Ordini personali usa il componente OrderDetail per mostrare lo stato corrente dell'ordine. L’azienda di pizze vuole che i clienti vedano in tempo reale l'avanzamento dell’ordine. Il componente viene aggiornato per richiamare un metodo .NET da JavaScript che ottiene in modo continuo lo stato dell'ordine fino a quando non viene visualizzato lo stato di consegna.

  1. In Visual Studio Code Esplora risorse, espandere Pages e quindi selezionare OrderDetail.razor.

  2. Nel file OrderDetail.razor, aggiungere la dichiarazione seguente nella parte superiore del componente, nell'ultima istruzione @inject.

    @implements IDisposable
    

    La dichiarazione @implements consente di definire un metodo Dispose.

  3. Aggiungete una rotellina alla pagina per fornire al cliente feedback sullo stato di aggiornamento della pagina. In <div class="track-order-details">, sopra l'istruzione @foreach aggiungere il seguente codice:

    @if (IsOrderIncomplete)
    {
        <div class="spinner-grow text-danger float-right" role="status">
            <span class="sr-only">Checking your order status...</span>
        </div>
    }
    
  4. Nella direttiva @code, nella dichiarazione di proprietà OrderId, aggiungere i seguenti membri.

    bool IsOrderIncomplete =>
        orderWithStatus is null || orderWithStatus.IsDelivered == false;
    
    PeriodicTimer timer = new(TimeSpan.FromSeconds(3));
    
  5. Sostituire il metodo OnParametersSetAsync esistente con il codice seguente:

    protected override async Task OnParametersSetAsync() =>
        await GetLatestOrderStatusUpdatesAsync();
    

    Il codice ora chiama il metodo GetLatestOrderStatusUpdatesAsync per aggiornare lo stato dell'ordine.

  6. Aggiungere i seguenti metodi dopo il metodo OnParametersSetAsync aggiornato.

    protected override Task OnAfterRenderAsync(bool firstRender) =>
        firstRender ? StartPollingTimerAsync() : Task.CompletedTask;
    
    async Task GetLatestOrderStatusUpdatesAsync()
    {
        try
        {
            orderWithStatus = await HttpClient.GetFromJsonAsync<OrderWithStatus>(
                $"{NavigationManager.BaseUri}orders/{OrderId}");
        }
        catch (Exception ex)
        {
            invalidOrder = true;
            Console.Error.WriteLine(ex);
        }
    }
    
    async Task StartPollingTimerAsync()
    {
        while (IsOrderIncomplete && await timer.WaitForNextTickAsync())
        {
            await GetLatestOrderStatusUpdatesAsync();
            StateHasChanged();
        }
    }
    
    public void Dispose() => timer.Dispose();
    

    Il componente OrderDetail inizia il polling dopo il rendering della pagina e lo arresta quando l'ordine viene recapitato. Mentre lo stato dell'ordine è incompleto, la funzione StartPollingTimerAsync usa un PeriodicTimer per attendere in modo asincrono il tick successivo. Quando l'ordine viene recapitato, la rotellina animata viene rimossa e la pagina mostra lo stato finale dell'ordine.

  7. In Visual Studio Code, premere F5 o selezionare Esegui>Avvia debug.

  8. Ordinare una pizza nell’app. Passare alla schermata Ordini personali e verificare che il punto rosso animato venga visualizzato quando l'ordine è incompleto e scompare quando lo stato indica Recapitato.

    Animation showing the order status changing in real-time.

  9. Premere MAIUSC+F5 o selezionare Esegui>Arresta debug per arrestare l'app.