Running Ruby On Rails With Postgres In A Docker Container

Ruby On Rails With PostgreSQL and Docker

This project assumes:
  1. You are running MacOS,  a Linux distro, or Windows with WSL (Windows Subsystems For Linux)
  2. Know how to use the Terminal in before mentioned Operating Systems
  3. You have Visual Studio Code, and have it set up to open from a terminal command with "code ."
  4. You are somewhat familiar with Ruby and Rails

Necessary Installs

Docker

Install Docker according to the operating system you will be using.https://docs.docker.com/engine/install/

Docker-Compose

Install docs can be found here. https://docker-docs.netlify.app/compose/install/

Project Setup

Create Project Directory

In whatever directory you keep your projects, create a directroy for your project You can copy what's below, or use your own name.

$ mkdir rails_postgres_docker_demo

I'm using rails_postgres_docker_demo for this tutorial. Then cd into the directory you just made.

$ cd rails_postgres_docker_demo

Create Necessary Initial Files

We will be needing to create 3 initial files in our new directory they are, Dockerfile, docker-compose.yml & a Gemfile. Create them by running below commands

$ touch Dockerfile docker-compose.yml Gemfile

Open Visual Studio Code by tying "code ."

$ code .

Once Visual Studio Code has opened hit ⌘+p and type part of the file name you want to open and it will appear in the file results

In your file named Dockerfile paste the following:

# Date: 2023-01-01 You may wish change the ruby version depending upon what you are using. For instance, at the time
# of this writing, the latest version of ruby available to rbenv users is 3.1.2. You can check for what versions are available for Docker here
#https://hub.docker.com/_/ruby
FROM ruby:3.1.2-alpine

RUN apk add git

RUN apk add --update build-base bash bash-completion libffi-dev tzdata postgresql-client postgresql-dev nodejs npm yarn

WORKDIR /app

COPY Gemfile* /app/

RUN gem install bundler

RUN bundle install

RUN bundle binstubs --all

RUN touch $HOME/.bashrc

RUN echo "alias ll='ls -alF'" >> $HOME/.bashrc
RUN echo "alias la='ls -A'" >> $HOME/.bashrc
RUN echo "alias l='ls -CF'" >> $HOME/.bashrc
RUN echo "alias q='exit'" >> $HOME/.bashrc
RUN echo "alias c='clear'" >> $HOME/.bashrc

CMD [ "/bin/bash" ]

Create docker-compose.yml 

And paste the following into your docker-compose.yml file.

version: '3'
services:
db:
image: postgres:14.2-alpine
container_name: project-postgres-14.2
volumes:
- postgres_data:/var/lib/postgresql/data
command: "postgres -c 'max_connections=500'"
environment:
#Change the below values to your own
POSTGRES_DB: project_db
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
ports:
- "5432:5432"
web:
build: .
#Below is the command to run the rails server in the background after removing the server.pid file, if it exists
command: bash -c "rm -f tmp/pids/server.pid && bundle exec rails s -p 3000 -b '0.0.0.0'"
environment:
#Change the below values to your own -- Needs to match the values in the db service
DB_HOST: db
DB_NAME: project_db
DB_USERNAME: postgres
DB_PASSWORD: postgres
volumes:
- .:/app:cached
ports:
- "3000:3000"
depends_on:
- db
volumes:
postgres_data: {}
networks:
default:
name: project-network-name

Into your Gemfile paste the following

source 'https://rubygems.org'
gem 'rails', '~> 7.0.2', '>= 7.0.2.2'

Run your Dockerfile and Start up your server

In you terminal window, inside the directory of your project run the following to initiate your docker containers. This may take a while.

$ docker-compose run --no-deps web rails new . --force --database=postgresql

Note, that with the call to rails, you can call other rails options other than just the database type. You can call the --api, or any number of other rails configuration options.

Now that the Docker containers have been built, you can build the application by running:

$ docker-compose build
$ docker-compose up

Afterward we need to update our rails config/database.yml file to look like the following

default: &default
adapter: postgresql
encoding: unicode
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
host: <%= ENV.fetch('DB_HOST', 'localhost') %>
username: <%= ENV['DB_USERNAME'] %>
password: <%= ENV['DB_PASSWORD'] %>

development:
<<: *default
database: app_development
test:
<<: *default
database: app_test

production:
<<: *default
database: app_production
username: app
password: <%= ENV["APP_DATABASE_PASSWORD"] %>


  

Migrating the Database

Now we can open docker application, and use it to launch a terminal to the  running docker project by clicking the icon circled in red below. You can also launch Visual Studio Code by clicking on it's open icon.


Now that the terminal is open for the web-1 container, we can run our  rake commands, and interact with rails running in the docker container. 

$ rake db:create 
$ rake db:migrate

Now we can work on the project just like any other Ruby on rails project in the docker terminals and VS Code. 


We can access the application at the usual http://localhost:3000 which can be changed by editing the build command in the web portion of docker-compose.yml

Comments