Bluesky’s firehose – som at drikke af en brandhane?

At konsumere data fra Bluesky’s firehose kan bedst beskrives som at drikke af en brandhane – en konstant strøm af information, der kræver både skarp filtrering og effektiv behandling for at få mening ud af kaosset.

Kom med bag kulisserne og læs om de tekniske udfordringer et system til at filtrere indlæg fra hele Bluesky-netværket for over 10.000 danske Bluesky-konti – og hvilke løsninger, der virkede.

Hvad er Bluesky’s Firehose?

Bluesky’s firehose er en højhastigheds-datastream, der sender realtidsindhold fra netværket til forbrugere. Firehose er navnet på den konstante strøm af millioner af indlæg, kommentarer, opdateringer af brugeprofiler og andre datapunkter, der flyder gennem en enkelt forbindelse. For udviklere, der ønsker at analysere eller filtrere specifikt indhold, kan det være en monumental opgave at håndtere både datamængden og kompleksiteten.

Mission: Fokus på dansk indhold

Opgaven var konceptualt enkel, men kompleks i udførelse: At identificere og udvælge alle indlæg fra danske Bluesky-brugere i en strøm af global data. Med over 10.000 identificerede danske konti skulle der bygges en løsning, der hurtigt kunne matche hver eneste datapakke med vores liste af danske Decentralized Identifiers (DIDs).

Denne udfordring rejste flere tekniske spørgsmål:

1. Hvordan sikres, at vores system kan håndtere hastigheden og datamængden i firehose-streamen?

2. Hvordan filtreres data effektivt uden at flaskehalse opstår?

3. Hvordan bevares fleksibilitet til f.eks. at tilføje eller fjerne DIDs, uden at det påvirker ydeevnen?

De tekniske udfordringer

1. Hastighed: At følge med brandhanen

En af de største udfordringer er firehose’ens hastighed. Strømmen af data er kontinuerligt høj og kræver, at løsningen kan processere hver enkelt datapakke i realtid. Hvis vi ikke følger med, risikerer vi at miste værdifulde datapunkter.

Valget faldt på en løsning baseret på Go (Golang), kendt for sin høje ydeevne og evne til at håndtere samtidige processer effektivt. Ved hjælp af Go’s goroutines og kanaler blev det muligt at opsætte en pipeline, der samtidig kunne læse, dekode og filtrere data uden flaskehalse.

Bluesky Indigo er navnet på platformens adgang fra programmeringssproget GO, og den samt en implementering af samme findes tilgængeligt på github.

2. Filtrering: Hvor hurtigt kan vi finde 10.000 DIDs?

At matche indlæg med vores liste af danske DIDs var en nøgleudfordring. Oprindeligt brugte vi et simpelt Go-map (map[string]bool), som giver O(1)-opslagstid. Det betyder at opslagstiden, der bruges til at afgøre om en besked er relevant eller ej, er den samme for 10 eller 10.000 værdier. Og dette fungerer faktisk fint. DID’erne findes i en fil, som loades ind i Go-map’et når processen starter. Indlæsningen tager godt og vel et sekund.

Firehose’n leverer gerne flere hundrede – måske op imod tusinder af beskeder pr. sekund. Hver besked skal udpakkes (for den er modtaget i en såkaldt CBOR-encoding). Udpakningen går stærkt, og så snart afsenderens DID kan uddrages fra beskeden, kan vi undersøge om den findes i vores map.

For Twitter’s vedkommende kunne man (ihvertfald i “gamle dage”) – sende en liste af filtre af bruger id’er, som ville være de eneste konti man ville modtage indlæg fra via Twitters firehose. Med Bluesky og AT protokollen, er firehosen ens (og omfangsrig) for alle, og man må selv foretage filtrering af relevant indhold. Man skal altså ikke bare have adgang til en hurtig maskine på en hurtig forbindelse, men man skal også sikre at man ikke støder mod en eller anden begrænsning i mængden af trafik fra serverhosten.

Skulle vi støde på en begrænsning i performance, hvis vi f.eks. oplever at der pludselig er 100.000 danskere på Bluesky, vil det måske blive relevant at se på den såkaldte Bloom-filtrering. Ved at loade brugernes DID ind i et map, bruger vi hukommelse, og bliver hukommelsesforbruget problematisk, kan Bloomfiltrering måske gøre en forskel i performance.

2. Skalerbarhed og fleksibilitet

At vedligeholde en liste på 10.000+ DIDs kræver en dynamisk og skalerbar løsning. Vi designede et API, der gør det muligt at opdatere listen i realtid uden at stoppe dataflowet. Dette sikrer, at vores system altid er up-to-date, selv hvis nye danske brugere tilslutter sig Bluesky.

Endelig skal indholdet fra de relevante brugeres posts på Bluesky gemmes i en fil. Database nedetid er sjældent, man at miste adgangen til et filsystem er sjældnere. Derfor skrives nye indlæg ikke direkte til databasen, men via filer, der senere kan samles op af andre processer og gemmes i databasen. Går databasen offline, mister vi ikke data, men har i værste fald en forsinkelse der kan indhentes når databasen er online igen.

