- login to 'AWS Management Console' (https://aws.amazon.com/console/)
- from 'Services'(in navbar) choose 'EC2'
- from 'Create Instance' section, click on 'Launch Instance'
- then select 'AMI' (Amazon Machine Image), we will be using 'Ubuntu Server 16.04 LTS (HVM)' as example
- select 'Instance Type' as per your requirement
- then click 'Next:Configure Instance Details' to continue
change 'Configure Instance Details' or used as default settings
- click 'Next: Add Storage'
adjust size as per your need (default is 8GB)
- click 'Next: Tag Instance'
create tag if you need any tagging for your instance
- click 'Next: Configure Security Group'
click 'Add Rule' to add new rule(for port, ip address etc.)
default you can set it to -
SSH TCP 22 Anywhere 0.0.0.0/0
HTTP TCP 80 Anywhere 0.0.0.0/0
- then click 'Review and Launch'
check all your setting, then click 'Launch'
- select existing or create new keypair to connect to your instance
click 'Launch Instance', this will generate the key (in case of new keypair) & launches your instance
find 'Public IP' from 'Description'
- you can generate an Elastic IP from 'Network & Security' tab
- click 'Allocate new address'
- then click 'Allocate', this will generate an Elastic IP
- click 'Close', this will redirect you to Elastic IP Dashboard
- select you Elastic IP & on right click select 'Associate address'
- choose you instance (whom you want to associate) & click 'Associate'
this will replace your Public IP with Elastic IP (& now this IP is used)
#login to your server from terminal using pem file (generated private key)
- ssh -i "<Path of your pem file>" ubuntu@<Public IP Address>
- sudo apt-get update && sudo apt-get -y upgrade #to update existing packages
- sudo adduser deploy #create 'deploy' user for deploying the application to server
- sudo adduser deploy sudo #provide sudo privilege
- su - deploy
- ssh-keygen #do not set a passphrase for the key
- cat .ssh/id_rsa.pub
- copy the ssh-key & set it as your deploy key on your repository(project on bitbucket or github)
- copy your system public ssh-key & paste it into the following file on your instance as deploy user
nano .ssh/authorized_keys #save & exit
- sudo apt-get install git
- sudo apt-get install nginx
- sudo nano /etc/nginx/sites-available/default #to configure default site
#add this content to file
upstream app {
# Path to Puma SOCK file, as defined previously
server unix:/home/deploy/<application name>/shared/tmp/sockets/puma.sock fail_timeout=0;
}
server {
listen 80;
server_name localhost;
root /home/deploy/<application name>/current/public;
try_files $uri/index.html $uri @app;
location / {
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header Host $host;
proxy_redirect off;
proxy_http_version 1.1;
proxy_set_header Connection '';
proxy_pass http://app;
}
location ~ ^/(assets|fonts|system)/|favicon.ico|robots.txt {
gzip_static on;
expires max;
add_header Cache-Control public;
}
error_page 500 502 503 504 /500.html;
client_max_body_size 4G;
keepalive_timeout 10;
}
- su - deploy
- sudo apt-get install libgdbm-dev libncurses5-dev automake libtool bison libffi-dev
- gpg --keyserver hkp://keys.gnupg.net --recv-keys 409B6B1796C275462A1703113804BB82D39DC0E3 7D2BAF1CF37B13E2069D6956105BD0E739499BDB
- curl -sSL https://get.rvm.io | bash -s stable
- source ~/.rvm/scripts/rvm
- rvm install 2.5.1
- rvm use 2.5.1 --default
- ruby -v
- gem install bundler #install bundler
- curl -sL https://deb.nodesource.com/setup_8.x | sudo -E bash -
- sudo apt-get install -y nodejs
# install mysql
- sudo apt-get install mysql-server mysql-client libmysqlclient-dev
# setup postgresql
- sudo sh -c "echo 'deb http://apt.postgresql.org/pub/repos/apt/ xenial-pgdg main' > /etc/apt/sources.list.d/pgdg.list"
- wget --quiet -O - http://apt.postgresql.org/pub/repos/apt/ACCC4CF8.asc | sudo apt-key add -
- sudo apt-get update
- sudo apt-get install postgresql-common
- sudo apt-get install postgresql-9.5 libpq-dev
# create postgresql user
- sudo -u postgres createuser foo -s
# set password
- sudo -u postgres psql
postgres=# \password chris
- mkdir <application name>
- mkdir -p <application name>/shared/config
- nano <application name>/shared/config/database.yml
#for rails 5.2 'master.key' file is used for secret key
- nano <application name>/shared/config/master.key
- add key from master.key of your application to this file
eg: da54dd7f691dd9d8707c3f67ec9d076f
#for rails lower versions 'application.yml' or 'secrets.yml' is used for secret key
- nano <application name>/shared/config/application.yml
OR
- nano <application name>/shared/config/secrets.yml
- add SECRET_KEY_BASE from your application to this file (or you can generate your own secret key base)
SECRET_KEY_BASE: "8a2ff74119cb2b8f14a85dd6e213fa24d8540fc34dcaa7ef8a35c246ae452bfa8702767d19086461ac911e1435481c22663fbd65c97f21f6a91b3fce7687ce63"
Server configurations are done. Now configure your rails application.
#configuring capistrano
#add this to gemfile
group :development do
gem 'capistrano'
gem 'capistrano3-puma'
gem 'capistrano-rails', require: false
gem 'capistrano-bundler', require: false
gem 'capistrano-rvm'
end
- bundle install
#create configuration files for capistrano
- bundle exec cap install
#this command will create
config/deploy.rb
config/deploy/production.rb
config/deploy/staging.rb
#add these line to capfile
require 'capistrano/bundler'
require 'capistrano/rvm'
require 'capistrano/rails/assets' # for asset handling add
require 'capistrano/rails/migrations' # for running migrations
require 'capistrano/puma'
install_plugin Capistrano::Puma # Default puma tasks
#upload puma config
- cap production puma:config
Edit deploy.rb
lock '3.11.0' #capistrano version
set :application, '<application name>'
set :repo_url, '<git application path>' # Edit this to match your repository
set :branch, :master #use `git rev-parse --abbrev-ref HEAD`.chomp for pick current branch
set :deploy_to, '/home/deploy/<application name>'
set :pty, true
set :linked_files, %w{config/database.yml config/application.yml} #if rails 5.2 & above master.key is used insted of application.yml
set :linked_dirs, %w{log tmp/pids tmp/cache tmp/sockets vendor/bundle public/system public/uploads}
set :keep_releases, 5
Edit the config/deploy/staging.rb
set :rails_env, 'staging'
set :puma_env, fetch(:rack_env, fetch(:rails_env, 'staging'))
server '<staging server public IP address>', user: 'deploy', roles: %w{web app db}
Edit the config/deploy/production.rb
set :rails_env, 'production'
set :puma_env, fetch(:rack_env, fetch(:rails_env, 'production'))
server '<production server public IP address>', user: 'deploy', roles: %w{web app db}
Deploy code to AWS
cap staging deploy #for staging server
cap production deploy #for production server
#login to server & finally restart the nginx
sudo service nginx restart
Thanks for making this easy and available!!!