Introduzione a GlusterFS: uno storage scalabile e distribuito

GlusterFS è un file system open source distribuito e scalabile orizzontalmente, la cui capacità può essere dinamicamente espansa mediante l’aggiunta di nuovi nodi. GlusterFS è in grado di arrivare a gestire fino a diversi peta byte, migliaia di client e diverse aree dati (storage) organizzandole in blocchi che rende accessibili su Infiniband RDMA (remote direct memory access, fibra ottica) o connessioni TCP/IP.
Le risorse “memoria e disco” vengono rese disponibili sotto un unico punto di condivisione e tali risorse possono essere montate dai client mediante tre diversi protocolli: CIFS, NFS od il client nativo Gluster.
Questo articolo effettua una prova su strada di GlusterFS, introducendone i concetti e sperimentandone le funzionalità.

Introduzione

Nel file system Gluster, il termine con cui si identifica una risorsa condivisa è volume, ossia un insieme logico di blocchi (bricks), dove per blocco si intende una directory esportata da un server compreso nel pool degli storage fidati (trusted storage pool).

I termini base necessari a comprendere il funzionamento di GlusterFS sono quindi i seguenti:

  • brick: rappresenta il filesystem effettivo che verrà assegnato ad un volume;
  • translator: una potente componente (sotto forma di shared object) che consente di estendere le funzionalità del filesystem originale (il brick);
  • subvolume: un brick dopo che è stato processato da almeno un translator;
  • volume: la condivisione effettiva, dopo che è passata per tutti i translator;
  • server: la macchina (virtuale o reale) che ospita il filesystem ed all’interno della quale verranno registrati i dati;
  • client: la macchina che monta il volume (che può agire anche da server);

Esistono diverse tipologie di volume, e principali sono le seguenti:

  • Distributed: distribuisce i file all’interno dei brick del volume;
  • Replicated: replica i file nei brick del volume;
  • Striped: blocchi di dati (stripes) vengono registrati nei brick del volume;
  • Distributed striped: distribuisce i file nei blocchi di dati (stripes) presenti nei brick del volume;
  • Distributed replicated: distribuisce i file nelle repliche presenti nei brick del volume;

A queste tipologie si aggiungono le combinazioni Distributed striped replicated e Striped replicated, i cui nomi sono autoesplicativi. Per ulteriori approfondimenti, consultare la documentazione ufficiale del progetto presso il sito ufficiale, capitolo 5, “Setting up GlusterFS Server Volumes“.

Come riportato da Wikipedia, la logica, il funzionamento e la gestione di GlusterFS sono estremamente semplici: non è necessaria la configurazione di un cluster per gestire l’accesso condiviso contemporaneo alla stessa area dati: è infatti il demone stesso, glusterd, ad occuparsi di questo aspetto. GlusterFS supporta anche la replica geografica, che prevede la replica asincrona di un volume su un server dislocato non per forza nella stessa rete degli altri nodi. Si pensi alla portata di tale aspetto nell’ambito backup.

glusterFS rappresenta la soluzione ottimale nel momento in cui si necessita di un’area dati condivisa, accessibile da più nodi e facilmente espandibile in termini di spazio.

Mettere le cose in pratica

Per simulare un’ambiente operativo sono state preparate tre macchine linux su cui è stato installato Gluster. Su due sistemi è stata configurato un file system condiviso mediante Gluster, montato attraverso il client nativo glusterfs sulla terza macchina.

La distribuzione Linux utilizzata è Ubuntu server 12.04. La scelta è stata fatta in base alla presenza del software Gluster versione 3.3, già pacchettizzata senza necessità di essere compilato.
Il software installato si può scaricare qui.

Per installarlo è stato dato il seguente comando:

# sudo su
# dpkg -i glusterfs_3.3.0-1_amd64.deb

Su entrambi i server è necessario creare l’area che si vuole rendere disponibile come “brick” :

# mkdir /gluster

Per questioni di performance, l’area del filesystem da destinare a brick viene formattata come xfs.
Nelle macchine di test è stata quindi riservata una partizione apposita (un logical volume, /dev/vgbase/gluster), formattata in xfs:

# mkfs.xfs /dev/vgbase/gluster 
meta-data=/dev/vgbase/gluster    isize=256    agcount=4, agsize=25856 blks
         =                       sectsz=512   attr=2, projid32bit=0
data     =                       bsize=4096   blocks=103424, imaxpct=25
         =                       sunit=0      swidth=0 blks
naming   =version 2              bsize=4096   ascii-ci=0
log      =internal log           bsize=4096   blocks=1200, version=2
         =                       sectsz=512   sunit=0 blks, lazy-count=1
