Generare file PDF da Blazor WebAssembly con iText

di Marco De Sanctis, in ASP.NET Core,

Nello scorso script (https://www.aspitalia.com/script/1456/Generare-File-Download-Blazor-WebAssembly.aspx) abbiamo visto come possiamo scatenare il download di un file da Blazor WebAssembly tramite un componente custom che abbiamo chiamato FileSaver. Questa tecnica può essere utile in una grande varietà di contesti, come per esempio la generazione al volo di file PDF per l'utente.

Come al solito, il primo passo è quello di aggiungere i corrispondenti pacchetti NuGet. Nel nostro caso useremo la libreria iText.

dotnet add package itext7
dotnet add package itext7.bouncy-castle-adapter

A questo punto abbiamo a disposizione un potente strumento per creare il contenuto di un file PDF direttamente in un MemoryStream. Modifichiamo allora la pagina FetchData per consentire il download di questo tipo di file:

@page "/fetchdata"
@using iText.Kernel.Colors;
@using iText.Kernel.Geom;
@using iText.Kernel.Pdf;
@using iText.Layout;
@using iText.Layout.Element;
@using iText.Layout.Properties;
@inject FileSaver FileSaver;

@* altro codice qui *@

<button class="btn btn-primary" @onclick="DownloadPdfStream">
    Download forecast data in Pdf
</button>

Con una tecnica del tutto analoga a quella del precedente script, possiamo iniziare a manipolare il modello a oggetti di iText per generare il file desiderato. Diamo innanzi tutto un'occhiata all'impostazione generale:

private async Task DownloadPdfStream()
{
    using var stream = new MemoryStream();
    var writer = new PdfWriter(stream);
    writer.SetCloseStream(false);

    var pdf = new PdfDocument(writer);

    var document = new Document(pdf, PageSize.A4);

    // ... qui codice che popola il document ...

    document.Close();

    stream.Position = 0;

    await this.FileSaver.SaveAsAsync("forecasts.pdf", stream);
}

Come possiamo notare, inizialmente costruiamo un MemoryStream che poi inviamo al corrispondente PdfWriter. Attenzione al fatto di impostare SetCloseStream a false, altrimenti questo oggetto chiuderà il MemoryStream in fase di flush dei contenuti, con il risultato da renderlo inaccessibile per il successivo download.

Successivamente, creiamo nell'ordine l'oggetto PdfDocument e finalmente il vero e proprio Document, che potremo poi popolare con il contenuto del forecast.

Una volta che il document è popolato correttamente, dobbiamo invocarne il metodo Close, così da salvare tutto il contenuto del buffer sullo stream, per poi inviarlo al nostro oggetto FileSaver che abbiamo costruito nel precedente script.

Il codice che popola il contenuto del document, è un po' tedioso, ma lo riportiamo per completezza:

// aggiungiamo un titolo alla pagina
document.Add(new Paragraph("Weather forecast")
            .SetTextAlignment(TextAlignment.CENTER)
            .SetFontSize(20));

// creiamo la tabella per i forecast
Table table = new Table(UnitValue.CreatePercentArray(4)).UseAllAvailableWidth();

// header
table.AddHeaderCell("Date");
table.AddHeaderCell("Temp. (C)");
table.AddHeaderCell("Temp. (F)");
table.AddHeaderCell("Summary");

// righe
foreach (var forecast in forecasts)
{
    table.AddCell(forecast.Date.ToShortDateString());
    table.AddCell(forecast.TemperatureC.ToString());
    table.AddCell(forecast.TemperatureF.ToString());
    table.AddCell(forecast.Summary);
}

document.Add(table);

Se abbiamo svolto i passaggi correttamente, il risultato sarà simile a quello in figura.


Attenzione a un aspetto importante: iText è disponibile gratuitamente come CommunityEdition, ma con licenza AGPLv3 (https://itextpdf.com/how-buy/AGPLv3-license), che tra le varie cose, obbliga a pubblicare il vostro progetto come open source. Alternativamente è possible acquistare una licenza commerciale.

Commenti

Visualizza/aggiungi commenti

| Condividi su: Twitter, Facebook, LinkedIn

Per inserire un commento, devi avere un account.

Fai il login e torna a questa pagina, oppure registrati alla nostra community.

Approfondimenti

I più letti di oggi