[keyserver] Add mysqldump to Node keyserver Docker container
Summary:
Our backup functionality relies on mysqldump being available on the same image that Node runs on.
Unfortunately, getting mysqldump 5.7 on this image has been quite a challenge.
- First thing I tried was to get it from the default apt repos, but it isn't there.
- Next I tried to use the same source that the MySQL image uses by inspecting its Docker layers
- I found it was using an older version of Debian (buster), so I tried downgrading our Node container's Debian version. As it turns out, bullseye (the newer version we're using) doesn't actually have MySQL 5.7... only buster does
- But it turns out the version for buster only has an x64 build, no ARM (Which is consistent with us needing this line)
- We could force our Node image to be emulated x64 on Mac but I wasn't excited about that prospect
- Next I considered using the default-mysql-client package
- Found out about it here
- But based on a comment on that StackOverflow, it looks like it's actually a MariaDB client, and there is some incompatibility with MySQL 5.7
- I spent most of the time trying different stuff I found online
- I tried all of the stuff from this StackOverflow
- I also tried this guide
- Ultimately nothing worked
- I also considered trying to use the mysqldump on the sepatate MySQL container, but this would only be possible from the host, which would either mean setting up Node on the host so we could use our existing code, or replacing our existing code with something like a bash script.
- Finally I settled on using mysqldump from MySQL 8
- To even get this installed separately from the full MySQL server, I had to add Debian's unstable repo
- Additionally I needed an extra config to disable some new MySQL 8 feature that was crashing when used with MySQL 5.7
- But I got it working!
Test Plan:
First, I configured keyserver/.env as follows:
COMM_MYSQL_DATABASE=commdev COMM_MYSQL_USER=commdev COMM_MYSQL_PASSWORD=pass COMM_JSONCONFIG_facts_landing_url='{"baseDomain":"http://localhost","basePath":"/commlanding/","baseRoutePath":"/commlanding/","https":false}' COMM_JSONCONFIG_facts_commapp_url='{"baseDomain":"http://localhost","basePath":"/comm/","https":false,"baseRoutePath":"/comm/"}' COMM_JSONCONFIG_facts_backups='{"enabled":true,"directory":"/home/comm/mysqldump"}'
Then I patched keyserver/docker-compose.yml to load MySQL from a bind-mounted backup (in), and to bind-mount the backups folder (out): https://gist.github.com/Ashoat/ebdd3ae0832a10a950d5f3c8f06f3feb
I also had to create the backups folder on the host machine.
Then I edited keyserver/src/cron/cron.js to increase the frequency of backups to every five minutes: https://gist.github.com/Ashoat/a4a338593b3b2ce1853a264244e6eb0b
Finally, I ran docker-compose down -v && docker-compose build --no-cache && docker-compose up on the host machine
Reviewers: palys-swm, atul
Reviewed By: atul
Subscribers: Adrian, yayabosh
Differential Revision: https://phabricator.ashoat.com/D4183