Κοινή χρήση μέσω


Κεφάλαιο 5: Δημιουργία και δημοσίευση ενός API Web στο Azure

Αφού εξασφαλιστεί ότι τα δεδομένα για την εφαρμογή τεχνικών πρέπει να προέρχονται από υπάρχοντα συστήματα μέσω ενός Web API, η Maria και η Kiana συνεργάζονται για να καθορίσουν ακριβώς ποιες πληροφορίες είναι απαραίτητες και σε ποια μορφή. Στη συνέχεια, η Kiana θα δημιουργήσει μια εφαρμογή web που θα εκθέτει το κατάλληλο Web API και θα φροντίζει ώστε να φιλοξενείται στο Azure. Η εφαρμογή μπορεί να συνδεθεί στο Azure από οποιοδήποτε σημείο και αν υπάρχει ασύρματη σύνδεση.

Καθορισμός των λειτουργιών Web API: Διαχείριση αποθέματος πεδίων

Η οθόνη Αναζήτηση στην ενότητα "Διαχείριση αποθέματος πεδίων" της εφαρμογής εμφανίζει μια λίστα με τα ανταλλακτικά για τα μπόιλερ και τα συστήματα κλιματισμού (αναφέρονται απλά ως ανταλλακτικά μπόιλερ). Η οθόνη Λεπτομέρειες επιτρέπει στον τεχνικό να δει περισσότερες πληροφορίες σχετικά με ένα επιλεγμένο ανταλλακτικό.

Στην υπάρχουσα βάση δεδομένων αποθέματος (με την ονομασία InventoryDB), οι πληροφορίες σχετικά με τα ανταλλακτικά υπάρχουν σε έναν μεμονωμένο πίνακα με το όνομα Εξαρτήματα μπόιλερ. Η Kiana καθορίζει ότι το Web API θα πρέπει να υποστηρίζει τα παρακάτω αιτήματα:

  • Αποκτήστε όλα τα ανταλλακτικά μπόιλερ.
  • Αποκτήστε τα στοιχεία ενός ανταλλακτικού με βάση το αναγνωριστικό ανταλλακτικού.

Καθορισμός των λειτουργιών Web API: Γνωσιακή βάση πεδίου

Στο υπάρχον σύστημα, η βάση δεδομένων της γνωσιακής βάσης (με το όνομα KnowledgeDB) περιέχει τρεις πίνακες που καταγράφουν και διαχειρίζονται τις σχέσεις μεταξύ συμβουλών, τεχνικών και ανταλλακτικών:

  • Συμβουλές οι οποίες περιέχουν τις λεπτομέρειες μιας συμβουλής. Κάθε συμβουλή περιγράφει μια σύνοψη μίας γραμμής που προσδιορίζει ένα συγκεκριμένο πρόβλημα (το θέμα) και μια πιο λεπτομερή επεξήγηση που περιγράφει τον τρόπο επίλυσης του προβλήματος (σώμα). Κάθε συμβουλή αναφέρεται επίσης σε ένα ανταλλακτικό και στον τεχνικό που κατέγραφε τη συμβουλή.
  • BoilerParts το οποίο περιέχει μια λίστα με τα ανταλλακτικά που αναφέρονται στις συμβουλές. Οι λεπτομέρειες των ανταλλακτικών αποθηκεύονται στον πίνακα BoilerParts στη βάση δεδομένων InventoryDB.
  • Μηχανικοί όπου παρατίθενται οι τεχνικοί που έχουν συντάξει κάθε συμβουλή.

Το τμήμα της γνωσιακής βάσης της εφαρμογής προς το παρόν περιέχει απλώς μια οθόνη συμβόλου κράτησης θέσης Πρόγραμμα περιήγησης. Η Maria θέλει να υλοποιήσει τις παρακάτω λειτουργίες:

  • Ο τεχνικός καθορίζει έναν όρο αναζήτησης στην οθόνη Αναζήτηση για να βρει όλες τις συμβουλές που αντιστοιχούν. Η αντιστοιχία μπορεί να είναι στο όνομα του ανταλλακτικού στο οποίο αναφέρεται η συμβουλή, στο κείμενο στο θέμα ή στο σώμα της συμβουλής ή στο όνομα ενός τεχνικού που είναι ειδικός σε ένα συγκεκριμένο τμήμα εξοπλισμού.

  • Όταν έχουν βρεθεί όλες οι συμβουλές που συμφωνούν, ο τεχνικός μπορεί να επιλέξει μια συμβουλή για να προβάλετε τις λεπτομέρειες της.

  • Ένας τεχνικός μπορεί επίσης να προσθέσει νέες συμβουλές στη γνωσιακή βάση, καθώς και να προσθέσει σημειώσεις και σχόλια στις υπάρχουσες συμβουλές.

    Η γνωσιακή βάση είναι μεγάλη και αναπτύσσεται και η υποβολή ερωτημάτων σε πολλούς πίνακες και στήλες μπορεί να περιλαμβάνει πολύπλοκη λογική που απαιτεί σημαντική υπολογιστική ισχύ. Για να μειώσει το φόρτο στο Web API, η Kiana αποφασίζει να χρησιμοποιήσει τη Γνωσιακή Αναζήτηση Azure για να παράσχει τη λειτουργικότητα της αναζήτησης, όπως περιγράφηκε παραπάνω. Για την υποστήριξη της εφαρμογής, η Kiana αποφασίζει ότι οι ακόλουθες λειτουργίες απαιτούνται από το Web API:

  • Εύρεση λεπτομερειών μιας συγκεκριμένης συμβουλής της γνωσιακής βάσης στον πίνακα Συμβουλές.

  • Ενημέρωση μιας υφιστάμενης συμβουλής γνωσιακής βάσης στον πίνακα Συμβουλές.

  • Προσθέστε μια νέα συμβουλή γνωσιακής βάσης στον πίνακα Συμβουλές, η οποία ενδέχεται να περιλαμβάνει επίσης την προσθήκη σειρών στους πίνακες BoilerParts και Μηχανικοί, εάν το συγκεκριμένο ανταλλακτικό ή ο τεχνικός δεν διαθέτει προς το παρόν σχετικές συμβουλές. Η ρουτίνα που εκτελεί πραγματικά τη λογική πίσω από την προσθήκη μιας νέας συμβουλής θα υλοποιηθεί ως εφαρμογή λογικής που καλείται από το Power Apps.

Καθορισμός των λειτουργιών Web API: προγραμματισμός

Ο προγραμματισμός συναντήσεων τεχνικών απαιτεί όχι μόνο την υποβολή ερωτημάτων, την προσθήκη και την κατάργηση των συναντήσεων, αλλά και την καταγραφή πληροφοριών σχετικά με τους πελάτες. Το υπάρχον σύστημα συναντήσεων καταγράφει αυτά τα δεδομένα σε τρεις πίνακες στη βάση δεδομένων SchedulesDB:

  • Συναντήσεις που περιλαμβάνει τις λεπτομέρειες κάθε συνάντησης, συμπεριλαμβανομένης της ημερομηνίας, της ώρας, του προβλήματος, των σημειώσεις και του τεχνικού που έχει ανατεθεί στην εργασία.
  • Πελάτες όπου περιλαμβάνονται οι λεπτομέρειες κάθε πελάτη, συμπεριλαμβανομένου του ονόματος, της διεύθυνσης και των στοιχείων επικοινωνίας του.
  • Μηχανικοί, όπου παρατίθεται κάθε τεχνικός που παρακολουθεί τις συναντήσεις.

