Dela via


Databasmarkörer

Gäller för: ✅Azure Data Explorer-

En databasmarkör är ett objekt på databasnivå som gör att du kan köra frågor mot en databas flera gånger. Du får konsekventa resultat även om det finns data-append eller data-retention åtgärder som utförs parallellt med frågorna.

Databasmarkörer är utformade för att hantera två viktiga scenarier:

  • Möjligheten att upprepa samma fråga flera gånger och få samma resultat, så länge frågan anger "samma datauppsättning".

  • Möjligheten att göra en "exakt en gång"-fråga. Den här frågan "ser" bara de data som en tidigare fråga inte såg, eftersom data inte var tillgängliga då. Med frågan kan du iterera, till exempel genom alla nyligen ankomna data i en tabell utan rädsla för att bearbeta samma post två gånger eller hoppa över poster av misstag.

Databasmarkören representeras i frågespråket som ett skalärt värde av typen string. Det faktiska värdet bör betraktas som ogenomskinlig och det finns inget stöd för någon annan åtgärd än att spara dess värde eller använda följande markörfunktioner.

Markörfunktioner

Kusto har tre funktioner för att implementera de två scenarierna ovan:

  • cursor_current(): Använd den här funktionen för att hämta databasmarkörens aktuella värde. Du kan använda det här värdet som ett argument för de två andra funktionerna.

  • cursor_after(rhs:string): Den här specialfunktionen kan användas på tabellposter som har IngestionTime-principen aktiverad. Den returnerar ett skalärt värde av typen bool som anger om postens ingestion_time() databasmarkörvärde kommer efter rhs databasmarkörvärdet.

  • cursor_before_or_at(rhs:string): Den här specialfunktionen kan användas på de tabellposter som har IngestionTime-principen aktiverad. Den returnerar ett skalärt värde av typen bool som anger om postens ingestion_time() databasmarkörvärde kommer före eller vid rhs databasmarkörvärdet.

De två specialfunktionerna (cursor_after och cursor_before_or_at) har också en bieffekt: När de används genererar Kusto aktuella värdet för databasmarkören till @ExtendedProperties resultatuppsättningen för frågan. Egenskapsnamnet för markören är Cursoroch dess värde är en enda string.

Till exempel:

{"Cursor" : "636040929866477946"}

Inskränkningar

Databasmarkörer kan bara användas med tabeller som IngestionTime-principen är aktiverad för. Varje post i en sådan tabell är associerad med värdet för databasmarkören som användes när posten matades in. Därför kan funktionen ingestion_time() användas.

Databasmarkörobjektet innehåller inget meningsfullt värde om inte databasen har minst en tabell som har en IngestionTime-princip definierad. Det här värdet kommer garanterat att uppdateras, efter behov av inmatningshistoriken, till sådana tabeller och de frågor som körs, som refererar till sådana tabeller. Det kan, eller kanske inte, uppdateras i andra fall.

Inmatningsprocessen checkar först in data, så att de är tillgängliga för frågor, och tilldelar först sedan ett faktiskt markörvärde till varje post. Att fråga efter data omedelbart efter inmatning med hjälp av en databasmarkör kanske inte innehåller de sista posterna som lagts till eftersom markörens värde ännu inte har tilldelats. Om du hämtar det aktuella databasmarkörvärdet upprepade gånger kan det också returnera samma värde, även om inmatningen gjordes däremellan, eftersom endast en markörincheckning kan uppdatera dess värde.

Att köra frågor mot en tabell baserat på databasmarkörer är bara garanterat att "fungera" (ge exakt en gång garantier) om posterna matas in direkt i tabellen. Om du använder omfattningskommandon, till exempel .move-omfattningar eller .replace-omfattningar för att flytta data till tabellen, eller om du använder .rename-tabell, är det inte säkert att du undviker att behöva köra frågor mot den här tabellen med hjälp av databasmarkörer. Det beror på att inmatningstiden för posterna tilldelas när de ursprungligen matas in och inte ändras under åtgärden för flyttintervall.

När omfattningarna flyttas till måltabellen kanske det tilldelade markörvärdet redan har bearbetats och nästa fråga från databasmarkören missar de nya posterna.

Exempel: Bearbeta poster exakt en gång

För en tabell Employees med schema [Name, Salary]använder du följande process för att kontinuerligt bearbeta nya poster när de matas in i tabellen:

// [Once] Enable the IngestionTime policy on table Employees
.set table Employees policy ingestiontime true

// [Once] Get all the data that the Employees table currently holds 
Employees | where cursor_after('')

// The query above will return the database cursor value in
// the @ExtendedProperties result set. Lets assume that it returns
// the value '636040929866477946'

// [Many] Get all the data that was added to the Employees table
// since the previous query was run using the previously-returned
// database cursor 
Employees | where cursor_after('636040929866477946') // -> 636040929866477950

Employees | where cursor_after('636040929866477950') // -> 636040929866479999

Employees | where cursor_after('636040929866479999') // -> 636040939866479000