MySQL propose depuis de nombreuses années un outil pour réaliser des dumps logiques, le fameux mysqldump que tout le monde connait. Malheureusement trop souvent utilisé à tord et notamment avec de trop grosses volumétries pour cet outil qui n’a pas réellement évolué depuis longtemps. Il est monothreadé, les exports sont longs et les imports encore plus.
Connaissez vous MySQLPump avec un P ?
Avec MySQL 5.7 un nouvel est outil est sortit, mysqlPump, une variante multithread avec des nouveaux filtres, cependant lors de la sortie, une indication a été donnée de ne pas l’utiliser tout de suite car il n’était pas fonctionnelle à 100% (et nous avons vécu ses défauts avec un de nos clients). Les problèmes rencontrés ont été corrigés dans les patchs suivants, sauf erreur de ma part. Mais il n’a pas percé et il est aujourd’hui un inconnu, alors qu’il est toujours présent en version 8.0. Son nom semble être un clin d’œil à l’outil de dump Oracle, EXP et son évolution EXPDP pour Export Data Pump, le fameux P.
Le nouvel outil fait partit du package util() de l’outil MySQL Shell. De nouveaux outils sont ajoutés régulièrement à l’intérieur au fil des versions.
Cet outil est multithreadé et compresse par défaut les dumps.
Le dump se lance simplement avec la commande suivante en mode Javascript, util.dumpInstance(‘nomdudump’)
[root@localhost ~]# mysqlsh root@localhost MySQL localhost:33060+ ssl JS - util.dumpInstance('/tmp/testdump') Acquiring global read lock All transactions have been started Locking instance for backup Global read lock has been released Writing global DDL files Writing users DDL Preparing data dump for table `testdump`.`mytable` Data dump for table `testdump`.`mytable` will be chunked using column `id` Running data dump using 4 threads. NOTE: Progress information uses estimated values and may not be accurate. Writing DDL for schema `testdump` Writing DDL for table `testdump`.`mytable` Data dump for table `testdump`.`mytable` will be written to 1 file 1 thds dumping - 100% (1 rows / ~1 rows), 0.00 rows/s, 0.00 B/s uncompressed, 0.00 B/s compressed Duration: 00:00:00s Schemas dumped: 1 Tables dumped: 1 Uncompressed data size: 2 bytes Compressed data size: 0 bytes Compression ratio: 2.0 Rows written: 1 Bytes written: 0 bytes Average uncompressed throughput: 2.00 B/s Average compressed throughput: 0.00 B/s
La progression est aussi affichée pendant le dump. Le résultat n’est pas un simple fichier mais plutôt un répertoire contenant plusieurs fichiers. Dans notre exemple il n’y a qu’une base testdump et une table mytable à l’intérieur. Dans le même esprit un outil est présent pour dumper précisément des schémas et non toute l’instance.
[root@localhost ~]# ls /tmp/testdump/ @.done.json @.post.sql testdump.json testdump@mytable@@0.tsv.zst.idx testdump@mytable.sql @.users.sql @.json @.sql testdump@mytable@@0.tsv.zst testdump@mytable.json testdump.sql
On retrouve à l’intérieur les fichiers avec du JSON et du SQL. L’ensemble correspond à un seul dump. Sans rentrer dans les détails, pour améliorer les temps d’export et d’import il est préférable de travailleur sur plusieurs fichiers et que chaque élément soit séparé (ou sous un référentiel dans les en têtes de fichier comme un dump Oracle expdp).
À l’avenir il sera peut être possible d’avoir un seul fichier en sortie, mais vous pouvez aussi faire un tar du répertoire.
Pour le chargement il est lui aussi optimisé, avec du parallélisme et de nombreuses options.
La syntaxe de la commande est util.loadDump(‘dumpname’, {option})
MySQL localhost:33060+ ssl JS - util.loadDump("/tmp/testdump", {dryRun: true}) ERROR: The 'local_infile' global system variable must be set to ON in the target server, after the server is verified to be trusted.
Comme on peut le voir le chargement est bloqué pour des raisons de sécurité, vous ne pouvez pas le charger directement il est nécessaire d’activer l’option LOCAL_INFILE (en mode SQL). Ce paramètre peut être définit juste pour l’import et ensuite désactivé.
L’option {dryRun} permet de voir ce qui va être chargé, la liste des tables/bases etc. sans l’exécuter.
Activation du paramètre Local_infile :
MySQL localhost:33060+ ssl JS - \sql Switching to SQL mode... Commands end with ; MySQL localhost:33060+ ssl SQL - set persist local_infile=0; Query OK, 0 rows affected (0.0006 sec)
MySQL localhost:33060+ ssl JS - util.loadDump("/tmp/testdump", {dryRun:true}) Loading DDL and Data from '/tmp/testdump' using 4 threads. dryRun enabled, no changes will be made. Target is MySQL 8.0.21. Dump was produced from MySQL 8.0.21 Checking for pre-existing objects... Executing common preamble SQL Executing DDL script for schema `testdump` Executing DDL script for `testdump`.`mytable` Executing common postamble SQL No data loaded. 0 warnings were reported during the load.
Le dump de test ne contient que la base testdump et la table mytable à l’intérieur. Maintenant sans le dryRun:
MySQL localhost:33060+ ssl JS - util.loadDump("/tmp/testdump") Loading DDL and Data from '/tmp/testdump' using 4 threads. Target is MySQL 8.0.21. Dump was produced from MySQL 8.0.21 Checking for pre-existing objects... Executing common preamble SQL Executing DDL script for schema `testdump` Executing DDL script for `testdump`.`mytable2` [Worker000] testdump@mytable2@@0.tsv.zst: Records: 1 Deleted: 0 Skipped: 0 Warnings: 0 Executing common postamble SQL 1 chunks (1 rows, 2 bytes) for 1 tables in 1 schemas were loaded in 1 sec (avg throughput 2.00 B/s) 0 warnings were reported during the load.
Le dump a bien été chargé, nous avons bien récupéré notre table avec ses enregistrement :
MySQL localhost:33060+ ssl SQL - select * from testdump.mytable; +----+ | id | +----+ | 1 | +----+ 1 row in set (0.0005 sec)
L’utilisation de ces outils est très simple. Ils servent aussi pour MySQL Database Service sur le cloud Oracle, de nombreuses options sont intégrées qui y sont associées.
Pour plus d’informations n’hésitez pas à consulter la documentation officielle :
https://dev.mysql.com/doc/mysql-shell/8.0/en/mysql-shell-utilities-dump-instance-schema.html
https://dev.mysql.com/doc/mysql-shell/8.0/en/mysql-shell-utilities-load-dump.html