Σημείωση

Η βάση δεδομένων περιέχει ουσιαστικά έναν τέταρτο πίνακα με το όνομα AppointmentsStatus. Αυτός ο πίνακας περιέχει μια λίστα έγκυρων τιμών για την κατάσταση μιας συνάντησης και είναι απλώς μια αναζήτηση που χρησιμοποιείται από άλλα τμήματα του υπάρχοντος συστήματος συναντήσεων.

Η Kiana αποφασίζει ότι οι ακόλουθες λειτουργίες θα είναι χρήσιμες για το τμήμα προγραμματισμού πεδίων της εφαρμογής:

  • Βρείτε όλες τις συναντήσεις για έναν καθορισμένο τεχνικό.
  • Βρείτε όλες τις συναντήσεις για την τρέχουσα ημέρα για έναν καθορισμένο τεχνικό.
  • Βρείτε την επόμενη προγραμματισμένη συνάντηση για έναν καθορισμένο τεχνικό.
  • Ενημερώστε τις λεπτομέρειες μιας συνάντησης, όπως την προσθήκη σημειώσεων ή μιας φωτογραφίας.
  • Βρείτε λεπτομέρειες σχετικά με έναν πελάτη.

Δημιουργία του Web API: Διαχείριση αποθέματος πεδίων

Τα υπάρχοντα συστήματα αποθηκεύουν δεδομένα χρησιμοποιώντας τη βάση δεδομένων Azure SQL. Η Kiana αποφασίζει να δημιουργήσει το Web API χρησιμοποιώντας το Entity Framework Core επειδή αυτή η προσέγγιση μπορεί να δημιουργήσει μεγάλο ποσοστό κώδικα που υποβάλλει ερωτήματα, εισάγει και ενημερώνει αυτόματα τα δεδομένα. Το πρότυπο ΑΡΙ Web που παρέχεται από τη Microsoft μπορεί επίσης να δημιουργήσει τις περιγραφές Swagger που περιγράφουν κάθε λειτουργία στο API. Αυτές οι περιγραφές είναι χρήσιμες για τον έλεγχο των λειτουργιών API. Πολλά εργαλεία μπορούν να χρησιμοποιήσουν αυτές τις πληροφορίες για την ενσωμάτωση του API με άλλες υπηρεσίες, όπως η Διαχείριση API Azure.

Η Kiana ξεκίνησε με τη λειτουργία "Απόθεμα πεδίων", επειδή αυτό είναι το πιο απλό. Οι λειτουργίες Αποθέματος πεδίου στο Web API θέτει ερώτημα σε έναν μεμονωμένο πίνακα, BoilerParts στη βάση δεδομένων InventoryDB. Αυτός ο πίνακας περιέχει τις στήλες που εμφανίζονται στην εικόνα που ακολουθεί.

Ο πίνακας BoilerParts που εμφανίζει τις στήλες Αναγνωριστικό, Όνομα, CategoryId, Τιμή, Επισκόπηση, NumberInStock και ImageURL.

Η Kiana υιοθέτησε την προσέγγιση "πρώτα κώδικας" για τη δημιουργία του Web API και έκανε τα εξής.

  1. Καθόρισε τη δική της κλάση C# μοντέλου που αντικατοπτρίζει τη δομή του πίνακα BoilerParts στη βάση δεδομένων InventoryDB.

  2. Δημιούργησε μια κλάση περιβάλλοντος πλαισίου οντοτήτων που χρησιμοποιεί το Web API για τη σύνδεση στη βάση δεδομένων, για την εκτέλεση ερωτημάτων.

  3. Ρυθμίσατε την κλάση περιβάλλοντος για σύνδεση στη βάση δεδομένων InventoryDB στο Azure.

  4. Χρησιμοποιήθηκαν τα εργαλεία γραμμής εντολών του πλαισίου οντοτήτων για τη δημιουργία μιας κλάσης ελεγκτή Web API που υλοποιεί αιτήματα HTTP REST για κάθε μία από τις λειτουργίες που μπορούν να εκτελεστούν στον πίνακα BoilerParts.

  5. Χρησιμοποιήθηκε το Swagger API για τη δοκιμή του Web API.

Η εικόνα που ακολουθεί εμφανίζει τη δομή υψηλού επιπέδου του Web API.

Δομή υψηλού επιπέδου του Web API αποθέματος.

