Jan 19, 2015

Creating and Persisting Databases outside your container using the Tutum/MySQL Docker Image

I'm presently hacking on Docker and I ran into a few issues getting the Tutum/MySQL Docker Image working on Fedora 21. This overview assumes that you've already gone through the basics to get Docker running on F21.

The issue I'm having is that I want to launch the MySQL container but persist the actual data (i.e. the System and Application Database) elsewhere. To do this we have to pass in a -v argument to the Docker run statement, which mounts your alternative host path to the /var/lib/mysql location in the container.

In order to do this one runs the following command to mount /opt/mysql on my F21 host server to /var/lib/mysql (which is where MySQL DBs live) in the container:

[root@localhost mysql]# docker run -d -v /opt/mysql:/var/lib/mysql tutum/mysql /bin/bash -c "/usr/bin/mysql_install_db"
3224ede26db55241b320655da14bbf2737212fb3889b871ff5aa03307edf9ac8

However, if you check the logs, you'll notice that the attempt failed:

[root@localhost mysql]# docker logs 3224ede26db55241b320655da14bbf2737212fb3889b871ff5aa03307edf9ac8
chown: changing ownership of '/var/lib/mysql': Permission denied
Cannot change ownership of the database directories to the 'mysql'
user.  Check that you have the necessary permissions and try again.

To resolve this issue, you need to attach a --privileged directive to the docker run command as follows:

[root@localhost opt]# docker run --privileged -d -v /opt/mysql:/var/lib/mysql tutum/mysql /bin/bash -c "/usr/bin/mysql_install_db"

This will run the appropriate script in the container to create the system database and store it on your host machine and then return and release the container.  The next step is to relaunch the image with it mounted to the same system directory

[root@localhost opt]# docker run --privileged -d -p 3306:3306 -v /opt/mysql:/var/lib/mysql tutum/mysql
aa9b0ddf604908138c586a75370094c504e50870b67ce4448cfbfec0b9872f90

This should work. You can shell into the container and run the necessary SQL scripts or MySQL Admin commands to create any additional databases you wish. All Databases and their modifications will always be persisted outside of the container to the mounted directory that was specified.  For example:

[root@localhost opt]# docker exec -it aa9b0ddf6049 bash
root@aa9b0ddf6049:/# mysql

CREATE DATABASE us_states;
USE us_states;
CREATE TABLE states (id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, state CHAR(25), population INT(9));
INSERT INTO states (id, state, population) VALUES (NULL, ‘Alabama’, ‘4822023’);
QUIT;

root@aa9b0ddf6049:/# exit

[root@localhost opt]# docker stop [containerID]

In some cases I have got an exception when trying to start the MySQL docker image that states:

Cannot start container [container id]: (exit status 1)  

I find that I can get resolve this by simply restarting the docker service and trying again:

systemctl docker restart

No comments: