Meir om spørjingar og organisering av data i Cloud Firestore
Frå datamodellering med relasjonsdatabasar (SQL) er du kanskje vand til at data blir organisert over fleire tabellar som har relasjonar til kvarandre. Om vi til dømes har ein database over hotell og vil registrere hotellromma på kvart enkelt hotell, ville vi i SQL ha laga ein tabell for hotell og ein tabell for hotellrom. Så hadde vi kopla desse saman med ein ein-til-mange-relasjon.
I dokumentbaserte databasar (NoSQL) blir data organiserte på ein annan måte. Sidan kvart enkelt databaseobjekt er lagra som eit frittståande dokument, med i utgangspunktet ingen reglar for kva data som skal inn i kvart enkelt dokument, kan vi ikkje basere oss på koplingar med nøklar og framandnøklar, slik som i SQL. I dokumentbaserte databasar er dokument i staden organiserte i samlingar (collections) og undersamlingar (subcollections). Hotelldatabasen i dømet vårt vil då vere organisert med alle hotella i ei samling, og romma vil vere undersamlingar til kvart hotell.
Dette kan verke ulogisk om du er vand til relasjonsdatabasar, der det blir lagt mykje vekt på struktur, og der det er eit viktig prinsipp å unngå dobbeltlagring, men begge modellane følger det same prinsippet: Eitt hotell har fleire rom, og eitt rom høyrer til eitt hotell.
NoSQL gir deg derimot meir fleksibilitet. Det er ingenting i vegen for at fleire hotell har like romnummer, som dei ofte har, fordi romma blir lagra under kvart hotell, og ID-ane treng då berre å vere unike for kvart hotell. Det er heller ikkje noko problem om eit hotell ikkje har romnummer, men unike namn på romma, eller kombinasjonar av bokstavar og tal. Det kan òg variere kva slags informasjon som er relevant å ha med i databasen ut frå profilen til hotellet. Nokre hotell har kanskje fokus på velvære og vil registrere om rommet har boblebad, steamdusj eller massasjestolar, mens andre vil berre registrere om rommet har bad eller ikkje. Det er ikkje noko problem i ein NoSQL-database.
Kva med mange-til-mange-relasjonar? Sjå for deg ein database for å registrere elevar, kva fag dei har teke, og kva karakter dei har fått i dei ulike faga. Ein datamodell for denne relasjonsdatabasen kan sjå slik ut:
I Firebase kan dette gjerast på nesten same måte ved å lage to parallelle samlingar for elevar og fag og ei eiga samling for å halde orden på kva elevar som har teke kva fag, og kva karakterar dei har fått.
Forskjellen på dette og ein mange-til-mange-relasjon i SQL er korleis spørjingar fungerer. I SQL kunne vi ha brukt ei spørjing med JOIN for å hente data frå fleire tabellar samtidig. NoSQL har ikkje støtte for framandnøklar og JOIN-operasjonar, så for å hente ut data frå fleire tabellar, må vi køyre fleire separate spørjingar. I NoSQL kan vi heller ikkje definere på førehand kva felt vi vil hente ut, slik som vi kan gjere i SQL med SELECT.
For å hente ut namn og karakter på alle elevar i faget utvikling kunne SQL-spørjinga ha sett slik ut:
I Cloud Firestore må vi lage fleire åtskilde spørjingar, slik:
Dersom du har brukt SQL før, veit du at du i SQL kan kombinere vilkår, sorterting, gruppering og meir for å få akkurat det resultatet du ønsker frå databasen. På grunn av måten data er organisert i Cloud Firestore på, er det ein del avgrensingar på korleis du kan forme ut spørjingar. Dersom du har eit vilkår (where()
), kan du ikkje sortere (orderBy()
) etter noko anna enn den parameteren du brukte i vilkåret.
I dette dømet vil du få ei feilmelding fordi det er brukt ulike parametrar i where()
(alder) og orderBy()
(etternamn). Dette er fordi ei slik spørjing vil ta lengre tid å gjennomføre, og det vil skape meir trafikk til og frå databasen. Det er likevel mogleg å gjennomføre ei slik spørjing ved å lage ein samansett indeks (composite index) i Firebase-konsollen. Dette er det mogleg å gjere direkte frå feilmeldinga du får dersom du prøver å køyre spørjinga i dømet. Feilmeldinga vil innehalde ei lenke til Firebase-konsollen som lar deg opprette akkurat den samansette indeksen du treng, men du bør vere varsam med å lage for mange, då du berre har moglegheit til å lage 50 samansette indeksar til kvar database. Det er meir formålstenleg å sortere resultatet du får tilbake (som ein array) enn at Firestore sorterer dette for deg.
På same måte vil du i utgangspunktet ikkje kunne køyre spørjingar mot fleire undersamlingar samtidig. I hotelldømet over vil du til dømes ikkje kunne søke etter ledige dobbeltrom frå fleire hotell samtidig. Dette kan òg løysast ved å lage ein samansett indeks i Firebase-konsollen, eller du kan køyre fleire separate spørjingar mot kvart hotell og samle resultata i ei liste (array), som du kan sortere og søke i via ditt eige skript.
Meir informasjon
Firebase tilbyr informasjon om korleis Firestore-databasen er bygd opp, og korleis han blir brukt i videospelelista "Get to know Cloud Firestore" på YouTube.
Her er lenke til to videoar som forklarer prinsippa bak det du har lese om i denne artikkelen:
Relatert innhald
Ved hjelp av datamodellering planlegg ein korleis ein database skal byggjast opp ved å setje opp tabellar og angi kva forhold desse har til kvarandre.
Når vi skal hente data frå Cloud Firestore, kan vi hente ut eitt enkelt dokument, alle dokumenta i ei samling, eller vi kan hente data med spørjingar.