In mijn vorige blog (link) heb ik het eerste hoofdstuk van het boek over AZ-203 besproken. Deze week heb ik het 2e hoofdstuk gelezen. Dit hoofdstuk gaat over de verschillende "apps" die je met Azure online kunt brengen, een web-app, een API, een API voor mobile apps (waarmee je bijvoorbeeld push-meldingen kunt sturen) en Azure Functions, state-less code in de cloud die je aan kunt roepen. Azure App Service is een Platform as a Service, dus je hoeft je niet druk te maken over de infrastructuur.
Azure App Service web apps
Basis van de web-apps zijn virtuele machines. Je moet configureren welke regio, aantal VM's, de grootte van de VM's, welk OS, pricing tier (F1 of D1). F1 is de Free Tier, met S1 en P1 kun je backups maken en deployment slots gebruiken. Linux kan trouwens geen gebruik maken van de F1 of D1.
Het deployen kan op verschillende manieren: ZIP of WAR bestanden, vervolgens met de Kudu-service kun je de code deployen. FTP, Cloud synchronization (koppeling met een Dropbox of OneDrive-folder), Continuous Deployment (Github, Gitlab, BitBucket) en dan via Kudu, Azure Pipelines, Azure DevOps deployen, je lokale GIT-repo (je kunt je eigen code pushen en Kudu pakt het dan weer op), ARM template (met Visual Studio en een ARM template kun je ook code overzetten).
Bij een aantal opties wordt Kudu genoemd, het Github-project van die tool kan je meer informatie aanleveren: link. Je kunt deze tool ook buiten Azure runnen.
Mocht je bij deployment resources nodig hebben die op je eigen netwerk staan, dat is te realiseren met VNet integratie (Standard, Premium, PremiumV2 tiers). De web-app kan dan bij je virtuele netwerk komen (site-to-site VPN). Of via een hybride connectie. Daarbij gaat het via de Azure Service bus en op basis van TCP host en poorten.
In de configuratie kun je zaken instellen die je ook in een "gewone" IIS kunt doen, virtuele applicaties en mappen, handler mappings om bepaalde bestands-extensies te verwerken. Voor de rest de framework-versie, platform (32 of 64 bit), Web Sockets (als je SignalR gebruikt moet deze optie aan staan), Always On: normaal komt je app na 30 minuten "niets doen" in een slaap-stand, Managed Pipeline Version (pipeline-mode voor IIS), HTTP versie (HTTP/2 activeren), ARR Affinity (zelfde sessie altijd naar dezelfde machine, Auto Swap (stage slot bijgewerkt: automatisch om naar productie), Debugging (via Visual Studio door je code heen kunnen lopen).
Sommige taken wil je "op de achtergrond" laten uitvoeren, de background-tasks. Azure heeft hier de WebJobs voor. Dit kan alleen op een Windows-omgeving uitgevoerd worden. Omdat je ook dingen mat Azure Functions zou kunnen doen, heeft Microsoft uitgelegd wat de verschillen zijn, dat kun je hier nalezen: link. Je hebt 2 types, de continuous, een eindeloze loop die de taak uitvoert, dit type kun je debuggen. De triggered wordt op basis van een schema uitgevoerd. Deze kun je niet remote debuggen.
Bij triggered job gebruik je een CRON-expressie. Bij mij wel bekend, voor meer info kun je hier kijken: link. In het boek zien we een voorbeeld van een trigger op een Queue, daarbij wordt voor meer informatie verwezen naar deze pagina: link. Er is een SDK voor WebJobs en die kun je hier bekijken: link. En als je wilt weten hoe je Application Insight logging toevoegt (lijkt me handig), daarvoor kun je deze tutorial volgen: link.
Met "Diagnostic Logging" kun je zien wat er gebeurt, wat er fout gaat en (hopelijk) waar dat door komt. De Webserver kan logs maken: Detailed Error Logging. Statuscode groter of gelijk aan 400: HTML genereren met info. Maximaal 50 error bestanden (26 oudste worden automatisch verwijderd). Failed Request Tracing: Trace van IIS componenten in de processen waar het fout ging. Een nieuwe map voor een nieuwe error, zelfde policies als detailed error logging. Web Server Logging: de standaard logs die we van IIS kennen, W3C formaat. Dan heb je nog Application Diagnostics, met de System.Diagnostics.Trace class kun je zelf zaken wegschrijven. Als je naar Application Insights data wilt wegschrijven, dan moet je daar de SDK van toevoegen. Deployment diagnostics, staat automatisch aan, zodat je bij een mislukt deployment kunt uitzoeken wat er nu fout ging.
Je kunt de bestanden opslaan op het file-systeem of in een BLOB. Op het file-systeem kun je deze in de mappen /LogFiles terugvinden.
Azure App Service mobile apps
Het is handig om "push notificaties" te kunnen gebruiken. De gebruiker heeft de APP, die moet geregistreerd worden op de PNS (Platform Notification System) om berichten te kunnen sturen. Een PNS is platform afhankelijk. Apple heeft de Apple Push Notification Service (link). Google de Firebase Cloud Messaging (link) en Microsoft gebruikt Windows Notification Service (link). Microsoft biedt met de Azure Notification Hub een oplossing om alles aan te sturen.
Als je in je mobiele app "offline sync" mogelijk wilt maken, moet je gebruik maken van sync acties, de IMobileServiceSyncTable en MSSyncTable. De CRUD-acties worden uitgevoerd op /tables. Op Android en Windows gaat dit via een SQLite database, op iOS met Core Data en je moet nog wat extra's doen bij initialisatie: IMobileServicesSyncContext.InitializeAsync(localstore). Als er weer connectie is kun je een Push doen, je wijzigingen gaan naar de cloud, Pull, haal de data binnen, Incremental Sync, met een eigen query-naam kun je zorgen dat alleen "gewijzigd sinds" records binnen gehaald worden. En de Purge, hiermee gooi je jouw CUD-acties weg.
Met "instrumentation" kun je zien wat er met jou app gebeurt (bijvoorbeeld problemen, maar ook statistieken). Hiervoor wordt de App Center SDK gebruikt. Het bestaat uit Analytics (gedrag tijdens gebruik, iets in de winkelwagen gezet, maar daar niets mee gedaan), Diagnostics: crash report met stack-trace, Distribute: voordat de app in een store staat kun je deze al door een aantal selecte gebruikers laten testen, Push: met App Center kun je direct Push meldingen versturen.
Azure App Service API apps
Je kunt je eigen REST API's draaien. Standaard staat de boel open, mogelijk wil je dat niet. Azure App Service biedt veel mogelijkheden om de boel af te schermen. Bijvoorbeeld Azure Active Directory, of via een social media account (Facebook/Google/Twitter) of met een Microsoft-account. Het boek geeft aan dat dit type API meestal gebruikt wordt door een front-end van een site. Met deze tutorial kun je dat bekijken: link. Als je een request in javascript doet vanaf www.site.nl naar api.site.nl, dan wordt dat standaard geweigerd, aangezien dit een "ander domein" is. Hiervoor heb je CORS, je kunt in Azure (of in je eigen code) aangeven welke domeinen erbij mogen. Je kiest 1 van deze opties, want Azure is leidend, als je andere instellingen in je code zet is dat verwarrend, want die eigenschappen worden genegeerd. Je kunt online documentatie krijgen van je API met Swagger (OpenAPI). Zo heb je ook SwashBuckle en NSwag, maar op deze pagina van Swagger kun je meer alternatieven vinden: link.
Azure Functions
Een app service, daar betaal je continu voor. Bij Azure Functions betaal je alleen voor de seconden dat een functie gebruikt wordt. Er is een trigger die een functie aanroept, deze krijgt input bindings, voert zijn acties uit en levert het resultaat aan de output bindings. In C# declareer je bindings en triggers door methoden en parameters te decoreren. Bij andere talen gebruik je het function.json bestand. Daarbij moet bij een binding minimaal aangegeven worden: type: bijvoorbeeld "eventHub", direction: in (voor input) en out (voor output), name: dit attribuut wordt gebruikt om de koppeling te maken met de data in de functie. In deze lijst kun je alle bindings zien die ondersteund worden: link. Als je zelf binding-extensions wilt installeren, dan kun je hier informatie vinden: link. Je kunt in je code soms triggers of bindings aan een dynamische waarde moeten koppelen. Die zet je tussen { en }, in het boek zien we een {data.url}. Meer uitleg daarover kun je hier vinden: link.
Een functie wordt gestart met een trigger, daar zijn 3 types van. Data operation, er is nieuwe data aangemaakt, bijgewerkt, bijvoorbeeld CosmosDB, Event Grid, Blob Storage, Service Bus. Timers, gebaseerd op een schema, Webhooks, HTTP eindpunt wat aangeroepen kan worden. In het boek worden de versies van Azure Functions genoemd, versie 1 op framework 4.8 en versie 2 op .NET Core 2.1. Inmiddels is er versie 3 (op .NET Core 3.1) en is versie 1 op "deprecated" gezet: link.
De HTTP Trigger accepteert een aantal parameters: Authlevel, anonymous (geen key nodig), function (een specifieke key mee leveren, is de standaard), admin (master key meegeven: niet secure!). Methods: geef aan of je GET/POST/PUT/DELETE accepteert. Als je de WebHookType-parameter mee geeft, moet je niets met Methods doen. Route: standaard is jouwfunctieapp.azurewebsites.net/api/jouwfunctienaam. WebHookType: Generic (algemene providers), Github (Github webhooks), slack (Slack webhooks).
Elke app heeft een /admin/host/status endpoint. Die is beveiligd met een access-code of authenticatie keys. Met HTTP triggers zijn je endpoints ook afgeschermd, maar die keys zijn anders. host: gedeeld door alle functies, je kunt dus alles uitvoeren, function: beschermen alleen de functie waar ze zijn gedefinieerd.
Bovenstaande wordt niet aangeraden voor productie-omgevingen. Hiervoor gebruik je Function App Authentication / Authorization: Active Directory of andere 3rd party. Azure API Management (APIM), op basis van IP-adres of certificaat, App Service Environment (ASE): dedicated hosting-omgeving, met een front-end gateway waar authenticatie kan worden uitgevoerd.
Limieten die gelden zijn, maximale request lengte: 100MB, maximale URL lengte: 4.096 bytes, execution time-out: minder dan 2.5 minuten.
Azure Functies zijn over het algemeen: aanroep - uitvoeren - klaar. Maar soms heb je Durable Functions nodig. Dit is een extensie op Azure Functies. Hiermee kun je function-calls aan elkaar rijgen, kun je met code een workflow aangeven en zorgen dat de status van de workflow altijd consistent is. Je kunt er met C#, F# en JavaScript gebruik van maken.
Je werkt met verschillende functies. Die hebben verschillende rollen; activity: deze functies doen het echte werk, orchestrator: voor het aansturen, dus timers, threads die op externe events wachten, client: het beginpunt van de workflow, aangemaakt door een trigger. Deze functie maakt de orchestrator-functies aan door een orchestration trigger te sturen.
Je hebt nu dus 2 nieuwe type triggers, orchestration-triggers (deze moeten altijd in sync-code uitgevoerd worden) en activity-triggers.
Als je een orchestration-functie bouwt, dan kun je dat op verschillende manieren doen. Chaining: de activity-functions vormen een bepaalde volgorde, output van de ene functie is input voor de volgende. Fan out/fan in: je orchestration functie voert verschillende activity-functions parallel uit en voert die output naar 1 "aggregate" activity-functie die dit verwerkt. Async HTTP API's: deze houdt de status bij van langdurige calls naar externe cliƫnts. Monitor: met dit pattern kun je herhalende taken met flexibele tijds-intervallen aanmaken. Human interaction: dit pattern gebruik je als je functies gebaseerd zijn op events die een persoon kan activeren. Op deze pagina krijg je een overzicht van deze patronen en uitleg: link.