Vapor Swift MySql Docker-Compose

Borama Apps
Apr 12 · 2 min read

On the local machine let’s create folder vapor and initialize vapor template:

vapor new server

Move to /server folder and edit Package.swift replacing SQLite with MySQL:

Next update dependencies with

vapor update

We need to update our Todo model and configure.swift

In the configure.swift replace references to MySQLite and also add function to read environment arguments. We will pass them when starting up docker-compose.

The project will build now but we need database!

Create docker-compose.yml:

And .env file:

In our Vapor app we’ll connect to the database using host “db”, not “localhost” or “0.0.0.0”, because this is how docker network will expose db service.

We can now run our vapor project in Xcode:

vapor xcode -y

We can add todos using curl:

curl --header "Content-Type: application/json" --request POST --data '{"title":"todo1"}' localhost:8080/todos

and confim the server is

curl localhost:8080/todos

We have server working fine with database, let’s run it from docker. The template provides docker file, we will modify it a little bit:

Also let’s update docker-compose.yml to include this vapor server app docker:

It’s important to first run database because it could not be ready to accept connections (we use depends_on but it’s not enough!)

First start the database:

docker-compose up -d db

next start the vapor server:

docker-compose up

We can now deploy our created server to remote server using docker-registry.

First create api image and push it to registry. I’m using private registry:

docker build -t todoserver:1.0.0 . -f web.Dockerfile
docker tag todoserver:1.0.0 borama.info/todoserver
docker push borama.info/todoserver

On remote server create directory vapor.

Copy docker-compose.yml and .env file to the remote server I’m using scp ie.:

scp .env me@1.2.3.4:/home/me/todoserver

Pull vapor server image:

docker pull borama.info/todoserver:latest

We need to update server’s docker-compose.yml to use create image and not build it.

I’m mapping api port to 9081 because other ports I have in use. Also I’m not exposing database ports, 3306 will be available to the api anyway. And I don’t need external db access here.

Again first start db than the api otherwise you will get:

Fatal error: Error raised at top level: NIO.ChannelError.connectFailed(NIO.NIOConnectionError(host: "db", port: 3306, dnsAError: nil, dnsAAAAError: nil, connectionErrors: [NIO.SingleConnectionFailure(target: [IPv4]db/172.25.0.2:3306, error: connection reset (error set): Connection refused (errno: 111))]

Also the same error can occur if trying to connect using wrong port or host. Important point is that exposed port is for the external network, not the network created by docker.

I’m using nginx and to access vapor server inside my nginx file I use:

location /todos/ {   proxy_pass http://localhost:9081/;}

If you have more advanced setup you might want to use Docker Swarm, which would help with passing secrets (passwords etc.)

That’s it!

Full repository:

https://github.com/standinga/vapordockercomposetodo

Please check my IOS and Android apps!

Follow me on twitter :)

Borama Apps

Written by

ios, android, web apps. https://borama.co, http://twitter.com/boramaapps

Welcome to a place where words matter. On Medium, smart voices and original ideas take center stage - with no ads in sight. Watch
Follow all the topics you care about, and we’ll deliver the best stories for you to your homepage and inbox. Explore
Get unlimited access to the best stories on Medium — and support writers while you’re at it. Just $5/month. Upgrade