Cos’è un cluster ?
Articolo del 06-05-2009

Un cluster può essere definito come un insieme di computer, o nodi, che cooperano tra loro attraverso un canale di comunicazione che tipicamente è una rete Ethernet. Lo scopo principale di un cluster ad alta disponibilità (High Availability Cluster) è quello di gestire servizi, noti anche come risorse, con un’elevata continuità.
Lo stato del cluster è costituito dall’insieme degli stati di tutti i nodi e di tutte le risorse.


Il ruolo di Pacemaker in HA Linux

Pacemaker (noto anche come CRM, Cluster Resource Manager) è un programma per sistemi operativi Linux col compito di gestire le risorse di un cluster ad alta disponibilità (HA: High-Availability). Pacemaker utilizza l’infrastruttura di un cluster (OpenAIS oppure Heartbeat) per avviare, chiudere e monitorare lo stato di salute dei servizi (chiamati anche risorse) forniti da un cluster. I test si sono spinti fino a mettere assieme 16 nodi gestiti con successo con Pacemaker.
Di seguito viene illustrata l’architettura software di un cluster basato su Pacemaker (fonte immagine http://clusterlabs.org/):

Crm

Figura 1 – Architettura software del cluster

Le componenti più importanti:
1. CIB (Cluster Information Base, è un file XML contenente la configurazione e lo stato attuale del cluster. E’ presente ed uguale su tutti i nodi)
2. CRMd (Cluster Resource Management daemon, è il daemon di Pacemeaker che gira su ogni nodo, ma solo su uno svolge anche il ruolo di DC, Designated Coordinator. Il DC istruisce il Local Resource Manager, o i CRMd degli altri nodi, nella gestione delle risorse)
3. PEngine (PE o Policy Engine, calcola lo stato ideale del cluster e fornisce le direttive al DC)
4. STONITHd (Shoot The Other Node In The Head, arresta i nodi 'erranti' con lo scopo di proteggere i dati)

Heartbeat include Pacemaker (o CRM) fino alla versione 2.1.4, a partire dalle versioni successive è necessario installare sul nodo sia Heartbeat che Pacemaker.
Sinteticamente, si può dire che Pacemaker collabora con Heartbeat (oppure con OpenAIS) per gestire i nodi di un cluster e farli comunicare tra loro.

La configurazione di Pacemaker in generale

Il file cib.xml è costituito da due sezioni principali: la configurazione e lo stato del cluster.
Lo stato del cluster contiene a sua volta la storia dei nodi e delle risorse per derivare la situazione attuale del cluster.
La configurazione contiene quattro importanti sottosezioni:
- Opzioni di configurazione (crm_config)
- Nodi
- Risorse
- Relazioni tra risorse (Constraints)

ATTENZIONE: Non modificare a mano il file cib.xml, utilizzare i tool forniti da Pacemaker. Per le operazioni principali, dopo avere predisposto alcuni file come di seguito indicato, è sufficiente l’utilizzo dell’interfaccia grafica hb_gui.

In pratica non c’è bisogno di impostare/modificare le Opzioni di configurazione, visto che vengono aggiornate automaticamente. Cosa diversa avviene per le altre sottosezioni.

Installazione e configurazione del cluster

Per queste operazioni si fa riferimento alla versione Linux CentOS 5.3 e alla versione Heartbeat 2.1.3. Si assume che i nodi siano due e che i nomi, restituiti dal comando uname –n, siano: nodo-a (10.10.0.11) e nodo-b (10.10.0.22). I servizi/risorse da tenere sempre attivi siano:

- un indirizzo IP: 10.10.0.100 (sul quale risponde un server web)
- un server web (apache)

Eseguire le seguenti operazioni sui due nodi, creazione utente, gruppo e installazione di heartbeat:

[root@nodo-a ~]# groupadd haclient
[root@nodo-a ~]# useradd hacluster -g haclient
[root@nodo-a ~]# passwd hacluster
[root@nodo-a ~]# yum install heartbeat
[root@nodo-a ~]# yum install heartbeat-gui

Creare il file di configurazione (stile v2) di heartbeat /etc/ha.d/ha.cf (per i dettagli delle opzioni fare riferimento a http://www.linux-ha.org/wiki/Ha.cf) sul nodo-a:

[root@nodo-a ~]# vi /etc/ha.d/ha.cf

# Inizio file /etc/ha.d/ha.cf
udpport 694
crm yes
keepalive 4
deadtime 30
initdead 60
auto_failback on
# Interfaccia o interfacce di rete da usare (modificare in base alle esigenze):
bcast eth0 eth1
#
Host per verificare le connessioni di rete (modificare in base alle esigenze):
ping 10.10.0.1 10.10.0.2
# Questi sono i nodi del cluster che verranno inclusi in cib.xml:
node nodo-a nodo-b
deadping 30
use_logd yes
# Fine file /etc/ha.d/ha.cf

Creare il file di impostazione dell’autenticazione dei nodi del cluster /etc/ha.d/authkeys (per i dettagli delle opzioni fare riferimento a http://www.linux-ha.org/wiki/Authkeys) sul nodo-a:

[root@nodo-a ~]# vi /etc/ha.d/authkeys

# Inizio file /etc/ha.d/authkeys
auth 2
1 crc
2 sha1 LaMiaChiaveSegreta
3 md5 LaMiaChiaveSegreta
# Fine file /etc/ha.d/authkeys

Consentire solo a root di leggere il file authkeys:

[root@nodo-a ~]# chmod 600 /etc/ha.d/authkeys

Ora è possible avviare heartbeat sul nodo-a:

[root@nodo-a ~]# /etc/init.d/heartbeat start

Copiare i due file appena creati sul nodo-b:

[root@nodo-a ~]# scp /etc/ha.d/ha.cf nodo-b:/etc/ha.d/
[root@nodo-a ~]# scp /etc/ha.d/authkeys nodo-b:/etc/ha.d/

Collegarsi al nodo-b e avviare heartbeat.

Il log di heartbeat viene inserito nel file /var/log/messages.

Se tutte le operazioni sono state finora eseguite correttamente, heartbeat è in esecuzione sui due nodi, il cluster è attivo senza risorse. Con riferimento al file cib.xml, abbiamo definito le prime due sottosezioni.

Aggiungere le risorse

Esistono vari comandi per modificare le risorse, ad esempio cibadmin, ma in questa guida si utilizzerà solo il più semplice programma hb_gui. Essendo questo una interfaccia grafica, può girare senza problemi se il nodo dispone del supporto della grafica (X-Server), altrimenti bisogna utilizzare un X-Server remoto, cioè su un altro host che ne dispone. In questa sede verrà considerata la prima ipotesi, in caso di X-Server remoto si può fare riferimento a http://www.linuxfocus.org/English/January2002/article222.shtml

Le modifiche effettuate tramite hb_gui vengono effettuate solo una volta, da uno qualsiasi dei nodi, e vengono automaticamente applicate per tutti i nodi. Il file cib.xml viene automaticamente aggiornato su tutti i nodi del cluster.

Lanciare il programma con:

[root@nodo-a ~]# hb_gui &

Cliccare su Connection > Login:

 

 Login ha

Figura 2 – Finestra di Login di hb_gui

Cliccare sulla voce di menu Resources > Add new item > Native > OK. Inserire i dati come nella figura:

 Risorsa IP

Figura 3 – Aggiunta di una risorsa di classe IPaddr

La risorsa identificata con ID resource_ip è stata creata, lo stato iniziale è stopped (default), per cui è necessario avviarla selezionandola e cliccando sul triangolo verde rivolto verso destra .
La risorsa IPaddr attiva l’indirizzo IP 10.10.0.100 come interfaccia di rete virtuale. Le risorse vengono raggruppate in classi, per una descrizione più dettagliata delle classi fare riferimento a:
http://www.linux-ha.org/ResourceAgent
NOTA: le classi standard più evolute sono quelle OCF, le classi LSB utilizzano i ben noti script posizionati in /etc/init.d/ per avviare, chiudere e monitorare i servizi.

Cliccare sulla voce di menu Resources > Add new item > Native > OK. Inserire i dati come nella figura:

Risorsa Http 

Figura 4 – Aggiunta di una risorsa di tipo httpd

Se tutto è andato bene la situazione sarà simile alle seguente:

Stato cluster
Figura 5 – Stato del cluster: due nodi e due risorse attive

 

Alcune osservazioni:

- Il nodo-b è il DC (Designed Coordinator), questo viene deciso automaticamente dal cluster.
- Una risorsa è attiva sul nodo-a (http) e un’altra sul nodo-b (l’indirizzo ip). Questa è una situazione incoerente, in quanto il server web deve rispondere all’ip 10.10.0.100.
- Le risorse sono state allocate in modo casuale.

Per modificare il comportamento del cluster dobbiamo:

1. Creare un Constraint Colocation per imporre al cluster di attivare le due risorse sullo stesso nodo (su un nodo qualsiasi, purché stiano assieme).
2. Creare un Constraint Order per ordinare al cluster di attivare prima l’indirizzo IP e poi avviare il server web.
3. Creare una Location per consentire al cluster di attivare le risorse su uno specifico nodo, ad esempio sul nodo-a.

Creazione della colocation (Add new item > Colocation > OK):

 

 Colocation

Figura 6 – Impostazione campi della colocation

Dopo aver cliccato su OK, dinamicamente il cluster attiverà le due risorse su uno stesso nodo, (nodo-a oppure nodo-b).
Aggiunta dell’ordine di avvio delle risorse (quello di chiusura sarà l’inverso):

 

 Ordine

Figura 7 – Impostazione campi dell’order

 

Questo constraint non provocherà nessuna variazione di stato del cluster, in quanto l’ordine tra le risorse è, in questo momento, già definito così.

Aggiunta della location per indicare il nodo su quale allocare le risorse:

 Location

Figura 8 – Impostare il nome della location

Aggiunta di una Expression che specifica il nodo sul quale attestare le risorse, aggiornare poi lo score a INFINITY:

 Location expression

Figura 9 – Impostare una espressione per la location

Il campo Score, previsto per alcuni constraint, è utilizzato per attribuire un “peso” alla permanenza di una risorsa su un nodo. In altre parole, un constraint con uno score più alto prevale su un constraint con uno score più basso. –INFINITY significa che il constraint non ha mai la precedenza su altri, INFINITY significa che il constraint ha sempre la precedenza su altri. Il valore 0 (default) non esprime alcuna preferenza.

La situazione del cluster, dopo aver impostato i valori per i constraint, dovrebbe essere questa:

Stato (2) 

Figura 10 – Il constraint colocation

Dopo aver verificato la funzionalità del cluster, attivare heartbeat e disattivare le risorse all’avvio sui due nodi, heartbeat curerà il loro avvio e la loro chiusura:

[root@nodo-a ~]# chkconfig heartbeat on
[root@nodo-a ~]# chkconfig httpd off

Le operazioni di monitoring

Una funzione importante è quella del monitoraggio delle risorse. Ad esempio, si può verificare periodicamente che il web server sia attivo e, nel caso sia fermo, avviarlo.
Selezionare la risorsa http, selezionare la scheda Operations e cliccare su Add operation. Inserire i dati come illustrato:

 Monitoring

Figura 11- Monitoraggio di un servizio

 

Per testare la funzionalità, si può chiudere brutalmente il web server sul nodo-a con:

[root@nodo-a ~]# killall httpd

Dopo alcuni secondi il servizio verrà automaticamente riavviato e il tutto sarà aggiornato in tempo reale sull’interfaccia hb_gui.

I gruppi di risorse

Molto spesso più risorse devono essere trattate allo stesso modo, nel senso che devono rispettare le stesse politiche. Per semplificare la gestione di tali risorse Pacemaker fa uso dei gruppi.
Con riferimento all’esempio di sopra, le risorse ip e http vengono incluse in un gruppo denominato group_web. A questo punto serve un solo constraint, location, associato al gruppo appena creato, posto che la creazione avvenga così:

 Resource group

Figura 12 – Creazione di un gruppo di risorse.
Notare il campo Ordered=True e Collocated=True

 

L’ordine di avvio dei servizi (prima ip e poi http) viene automaticamente rispettato poiché la sequenza visuale in hb_gui viene seguita nell’avvio dei servizi (ed in senso inverso nella chiusura) nell’ambito del gruppo.
Dopo le modifiche effettuate, la situazione sarà la seguente. La funzionalità del cluster è la stessa di prima e disposta in modo più semplice e flessibile:

 

 Group location

Figura 13 – Le risorse raggruppate

Fencing

In un cluster HA ci sono situazioni in cui il software di gestione non è in grado di definire correttamente lo stato dello stesso cluster. Il Fencing è un metodo adottato per riportare lo stato del cluster alla "normalità", cioè ad una situazione consistente ed evitare, principalmente, danni ai dati.
Il Fencing è una componente del cluster che, in pratica, nega l’accesso ad una risorsa (ad esempio ad un hard disk) ad un nodo se quest’ultimo perde il contatto con gli altri nodi, rendendo inconsistente lo stato del cluster (rif. http://sources.redhat.com/cluster/wiki/FAQ/Fencing).
Il Fencing può avvenire a livello di risorsa o a livello di nodo (in questo secondo caso il nodo viene spento e/o riavviato).
Stonith è il sistema di Fencing di Pacemaker e agisce a livello di nodo facendo uso di device come iLO, power switch etc.

Configurare stonith

Per configurare stonith (http://clusterlabs.org/):

  1. Trovare il driver giusto per la propria device (iLO, power switch…): stonith –L
  2. Identificare i parametri richiesti dalla device: stonith -t {type} –n
  3. Creare un file stonith.xml contenente una risorsa di classe stonith, di tipo {type} ed un valore per ciascuno dei parametri restituiti al punto 2
  4. Creare un clone (i cloni vengono usati per avviare più istanze di una stessa risorsa su più nodi) della risorsa solo se la stessa azione vale per più di un nodo.
  5. Aggiornare la configurazione utilizzando cibadmin:
    cibadmin -C -o resources --xml-file stonith.xml

Visualizzazione transizioni e dipendenze

Per mostrare le risorse e le loro relazioni viene utilizzato il comando ptest (incluso in heartbeat) e graphviz per l’output grafico. Questo tool è utile anche per simulazioni.
Si  riportano alcune note del grafico eventualmente prodotto:

- Le frecce indicano l’ordine delle dipendenze
- Le azioni con bordo verde e testo nero sono transizioni effettive
- Le azioni con bordo verde e testo arancio sono  pseudo azioni col solo scopo di semplificare il grafico
- Le azioni con testo nero vengono inviate al LRM
- I loop dipendono da errori di implementazione del cluster o bug di heartbeat

Un esempio di grafico delle transizioni e dipendenze:

 Transizioni
 
Figura 14 – Transizioni e dipendenze (visualizzazione parziale)


Comandi per la generare il grafico:
[root@nodo-a ~]# cibadmin -Q | grep -v lrm > /tmp/`hostname`.xml
[root@nodo-a ~]# ptest -D /tmp/`hostname`.dot  -X /tmp/`hostname`.xml
[root@nodo-a ~]# dot -Tpdf -o /tmp/`hostname`.pdf /tmp/`hostname`.dot