Esercizio - Leggere e scrivere nei file

Completato

È anche possibile usare la classe File in .NET per scrivere i dati nei file e leggere i dati dai file.

Lo straordinario programma .NET per Tailwind Traders è quasi pronto. Fino ad ora, il codice può leggere il contenuto di qualsiasi directory, trovare tutti i file con estensione json e creare un file totals.txt.

In questo esercizio il progetto viene completato leggendo i file con estensione json, aggiungendo i totali dei negozi e scrivendo il totale complessivo nel file totals.txt.

Aggiungere System.Text.Json al progetto

  1. Usando il terminale, aggiungere Json.NET al progetto.

    dotnet add package System.Text.Json
    

Preparati per i dati sulle vendite

  1. All'inizio di Program.cs aggiungere using Newtonsoft.Json:

    using System.Text.Json;
    
  2. In Program.cs direttamente sotto il metodo FindFilesaggiungere un nuovo elemento record che modellerà i dati di sales.json:

    record SalesData (double Total);
    

Creare un metodo per calcolare il totale delle vendite

  1. In Program.cs, appena prima della riga record aggiunta nel passaggio precedente, creare una nuova funzione che calcolerà il totale delle vendite. Questo metodo deve accettare un oggetto IEnumerable<string> di percorsi di file da scorrere.

    double CalculateSalesTotal(IEnumerable<string> salesFiles)
    {
        double salesTotal = 0;
    
        // READ FILES LOOP
    
        return salesTotal;
    }
    
  2. All'interno del metodo sostituire // READ FILES LOOP con un ciclo che scorre salesFiles, legge il file, analizza il contenuto come JSON e quindi incrementa la variabile salesTotal con il valore total del file:

    double CalculateSalesTotal(IEnumerable<string> salesFiles)
    {
        double salesTotal = 0;
    
        // Loop over each file path in salesFiles
        foreach (var file in salesFiles)
        {      
            // Read the contents of the file
            string salesJson = File.ReadAllText(file);
    
            // Parse the contents as JSON
            SalesData? data = JsonSerializer.Deserialize<SalesData?>(salesJson);
    
            // Add the amount found in the Total field to the salesTotal variable
            salesTotal += data?.Total ?? 0;
        }
    
        return salesTotal;
    }
    

Chiamare il metodo CalculateSalesTotals

  1. Nel file Program.cs aggiungere una chiamata alla funzione CalculateSalesTotal subito prima della chiamata di File.WriteAllText:

    var currentDirectory = Directory.GetCurrentDirectory();
    var storesDir = Path.Combine(currentDirectory, "stores");
    
    var salesTotalDir = Path.Combine(currentDirectory, "salesTotalDir");
    Directory.CreateDirectory(salesTotalDir);
    
    var salesFiles = FindFiles(storesDir);
    
    var salesTotal = CalculateSalesTotal(salesFiles); // Add this line of code
    
    File.WriteAllText(Path.Combine(salesTotalDir, "totals.txt"), String.Empty);
    

Scrivere il totale nel file totals.txt

  1. Nel file Program.cs modificare il blocco File.WriteAllText per scrivere il valore della variabile salesTotal nel file totals.txt. Nel frattempo, cambia anche la chiamata File.WriteAllText in File.AppendAllText in modo da non sovrascrivere alcun elemento nel file.

    var currentDirectory = Directory.GetCurrentDirectory();            
    var storesDir = Path.Combine(currentDirectory, "stores");
    
    var salesTotalDir = Path.Combine(currentDirectory, "salesTotalDir");
    Directory.CreateDirectory(salesTotalDir);            
    
    var salesFiles = FindFiles(storesDir);
    
    var salesTotal = CalculateSalesTotal(salesFiles);
    
    File.AppendAllText(Path.Combine(salesTotalDir, "totals.txt"), $"{salesTotal}{Environment.NewLine}");
    
  2. Premere CTRL+S / CMD+S per salvare il file Program.cs.

Eseguire il programma

  1. Eseguire il programma dal terminale:

    dotnet run
    

    Il programma non genera alcun output. Se si osserva il contenuto del file salesTotalDir/totals.txt, si vedrà il totale di tutte le vendite del file sales.json.

  2. Eseguire di nuovo il programma dal terminale.

    dotnet run
    
  3. Selezionare il file salesTotalDir/totals.txt.

    Il file totals.txt ha ora una seconda riga. Ogni volta che si esegue il programma, i totali vengono sommati di nuovo e viene scritta una nuova riga nel file.

Si è visto come creare uno strumento intelligente, affidabile e pratico che Tailwind Traders può usare per elaborare tutte le vendite dei negozi ogni notte. Nell'unità successiva verranno riepilogati i concetti appresi e proposti alcuni suggerimenti utili.

Se si riscontrano problemi

durante l'esecuzione di questo esercizio, di seguito è riportato il codice completo per questo progetto:

using Newtonsoft.Json; 

var currentDirectory = Directory.GetCurrentDirectory();
var storesDirectory = Path.Combine(currentDirectory, "stores");

var salesTotalDir = Path.Combine(currentDirectory, "salesTotalDir");
Directory.CreateDirectory(salesTotalDir);   

var salesFiles = FindFiles(storesDirectory);

var salesTotal = CalculateSalesTotal(salesFiles);

File.AppendAllText(Path.Combine(salesTotalDir, "totals.txt"), $"{salesTotal}{Environment.NewLine}");

IEnumerable<string> FindFiles(string folderName)
{
    List<string> salesFiles = new List<string>();

    var foundFiles = Directory.EnumerateFiles(folderName, "*", SearchOption.AllDirectories);

    foreach (var file in foundFiles)
    {
        var extension = Path.GetExtension(file);
        if (extension == ".json")
        {
            salesFiles.Add(file);
        }
    }

    return salesFiles;
}

double CalculateSalesTotal(IEnumerable<string> salesFiles)
{
    double salesTotal = 0;
    
    // Loop over each file path in salesFiles
    foreach (var file in salesFiles)
    {      
        // Read the contents of the file
        string salesJson = File.ReadAllText(file);
    
        // Parse the contents as JSON
        SalesData? data = JsonConvert.DeserializeObject<SalesData?>(salesJson);
    
        // Add the amount found in the Total field to the salesTotal variable
        salesTotal += data?.Total ?? 0;
    }
    
    return salesTotal;
}

record SalesData (double Total);