Inleiding
Vandaag de dag wordt met een database in de praktijk een zogenoemde relationele database bedoeld. Dat is niet altijd zo geweest: ook voordat het relationele model in 1970 werd bedacht, waren er elektronische databases, zoals IMS en IDMS.
Dat uiteindelijk het relationele model toch de standaard is geworden, is niet vreemd: bij dit model stond de opbouw en de organisatie van een database los van de manier van opslag. Gegevens worden op een gestandaardiseerde manier opgeslagen, buiten de applicatie die de gegevens gebruikt. De inhoud van een database is daardoor veel toekomstbestendiger en kan makkelijker op een andere manier worden gebruikt dan waarvoor de gegevens oorspronkelijk zijn opgeslagen.
Toch voldoet het relationele model niet altijd. Relationele databases blinken niet uit in het verwerken van grote hoeveelheden gegevens of het serveren van gegevens onder hoge druk, tenzij fors wordt geïnvesteerd in hardware. Ook is een relationele database soms simpelweg niet nodig, omdat informatie bijvoorbeeld maar op één manier wordt opgeslagen en complexe query's op data niet nodig zijn. In andere gevallen biedt een relationele database te weinig functionaliteit, bijvoorbeeld bij het leggen van een groot aantal verbanden tussen punten.
Voor dit soort doeleinden zijn NoSQL-databases bedoeld. NoSQL is een verwijzing naar SQL, een door IBM ontwikkelde taal voor het werken met gegevens in een relationele database. SQL is de gangbare taal die wordt gebruikt om te werken met relationele databases. Onder andere MySQL, Microsofts SQL Server, Oracle Database en PostgreSQL leunen zwaar op SQL.
Bij de term NoSQL staat 'No' niet voor 'geen', maar voor not only, waarmee wordt bedoeld dat relationele databases niet overal geschikt voor zijn. Een sluitende definitie van NoSQL is bijna niet te geven, al is er één eigenschap die ze verenigt: ze verschillen op een of meer punten van traditionele relationele databases.

Een IMS-database
Relaties
Een relationele database bestaat formeel uit schema's: een logische container voor het opslaan van gegevensstructuren, bijvoorbeeld tabellen. In die tabellen zijn entiteiten opgeslagen. Elke entiteit neemt één tabelrij in beslag en heeft een of meer attributen. In een rij wordt alle informatie over die entiteit opgeslagen; in een kolom zijn gelijkwaardige attributen over verschillende entiteiten opgenomen. Een relationele database bestaat dus uit twee dimensies. Ook kunnen relaties tussen schema's worden gelegd: informatie uit meerdere tabellen kan worden gecombineerd.