Η Kiana χρησιμοποίησε την παρακάτω διαδικασία για τη δημιουργία του Web API χρησιμοποιώντας τα εργαλεία γραμμής εντολών .NET 6.0 και το Visual Studio Code:

  1. Ανοίξτε ένα παράθυρο τερματικού στο Visual Studio Code.

    Παράθυρο νέου τερματικού στο VS Code.

  2. Εκτελέστε την παρακάτω εντολή για να δημιουργήσετε ένα νέο έργο Web API με το όνομα FieldEngineerApi.

    dotnet new webapi -o FieldEngineerApi
    
  3. Ανοίξτε τον φάκελο FieldEngineerApi.

    Ανοίξτε τον φάκελο FieldEngineerApi.

  4. Καταργήστε το παράδειγμα ελεγκτή WeatherForecastController.cs και το αρχείο κλάσης WeatherForecast.cs που δημιουργήθηκε από το πρότυπο Web API.

    Διαγραφή αρχείων WeatherForecast.

  5. Στο παράθυρο Τερματικό, προσθέστε τα παρακάτω πακέτα και εργαλεία του πλαισίου οντοτήτων μαζί με την υποστήριξη για τη χρήση του SQL Server στο έργο.

    dotnet add package Microsoft.EntityFrameworkCore.SqlServer
    
    dotnet add package Microsoft.VisualStudio.Web.CodeGeneration.Design
    
    dotnet add package Microsoft.EntityFrameworkCore.Design
    
    dotnet add package Microsoft.AspNetCore.Mvc.NewtonsoftJson
    
    dotnet tool install --global dotnet-ef
    
    dotnet tool install --global dotnet-aspnet-codegenerator
    
  6. Στον φάκελο FieldEngineerApi δημιουργήστε ένα νέο φάκελο με το όνομα Μοντέλα.

    Δημιουργία φακέλου μοντέλων.

  7. Στον φάκελο Μοντέλα, δημιουργήστε ένα αρχείο κώδικα C# με το όνομα BoilerPart.cs.

    Δημιουργία κατηγορίας BoilerPart.

  8. Σε αυτό το αρχείο, προσθέστε τις ακόλουθες ιδιότητες και πεδία. Αυτές οι ιδιότητες και τα πεδία αντικατοπτρίζουν τη δομή του πίνακα BoilerParts στη βάση δεδομένων InventoryDB.

    using System.Collections.Generic;
    using System.ComponentModel.DataAnnotations;
    using System.ComponentModel.DataAnnotations.Schema;
    
    namespace FieldEngineerApi.Models
    {
    
        public class BoilerPart
        {
            [Key]
            public long Id { get; set; }
    
            public string Name { get; set; }
    
            public string CategoryId { get; set; }
    
            [Column(TypeName = "money")]
            public decimal Price { get; set; }
    
            public string Overview { get; set; }
    
            public int NumberInStock { get; set; }
    
            public string ImageUrl { get; set; }
        }
    }
    
  9. Στον φάκελο Μοντέλα, δημιουργήστε ένα άλλο αρχείο κώδικα C# με το όνομα InventoryContext.cs. Προσθέστε τον παρακάτω κωδικό σε αυτήν την κλάση. Η κλάση παρέχει τη σύνδεση μεταξύ του ελεγκτή (θα δημιουργηθεί στη συνέχεια) και της βάσης δεδομένων.

    using Microsoft.EntityFrameworkCore;
    
    namespace FieldEngineerApi.Models
    {
        public class InventoryContext : DbContext
        {
            public InventoryContext(DbContextOptions<InventoryContext> options)
                : base(options)
            {
    
            }
    
            public DbSet\<BoilerPart\> BoilerParts { get; set; }
        }
    }
    
  10. Επεξεργαστείτε το αρχείο appsettings.Development.json για το έργο και προσθέστε μια ενότητα ConnectionStrings με την παρακάτω συμβολοσειρά σύνδεσης InventoryDB. Αντικαταστήστε το <server name> με το όνομα του διακομιστή της βάσης δεδομένων SQL που δημιουργήσατε για να διατηρηθεί η βάση δεδομένων InventoryDB.

    {
        "ConnectionStrings": {
            "InventoryDB": "Server=tcp*:<server name>*.database.windows.net,1433;Initial Catalog=InventoryDB;Persist Security Info=False;User ID=sqladmin;Password=Pa55w.rd;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;"
        },
        "Logging": {
            "LogLevel": {
                "Default": "Information",
                "Microsoft": "Warning",
                "Microsoft.Hosting.Lifetime": "Information"
            }
        }
    }
    

    Σημαντικό

    Για τους σκοπούς αυτού του οδηγού μόνο, η συμβολοσειρά σύνδεσης περιέχει το αναγνωριστικό χρήστη και τον κωδικό πρόσβασης για τη βάση δεδομένων. Σε ένα σύστημα παραγωγής, δεν πρέπει να αποθηκεύετε αυτά τα στοιχεία σε μη σαφές κείμενο σε ένα αρχείο ρύθμισης παραμέτρων.

  11. Επεξεργαστείτε το αρχείο Startup.cs και προσθέστε τα παρακάτω χρησιμοποιώντας οδηγίες στην αρχή του αρχείου.

    using FieldEngineerApi.Models;
    using Microsoft.EntityFrameworkCore;
    
  12. Στην κλάση Εκκίνηση, βρείτε τη μέθοδο ConfigureServices. Προσθέστε την παρακάτω δήλωση σε αυτήν τη μέθοδο.

    public void ConfigureServices(IServiceCollection services)
    {
    
        services.AddDbContext<InventoryContext>(options =>
            options.UseSqlServer(Configuration.GetConnectionString("InventoryDB")));
    
        services.AddControllers();
        ...
    }
    
  13. Τροποποιήστε τη μέθοδο Ρύθμιση παραμέτρων και ενεργοποιήστε το περιβάλλον εργασίας χρήστη Swagger ακόμα και όταν η εφαρμογή εκτελείται σε λειτουργία παραγωγής, όπως φαίνεται (αυτή η αλλαγή προϋποθέτει τη μετεγκατάσταση των δύο μεθόδων app.UseSwagger εκτός της δήλωσης if).

    public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
        }
        app.UseSwagger();
        app.UseSwaggerUI(c => c.SwaggerEndpoint("/swagger/v1/swagger.json", "FieldEngineerApi v1"));
    
        ...
    }
    

    Σημαντικό

    Αυτή η αλλαγή επιτρέπει στο τελικό σημείο Swagger να εκτίθεται για ενοποίηση της Διαχείρισης API. Μετά τη ρύθμιση παραμέτρων της Διαχείρισης API, θα πρέπει να μεταφέρετε αυτόν τον κώδικα ξανά εντός της πρότασης if και να αναδιανείμετε το Web API. Μην αφήσετε ποτέ το τελικό σημείο Swagger ανοιχτό σε ένα σύστημα παραγωγής.

  14. Στο παράθυρο Τερματικό, εκτελέστε την παρακάτω εντολή για να δημιουργήσετε τον ελεγκτή BoilerParts από την κλάση μοντέλου BoilerPart και την κλάση περιβάλλοντος InventoryContext.

    dotnet aspnet-codegenerator controller ^
        -name BoilerPartsController -async -api ^
         -m BoilerPart -dc InventoryContext -outDir Controllers
    

    Ο ελεγκτής BoilerParts πρέπει να δημιουργηθεί στον φάκελο Ελεγκτές.

    [!NOTE] Ο χαρακτήρας τερματισμού γραμμής, ^, αναγνωρίζεται μόνο από τα Windows. Εάν εκτελείτε Visual Studio Code σε σύστημα Linux, χρησιμοποιήστε τον χαρακτήρα \ αντί για αυτό.

  15. Ανοίξτε το αρχείο BoilerParts.cs στον φάκελο Ελεγκτές και εξετάστε τα περιεχόμενά του. Η κλάση BoilerPartsController εκθέτει τις ακόλουθες μεθόδους REST:

    • GetBoilerParts() που επιστρέφει μια λίστα όλων των αντικειμένων BoilerPart από τη βάση δεδομένων.
    • GetBoilerPart(long id), το οποίο ανακτά τις λεπτομέρειες του καθορισμένου τμήματος του μπόιλερ.
    • PutBoilerPart(long id, BoilerPart boilerPart), το οποίο ενημερώνει ένα τμήμα του μπόιλερ στη βάση δεδομένων με τις λεπτομέρειες στο αντικείμενο BoilerPart που καθορίζονται ως παράμετρος.
    • PostBoilerPart(BoilerPart boilerPart), που δημιουργεί ένα νέο τμήμα μπόιλερ.
    • DeleteBoilerPart(long id), που καταργεί το καθορισμένο τμήμα μπόιλερ από τη βάση δεδομένων.

    Σημείωση

    Η εφαρμογή του τεχνικού απαιτεί μόνο τις δύο μεθόδους λήψης αλλά οι άλλες είναι χρήσιμες για την εφαρμογή διαχείρισης αποθέματος επιτραπέζιου υπολογιστή (δεν καλύπτονται από αυτόν τον οδηγό).

  16. Μεταγλώττιση και δημιουργία του Web API.

    dotnet build
    

Το Web API πρέπει να δημιουργείται χωρίς να αναφέρει σφάλματα ή προειδοποιήσεις.

Ανάπτυξη του Web API στο Azure: Διαχείριση αποθέματος πεδίων

