/docker-ruby-passenger

Docker image with ruby and passenger configured, specially for capistrano deployment target

Primary LanguageDockerfileMIT LicenseMIT

Docker image with Ruby and Passenger, specialized for capistrano target

NOITCE: I mainly used this in my own project, so use on your own risk, this might contained some opinionated settings.

Features

Based on phusion/passenger-docker, with following settings:

  • Nginx enabled and Exposed 80 for nginx
  • Passenger enabled
  • Set to use capistrano as deployment tools
  • /home/app as the root directory for capistrano deploy target
  • Expose 22 for SSH access, so that capistrano can do the the deploy
  • Following env variables will be passed to nginx and Rails app: SECRET_KEY_BASE, DB_HOST, DB_PORT, DB_USER, DB_PASSWORD
  • Set timezone to China timezone
  • Use zh_CN.UTF-8 as the locale
  • sidekiq daemon will be launched if it has been integrated in this container, the configuration file should be located as config/sidekiq.yml
  • Logs will be rotated by logrotator daily, max 100MB, and 60 retention.

Idea

The idea is pretty straight forward, create a container with passenger and nginx enabled, for running the Rails application. But, we will use capistrano for deploying, to support that, we need to allow SSH access to the container. So, the idea is to forward the SSH access to the container, so that the container can be used as a capistrano deployment target.

And, to make sure caches can be utilized, I used docker volume to storing the web application files, so that even recreating container won't take much time on subsequent bundle install and assets:precompile.

Why this way? Well, I tried, actually, I just love how capistrano works. I tried some other ways for using docker in Rails app, there are more or less issues, but mostly, what bothered me the most is, slower than capistrano.

Usage

  • Let's assume the container name will foo and the data vol will be named as foo as well.
  • Assume the database is postgres and the container name is foo-psql
  • Assume the redis server is foo-redis
  • We will need SSH port to be forward, assume we will forward port 22 and 80 to 20022 and 20080
  • If we need to config nginx manuall, for main server configration, we can just map file in host to /etc/nginx/sites-enabled/webapp.conf, or something else in this directory. Same rule goes to nginx configuration files located in /etc/nginx/main.d/, for nginx HTTP configurations.
  • If we need to share same authorized_keys setting as the host, simply map the /root/.ssh/authorized_keys file, or you can also echo the public key into the container after container created, it can be done via a bash script
  • If sidekiq is not required, simply delete /etc/service/sidekiq/run/sidekiq.sh after the container is created, I used to manage different branches for image with or without sidekiq, but it seems just too much
# Create data vol
docker volume create --name foo
# Create the app container
docker run --name foo -d --restart="always" \
--link foo-psql:psql \
--link foo-redis:redis \
-e RAILS_ENV=production -e DB_HOST=psql -e DB_PORT=5432 \
-e DB_USER=postgres -e DB_PASSWORD=xxxxxx \
-e SECRET_KEY_BASE=xxxxxxxxxx \
-v foo:/home/app \
-v /root/.ssh/authorized_keys:/root/.ssh/authorized_keys:ro \
-v /foo/bar/conf/webapp.conf:/etc/nginx/sites-enabled/webapp.conf:ro \
-v /foo/bar/certs/:/etc/nginx/certs/:ro \
-p 0.0.0.0:20022:22 -p 0.0.0.0:20080:80 \
registry.cn-hangzhou.aliyuncs.com/pzgz/docker-ruby-passenger:v*.*.*

# Then you can try the login with SSH key from your remote
ssh root@foo.bar.com -p 20022

Branches

  • ruby23: Ruby 2.3, legacy version, no sidekiq included
  • ruby24: Ruby 2.4, legacy version, no sidekiq included
  • ruby24-sidekiq: Ruby 2.4, legacy version, sidekiq included
  • ruby25: Ruby 2.5, current version, no sidekiq included
  • ruby25-sidekiq: Ruby 2.5, current version, sidekiq included
  • master: Main stream branch, the above legacy versions won't be updated unless needed. Updates will be carried out from master branch, and releases will be cut by tag with naming convensino: release-v1.2.3

Known Issues

  • Downloaded excel attachment generated by Axlsx appear to have weired filename(乱码) if it's in Chinese, root cause TBD