realtime =nessuno                extsz=4096   blocks=0, rtextents=0

Il motivo dell’utilizzo del filesystem xfs è presto detto: utilizzare XFS su ogni brick che esporta spazio consente di avere brick larghi fino a 9 milioni di terabytes [1], limitando lo spazio di una condivisione Gluster a 6.75 X 10^9 TeraBytes (Uno spazio veramente immenso).

mount /dev/mapper/vgbase-gluster /gluster/

Il comando per gestire questo tipo di file system condiviso è gluster, per avere l’elenco delle opzioni disponibili digitare gluster help.

Avviare il demone di gluster:

# service glusterd start
 * Starting glusterd service glusterd      [ OK ]

Per inserire un host nel pool dei server disponibili a condividere brick, eseguire il seguente comando per ogni nodo coinvolto:

# gluster peer probe <nome host>

Seguendo sul nodo interessato l’avvenuta aggiunta:

# tailf /var/log/glusterfs/etc-glusterfs-glusterd.vol.log 
[2012-07-29 17:22:28.090065] I [glusterd-handshake.c:397:glusterd_set_clnt_mgmt_program] 0-: Using Program glusterd mgmt, Num (1238433), Version (2)
[2012-07-29 17:22:28.090166] I [glusterd-handshake.c:403:glusterd_set_clnt_mgmt_program] 0-: Using Program Peer mgmt, Num (1238437), Version (2)
[2012-07-29 17:22:28.092803] I [glusterd-rpc-ops.c:218:glusterd3_1_probe_cbk] 0-glusterd: Received probe resp from uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2, host: 192.168.122.11
[2012-07-29 17:22:28.094504] I [glusterd-rpc-ops.c:286:glusterd3_1_probe_cbk] 0-glusterd: Received resp to probe req
[2012-07-29 17:22:28.094617] I [glusterd-rpc-ops.c:328:glusterd3_1_friend_add_cbk] 0-glusterd: Received ACC from uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2, host: 192.168.122.11, port: 0
[2012-07-29 17:22:28.094677] I [glusterd-sm.c:509:glusterd_ac_send_friend_update] 0-: Added uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2, host: 192.168.122.11
[2012-07-29 17:22:28.099684] I [glusterd-handler.c:1627:glusterd_handle_friend_update] 0-glusterd: Received friend update from uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2
[2012-07-29 17:22:28.099786] I [glusterd-handler.c:1672:glusterd_handle_friend_update] 0-: Received uuid: 87b31a4c-86ce-493d-a4b2-e59766439b58, hostname:192.168.122.12
[2012-07-29 17:22:28.099821] I [glusterd-handler.c:1681:glusterd_handle_friend_update] 0-: Received my uuid as Friend
[2012-07-29 17:22:28.099987] I [glusterd-rpc-ops.c:510:glusterd3_1_friend_update_cbk] 0-management: Received ACC from uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2

Il nodo da cui i comandi vengono lanciati non necessita di essere aggiunto:

root@ubuntu-vm:~# gluster peer probe 192.168.122.11
Probe on localhost not needed

Per verificare quali sono gli host inseriti nel pool, ed eventualmente il loro stato, sul nodo primario è possibile lanciare il comando:

# gluster peer status
Number of Peers: 1
 
Hostname: 192.168.122.12
Uuid: 87b31a4c-86ce-493d-a4b2-e59766439b58
State: Peer in Cluster (Connected)

Lo stesso comando, lanciato sul secondo nodo, produrrà un output differente:

# gluster peer status
Number of Peers: 1
 
Hostname: 192.168.122.11
Uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2
State: Peer in Cluster (Connected)

Su uno dei nodi inseriti nel pool definire il volume replicato da condividere:

# gluster volume create gluster-share replica 2 transport tcp 192.168.122.11:/gluster 192.168.122.12:/gluster
Creation of volume gluster-share has been successful. Please start the volume to access data.

Dopo aver definito il volume bisogna farlo partire:

# gluster volume start gluster-share
Starting volume gluster-share has been successful

Per sapere lo stato dei volumi:

# gluster volume info
 
Volume Name: gluster-share
Type: Replicate
Volume ID: 3524f420-ea06-4b5b-b311-58050ac86e22
Status: Started
Number of Bricks: 1 x 2 = 2
Transport-type: tcp
Bricks:
Brick1: 192.168.122.11:/gluster
Brick2: 192.168.122.12:/gluster

Per sapere lo stato di un volume in particolare:

# gluster volume info gluster-share

Dopo aver configurato ed attivato il volume, si procede con il montarlo (su una macchina); nell’ambiente di test si è deciso di utilizzare il client nativo gluster:

# mkdir /gluster-share
# mount.glusterfs 192.168.122.11:/gluster-share /gluster-share

Test funzionale

Per testare la funzionalità del sistema, verrà spento il primo nodo, controllando sul nodo sopravvissuto la rilevazione del guasto:

# tailf /var/log/glusterfs/etc-glusterfs-glusterd.vol.log 
[2012-07-29 17:39:23.362429] I [glusterd-handler.c:542:glusterd_req_ctx_create] 0-glusterd: Received op from uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2
[2012-07-29 17:39:23.524278] I [glusterd-utils.c:1192:glusterd_volume_start_glusterfs] 0-: About to start glusterfs for brick 192.168.122.12:/gluster
[2012-07-29 17:39:23.542639] I [glusterd-handler.c:1458:glusterd_op_commit_send_resp] 0-glusterd: Responded to commit, ret: 0
[2012-07-29 17:39:23.542718] I [socket.c:1798:socket_event_handler] 0-transport: disconnecting now
[2012-07-29 17:39:23.542745] I [socket.c:1798:socket_event_handler] 0-transport: disconnecting now
[2012-07-29 17:39:23.542771] I [socket.c:1798:socket_event_handler] 0-transport: disconnecting now
[2012-07-29 17:39:23.544404] I [glusterd-handler.c:1359:glusterd_handle_cluster_unlock] 0-glusterd: Received UNLOCK from uuid: 03aa3e91-3124-47ff-af00-a57f9742d7b2
[2012-07-29 17:39:23.544584] I [glusterd-handler.c:1335:glusterd_op_unlock_send_resp] 0-glusterd: Responded to unlock, ret: 0
[2012-07-29 17:39:23.566773] I [glusterd-pmap.c:238:pmap_registry_bind] 0-pmap: adding brick /gluster on port 24009
[2012-07-29 17:47:28.688821] W [socket.c:1512:__socket_proto_state_machine] 0-management: reading from socket failed. Error (Transport endpoint is not connected), peer (192.168.122.11:24007)

Lato client (la macchina che monta il filesystem remotamente) viene rilevata l’anomalia:

# tailf /var/log/glusterfs/gluster-share.log 
[2012-07-29 17:41:50.928694] I [fuse-bridge.c:4193:fuse_graph_setup] 0-fuse: switched to graph 0
[2012-07-29 17:41:50.928884] I [client-handshake.c:453:client_set_lk_version_cbk] 0-gluster-share-client-1: Server lk version = 1
[2012-07-29 17:41:50.928924] I [client-handshake.c:453:client_set_lk_version_cbk] 0-gluster-share-client-0: Server lk version = 1
[2012-07-29 17:41:50.929069] I [fuse-bridge.c:3376:fuse_init] 0-glusterfs-fuse: FUSE inited with protocol versions: glusterfs 7.13 kernel 7.17
[2012-07-29 17:41:50.930877] I [afr-common.c:1964:afr_set_root_inode_on_first_lookup] 0-gluster-share-replicate-0: added root inode
[2012-07-29 17:47:28.664518] W [socket.c:1512:__socket_proto_state_machine] 0-gluster-share-client-0: reading from socket failed. Error (Transport endpoint is not connected), peer (192.168.122.11:24009)
[2012-07-29 17:47:28.664628] I [client.c:2090:client_rpc_notify] 0-gluster-share-client-0: disconnected
[2012-07-29 17:47:28.665911] W [socket.c:1512:__socket_proto_state_machine] 0-glusterfs: reading from socket failed. Error (Transport endpoint is not connected), peer (192.168.122.11:24007)
[2012-07-29 17:48:13.060541] E [socket.c:1715:socket_connect_finish] 0-gluster-share-client-0: connection to 192.168.122.11:24009 failed (No route to host)
[2012-07-29 17:48:13.060771] E [socket.c:1715:socket_connect_finish] 0-glusterfs: connection to 192.168.122.11:24007 failed (No route to host)

Ma operativamente non cambia nulla:

# mount
...
...
192.168.122.11:/gluster-share on /gluster-share type fuse.glusterfs (rw,default_permissions,allow_other,max_read=131072)
# ls /gluster-share
glusterfs_3.3.0-1_amd64.deb

Conclusioni

E’ facile capire come le potenzialità di questo progetto siano enormi. Uno storage scalabile che possegga la semplicità di configurazione e la dinamicità di GlusterFS rappresenta qualcosa di estremamente utile nell’attuale mercato tecnologico. E’ credibile pensare di poter iniziare a rinunciare a storage preconfezionati? Soltanto il tempo lo dirà. Certo GlusterFS avrà la sua parte da recitare, non a caso il progetto è stato acquisito da Red Hat.