CouchDB conosciamolo meglio

couchDBQuesto articolo e’ la continuazione della precedente “Introduzione a CouchDB” per cui riprenderemo alcune informazioni di base gia viste per poi allargare alcuni importanti concetti ed aspetti che riguardano questo interessantissimo documentale via HTTP.


Apache CouchDB
e’ un moderno documentale, document-oriented, richiamabile semplicemente con l’HTTP e che al tempo stesso offre le piu’ avanzate funzionalita’ di replicazione dati e di ricerca in parallelo (Map/Reduce).

Caratteristiche

Scritto in: Erlang
Punto principale: Consistenza DB consistency, facilità d’uso
Licenza: Apache
Protocolli: HTTP/REST
Replicazione bidirezionale continua o ad-hoc con individuazione dei conflitti, replicazione master-master
MVCC – le operazioni di scrittura non bloccano le letture
Sono disponibili le versioni precedenti dei documenti
Progettazione crash-only (reliable)
Necessità di compattazioni nel tempo
Viste: embedded map/reduce
Viste formattate: lists & shows
Possibilità di validazione server-side dei documenti
Possibile autenticazione
Aggiornamenti real-time attraverso _changes (!)
Gestione degli allegati e, CouchApps (standalone js apps)
libreria jQuery inclusa
Utilizzo ideale: Per accumulazione dei dati con cambi occasionali sui quali vengono eseguite query predefinite. Situazioni in cui la gestione delle versioni è importante.
Per esempio: CRM, sistemi CMS. Situazioni in cui la replicazione master-master è una caratteristica interessante (ad esempio multisito).

In CouchDB non esistono tabelle. Il contenuto informativo è suddiviso in diversi database che fungono da contenitori di documenti con strutture potenzialmente disomogenee tra di loro. Il documento è il fulcro di questo software (e di quelli che come lui condividono l’approccio document-oriented).
Un documento è formato da un insieme di coppie chiave-valore.
A differenza dei database relazionali CouchDB non possiede il concetto di schema e quindi ogni documento in ogni database può essere strutturato in modo diverso dagli altri.

Le uniche due chiavi obbligatorie sono:
_id serve per identificare univocamente il documento (è comparabile, semanticamente, alla chiave primaria dei database relazionali)
_rev viene utilizzata per la gestione delle revisioni, ad ogni operazione di modifica infatti la chiave “_rev” viene aggiornata (questo meccanismo è alla base della prevenzione dei conflitti
in fase di salvataggio su CouchDB).

Questo accorgimento permette inoltre di poter interrogare il DBMS su versioni del documento non più attuali in quanto, con un approccio simile a quello di Subversion, CouchDB mantiene memoria di ogni revisione, da quella iniziale alla più recente.

L’altra grande differenza rispetto ai tradizionali RDBMS è il meccanismo di gestione delle query. Nei database relazionali una volta specificate e popolate le tabelle è possibile eseguire query utilizzando un linguaggio conosciuto come SQL (ne esistono vari dialetti ma il concetto non cambia nell’essenza);
a fronte di una query il RDBMS utilizza indici interni e le proprie relazioni per costruire in tempo reale una tabella di risultato (che può, nelle query più semplici, essere un sottoinsieme della tabella di partenza).

Questa soluzione riesce ad essere performante in quanto i dati sono strutturati con questo preciso scopo; inoltre il database non deve conoscere a priori le query che verranno eseguite ma può rispondere a qualsiasi interrogazione, purché sia stilata usando SQL valido.

Consistenza dei dati e replicazione

CouchDB non utilizza alcun meccanismo di locking ma sfrutta l’MVCC (Multiversion Concurrency Control): ogni modifica di un oggetto ne crea una nuova versione. Le versioni precedenti non vengono cancellate. Se due modifiche vanno in conflitto poiche’ accedono allo stesso documenti, la seconda riceve un errore in save. L’applicazione deve riprendere l’ultima versione del documento e rieseguire l’UPDATE.
L’isolamento e’ mantenuto solo a livello di un singolo documento, questa e’ una notevole semplificazione, rispetto alla complessa logica transazionale di altri database, ma consente l’ottimizzazione, la parallelizzazione e la distribuzione dei dati in modo semplice. A livello di accesso al file di dati ogni singola modifica ad un documento rispetta le proprieta ACID (Atomic Consistent Isolated Durable) con la serializzazione delle modifiche sui documenti e la scrittura sincrona sul disco.

Piu’ database CouchDB possono essere collegati tra loro in modo molto semplice. I database vengono aggiornati tra loro con una replicazione peer-to-peer incrementale implementata nativamente nell’engine. CouchDB permette una replicazione bidirezionale asincrona, utilizza un meccanismo automatico di risoluzione dei conflitti e fornisce una eventual consistency tra i database. Se i database sono ospitati su nodi differenti si ottiene con questo la distribuzione dei dati.
La replicazione di CouchDB puo’ essere utilizzata sia per sincronizzare database locali che per complesse configurazioni con sharding dei dati.

Per lavorare su CouchDB esiste anche la possibilita’ di installare CouchApp, in pratica una serie di script che permettono di costruire completi applicazioni stand-alone per il database usando solo HTML e JavaScript. Poiche’ il database stesso risponde in HTTP e’ possibile concentrare su un solo nodo (eventualmente replicabile) la classica pila applicativa web a tre livelli.

CouchDB si e’ cosi’ rapidamente imposto sul mercato, diventando uno tra i piu’ usati database non relazionali. In pratica i due piu’ diffusi NoSQL documentali sono CouchDB e MongoDB: entrambi sono velocissimi (memorizzano i dati in BSON/JSON), sono scalabili in modo nativo su piu’ nodi e non forniscono un’interfaccia SQL.

Per una documentazione piu’ dettagliata si rimanda al sito ufficiale di Apache CouchDB.

 

Per ora e’ tutto, alla prossima e, buon divertimento!

Not Only SQL

NoSQL Database

NoSQL Database

NoSQL è l’acronimo di “Not only SQL” e viene usato generalmente per indicare quei database che non usano un modello di dati relazionale e quindi potrebbero non usare SQL come linguaggio di interrogazione. Dunque il concetto è di per se’ stesso più antico dei RDBMS, eppure è tornato in auge quando, per varie motivazioni, i database non relazionali hanno mostrato diversi vantaggi, rispetto ai database SQL tradizionali.

Una delle principali motivazioni per l’uso di tali database è rappresentata dalla scalabilità. La scalabilità è un requisito sempre più importante per le applicazioni web, e ciò è dovuto a molti fattori: l’esplosione del numero di utenti della rete (letteralmente esponenziale negli ultimi dieci anni secondo i dati del ISC Domain Survey ), la sempre maggiore diffusione di OpenID, quindi la sinergia tra le varie community e tra esse e i fornitori di servizi, ma anche la crescente disponibilità di dispositivi con accesso ad Internet come smartphone, tablet e altri dispositivi portatili.

La scalabilita’ 

La scalabilita’ orizzontale si ha se l’aumento delle risorse si riferisce all’aumento dei nodi nel sistema, cioè il sistema riesce a parallelizzare il carico di lavoro e gestire il

  • fault tolerance
  • load balancing
  • high availability

Avere piu’ macchine per poter disrtibuire e replicare i dati su piu’ nodi, questo lo rende ideale per ambienti quali

  • ambienti distribuiti
  • affidabilita’
  • elevate prestazioni

il tutto in bundle , senza bisogno di software aggiuntivi.

Scalabilità verticale

La scalabilità verticale si ottiene quando, per aumentare le prestazioni dell’intero sistema, si aumentano le risorse di un singolo nodo del sistema, ad esempio utilizzando una CPU con frequenza maggiore o incrementando la memoria disponibile. Il vantaggio di questo tipo di scalabilità è che generalmente non è necessario modificare le applicazioni, ne’ sono richiesti interventi amministrativi. Lo svantaggio consiste innanzitutto nel costo, perche’ l’aggiornamento spinto di una macchina può essere economicamente molto più gravoso dell’acquisto di una ulteriore macchina di pari potenza.

I principali metodi d’implementazione dei database NoSQL sono i seguenti:

Coloumnfamily: i dati sono organizzati in righe e colonne, ma le righe possono avere quante colonne si vogliono e non c’è bisogno di definire le colonne come prima cosa.

Document store: è l’evoluzione del metodo key/value, rispetto ai normali database relazionali invece che immagazzinare i dati in tabelle con dei campi fissi, questi vengono messi in un documento che può contenere illimitati campi di illimitata lunghezza, così se ad esempio di una persona conosciamo solo nome e cognome, ma magari di un’altra persona anche indirizzo, data di nascita e codice fiscale, si evita che per il primo nominativo ci siano campi inutilizzati che occupano inutilmente spazio.

Graph: i dati vengono immagazzinati sotto forma di strutture a grafi, rendendo più performante l’accesso a questi da applicativi orientati agli oggetti.

Key/Value: in questo caso i dati vengono immagazzinati in un elemento che contiene una chiave assieme ai dati veri e propri, questo metodo è il più semplice da implementare, ma anche il più inefficiente se la maggior parte delle operazioni riguardano soltanto una parte di un elemento.

 

Pro e Contro dei database non relazionali

Vantaggi

  • Dato che un elemento contiene tutte le informazioni necessarie non serve usare i dispendiosi (in termini di performance) JOIN come invece avviene per i database relazionali.
  • La semplicità di questi database è uno degli elementi fondamentali, è proprio questo che permette di scalare in orizzontale in maniera così efficiente, molti NRDBMS, infatti, permettono di aggiungere nodi a caldo in maniera impercettibile dall’utente finale.
  • Scegliendo un database adatto alla mappatura più diretta alle object classes del proprio applicativo si possono ridurre di molto i tempi dedicati allo sviluppo del metodo di scambio dati tra il database e l’applicativo stesso (il cosiddetto object-relational mapping che è invece necessario in presenza di database relazionali).

Svantaggi

  • La semplicità di questi database, però, porta anche alla mancanza dei controlli fondamentali sull’integrità dei dati, il compito ricade quindi totalmente sull’applicativo che dialoga col database che ovviamente dovrebbe essere testato in modo molto approfondito prima di essere messo in produzione. Per fare un esempio, se avessimo un database dei clienti coi relativi ordini effettuati immagazzinati in elementi diversi, anche se è possibile definire una relazione attraverso le chiavi, in un database non relazionale alla cancellazione di un cliente tutti gli ordini resterebbero comunque nel database, è quindi l’applicativo che una volta impartito il comando di cancellazione dell’utente X deve anche andare a cancellare tutti i relativi ordini, cosa che invece in un database relazionale è gestita direttamente dal database stesso.
  • La mancanza di uno standard universale (come può essere l’SQL) è un’altra delle pecche di questi database non relazionali, ogni database ha infatti le proprie API e il suo metodo di storing e di accesso ai dati. Detto questo, risulta palese che se lo sviluppo del database sul quale abbiamo basato il nostro applicativo venisse interrotto, il passaggio ad un altro database non sarebbe sicuramente una cosa immediata, ma richiederebbe alcuni cambi più o meno radicali da apportare all’applicativo, è quindi bene tenere in considerazione la cosa al momento del brainstorming iniziale.