Azure Functions giver mulighed for at automatisere og eksekvere kode baseret på tidsplaner ved hjælp af Timer Trigger. En Timer Trigger-funktion aktiveres ved definerede tidspunkter eller intervaller, som kan styres via et cron-udtryk i konfigurationen. For at teste og validere disse funktioner i et lokalt udviklingsmiljø kræves flere trin, som sikrer korrekt opsætning og funktionalitet, inden funktionerne deployeres til skyen.

For at begynde testningen skal projektet startes i en lokal udviklingsplatform såsom Visual Studio Code, hvor de nødvendige Azure-værktøjer og emuleringer, som eksempelvis Azurite, er installeret og kørende. Når projektet kører, kan man via HTTP-anmodninger hente information om de tilgængelige funktioner, herunder både HTTP-triggerede og Timer Trigger-funktioner. Disse oplysninger leveres som JSON-dokumenter, som indeholder metadata, bindings-typer, autorisationsniveauer og planlægningsdetaljer, hvilket er afgørende for at forstå funktionens opførsel og integration.

Timer Trigger-funktionen kan manuelt trigges ved at sende en POST-anmodning med et tomt JSON-objekt til den administrative endpoint. Dette er væsentligt, da funktionen ellers kun ville aktiveres ved det næste planlagte tidspunkt. Manuelle kald muliggør hurtig test og fejlfinding uden at skulle vente på det næste tidsinterval. Det er vigtigt, at kroppen af anmodningen er korrekt formateret som et tomt JSON-objekt, da en manglende eller forkert anmodningskrop resulterer i en klientfejl (400 Bad Request).

Når funktionen kører, registrerer loggen præcist tidspunktet for udførelsen samt de næste planlagte udførsler, typisk i UTC-tid. Denne logning er essentiel for at forstå og monitorere funktionen over tid, især hvis der opstår uventede forsinkelser eller ændringer i udførselsmønsteret. Timer Trigger-funktionen kan også køre straks efter genstart, hvis den har været ude af drift længere end dens planlagte interval, hvilket sikrer, at ingen planlagte udførsler går tabt.

Et konkret eksempel viser en Timer Trigger-funktion, der henter oplysninger fra en ekstern kilde som Amazon, hvor funktionen foretager en HTTP GET-anmodning til en specifik URL og udtrækker relevante data såsom bestseller-rangeringer. Den korrekte parsing og håndtering af sådanne data sikrer, at applikationen kan reagere dynamisk på ændringer i eksterne systemer. Der logges både succesfulde HTTP-anmodninger og eventuelle fejl i dataudtrækningen, hvilket er vitalt for robusthed i produktionen.

Det er vigtigt at forstå, at Timer Trigger-funktioners pålidelighed afhænger af korrekt konfiguration af både tidsplan og miljø. Lokale testmiljøer simulerer forholdene i skyen, men kan ikke altid fange alle scenarier, især ved uforudsete nedetider eller netværksproblemer. Derfor bør der også etableres overvågning og fejlhåndtering i produktionen, for at sikre at funktionerne eksekveres som forventet og for at reagere på potentielle fejl hurtigt.

Derudover bør læseren være opmærksom på betydningen af time zones og UTC-tid, da timer triggers ofte konfigureres til at køre i UTC, hvilket kan føre til misforståelser, hvis lokal tid ikke håndteres korrekt i applikationen. Det er også afgørende at sikre, at timer-funktioner ikke overlapper hinanden ved længerevarende udførsler, hvilket kan føre til ressourcemæssige konflikter.

At beherske Azure Functions’ Timer Trigger-mekanismer og korrekt teste dem lokalt giver udviklere en stærk platform til at bygge skalerbare, serverløse applikationer, der kan køre baggrundsprocesser på faste tidspunkter med høj pålidelighed.

Hvad er forskellen på udvikling på tværs af platforme og hvordan kan du vælge det rette værktøj?

GitHub Codespaces er et fuldt konfigureret udviklingsmiljø baseret på Visual Studio Code, som kan opstartes i et cloud-miljø og tilgås gennem enhver webbrowser. Det understøtter Git-repositories, udvidelser og en indbygget kommandolinjegrænseflade, hvilket giver dig mulighed for at redigere, køre og teste koden fra enhver enhed. I modsætning til det cloud-baserede miljø kræver det, at du bruger Visual Studio til Mac for at udvikle applikationer, der kan køre på Apple-enheder. Visual Studio 2022 for Mac giver mulighed for at udvikle forskellige typer applikationer, fra konsolapplikationer til web- og mobilapps, mens du også kan skabe apps til macOS, iOS og iPadOS. For at kompilere apps til Apple-enheder som iPhone og iPad, kræves det dog, at du har Xcode, som kun kører på macOS.

For Windows-brugere tilbyder Visual Studio 2022 for Windows en lignende udviklingsplatform, som understøtter de fleste typer af applikationer, herunder desktop- og mobilapps. Dog er det vigtigt at bemærke, at selvom du kan bruge Visual Studio til at skrive en cross-platform mobilapp med .NET MAUI, kræves der stadig macOS og Xcode for at kunne kompilere koden til iOS-enheder. Visual Studio 2022 for Windows fungerer kun på Windows 10 version 1909 eller nyere og kræver en 64-bit version. Version 17.4 er den første version, der understøtter native Arm64.

Jeg har selv benyttet flere forskellige enheder og software til at skrive og teste koden til denne bog. Jeg har blandt andet arbejdet med en HP Spectre (Intel) bærbar, en Apple Silicon Mac mini (M1) desktop og en Raspberry Pi 400 (ARM v8) desktop. For at få et godt indblik i udviklingen på tværs af platforme er det vigtigt at forstå forskellene i hardware og software, da de kan skabe unikke udfordringer og muligheder, afhængigt af hvad du udvikler. For eksempel, mens en Raspberry Pi er billig og giver god indsigt i Linux-miljøer, kræver udviklingen til Apple-enheder, at du benytter en Mac med Xcode.

I denne bog har jeg fokuseret på at bruge Visual Studio Code og Visual Studio 2022, fordi de tilbyder et fleksibelt udviklingsmiljø, der kan bruges på tværs af forskellige systemer. Visual Studio Code, som kan køre på både macOS, Windows og Linux, tilbyder et stort bibliotek af udvidelser, der gør det muligt at tilpasse editoren til ens behov. Derudover er det ideelt til at arbejde med web- og datatjenester, især når du benytter REST-klienten til at teste disse tjenester.

Når du vælger dit udviklingsmiljø, er det vigtigt at vælge et værktøj, som ikke blot passer til dine præferencer, men som også kan understøtte de platforme, du sigter mod at udvikle til. Med .NET 7 understøttes deployment på en lang række platforme: Windows (både x86, x64 og Arm64), macOS (fra version 10.15), Linux (inklusive Ubuntu, Debian og CentOS), samt mobilplatforme som Android og iOS. Denne bredde gør det muligt at udvikle cross-platform applikationer med .NET, men du bør være opmærksom på, at der er nogle platforme, som kræver specifik hardware og software. For eksempel, selvom du kan udvikle på Windows ARM-enheder som Microsoft Surface Pro X, kræver det specifik support for ARM64.

Desuden er det nødvendigt at have opdateret software og SDK’er for at kunne udvikle og deployere korrekt. Det anbefales at installere .NET SDK’erne for både version 6.0 og 7.0, da version 6.0 er Long Term Support (LTS), og derfor er stabil i lang tid, mens 7.0 er den nyeste version. For at komme i gang med udviklingen på Windows kan du downloade Visual Studio 2022 og vælge de nødvendige arbejdsbelastninger, som f.eks. ASP.NET og webudvikling, .NET Multi-platform App UI development og .NET desktop development. Ved at følge disse trin kan du hurtigt komme i gang med at udvikle på tværs af forskellige platforme og enheder.

Vigtigt at forstå er, at udviklingen på tværs af platforme kræver en grundlæggende forståelse af de specifikke krav for hver platform. For eksempel, hvis du planlægger at udvikle en mobilapp til iOS, skal du bruge macOS og Xcode, selvom du skriver koden på en Windows-enhed. Dette kan være en barriere, hvis du ikke har adgang til den nødvendige hardware, men det er et nødvendigt skridt, hvis du ønsker at udvikle apps til Apple-enheder.

Hvordan håndteres datarelationer og konsistens i Azure Cosmos DB?

I Azure Cosmos DB spiller valg af datamodellering og konsistensniveau en afgørende rolle for både ydeevne og pålidelighed. Når vi arbejder med relaterede data, må vi nøje overveje, hvornår det er hensigtsmæssigt at normalisere data, altså at adskille relaterede informationer i forskellige dokumenter og referere mellem dem, kontra at embedde (indlejre) data direkte i dokumenterne.

Embedning af data kan være fordelagtigt, når de relaterede data sjældent ændres, eller når læsning af data bør være hurtig og uden behov for komplekse opslag. For eksempel, hvis man vil vise de mest likede kommentarer øverst under en artikel, kan disse indlejres direkte i artikelens dokument, mens de øvrige kommentarer opbevares separat og refereres til via primære nøgler. Omvendt, hvis data ændres ofte eller relationerne er mange-til-mange og ubundne i omfang, er normalisering at foretrække for at undgå dyre opdateringer i flere dokumenter.

I praksis kan det give mening at embedde langsigtede investeringsdata som købskurs og månedlige priser, men referere til mere volatile data som daglige aktiekurser for dagshandel. Denne balance mellem embedding og referencing er en nøglefaktor for at optimere både læse- og skriveperformance.

Azure Cosmos DB tilbyder desuden fem forskellige konsistensniveauer, hvilket adskiller den fra mange andre NoSQL-databaser, der typisk kun tilbyder stærk eller eventual konsistens. Disse niveauer spænder fra stærk konsistens, som sikrer linearisering på tværs af alle regioner globalt, til eventual konsistens, hvor data kan læses inkonsistent midlertidigt, men vil konvergere over tid. Imellem findes blandt andet bounded staleness, session og consistent prefix, der balancerer tilgængelighed, latenstid og konsistens efter behov.

Valget af konsistensniveau har direkte indflydelse på latens og tilgængelighed. Stærk konsistens kan for eksempel øge skrive-latensen og reducere læsetilgængeligheden, da systemet venter på global replikation. Mere afslappede niveauer tillader hurtigere adgang men kræver at applikationen håndterer mulige inkonsistenser.

Azure Cosmos DB er opbygget hierarkisk med konto, database, container, partition og item. Partitioner er særligt vigtige, da de definerer, hvordan data fysisk og logisk organiseres og skaleres. Det er derfor essentielt at vælge en partitioneringsnøgle, der sikrer jævn fordeling af data og workload, samt optimerer transaktioners omfang inden for den logiske partition.

Gennemstrømning i Cosmos DB måles i request units per second (RU/s), som er en abstraheret enhed for systemets ressourceforbrug ved forespørgsler og operationer. Provisionering af throughput skal estimeres nøje i forhold til forventet belastning, da overskridelse af den tildelte RU/s fører til rate limiting og forsinkelser i applikationen. Prisfastsættelsen afhænger af throughput og lagringsmængde, og der findes et gratis niveau, som understøtter op til 1.000 RU/s og 25 GB lager.

I arbejdet med Cosmos DB er det vigtigt at forstå, at dataarkitektur ikke blot handler om lagring, men i høj grad om, hvordan man vælger at håndtere datarelationer, konsistens og skalering. Ved at balancere embedding og referencing, forstå konsekvenserne af forskellige konsistensniveauer, og optimere partitioneringsstrategier, kan man opnå en effektiv, pålidelig og skalerbar løsning.

Det er væsentligt for læseren at være opmærksom på, at konsistensniveauer også påvirker programmørens ansvar. Slappere konsistens betyder ofte, at applikationen må designe mekanismer til at håndtere mulige uoverensstemm

Hvordan håndtere NoSQL-data med Azure Cosmos DB: Oprettelse, hentning og sletning af produkter