Η Kiana έχει αναπτύξει και έχει δοκιμάσει το Web API εκτελώντας τις ακόλουθες εργασίες:

  1. Χρησιμοποιώντας την επέκταση Λογαριασμού Azure στο Visual Studio Code, συνδεθείτε στη συνδρομή σας στο Azure.

  2. Από το παράθυρο τερματικού στο Visual Studio Code, δημιουργήστε μια νέα ομάδα πόρων με το όνομα webapi_rg στη συνδρομή σας στο Azure. Στην παρακάτω εντολή, αντικαταστήστε το <location> με την πλησιέστερη περιοχή Azure.

    az group create ^
        --name webapi_rg ^
        --location <location>
    
  3. Δημιουργήστε ένα σχέδιο υπηρεσίας εφαρμογής Azure για την παροχή των πόρων για φιλοξενία του Web API.

    az appservice plan create ^
        --name webapi_plan ^
        --resource-group webapi_rg ^
        --sku F1
    

    Σημείωση

    F1 είναι το δωρεάν SKU για σχέδια υπηρεσιών εφαρμογών. Παρέχει περιορισμένη ταχύτητα και παραγωγική ικανότητα και είναι κατάλληλο μόνο για σκοπούς ανάπτυξης.

  4. Δημιουργήστε μια εφαρμογή web Azure χρησιμοποιώντας το σχέδιο υπηρεσίας εφαρμογής. Αντικαταστήστε το <webapp name> με ένα μοναδικό όνομα για την εφαρμογή web.

    az webapp create ^
        --name <webapp name> ^
        --resource-group webapi_rg ^
        --plan webapi_plan
    
  5. Στο Visual Studio Code, επεξεργαστείτε το αρχείο appSettings.json και προσθέστε την ίδια συμβολοσειρά σύνδεσης που γράψατε προηγουμένως στο αρχείο appSettings.Development.json. Αντικαταστήστε το <server name> με το όνομα του διακομιστή της βάσης δεδομένων SQL που δημιουργήσατε για να διατηρηθεί η βάση δεδομένων InventoryDB.

    {
        "ConnectionStrings": {
            "InventoryDB": "Server=tcp:<server name>.database.windows.net,1433;Initial Catalog=InventoryDB;Persist Security Info=False;User ID=sqladmin;Password=Pa55w.rd;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;"**
        },
        "Logging": {
            "LogLevel": {
                "Default\: "Information",
                "Microsoft": "Warning",
                "Microsoft.Hosting.Lifetime": "Information"
            }
        },
        "AllowedHosts": "*"
    }
    
  6. Στο παράθυρο Τερματικό, ετοιμάστε το Web API για ανάπτυξη στο Azure.

    dotnet publish -c Release -o ./publish
    

    Αυτή η εντολή αποθηκεύει τα πακέτα αρχείων σε έναν φάκελο με το όνομα δημοσίευση.

  7. Στον Κώδικα του Visual Studio, κάντε δεξί κλικ στον φάκελο δημοσίευση και, στη συνέχεια, επιλέξτε Ανάπτυξη σε εφαρμογή Web.

    Ανάπτυξη της εφαρμογής Web από VS Code.

  8. Επιλέξτε το όνομα της εφαρμογής web που δημιουργήσατε νωρίτερα στο βήμα 4 (<webapp name>). Στο παρακάτω παράδειγμα, η εφαρμογή web ονομάζεται my-fieldengineer-webapp.

    Επιλέξτε την εφαρμογή Web.

  9. Στην προτροπή στο παράθυρο διαλόγου Visual Studio Code, επιλέξτε Ανάπτυξη για να αποδεχτείτε την προειδοποίηση και να αναπτύξετε την εφαρμογή web.

    Προειδοποίηση ανάπτυξης VS Code.

  10. Επαληθεύστε ότι η εφαρμογή web έχει αναπτυχθεί με επιτυχία και, στη συνέχεια, μεταβείτε στην τοποθεσία Web.

    Περιήγηση στο παράθυρο διαλόγου τοποθεσίας Web στο VS Code.

  11. Η τοποθεσία Web θα ανοίξει σε ένα νέο παράθυρο προγράμματος περιήγησης, αλλά θα εμφανίσει σφάλμα HTTP 404 (δεν βρέθηκε). Αυτό συμβαίνει επειδή οι λειτουργίες API Web είναι διαθέσιμες μέσω τελικού σημείου api αντί της ρίζας της τοποθεσίας Web. Αλλάξτε τη διεύθυνση URL σε https://<webapp name>.azurewebsites.net/api/BoilerParts. Αυτή η URI καλεί τη μέθοδο GetBoilerParts στον ελεγκτή BoilerParts. Το Web API θα πρέπει να ανταποκριθεί με ένα έγγραφο JSON που παραθέτει όλα τα εξαρτήματα του μπόιλερ στη βάση δεδομένων InventoryDB.

    Η λίστα εξαρτημάτων εμφανίζεται στο πρόγραμμα περιήγησης Web.

  12. Αλλάξτε τη διεύθυνση URL στο πρόγραμμα περιήγησης σε https://<webapp name>.azurewebsites.net/swagger. Θα πρέπει να εμφανίζεται το Swagger API. Πρόκειται για ένα γραφικό περιβάλλον εργασίας χρήστη, το οποίο επιτρέπει σε έναν προγραμματιστή να επαληθεύσει και να δοκιμάσει καθεμία από τις λειτουργίες σε ένα Web API. Επίσης, λειτουργεί ως χρήσιμο εργαλείο τεκμηρίωσης.

    Το περιβάλλον εργασίας χρήστη Swagger εμφανίζει τη λίστα λειτουργιών.

  13. Επιλέξτε ΛΗΨΗ δίπλα στο τελικό σημείο /api/BoilerParts/{id} και μετά επιλέξτε Δοκιμή.

    Η οθόνη "Δοκιμή" στο περιβάλλον εργασίας χρήστη του Swagger

  14. Στο πεδίο αναγνωριστικό, εισαγάγετε το αναγνωριστικό ενός ανταλλακτικού και μετά επιλέξτε Εκτέλεση. Αυτή η ενέργεια καλεί τη μέθοδο GetBoilerPart(long id) στον ελεγκτή BoilerParts. Θα επιστρέψει ένα έγγραφο JSON με τις λεπτομέρειες του ανταλλακτικού ή ένα σφάλμα HTTP 404 εάν δεν βρεθεί κάποιο αντίστοιχο ανταλλακτικό στη βάση δεδομένων.

    Η απόκριση στο περιβάλλον εργασίας χρήστη Swagger.

  15. Κλείστε το πρόγραμμα περιήγησης στο Web και επιστρέψτε στο Visual Studio Code.

Δημιουργία και ανάπτυξη του Web API: Γνωσιακή βάση πεδίου

Οι λειτουργίες της γνωσιακής βάσης πεδίου στο Web API λειτουργούν σε τρεις πίνακες στη βάση δεδομένων KnowledgeDB: Συμβουλές, BoilerParts και Μηχανικοί. Η εικόνα που ακολουθεί εμφανίζει τις σχέσεις μεταξύ αυτών των πινάκων και των στηλών που περιέχουν.

Σχέσεις πινάκων γνωσιακής βάσης.