Diskadgang er, i dag, typisk et spørgsmål om at gemme noget på en Solid State disk, men selv denne kan være belastet på et system, der måske får travlt. Opgaven med at styre adgang til filen der skal skrives til, og selve skrivningen blev derfor flyttet ud i en goroutine, så denne del ikke ville kunne stå i vejen for indlæsning og behandling af den næste besked fra Bluesky’s firehose.

Strategien er altså hurtigst muligt at afgøre om en besked er irrelevant (ikke på vores DID-liste), og hurtigt springe videre til næste besked hvis det er tilfældet. Er beskeden relevant, skal vi så tidligt som muligt overlade det videre administrative arbejde til en goroutine, så hovedprocessen hurtigst muligt kan undersøge den næste besked fra firehosen. Jo tidligere vores kode kan afgøre irrelevans eller det modsatte, jo højere beskedfrekvens må vi forventes at kunne håndtere – og det er nødvendigt fordi den globale Bluesky-trafik må ventes at stige.

At Go, som kompileret sprog, er yderst velegnet til højtydende opgaver som denne er virkelig en gevinst.

Resultater

Efter nogle iterationer lykkedes det at skabe et robust system, der kan håndtere Bluesky’s firehose og filtrere danske indlæg uden forsinkelse. Vores løsning:

• Kan processere flere tusinde datapakker i sekundet.

• Har en ekstremt lav fejlrate takket være kombinationen af datastrukturer.

• Giver os mulighed for hurtigt at justere filtreringslogikken uden nedetid.

Hvad vi lærte

At arbejde med Bluesky’s firehose har kastet vigtige lektioner af sig om, hvordan man håndterer højhastighedsdatastreams. Effektiv filtrering og skalerbarhed er nøglen, når man arbejder med store datastrømme i realtid. Og ved at kombinere værktøjer som Go og optimerede datastrukturer kan man opnå en imponerende ydeevne.

Perspektiver for fremtiden

Bluesky’s firehose åbner dørene for en lang række innovative applikationer – fra sentimentanalyse til netværkskortlægning.

Har du lyst til at vide mere om arbejdet med Bluesky’s protokol og firehose, så tøv ikke med at tage kontakt.

Nej – du har ikke lagt mærke til mit arbejde nogen steder, og derfor har du måske brug for mig

Nu IT / Jens Ulrik – to sider af samme sag. Vi arbejder sammen med meget dygtige front-end folk, der får et website til at se lækre ud.

Det er en forventning hos alle, at en hjemmeside bare fungerer. Som besøgende er du ligeglad med om du er den eneste besøgende, eller om du er der sammen med 100.000 andre brugere på samme tid. Vores hjerne begynder allerede at overveje om en hjemmeside er i stykker, hvis ikke den viser dig noget indenfor det første sekund efter du har klikket dig ind på den.

Hvordan understøtter dit website en pludselig interesse?

Jeg skrev selv en gang et blogindlæg om hvordan en ændring i Facebook’s API gjorde livet surt for udviklere, og hvordan jeg havde arbejdet rundt om problemet. Det viste sig at være et populært emne blandt mange Facebook API-udviklere, så indlægget tiltrak sig stor opmærksomhed, men mit lille 10-kroners webhotel var ikke forberedt på trafikken, og blogindlægget der kunne have givet god omtale og sikkert masser af opgaver blev begrænset af den uventede interesse.

Festivalen Musik i Lejet’s website blev afviklet første gang i 2009. Siden starten er interessen steget eksplosivt hvert år, lige i timerne omkring billetsalget. De eftertragtede billetter bliver hvert år udsolgt på rekordtid – typisk indenfor den første halve time. En ekstern leverandør står for salg af billetter, men selve hjemmesiden oplever også ekstrem trafik lige på det tidspunkt hvor billetterne sættes til salg.

Det er ikke svært at købe sig fattig i store servere, der kan understøtte høje besøgstal. Det er bare penge ud ad vinduet, hvis de står og er arbejdsløse i årets øvrige 364 dage. Og det er her du kan få brug for mig. Du kan sikkert godt få en leverandør til at levere en løsning der kan holde sig i luften under svære vilkår, men det kan godt være at dit budget bliver lidt anstrengt. Festivalen bygger på frivillig arbejdskraft, og har aldrig haft et stort budget, så det er ekstra vigtigt at bruge pengene klogt. Det kræver en bred teknisk baggrundsviden, for det er muligt at optimere og tilpasse alle steder i bunken af teknologier et website er sat sammen af (og i dets netværksmiljø).

Har du brug for et Content Delivery Network?

Du kan f.eks. spare en anseelig mængde ved at stille et såkaldt Content Delivery Network (CDN) foran din webserver. Sådan en løsning vil aflaste din server ved at håndtere levering af de websider og billeder der alligevel ikke ændrer sig over tid – udover at den sikrer brugerne den samme hurtige svartid selv med en pludselig stigning i aktivitet. Et CDN kan også skærme mod angreb, som f.eks. DDoS-angreb, hvor mange computere forsøger at overbelaste din server på samme tid.

Selvom et CDN er en af de mest kost-effektive måder at sikre en stabil brugeroplevelse på dit website, findes der mange andre metoder til at forbedre brugeroplevelsen. Har du brug for hjælp til at få dit website til at skalere, levere gode brugeroplevelser og sikre det mod nedbrud, så ring mig op eller book et møde på Calendly https://calendly.com/nuitdk/30min.

Book 30 minutters møde