Når du arbejder med Azure Cosmos DB, kan du bruge SQL-lignende forespørgsler til at håndtere data på en effektiv måde. Denne proces kan deles op i flere faser: oprettelse af elementer, hentning af data og sletning af elementer. Her gennemgår vi, hvordan man arbejder med produkter i en container og bruger SQL-forespørgsler til at udføre de nødvendige operationer.

I denne guide fokuserer vi på at oprette produkter, liste dem og til sidst slette dem fra Cosmos DB. Vi benytter programmet Program.Methods.cs for at definere metoder til at håndtere disse operationer.

Når du opretter produktposterne, kan du begynde med at definere deres struktur i Cosmos DB. For eksempel kan du vælge at oprette 77 produktposter, som er registreret i containeren "Products". Når oprettelsen af elementerne er gennemført, kan du hurtigt bekræfte antallet af elementer i Azure Cosmos DB Emulator eller Azure Portal's Data Explorer. Dette er en praktisk måde at sikre, at dine data er blevet korrekt indsat i systemet.

For at liste disse produkter og vise deres detaljer som ID, navn og enhedspris, kan du skrive en SQL-forespørgsel, der henter alle elementer fra containeren. En simpel SQL-forespørgsel som "SELECT * FROM c" vil returnere alle produkter i containeren, og du kan bruge en FeedIterator til at gennemgå resultaterne. Det er også vigtigt at bemærke, at når du henter data, bliver hver forespørgsel faktureret i form af "Request Units" (RUs), og det er en god idé at holde styr på den samlede RUs for optimering af applikationen.

Hvis du ønsker at slette alle produkter i containeren, kan du definere en metode, der itererer over de eksisterende produkter og sletter dem én ad gangen. Igen bruges en SQL-forespørgsel som "SELECT * FROM c" til at hente alle produkterne, hvorefter du kalder DeleteItemAsync-metoden for hver produktpost. Dette sikrer, at alle data bliver fjernet fra containeren. Som med hentningen af data, skal du være opmærksom på omkostningerne i form af RUs, som vil akkumulere under sletningsoperationen.

En vigtig funktion i Azure Cosmos DB er muligheden for at bruge SQL-lignende forespørgsler til at filtrere og manipulere data. Med kommandoer som SELECT, FROM, WHERE, ORDER BY og DISTINCT kan du hente præcist de data, du har brug for. For eksempel kan du filtrere produkter baseret på kategori ved at skrive en forespørgsel som "SELECT p.id, p.productName, p.unitPrice FROM Items p WHERE p.category.categoryName = 'Beverages'". Dette gør det muligt at få en mere målrettet tilgang til dine data, hvilket er en fordel, når du arbejder med store datamængder.

Det er også muligt at kombinere flere SQL-operationer, som f.eks. at anvende betingelser som IN, BETWEEN, og LIKE for at filtrere specifikke værdier. Dette kan være nyttigt, når du arbejder med data, der kræver præcise søgninger eller mønsterbaserede matchninger.

Når du arbejder med Cosmos DB, skal du forstå, hvordan forskellige SQL-syntakser fungerer i en NoSQL-database. SQL-forespørgsler i Cosmos DB kan ikke nødvendigvis garantere samme ydeevne som traditionelle relationelle databaser, da Cosmos DB er optimeret til at håndtere store, distribuerede datamængder. Det er derfor afgørende at tænke på datamodeldesign og forespørgselsoptimering fra starten af.

Endelig er det vigtigt at bemærke, at Cosmos DB tilbyder flere måder at arbejde med data på, herunder syntakser til at oprette, hente og slette data. Men det er afgørende at optimere forespørgsler for at reducere omkostningerne i form af RUs. Effektiv datastyring handler ikke kun om at kunne oprette, hente og slette data, men også om at sikre, at du gør det på en måde, der er skalerbar og omkostningseffektiv.

I arbejdet med Azure Cosmos DB kan du drage fordel af disse værktøjer ved at have en klar forståelse af, hvordan du strukturerer dine data, optimerer forespørgsler og implementerer de nødvendige metoder til at administrere dine NoSQL-data effektivt.