Η Kiana υιοθέτησε μια παρόμοια προσέγγιση και για τη βάση δεδομένων της Γνωσιακής βάσης πεδίου που χρησιμοποιήθηκε για τη βάση δεδομένων διαχείρισης αποθέματος πεδίου και έκανε τα εξής:

  1. Δημιουργήστε κλάσεις μοντέλων C# που αντικατοπτρίζουν τη δομή του πίνακα Συμβουλές, BoilerParts και Μηχανικοί στη βάση δεδομένων KnowledgeDB. Ο κωδικός για καθεμία από αυτές τις κλάσεις εμφανίζεται στα εξής.

    Σημείωση

    Ο πίνακας BoilerParts στη βάση δεδομένων KnowledgeDB διαφέρει από τον πίνακα BoilerParts στη βάση δεδομένων InventoryDB. Για να αποφευχθεί η σύγκρουση ονομάτων, οι κλάσεις μοντέλων για τους πίνακες στη βάση δεδομένων KnowledgeDB έχουν το πρόθεμα KnowledgeBase.

    // KnowledgeBaseTips.cs
    
    using System.ComponentModel.DataAnnotations;
    
    namespace FieldEngineerApi.Models
    {
        public class KnowledgeBaseTip 
        {
            [Key]
            public long Id { get; set; }
    
            public long KnowledgeBaseBoilerPartId { get; set; }
    
            public virtual KnowledgeBaseBoilerPart KnowledgeBaseBoilerPart { get; set; }
    
            public string KnowledgeBaseEngineerId { get; set; }
    
            public virtual KnowledgeBaseEngineer KnowledgeBaseEngineer { get; set; }
    
            public string Subject { get; set; }
    
            public string Body { get; set; }
        }
    }
    

    Σημείωση

    Το αναγνωριστικό μηχανικού είναι μια συμβολοσειρά, όχι ένας αριθμός. Αυτό συμβαίνει επειδή τα υφιστάμενα συστήματα χρησιμοποιούν GUID για την αναγνώριση τεχνικών και άλλων χρηστών.

    // KnowledgeBaseBoilerPart.cs
    
    using System.Collections.Generic;
    using System.ComponentModel.DataAnnotations;
    
    namespace FieldEngineerApi.Models
    {
        public class KnowledgeBaseBoilerPart
        {
            [Key]
            public long Id { get; set; }
    
            public string Name { get; set; }
    
            public string Overview { get; set; }
    
            public virtual ICollection<KnowledgeBaseTip> KnowledgeBaseTips { get; set; }
        }
    }
    
    // KnowledgeBaseEngineer.cs
    
    using System.Collections.Generic;
    using System.ComponentModel.DataAnnotations;
    
    namespace FieldEngineerApi.Models
    {
        public class KnowledgeBaseEngineer
        {
            [Key]
            public string Id { get; set; }
    
            [Required]
            public string Name { get; set; }
    
            public string ContactNumber { get; set; }
    
            public virtual ICollection<KnowledgeBaseTip> KnowledgeBaseTips { get; set; }
        }
    }
    
  2. Δημιουργήστε μια άλλη κλάση περιβάλλοντος πλαισίου οντοτήτων που χρησιμοποιεί το Web API για τη σύνδεση στη βάση δεδομένων KnowledgeDB.

    // KnowledgeBaseContext.cs
    
    using Microsoft.EntityFrameworkCore;
    
    namespace FieldEngineerApi.Models
    {
        public class KnowledgeBaseContext : DbContext
        {
            public KnowledgeBaseContext(DbContextOptions<KnowledgeBaseContext> options)
                : base(options)
            {
    
            }   
    
            public DbSet<KnowledgeBaseBoilerPart> BoilerParts { get; set; }
    
            public DbSet<KnowledgeBaseEngineer> Engineers { get; set; }
    
            public DbSet<KnowledgeBaseTip> Tips { get; set; }
        }
    }
    
  3. Επεξεργαστείτε το αρχείο appsettings.Development.json για το έργο και προσθέστε την παρακάτω συμβολοσειρά σύνδεσης KnowledgDB με την ενότητα ConnectionStrings. Αντικαταστήστε το <server name> με το όνομα του διακομιστή της βάσης δεδομένων SQL που δημιουργήσατε για να διατηρηθεί η βάση δεδομένων KnowledgeDB.

    {
        "ConnectionStrings": {
            "InventoryDB": "Server=tcp:...",
            "KnowledgeDB": "Server=tcp:<server name>.database.windows.net,1433;Initial Catalog=KnowledgeDB;Persist Security Info=False;User ID=sqladmin;Password=Pa55w.rd;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;"
        },
        "Logging": {
            ...
            }
        }
    }
    

    Σημαντικό

    Για τους σκοπούς αυτού του οδηγού μόνο, η συμβολοσειρά σύνδεσης περιέχει το αναγνωριστικό χρήστη και τον κωδικό πρόσβασης για τη βάση δεδομένων. Σε ένα σύστημα παραγωγής, δεν πρέπει να αποθηκεύετε αυτά τα στοιχεία σε μη σαφές κείμενο σε ένα αρχείο ρύθμισης παραμέτρων.

  4. Επεξεργαστείτε το αρχείο Startup.cs και, στη μέθοδο ConfigureServices προσθέστε τις παρακάτω δηλώσεις.

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddDbContext<InventoryContext>...;
    
        services.AddDbContext<KnowledgeBaseContext>(options =>  
            options.UseSqlServer(Configuration.GetConnectionString("KnowledgeD")));
    
        services.AddControllers().AddNewtonsoftJson(
            options => options.SerializerSettings.ReferenceLoopHandling = Newtonsoft.Json.ReferenceLoopHandling.Ignore**
        );
    
        services.AddControllers();
        ...
    }
    

    Η δεύτερη δήλωση ελέγχει τον τρόπο με τον οποίο τα δεδομένα σειριοποιούνται κατά την ανάκτησή τους. Μερικές από τις κλάσεις μοντέλων έχουν αναφορές σε άλλες κλάσεις μοντέλων, οι οποίες με τη σειρά τους μπορούν να αναφέρονται σε περαιτέρω κλάσεις μοντέλων. Μερικές από αυτές τις αναφορές μπορεί να περιέχουν επαναλαμβανόμενους βρόχους (η Οντότητα Α αναφέρεται στην Οντότητα Β, η οποία αναφέρεται στην οντότητα Α, η οποία αναφέρει ξανά την οντότητα Β, και άλλα). Η επιλογή ReferenceLoopHandling κάνει το εργαλείο σειριοποίησης να παραβλέπει τέτοιους βρόχους στα δεδομένα και να επιστρέφει μόνο μια οντότητα και τα αντικείμενα στα οποία αναφέρεται αμέσως, αλλά τίποτα περισσότερο.

  5. Στο παράθυρο Τερματικό, εκτελέστε την παρακάτω εντολή για τη δημιουργία ελεγκτών από τις κλάσεις μοντέλων KnowledgeBaseBoilerTip, KnowledgeBaseBoilerPart και KnowledgeBaseEngineer και τις κλάσεις περιβάλλοντος KnowledgeBaseContext.

    dotnet aspnet-codegenerator controller ^
        -name KnowledgeBaseTipController -async -api ^
        -m KnowledgeBaseTip ^
        -dc KnowledgeBaseContext -outDir Controllers
    
    dotnet aspnet-codegenerator controller ^
        -name KnowledgeBaseBoilerPartController -async -api ^
        -m KnowledgeBaseBoilerPart ^
        -dc KnowledgeBaseContext -outDir Controllers
    
    dotnet aspnet-codegenerator controller ^
        -name KnowledgeBaseEngineerController -async -api ^
        -m KnowledgeBaseEngineer ^
        -dc KnowledgeBaseContext -outDir Controllers
    

    Οι τρεις ελεγκτές πρέπει να δημιουργηθούν στον φάκελο Ελεγκτές.

  6. Επεξεργαστείτε το αρχείο KnowledgeBaseBoilerPartController.cs. Αυτό το αρχείο περιέχει τον κώδικα για τον ελεγκτή KnowledgeBaseBoilerPart. Θα πρέπει να ακολουθεί το ίδιο μοτίβο με την κλάση BoilerPartsController που έχετε δημιουργήσει προηγουμένως, εκθέτοντας μεθόδους REST που δίνουν σε ένα πρόγραμμα-πελάτη τη δυνατότητα λίστας, ερωτήματος, εισαγωγής, ενημέρωσης και διαγραφής οντοτήτων. Προσθέστε την παρακάτω μέθοδο GetTipsForPart στον ελεγκτή.

    [Route("api/[controller]")]
    [ApiController]
    
    public class KnowledgeBaseBoilerPartController : ControllerBase
    {
        private readonly KnowledgeBaseContext _context;
    
        public KnowledgeBaseBoilerPartController(KnowledgeBaseContext context)
        {
            _context = context;
        }
    
        // GET: api/KnowledgeBaseBoilerPart/5/Tips
        [HttpGet("{id}/Tips")]
        public async Task<ActionResult<IEnumerable<KnowledgeBaseTip>>>GetTipsForPart(long id)
        {
            return await _context.Tips.Where(
                t => t.KnowledgeBaseBoilerPartId == id).ToListAsync();
        }
        ...
    }
    

    Αυτή η μέθοδος επιστρέφει όλες τις συμβουλές της γνωσιακής βάσης που αναφέρονται σε ένα συγκεκριμένο εξάρτημα. Υποβάλλει ερωτήματα στον πίνακα Συμβουλές στη βάση δεδομένων μέσω του αντικειμένου KnowledgeBaseContext για να βρει αυτές τις πληροφορίες.

  7. Επεξεργαστείτε το αρχείο KnowledgeBaseEngineerController.cs και προσθέστε την ακόλουθη μέθοδο στην κλάση KnowledgeBaseEngineerController.

    [Route("api/[controller]")]
    [ApiController]
    public class KnowledgeBaseEngineerController : ControllerBase
    {
        private readonly KnowledgeBaseContext _context;
    
        public KnowledgeBaseEngineerController(KnowledgeBaseContext context)
        {
            _context = context;
        }
    
        // GET: api/KnowledgeBaseEngineer/5/Tips
        [HttpGet("{id}/Tips")]
        public async Task\<ActionResult<IEnumerable<KnowledgeBaseTip>>> GetTipsForEngineer(string id)
        {
            return await _context.Tips.Where(t => 
                t.KnowledgeBaseEngineerId == id).ToListAsync();
        }
    
        ...
    }
    

    Η μέθοδος GetTipsForEngineer εντοπίζει όλες τις συμβουλές της γνωσιακής βάσης που δημοσιεύονται από τον καθορισμένο τεχνικό.

  8. Στο παράθυρο Τερματικό, μεταγλωττίστε και δημιουργήστε το Web API.

    dotnet build
    

    Το Web API πρέπει να δημιουργείται χωρίς να αναφέρει σφάλματα ή προειδοποιήσεις.

  9. Επεξεργαστείτε το αρχείο appSettings.json και προσθέστε τη συμβολοσειρά σύνδεσης για τη βάση δεδομένων KnowledgeDB. Αυτή η συμβολοσειρά πρέπει να είναι ίδια με εκείνη που γράψατε προηγουμένως στο αρχείο appSettings.Development.json..

    {
        "ConnectionStrings": {
            "InventoryDB": ...,
            "KnowledgeDB": "Server=tcp:<server name>.database.windows.net,1433;Initial Catalog=KnowledgeDB;Persist Security Info=False;User ID=sqladmin;Password=Pa55w.rd;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;"
        },
        "Logging": {
            ...
        },
        "AllowedHosts": "*"
    }
    
  10. Στο παράθυρο Τερματικό, ετοιμάστε το Web API για ανάπτυξη στο Azure.

    dotnet publish -c Release -o ./publish
    
  11. Στον Κώδικα του Visual Studio, κάντε δεξί κλικ στον φάκελο δημοσίευση και, στη συνέχεια, επιλέξτε Ανάπτυξη σε εφαρμογή Web. Ανάπτυξη στην ίδια εφαρμογή web Azure που δημιουργήσατε προηγουμένως. Επιτρέψτε στον οδηγό να αντικαταστήσει την υπάρχουσα εφαρμογή web με τον νέο κώδικα.

  12. Όταν ολοκληρωθεί η ανάπτυξη, μεταβείτε στην τοποθεσία Web αλλά αλλάξτε τη διεύθυνση URL του προγράμματος περιήγησης σε https://<webapp name>.azurewebsites.net/swagger. Οι λειτουργίες για τους ελεγκτές KnowledgeBaseBoilerPart, KnowledgeBaseEngineer και KnowldgeBaseTip θα πρέπει να παρατίθενται εκτός από τις υπάρχουσες λειτουργίες BoilerParts. Επαληθεύστε ότι οι λειτουργίες KnowledgeBaseBoilerPart περιλαμβάνουν μια λειτουργία ΛΗΨΗ για το URI /api/KnowledgeBaseBoilerPart/{id}/Συμβουλές και οι λειτουργίες KnowledgeBaseEngineer περιλαμβάνουν μια λειτουργία ΛΗΨΗ για το URI /api/KnowledgeBaseEngineer/{id}/Συμβουλές.

    Περιβάλλον εργασίας χρήστη Swagger με νέες λειτουργίες.

Δημιουργία και ανάπτυξη του Web API: Προγραμματισμός πεδίων

Οι λειτουργίες προγραμματισμού πεδίων χρησιμοποιούν τους πίνακες Συναντήσεις, AppointmentStatuses (αυτός είναι ένας απλός πίνακας αναζήτησης που παραθέτει τις έγκυρες τιμές κατάστασης συνάντησης), Πελάτες και Μηχανικοί που εμφανίζονται στην παρακάτω εικόνα. Αυτοί οι πίνακες αποθηκεύονται στη βάση δεδομένων SchedulesDB.

Σχέσεις πινάκων συναντήσεων και προγραμματισμού.

Για τη δημιουργία των λειτουργιών Web API για το τμήμα προγραμματισμού πεδίων του συστήματος, η Kiana εκτεθεί στις ακόλουθες εργασίες:

  1. Δημιουργήστε κλάσεις μοντέλων C# που αντικατοπτρίζουν τη δομή του πίνακα AppointmentStatus, Συναντήσεις, Πελάτες και Μηχανικοί στη βάση δεδομένων SchedulesDB. Ο παρακάτω κωδικός εμφανίζεται για καθεμία από αυτές τις κλάσεις.

    Σημείωση

    Η κλάση μοντέλου για τον πίνακα Μηχανικοί ονομάζεται ScheduleEngineer για να τη διακρίνει από το μοντέλο για τον πίνακα Μηχανικοί στη βάση δεδομένων InventoryDB.

    // AppointmentStatus.cs
    
    using Newtonsoft.Json;
    using System.Collections.Generic;
    using System.ComponentModel.DataAnnotations;
    
    namespace FieldEngineerApi.Models
    {
        public class AppointmentStatus {
            [Key]
            public long Id { get; set; }
    
            public string StatusName { get; set; }
            [JsonIgnore]
            public virtual ICollection<Appointment> Appointments { get; set; }
        }
    }
    
    // Appointment.cs
    
    using System;
    using System.ComponentModel.DataAnnotations;
    
    namespace FieldEngineerApi.Models
    {
        public class Appointment
        {
            [Key]
            public long Id { get; set; }
    
            [Required]
            public long CustomerId { get; set; }
    
            public virtual Customer Customer { get; set; }
    
            public string ProblemDetails { get; set; }
    
            [Required]
            public long AppointmentStatusId { get; set; }
    
            public virtual AppointmentStatus AppointmentStatus { get; set; }
    
            public string EngineerId { get; set; }
    
            public virtual ScheduleEngineer Engineer { get ; set; }
    
            [Display(Name = "StartTime")]
            [DataType(DataType.DateTime)]
            [DisplayFormat(DataFormatString = "{0:MM/dd/yyyy H:mm:ss}")]
            public DateTime StartDateTime { get; set; }
    
            public string Notes { get; set; }
    
            public string ImageUrl { get; set; }
        }
    }
    
    // Customer.cs
    
    using System.Collections.Generic;
    using System.ComponentModel.DataAnnotations;
    
    namespace FieldEngineerApi.Models
    {
        public class Customer
        {
            [Key]
            public long Id { get; set; }
    
            [Required]
            public string Name { get; set; }
    
            public string Address { get; set; }
    
            public string ContactNumber { get; set; }
    
            public virtual ICollection<Appointment> Appointments { get; set; }
        }
    }
    
    // ScheduleEngineer.cs
    using Newtonsoft.Json;
    using System.ComponentModel.DataAnnotations;
    using System.Collections.Generic;
    
    namespace FieldEngineerApi.Models
    {
        public class ScheduleEngineer
        {
            [Key]
            public string Id { get; set; }
    
            [Required]
            public string Name { get; set; }
    
            public string ContactNumber { get; set; }
    
            [JsonIgnore]
            public virtual ICollection<Appointment> Appointments { get; set; }
        }
    }
    
  2. Δημιουργήστε μια κλάση περιβάλλοντος πλαισίου οντοτήτων που χρησιμοποιεί το Web API για τη σύνδεση στη βάση δεδομένων SchedulesDB.

    // ScheduleContext.cs
    
    using System;
    using Microsoft.EntityFrameworkCore;
    
    namespace FieldEngineerApi.Models
    {
        public class ScheduleContext : DbContext
        {
            public ScheduleContext(DbContextOptions<ScheduleContext> options)
                : base(options)
            {
    
            }
    
            public DbSet<Appointment> Appointments { get; set; }
    
            public DbSet<AppointmentStatus> AppointmentStatuses { get; set; }
    
            public DbSet<Customer> Customers { get; set; }
    
            public DbSet<ScheduleEngineer> Engineers { get; set; }
        }
    }
    
  3. Επεξεργαστείτε το αρχείο appsettings.Development.json για το έργο και προσθέστε την παρακάτω συμβολοσειρά σύνδεσης SchedulesDB με την ενότητα ConnectionStrings. Αντικαταστήστε το <server name> με το όνομα του διακομιστή της βάσης δεδομένων SQL που δημιουργήσατε για να διατηρηθεί η βάση δεδομένων KnowledgeDB.

    {
        "ConnectionStrings": {
            "InventoryDB": "Server=tcp*: ...",
            "KnowledgeDB": "Server=tcp; ... ",
            "SchedulesDB": "Server=tcp:<server name>.database.windows.net,1433;Initial Catalog=SchedulesDB;Persist Security Info=False;User ID=sqladmin;Password=Pa55w.rd;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;"
        },
        "Logging": {
            ...
            }
        }
    }
    
  4. Επεξεργαστείτε το αρχείο Startup.cs και, στη μέθοδο ConfigureServices προσθέστε την παρακάτω δήλωση.

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddDbContext<InventoryContext>...;
    
        services.AddDbContex\<KnowledgeBaseContext>...;
    
        services.AddDbContext<ScheduleContext>(options =>
            options.UseSqlServer(Configuration.GetConnectionString("SchedulesDB")));
    
        services.AddControllers().AddNewtonsoftJson(...);
    
        ...
    }
    
  5. Στο παράθυρο Τερματικό, εκτελέστε την παρακάτω εντολή για τη δημιουργία ελεγκτών από τις κλάσεις μοντέλων Συνάντηση, Πελάτης και ScheduleEngineer και τις κλάσεις περιβάλλοντος ScheduleContext.

    Σημείωση

    Μην δημιουργείτε ξεχωριστό ελεγκτή για το μοντέλο AppointmentStatus.

    dotnet aspnet-codegenerator controller ^
        -name AppointmentsController -async -api ^
        -m Appointment ^
        -dc ScheduleContext -outDir Controllers
    
    dotnet aspnet-codegenerator controller ^
        -name CustomerController -async -api ^
        -m Customer ^
        -dc ScheduleContext -outDir Controllers
    
    dotnet aspnet-codegenerator controller ^
        -name ScheduleEngineerController -async -api ^
        -m ScheduleEngineer ^
        -dc ScheduleContext -outDir Controllers
    
  6. Επεξεργαστείτε το αρχείο AppointmentsController.cs. Στην κλάση AppointmentsControl, εντοπίστε τη μέθοδο GetAppointments. Τροποποιήστε τη δήλωση επιστροφής, όπως φαίνεται. Αυτή η αλλαγή διασφαλίζει ότι οι πληροφορίες Πελάτης, Μηχανικός και AppointmentStatus ανακτώνται ως μέρος της λειτουργίας ΛΗΨΗ. Αυτά τα πεδία αναφέρονται σε άλλες οντότητες που διαφορετικά θα ήταν null λόγω του αργού μηχανισμού φόρτωσης υποστήριξης του πλαισίου οντοτήτων.

    public class AppointmentsController : ControllerBase
    {
        private readonly ScheduleContext _context;
    
        public AppointmentsController(ScheduleContext context)
        {
            _context = context;
        }
    
        // GET: api/Appointments
    
        [HttpGet]
        public async Task<ActionResult<IEnumerable<Appointment>>> GetAppointments()
        {
            return await _context.Appointments
                .Include(c => c.Customer)
                .Include(e => e.Engineer)
                .Include(s => s.AppointmentStatus)
                .ToListAsync();
        }
    
        ...
    }
    
  7. Στο ίδιο αρχείο, τροποποιήστε τη μέθοδο GetAppointment(long id), όπως φαίνεται.

    // GET: api/Appointments/5
    [HttpGet("{id}")]
    public async Task<ActionResult<Appointment>> GetAppointment(long id)
    {
        var appointment = _context.Appointments
            .Where(a => a.Id == id)
            .Include(c => c.Customer)
            .Include(e => e.Engineer)
            .Include(s => s.AppointmentStatus);
    
        var appData = await appointment.FirstOrDefaultAsync();
        if (appData == null)
        {
            return NotFound();
        }
    
        return appData;
    }
    

    Αυτή η έκδοση της μεθόδου συμπληρώνει τα πεδία Πελάτης, Μηχανικός και AppointmentStatus μιας συνάντησης που ανακτάται (η αργή φόρτωση μπορεί να αφήσει τα πεδία αυτά κενά).

  8. Βρείτε τη μέθοδο PutAppointment και αντικαταστήστε την με τον ακόλουθο κώδικα. Αυτή η έκδοση της μεθόδου PutAppointmentP λαμβάνει τα πεδία σε μια συνάντηση που ένας χρήστης μπορεί να τροποποιήσει στην εφαρμογή και όχι σε ένα πλήρες αντικείμενο Συνάντηση.

    [HttpPut("{id}")]
    public async Task<IActionResult> PutAppointment(long id,
        string problemDetails, string statusName,
        string notes, string imageUrl)
    {
    
        var statusId = _context.AppointmentStatuses.First(s => 
            s.StatusName == statusName).Id;
    
        var appointment = _context.Appointments.First(e => 
            e.Id == id);
    
        if (appointment == null)
        {
            return BadRequest();
        }
    
        appointment.ProblemDetails = problemDetails;
        appointment.AppointmentStatusId = statusId;
        appointment.Notes = notes;
        appointment.ImageUrl = imageUrl;
        _context.Entry(appointment).State = EntityState.Modified;
    
        try
        {
            await _context.SaveChangesAsync();
        }
        catch (DbUpdateConcurrencyException)
        {
            if (!AppointmentExists(id))
            {
                return NotFound();
            }
            else
            {
                throw;
            }
        }
    
        return NoContent();
    }
    

    Σημείωση

    Ως γενικός κανόνας, οι λειτουργίες PUT πρέπει να τροποποιούν μόνο τα δεδομένα τα οποία θα πρέπει να έχει το δικαίωμα να ενημερώσει ένας χρήστης, όχι απαραίτητα σε κάθε πεδίο μιας οντότητας.

  9. Ανοίξτε το αρχείο ScheduleEngineerController.cs και προσθέστε τη μέθοδο GetScheduleEngineerAppointments στην κλάση ScheduleEngineerController.

    [Route("api/[controller]")]
    [ApiController]
    public class ScheduleEngineerController : ControllerBase
    {
        private readonly ScheduleContext _context;
    
        public ScheduleEngineerController(ScheduleContext context)
        {
            _context = context;
        }
    
        // GET: api/ScheduleEngineer/5/Appointments
        [HttpGet("{id}/Appointments")]
    
        public async Task<ActionResult<IEnumerable<Appointment>>> GetScheduleEngineerAppointments(string id)
        {
            return await _context.Appointments
                .Where(a => a.EngineerId == id)
                .OrderByDescending(a => a.StartDateTime)
                .Include(c => c.Customer)
                .Include(e => e.Engineer)
                .Include(s => s.AppointmentStatus)
                .ToListAsync();
        }
    
        ...
    }
    
    These methods retrieve the appointments for the specified technician.
    
    
  10. Edit the CustomerController.cs file and add the GetAppointments and GetNotes methods, as shown, to the CustomerController class.

    [Route("api/[controller]")]
    [ApiController]
    public class CustomerController : ControllerBase
    {
        private readonly ScheduleContext _context;
    
        public CustomerController(ScheduleContext context)
        {
            _context = context;
        }
    
        //GET: api/Customers/5/Appointments
        [HttpGet("{id}/Appointments")]
        public async Task<ActionResult<IEnumerable<Appointment>>> GetAppointments(long id)
        {
            return await _context.Appointments
                .Where(a => a.CustomerId == id)
                .OrderByDescending(a => a.StartDateTime)
                .ToListAsync();
        }
    
        //GET: api/Customers/5/Notes
        [HttpGet("{id}/Notes")]
        public async Task<ActionResult<IEnumerable<object>>> GetNotes(long id)
        {
            return await _context.Appointments
                .Where(a => a.CustomerId == id)
                .OrderByDescending(a => a.StartDateTime)
                .Select(a => 
                    new {a.StartDateTime, a.ProblemDetails, a.Notes})
                .ToListAsync();
        }
    
        ...
    }
    

    Η μέθοδος GetAppointments εντοπίζει όλες τις συναντήσεις για τον καθορισμένο πελάτη. Η μέθοδος GetNotes ανακτά όλες τις σημειώσεις που έκανε ο τεχνικός σε προηγούμενες επισκέψεις στον πελάτη.

  11. Επεξεργαστείτε το αρχείο appSettings.json και προσθέστε τη συμβολοσειρά σύνδεσης για τη βάση δεδομένων KnowledgeDB. Αυτή η συμβολοσειρά πρέπει να είναι ίδια με εκείνη που γράψατε προηγουμένως στο αρχείο appSettings.Development.json..

    {
        "ConnectionStrings": {
            "InventoryDB": ...,
            "KnowledgeDB": ...,
            "SchedulesDB": "Server=tcp:<server name>.database.windows.net,1433;Initial Catalog=SchedulesDB;Persist Security Info=False;User ID=sqladmin;Password=Pa55w.rd;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;"
        },
        "Logging": {
            ...
        },
        "AllowedHosts": "*"
    }
    
  12. Στο παράθυρο Τερματικό, μεταγλωττίστε και δημιουργήστε το Web API.

    dotnet build
    

    Το Web API πρέπει να δημιουργείται χωρίς να αναφέρει σφάλματα ή προειδοποιήσεις.

  13. Στο παράθυρο Τερματικό, ετοιμάστε το Web API για ανάπτυξη στο Azure.

    dotnet publish -c Release -o ./publish
    
  14. Στον Κώδικα του Visual Studio, κάντε δεξί κλικ στον φάκελο δημοσίευση και, στη συνέχεια, επιλέξτε Ανάπτυξη σε εφαρμογή Web. Ανάπτυξη στην ίδια εφαρμογή web Azure που δημιουργήσατε προηγουμένως. Επιτρέψτε στον οδηγό να αντικαταστήσει την υπάρχουσα εφαρμογή web με τον νέο κώδικα.

  15. Όταν ολοκληρωθεί η ανάπτυξη, μεταβείτε στην τοποθεσία Web αλλά αλλάξτε τη διεύθυνση URL του προγράμματος περιήγησης σε https://<webapp name>.azurewebsites.net/swagger. Επαληθεύστε ότι οι λειτουργίες για τους ελεγκτές Συναντήσεις, Πελάτης και ScheduleEngineer είναι πλέον διαθέσιμες.

Το Web API είναι πλέον έτοιμο για ενσωμάτωση στην εφαρμογή.