Deploy to AWS using Docker compose (simple)
It’s easy.
- Create the app
- Create a docker-compose.yml and Dockerfile
- Create an EC2 instance
- Copy your project files to your EC2 instance
- Run docker-compose on your EC2 instance, and voila!
STEP 1
First let’s make a Node.js app which connects to a MySQL database.
npm init -y
npm install express --save
npm install mysql --save
Note: If you’re using Sequelize or MongoDB etc., this tutorial still applies.
We’ve created a simple app with 3 files: database.js, index.js, and schema.sql.
Here’s the database.js. It connects to the database and handles queries.
Here’s the index.js (the Express server which handles incoming requests).
And here’s the schema.sql file, which we will run to create the database and table.
To run this server, we run this terminal command to create our database and table:
mysql -u root -p < server/schema.sql
Then this to launch our server:
node server
If we navigate to http://localhost:3000/api/1/attribute on our browser, we should see some JSON output.
Congrats! Now to Docker.
STEP 2
We need only two more files: a docker-compose.yml and Dockerfile, both in your project’s parent folder.
Here’s the docker-compose.yml:
We’re telling the docker-compose.yml file to build 2 services: ‘server’ and ‘database’.
And here’s the Dockerfile:
The ‘sleep 30’ command on line 13 makes the terminal sleep for 30 seconds. This is to ensure that MySQL is ready to listen for connections before we try to connect, otherwise a ‘ECONNREFUSED’ error will be thrown.
Connecting our database and server containers is easy. In database.js, simply change the connection object to a URL:
Line 12 shows the new connection. Your URL should look very similar to this:
mysql://root:password@database:3306/some_database
‘mysql’: required
‘root’: required
‘password’: the password which you specify in docker-compose.yml
‘database’: the name of the service you specify in docker-compose.yml
‘3306’: the default port for MySQL (leave it as 3306)
‘some_database’: the name of the database you specify in docker-compose.yml
Note that, since we won’t be able to run schema.sql inside Docker, lets move the schema.sql queries to our database.js (on line 19 above).
Now, we’re ready to spin up the Docker container. From the project directory, run:
docker-compose up
To confirm the container is running properly, navigate to http://localhost:3000/api/1/attribute in your browser to see the JSON response.
Congrats. Now to deploy.
STEP 3
After creating your AWS account, open the AWS console and then:
Now it’s easy. Delete the node_modules folder in your project directory, then CD in to the directory where you saved your .pem file and run this command:
chmod 400 yourkeyname.pem
Replace yourkeyname.pem with the name that you set when you downloaded this file. This is a required step. Now, from the same directory, run this command:
scp -r -i yourkeyname.pem ~/path/to/your/project/folder/from/root ec2-user@18.225.7.177:~/
Replace the ‘yourkeyname.pem’ with the name that you chose when you downloaded this file, and the ~/path/to/your/project/folder/from/root with the actual path to your project folder, and the ‘18.225.7.177’ with the IPv4 Public IP from your EC2 instance page. Leave everything else the same. This will push your entire project folder to your EC2 instance.
If prompted, ‘Are you sure..’ type ‘yes’.
After your files have all copied, run this command:
ssh -i yourkeyname.pem ec2-user@18.225.7.177
Now you’re inside your remote Ubuntu computer! Run ‘ls’ to make sure your directory has been copied over.
Now run the following 5 commands:
sudo yum updatesudo yum install dockersudo curl -L https://github.com/docker/compose/releases/download/1.21.0/docker-compose-`uname -s`-`uname -m` | sudo tee /usr/local/bin/docker-compose > /dev/nullsudo chmod +x /usr/local/bin/docker-composesudo ln -s /usr/local/bin/docker-compose /usr/bin/docker-compose
This will install both docker and docker-compose on your EC2 instance. To start docker, simply run:
sudo service docker start
Now simply CD into your project folder on the EC2 instance, and run:
sudo docker-compose up
Congrats, your app is now deployed!