De laatste tijd neemt de populariteit van NoSQL snel toe. NoSQL zet alle principes van een relationele database overboord. Een NoSQL-database kan juist eendimensionaal zijn, zoals MemcacheDB en SimpleDB, of juist in meer dan twee dimensies werken, zoals Cassandra en BigTable. Andere NoSQL-databases zijn weer ontworpen voor het leggen van verbanden.
NoSQL-databases hebben vaak geen of beperkte mogelijkheden voor joins: het combineren van twee schema's oftewel tabellen. Bij NoSQL-databases is dat zeer inefficiënt. In plaats daarvan moet de ontwikkelaar dit soort functionaliteit in zijn applicatie verwerken. Het ontbreken van joins kan een nadeel zijn, maar zorgt er ook voor dat veel NoSQL-databases een belangrijk voordeel hebben: horizontale schaalbaarheid.
Flexibel, maar zwaar
Relationele databases zijn flexibel, maar trekken een relatief zware wissel op een server. Wanneer veel dynamische gegevens worden opgevraagd, kan een databaseserver overbelast raken. De oplossing kan zijn om fors te investeren in hardware.
Horizontaal schalen - het bijplaatsen van servers - is met relationele databases echter erg lastig. Een relationele database die onder hoge druk moet presteren, kan alleen verticaal worden opgeschaald: de server zal simpelweg beter moeten presteren. Dat vereist forse investeringen: krachtige databaseservers van Oracle en IBM kosten al snel honderdduizenden of zelfs miljoenen euro's. Horizontaal schalen is relatief goedkoper: er kunnen servers met relatief eenvoudige hardware worden bijgeplaatst, zodat de performancewinst naar verhouding goedkoop is.
Een andere oplossing is gebruik van het intern geheugen voor caching. Zo kan memcached worden gebruikt om vaak opgevraagde informatie in het geheugen te cachen, en zo de beperkingen van software als MySQL op te vangen. In feite wordt met memcached het opvragen van gegevens uit de database omzeild: hoe complex de query ook is, als het antwoord al in het interne geheugen aanwezig is, kan het snel uitgeserveerd worden. In sommige gevallen is dat echter niet genoeg.
BigTable en Cassandra
Zoekmachines moeten op elke mogelijke zoekopdracht voorbereid zijn. Vaak opgevraagde antwoorden kunnen best gecached worden, maar een zoekopdracht naar een zeldzame Zuid-Amerikaanse plant moet net zo snel kunnen worden uitgevoerd. Het gaat niet alleen om de hoeveelheid requests, maar ook om de complexiteit ervan.
Dat wordt nog moeilijker wanneer zoekresultaten zijn gepersonaliseerd en er dus voor elke gebruiker voor elk zoekresultaat aparte pagina's moeten worden gegenereerd. Om die reden heeft zoekgigant Google een eigen database ontwikkeld: BigTable. Deze database-software wordt in verschillende Google-producten gebruikt en werkt zowel vanaf opslaggeheugen als intern geheugen.
BigTable
BigTable is in staat om met petabytes aan informatie te werken. Bovendien is BigTable ontworpen om horizontaal te schalen: de werklast kan over duizenden servers worden verdeeld. Verder is er ondersteuning voor compressie, en dat is nodig ook: een cel kan meer versies van dezelfde informatie bevatten, waarbij met timestamps wordt gewerkt.
BigTable heeft overeenkomsten met relationele databases, maar werkt in tegenstelling tot een relationele database met het uitlezen van kolommen - verzamelingen attributen dus - in plaats van regels. BigTable is closed-source, maar kan worden gebruikt via Googles App Engine-clouddienst. BigTable is beter geoptimaliseerd voor het uitlezen van gegevens dan voor het schrijven ervan.
Er zijn ook opensource-databases die op hetzelfde idee zijn gebaseerd, zoals Apache HBase, dat op het Hadoop-framework draait. Het pakket is geschreven in Java en is net als BigTable bedoeld voor grote hoeveelheden data. HBase wordt onder meer gebruikt door Facebook.
Requests kunnen worden gedaan via Rest en er is integratie met het Hadoop MapReduce-framework, dat ook al voor het verwerken van grote hoeveelheden data bedoeld is. HBase is vooral bruikbaar in applicaties waarbij het nodig is om op elk moment elke willekeurige entry te kunnen lezen en schrijven.
Cassandra
Facebook heeft indertijd ook zelf een NoSQL-database ontwikkeld: Cassandra. De ontwikkeling van deze software is inmiddels overgenomen door de Apache Software Foundation, die onlangs versie 1.0 aankondigde. Deze database wordt onder meer gebruikt door Reddit en Twitter. Cassandra is eveneens in Java geschreven en heeft zowel trekjes van BigTable als van Dynamo, een door Amazon ontwikkeld key-value-opslagsysteem. Cassandra is vooral geschikt voor het opslaan van gegevens: schrijven gaat sneller dan lezen.
BigTable draait bovenop GFS, het bestandssysteem van Google. GFS zorgt voor replicatie en consistentie, net zoals het Hadoop-bestandssysteem dat doet bij HBase. BigTable en HBase bieden verder ondersteuning voor transacties, waarmee kan worden voorkomen dat complexe opdrachten maar ten dele worden uitgevoerd. Hiermee kan inconsistentie in de data worden voorkomen. Deze ondersteuning is echter minder compleet dan bij de relationele databases. Bovendien blinken NoSQL-databases toch al niet uit in consistentie: horizontale schaalbaarheid is belangrijker.
Het Acid-principe
Relationele databases hanteren doorgaans strikte regels voor het invoeren, uitlezen en bijwerken van informatie. Ze werken volgens het acid-principe: atomicity, consistency, isolation en durability. Zulke databasesoftware zorgt ervoor dat bewerkingen op data niet in elkaars vaarwater zitten, dat alleen volledig afgeronde transacties worden doorgevoerd, dat data goed wordt opgeslagen en dat de database consistent wordt geüpdatet: deze moet altijd hetzelfde antwoord teruggeven.
Het acid-principe maakt relationele databases betrouwbaar, maar levert ook problemen op. Om het acid-principe te handhaven, kunnen entiteiten bijvoorbeeld exclusief door een opdracht worden geclaimd, zodat er niet tegelijkertijd meerdere bewerkingen op worden losgelaten. Dat locken levert echter wel schaalbaarheidsproblemen op. NoSQL-databases doen daarom vaak concessies op dit gebied. Eén of meer van de acid-eigenschappen worden dan geofferd voor betere prestaties.
De Cap-stelling
Het is een dilemma dat bekendstaat als de cap-stelling. Cap staat voor consistency, availability en partition tolerance. Consistency vereist dat een transactie overal wordt doorgevoerd, availability zegt dat een transactie altijd kan worden uitgevoerd, en met partition tolerance wordt bedoeld dat de database blijft doorwerken als de communicatie tussen servers wordt verstoord. Volgens de cap-stelling kan bij het ontwerp van de database maar met twee van deze eigenschappen goed rekening worden gehouden. Relationele databases scoren bijvoorbeeld slecht op het gebied van partition tolerance.
Veel NoSQL-databases doen op andere vlakken concessies. Zo is voor BigTable, MongoDB en HBase de beschikbaarheid het kind van de rekening. Cassandra en SimpleDB leveren weer in op het gebied van consistentie. Deze databases hanteren het principe van eventual consistency: uiteindelijk moeten databaserecords op alle locaties gelijk zijn, maar het kan tijdelijk zo zijn dat op één locatie afwijkende gegevens zijn opgeslagen.
Hoewel het gebrek aan consistentie een nadeel van veel NoSQL-databases is, maakt dat het wel makkelijker om vanuit verschillende locaties data te serveren, en daarmee horizontale schaalbaarheid te bieden. Er zijn overigens uitzonderingen: zo hebben Berkeley DB en het daarop gebaseerde Oracle NoSQL volledige acid-ondersteuning, maar deze zijn weer niet bedoeld om horizontaal te schalen.
Sleutels en waardes
Een type NoSQL-database dat makkelijk horizontaal schaalt, meestal ten koste van de consistentie, is key-value-storage. Dit systeem is net als BigTable-achtige opslag bedoeld voor grote hoeveelheden gegevens. Key-value-opslag is vooral geschikt voor gegevens die heel vaak moeten worden uitgelezen.
De Dynamo-database van Amazon is een goed voorbeeld van een key-value-storagesysteem. "Betrouwbaarheid is een van onze belangrijkste behoeften", zo staat in een paper over Dynamo. "Zelfs de kleinste uitval kan grote financiële gevolgen hebben en het vertrouwen van consumenten ondermijnen."
Amazon moet blijven werken als harde schijven, routers, serverracks of zelfs hele datacenters uitvallen. Gegevens moeten op elk moment toegankelijk zijn. Daarvoor is een relationele database volgens Amazon te veel van het goede: data zou in de meeste gevallen alleen via primary keys worden benaderd; complexere query's worden veel minder vaak uitgevoerd. Dynamo doet niets anders dan het opslaan van een waarde bij een primary key, en kan daardoor veel efficiënter zijn dan een complexe relationele database.
Amazon SimpleDB is gebaseerd op Dynamo en wordt via Amazon Web Services als commerciële dienst aangeboden. Er zijn nog veel andere key-value-databases, zoals Membase, MemcacheDB, Riak en Redis. Onlangs introduceerde ook Oracle een NoSQL-database, die is gebaseerd op de Java-implementatie van de Berkeley DB-opensourcedatabase, die vooral in embedded-systemen wordt gebruikt.
Document-DB's
Enigszins verwant aan key-value-storage is de document-oriented database, zoals MongoDB, CouchDB en Terrastore. Een tabel in een document-db bestaat, simpel gezegd, uit een verzameling key-value-eenheden. In elke entry kunnen verschillende soorten informatie worden opgeslagen, zonder dat de tabelstructuur hoeft te worden gewijzigd.
Een populaire document-db is MongoDB, die werkt met opslag van json-documenten. De software is geschreven in C++ en is als binary beschikbaar voor Windows, Linux, OS X en Solaris. MongoDB biedt bepaalde mogelijkheden die SQL ook biedt, zoals dynamische query's en indexen. De query's zijn in feite javascript-expressies.
Apache CouchDB biedt ongeveer dezelfde functionaliteit, maar is trager dan MongoDB. Wel biedt CouchDB, in tegenstelling tot veel andere NoSQL-databases, ondersteuning voor acid-transacties. Ook CouchDB werkt met json-documenten en is hoofdzakelijk geschreven in Erlang, waardoor het onder meer op Linux, Mac OS X en Windows draait.
Graafdatabases
Minder schaalbaar dan andere NoSQL-databases zijn graafdatabases. Zoals de naam wellicht al doet vermoeden, is de structuur van deze databases gebaseerd op grafen. Bij deze databases zijn onderlinge verbanden het uitgangspunt. Er is geen centrale index; in plaats daarvan worden er recursieve verbanden tussen entry's gelegd.
Graafdatabases kunnen bijvoorbeeld worden gebruikt voor sociale-netwerksites of wiki's, waarbij sprake is van een groot aantal onderlinge verbanden. Het is inefficiënt om voor elk mogelijk verband een sql-query uit te voeren, als er ook rechtstreekse verwijzingen naar andere data kunnen worden opgeslagen. Een populaire graafdatabase is de opensource-Java-database Neo4j.
Tot slot
NoSQL-databases zijn er in vele soorten en maten, en in veel gevallen doen ze iets wat met relationele databases minder goed kan. Met name horizontaal schalen is voor de gigantische databases van onder meer zoekmachines een groot pluspunt. Hoewel NoSQL-databases de afgelopen tijd steeds populairder zijn geworden, betekent dat niet dat relationele databases gaan verdwijnen. Voor veel doeleinden voldoen die namelijk prima: het is geen toeval dat ze de afgelopen dertig, veertig jaar tot de facto standaard zijn uitgegroeid.
Door de massaliteit van het internet is er echter een behoefte aan alternatieven ontstaan. De komende tijd zullen we daarom meer van NoSQL-databases gaan horen. Opensourceprojecten als Cassandra, HBase, CouchDB en MongoDB worden steeds stabieler en krijgen steeds meer functionaliteit. Het gevaar bestaat echter ook dat 'NoSQL' tot een buzzword verwordt, net zoals bijvoorbeeld 'cloud computing'. Beide begrippen zijn even uitgebreid als nietszeggend en het is daarom belangrijk in het achterhoofd te houden dat NoSQL-databases niet overal de oplossing voor zijn.