Project

General

Profile

MySQLReplication » History » Version 19

Simone Piccardi, 12/09/2013 01:16 PM

1 1 japoco romagnoli
h1. Configurare la replicazione di MySQL
2 2 japoco romagnoli
3 19 Simone Piccardi
Occorrono almeno due installazioni indipendenti di MySQL, una macchina deve fare da master, le altre da slave. Inoltre non è possibile per fare da slave per master diversi, questo significa che se si devono replicare database che stanno su macchine diverse, queste dovranno essere replicata su istanze diverse.
4 2 japoco romagnoli
5 19 Simone Piccardi
Prenderemo in considerazione solo il caso elementare di due macchine. Le due istanze devono essere configurate per essere raggiungibili via rete. La replicazione si basa sul configurare il master per creare un log binario con le operazioni che vengono eseguite in scrittura. Lo slave leggendo i file su cui vengono registrate queste operazione le ripete su se stesso per “allinearsi”.
6 2 japoco romagnoli
7 19 Simone Piccardi
h2. Configurazione del Master
8 1 japoco romagnoli
9 2 japoco romagnoli
10 19 Simone Piccardi
Il primo passo è la configurarazione del master, per questo occorre modificare il file @/etc/mysql/my.cnf@ per abilitare la connessione via rete e la scrittura del file di log binario. Le modifiche da effettuare prevedono linseremento delle seguenti configurazioni al posto di quelle installate normalmente dal pacchetto Debian di MySQL:
11 5 japoco romagnoli
12 3 japoco romagnoli
<pre>
13 3 japoco romagnoli
[...]
14 1 japoco romagnoli
bind-address	= 0.0.0.0
15 19 Simone Piccardi
# o bind-address = IP.DEL.SERVER.MASTER 
16 4 japoco romagnoli
[...]
17 1 japoco romagnoli
server-id = 1
18 3 japoco romagnoli
log_bin = /var/log/mysql/mysql-bin.log
19 3 japoco romagnoli
expire_logs_days = 10
20 6 japoco romagnoli
max_binlog_size = 100M
21 19 Simone Piccardi
binlog_do_db = nome_database_da_replicare
22 1 japoco romagnoli
[...]
23 5 japoco romagnoli
</pre>
24 5 japoco romagnoli
25 19 Simone Piccardi
Qualora si siano fatti tentativi precedenti, per ripartire da zero, è necessario cancellare eventuali vecchi file di log binario, in modo tale che il server crei un log pulito a prova di errore, con:
26 5 japoco romagnoli
27 5 japoco romagnoli
<pre>
28 5 japoco romagnoli
rm /var/log/mysql/mysql-bin.*
29 5 japoco romagnoli
</pre>
30 5 japoco romagnoli
31 19 Simone Piccardi
si provveda poi a riavviare il server MySQL, in modo che prenda le nuove configurazioni:
32 5 japoco romagnoli
33 1 japoco romagnoli
<pre>
34 19 Simone Piccardi
service mysql restart
35 1 japoco romagnoli
</pre>
36 5 japoco romagnoli
37 19 Simone Piccardi
A questo punto si dovrà impostare MySQL per abilitare un utente con accesso da remoto che possa leggere i log ed eseguire la replicazione, l'utente deve essere definito sul master, e sarà usato dagli slave per connettersi, questo si fa collegandosi con @mysql@ ed eseguendo il codice SQL:
38 6 japoco romagnoli
39 6 japoco romagnoli
<pre>
40 11 japoco romagnoli
GRANT REPLICATION SLAVE ON *.* TO '[nome_utente]'@'[indirizzo_ip_dello_slave]' IDENTIFIED BY '[password]';
41 1 japoco romagnoli
FLUSH PRIVILEGES;
42 8 japoco romagnoli
</pre>
43 8 japoco romagnoli
44 19 Simone Piccardi
Una volta attive le nuove configurazioni occorre trasferire i dati dal master allo slave per l'importazione iniziale. Questi devono essere in uno stato coerente per cui non è possibile eseguire operazioni sul database durante la sincronizzazione iniziale. Pur essendo possibile far eseguire tutta la transazione via rete, per mantenerla in stato coerente questa necessita di mantenere un lock sul database per tutto il tempo impiegato a replicare i dati, che con database popolati significativamente può essere anche molto lungo. 
45 8 japoco romagnoli
46 19 Simone Piccardi
Per questo è in genere preferibile fare un dump ad un certo momento e per ripartire dallo stato in cui lo si era fatto. In questo caso il lock è necessario solo per il tempo, in genere molto minore, in cui si crea il dump. Una volta effettuato il dump si potrà rimuovere il blocco e indicare allo slave, una volta importato il dump, di ripartire dal punto in cui questo era stato fatto usando le informazioni registrate sul file di log mantenuto dal master.  
47 7 japoco romagnoli
48 19 Simone Piccardi
Per far questo si deve collegarsi sulla CLI di MySQL, selezionare il database da replicare e bloccare le tabelle in scrittura, così da avere uno stato coerente dei dati, con le istruzioni:
49 19 Simone Piccardi
50 6 japoco romagnoli
<pre>
51 6 japoco romagnoli
USE nome_database
52 6 japoco romagnoli
FLUSH TABLES WITH READ LOCK;
53 6 japoco romagnoli
</pre>
54 6 japoco romagnoli
55 19 Simone Piccardi
Si dovrà poi controllare lo stato del master (che ci servirà per stabilire il punto da cui far ripartire la replicazione sullo slave) con il comando @SHOW MASTER STATUS@, questo darà un risultato del tipo:
56 6 japoco romagnoli
57 6 japoco romagnoli
<pre>
58 6 japoco romagnoli
mysql> SHOW MASTER STATUS;
59 6 japoco romagnoli
+------------------+----------+--------------+------------------+
60 6 japoco romagnoli
| File             | Position | Binlog_Do_DB | Binlog_Ignore_DB |
61 1 japoco romagnoli
+------------------+----------+--------------+------------------+
62 6 japoco romagnoli
| mysql-bin.000013 |      106 |              | nome_database    |
63 1 japoco romagnoli
+------------------+----------+--------------+------------------+
64 6 japoco romagnoli
1 row in set (0.00 sec)
65 1 japoco romagnoli
</pre>
66 6 japoco romagnoli
67 19 Simone Piccardi
A questo punto, senza chiudere la shell di MySQL (per evitare di perdere il lock sulle tabelle), si effettui il dump del database su un file @.sql@ da trasferire sul server slave con:
68 6 japoco romagnoli
69 6 japoco romagnoli
<pre>
70 19 Simone Piccardi
mysqldump -u root nome_database > nome_database.sql
71 6 japoco romagnoli
</pre>
72 6 japoco romagnoli
73 19 Simone Piccardi
una volta finita l'esportazione potremo tornare sulla shell di MySQL e sbloccare il lock in lettura con:
74 11 japoco romagnoli
75 6 japoco romagnoli
<pre>
76 6 japoco romagnoli
UNLOCK TABLES;
77 6 japoco romagnoli
</pre>
78 1 japoco romagnoli
79 19 Simone Piccardi
A questo punto le operazioni sul master sono terminate, la scrittura riprenderà, ma essendo registrata nel log lo slave sarà in grado di ripartire senza problemi utilizzando il punto di partenza indicato dai risultati di @SHOW MASTER STATUS@.
80 1 japoco romagnoli
81 16 japoco romagnoli
82 19 Simone Piccardi
h2. Configurazione dello Slave
83 15 japoco romagnoli
84 19 Simone Piccardi
Anche in questo caso occorre riconfigurare il server MySQL, in particolare occorrerà assegnargli un diverso @server-id@ ed inoltre occorrerà spostare @tmpdir@ su una directory il cui contenuto sia garantito in caso di riavvio, in quanto la cancellazione dei file temporanei potrebbe compromettere l'aggiornamento della replicazione. Rispetto al file di configurazione standard occorrerà apportare le seguenti modifiche:
85 1 japoco romagnoli
86 1 japoco romagnoli
<pre>
87 1 japoco romagnoli
[...]
88 1 japoco romagnoli
tmpdir          = /var/tmp
89 12 japoco romagnoli
[...]
90 12 japoco romagnoli
bind-address	= 0.0.0.0
91 19 Simone Piccardi
# o bind-address = IP.DEL.SERVER.SLAVE 
92 6 japoco romagnoli
[...]
93 6 japoco romagnoli
server-id = 2
94 6 japoco romagnoli
log_bin = /var/log/mysql/mysql-bin.log
95 6 japoco romagnoli
expire_logs_days = 10
96 6 japoco romagnoli
max_binlog_size = 100M
97 6 japoco romagnoli
[...]
98 6 japoco romagnoli
</pre>
99 7 japoco romagnoli
100 19 Simone Piccardi
e renderle effettive riavviando il server MySQL anche sulla macchina slave:
101 13 japoco romagnoli
102 13 japoco romagnoli
<pre>
103 13 japoco romagnoli
service mysql restart
104 13 japoco romagnoli
</pre>
105 13 japoco romagnoli
106 13 japoco romagnoli
107 19 Simone Piccardi
Per l'importazione iniziale dei dati occorrerà anzitutto creare sullo slave un database con lo stesso nome di quello che vogliamo replicare: 
108 19 Simone Piccardi
109 7 japoco romagnoli
<pre>
110 19 Simone Piccardi
mysqladmin -u root -p create nome_database_da_replicare
111 7 japoco romagnoli
</pre>
112 7 japoco romagnoli
113 19 Simone Piccardi
a questo punto si può caricare il file di dump @.sql@ direttamente sul database:
114 7 japoco romagnoli
115 7 japoco romagnoli
<pre>
116 7 japoco romagnoli
mysql nome_database < nome_database.sql
117 7 japoco romagnoli
</pre>
118 7 japoco romagnoli
119 7 japoco romagnoli
infine occorre impostare il server come slave passando anche i paramatri del master con cui interfacciarsi:
120 1 japoco romagnoli
121 1 japoco romagnoli
<pre>
122 13 japoco romagnoli
CHANGE MASTER TO master_host='nome_Master.Domain', master_user='nome_utente_Master', 
123 1 japoco romagnoli
master_port=3306, master_password='pw_utente_Master', master_log_file='mysql-bin.00000x', 
124 1 japoco romagnoli
master_log_pos=xxx;
125 13 japoco romagnoli
START SLAVE;
126 11 japoco romagnoli
</pre>
127 11 japoco romagnoli
128 17 japoco romagnoli
eventualmente si può controllare lo status dello slave da MySQL con:
129 11 japoco romagnoli
130 17 japoco romagnoli
<pre>
131 17 japoco romagnoli
SHOW SLAVE STATUS;
132 17 japoco romagnoli
</pre>
133 13 japoco romagnoli
134 17 japoco romagnoli
h2. Switching Slave to Master
135 11 japoco romagnoli
136 17 japoco romagnoli
Volendo cambiare il nostro server slave nel nuovo master su cui indirizzare i servizi che appoggiano sul database mysql replicato si deve prima di tutto andare a cambiare il file @/etc/mysql/my.cnf@ controllando che siano abilitate le opzioni di @log-bin@ e disabilitato tutto quello che riguarda i log del tipo @slave-updates@.
137 17 japoco romagnoli
Si deve anche verificare che il @bind-address@ sia effettivamente impostato su @0.0.0.0@ permettendo così il raggiungimento della macchina dalla rete:
138 1 japoco romagnoli
139 17 japoco romagnoli
<pre>
140 17 japoco romagnoli
[...]
141 17 japoco romagnoli
bind-address	= 0.0.0.0
142 17 japoco romagnoli
[...]
143 17 japoco romagnoli
log_bin = /var/log/mysql/mysql-bin.log
144 17 japoco romagnoli
expire_logs_days = 10
145 17 japoco romagnoli
max_binlog_size = 100M
146 17 japoco romagnoli
binlog_do_db = nome_database
147 17 japoco romagnoli
[...]
148 17 japoco romagnoli
</pre>
149 1 japoco romagnoli
150 17 japoco romagnoli
A questo punto, entrando in MySQL, si può fermate il server slave e reimpostarlo come nuovo master:
151 17 japoco romagnoli
152 17 japoco romagnoli
<pre>
153 17 japoco romagnoli
STOP SLAVE;
154 17 japoco romagnoli
RESET MASTER;
155 17 japoco romagnoli
</pre>
156 17 japoco romagnoli
157 18 japoco romagnoli
Volendo reimpostare l'ormai defunto master nel nuovo slave che replichi il nuovo master, dovremo