When I create a personal app in Rails and then deploy it on AWS, I always forget how to do it, so I'd like to write it down here.
--Assuming Rails 5.2 or higher
You can create a new key pair or an existing key pair. The key pair must not contain spaces.
Set the type to "HTTP", the protocol to "TCP", the port range to "80", and the source to "Custom / 0.0.0.0/0, :: / 0".
The following is also released so that HTTP connection can be made
local
$ cd ~
$ mkdir ~/.ssh
# .Create a directory called ssh
#Even if you get an error saying File exists.It means that the ssh directory exists, so let's proceed as it is.
$ mv Downloads/The name of the downloaded key.pem .ssh/
#Use the mv command to download the pem file from the download directory..Change to the ssh directory.
$ cd .ssh/
$ ls
#Check if the pem file exists
$chmod 600 The name of the downloaded key.pem
$ ssh -i Downloaded key name.pem ec2-user@Elastic IP associated with the created EC2 instance
#(For example, Elastic IP is 123.456.If it's 789, ssh-i Downloaded key name.pem [email protected] command is 789)
#(Using the downloaded key, ec2-Login as user)
server
[ec2-user@ip-172-31-25-189 ~]$ sudo yum -y update
[ec2-user@ip-172-31-25-189 ~]$ sudo yum -y install git make gcc-c++ patch libyaml-devel libffi-devel libicu-devel zlib-devel readline-devel libxml2-devel libxslt-devel ImageMagick ImageMagick-devel openssl-devel libcurl libcurl-devel curl
[ec2-user@ip-172-31-25-189 ~]$ sudo curl -sL https://rpm.nodesource.com/setup_6.x | sudo bash -
[ec2-user@ip-172-31-25-189 ~]$ sudo yum -y install nodejs
[ec2-user@ip-172-31-25-189 ~]$ git clone https://github.com/sstephenson/rbenv.git ~/.rbenv
#Pass through
[ec2-user@ip-172-31-25-189 ~]$ echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bash_profile
#Description for calling rbenv
[ec2-user@ip-172-31-25-189 ~]$ echo 'eval "$(rbenv init -)"' >> ~/.bash_profile
#.bash_Load profile
[ec2-user@ip-172-31-25-189 ~]$ source .bash_profile
#ruby-install build
[ec2-user@ip-172-31-25-189 ~]$ git clone https://github.com/sstephenson/ruby-build.git ~/.rbenv/plugins/ruby-build
#Do rehash
[ec2-user@ip-172-31-25-189 ~]$ rbenv rehash
[ec2-user@ip-172-31-25-189 ~]$ rbenv install 2.5.1
[ec2-user@ip-172-31-25-189 ~]$ rbenv global 2.5.1
[ec2-user@ip-172-31-25-189 ~]$ rbenv rehash #Do rehash
[ec2-user@ip-172-31-25-189 ~]$ ruby -v #Check version
#MySQL installation
[ec2-user@ip-172-31-25-189 ~]$ sudo yum -y install mysql56-server mysql56-devel mysql56
[ec2-user@ip-172-31-25-189 ~]$ sudo service mysqld start
[ec2-user@ip-172-31-25-189 ~]$ sudo /usr/libexec/mysql56/mysqladmin -u root password 'Password you want to set here'
#Check if you can enter with the PW set in MySQL
[ec2-user@ip-172-31-25-189 ~]$ mysql -u root -p
EC2 server
[ec2-user@ip-172-31-23-189 ~]$ ssh-keygen -t rsa -b 4096
You may be asked to enter about 3 steps such as passphrase on the way, but please proceed with the Enter key without entering anything.
EC2 server
[ec2-user@ip-172-31-23-189 ~]$ cat ~/.ssh/id_rsa.pub
Access the public key displayed on cat to Github and register it. https://github.com/settings/keys
After registering the key on Github, check if you can connect with SSH with the following command
EC2 server
[ec2-user@ip-172-31-23-189 ~]$ ssh -T [email protected]
Gemfile
group :development, :test do
gem 'capistrano'
gem 'capistrano-rbenv'
gem 'capistrano-bundler'
gem 'capistrano-rails'
gem 'capistrano3-unicorn'
end
local
$ bundle install
$ bundle exec cap install
Capfile editing
require "capistrano/setup"
require "capistrano/deploy"
require 'capistrano/rbenv'
require 'capistrano/bundler'
require 'capistrano/rails/assets'
require 'capistrano/rails/migrations'
require 'capistrano3/unicorn'
Dir.glob("lib/capistrano/tasks/*.rake").each { |r| import r }
config/deploy/production.rb
server '<Prepared Elastic IP>', user: 'ec2-user', roles: %w{app db web}
config/deploy.rb
# config valid only for current version of Capistrano
#Described the version of capistrano. Continue to use the fixed version and prevent troubles due to version change
lock '<Capistrano version>'
#Used to display Capistrano logs
set :application, '<Own application name>'
#Specify from which repository you want to pull your app
set :repo_url, '[email protected]:<Github username>/<Repository name>.git'
#Specify a directory to be referenced in common even if the version changes
set :linked_dirs, fetch(:linked_dirs, []).push('log', 'tmp/pids', 'tmp/cache', 'tmp/sockets', 'vendor/bundle', 'public/system', 'public/uploads')
set :rbenv_type, :user
set :rbenv_ruby, '<The version of ruby used in this app>'
#Which public key to use for deployment
set :ssh_options, auth_methods: ['publickey'],
keys: ['<Ssh key for EC2 instance on local PC(pem)Path to (eg~/.ssh/key_pem.pem)>']
#Location of the file containing the process number
set :unicorn_pid, -> { "#{shared_path}/tmp/pids/unicorn.pid" }
#Location of Unicorn configuration files
set :unicorn_config_path, -> { "#{current_path}/config/unicorn.rb" }
set :keep_releases, 5
set :linked_files, %w{ config/master.key }
after 'deploy:publishing', 'deploy:restart'
namespace :deploy do
task :restart do
invoke 'unicorn:stop'
invoke 'unicorn:start'
end
desc 'upload master.key'
task :upload do
on roles(:app) do |host|
if test "[ ! -d #{shared_path}/config ]"
execute "mkdir -p #{shared_path}/config"
end
upload!('config/master.key', "#{shared_path}/config/master.key")
end
end
before :starting, 'deploy:upload'
after :finishing, 'deploy:cleanup'
end
config/database.yml
production:
<<: *default
database: application_name_production
username: root
password: <%= ENV['DATABASE_PASSWORD'] %>
socket: /var/lib/mysql/mysql.sock
Gemfile
group :production do
gem 'unicorn', '5.4.1'
end
local
bundle install
config/unicorn.rb
app_path = File.expand_path('../../../', __FILE__)
worker_processes 1
#Specify current
working_directory "#{app_path}/current"
#Changed to refer to each in shared
listen "#{app_path}/shared/tmp/sockets/unicorn.sock"
pid "#{app_path}/shared/tmp/pids/unicorn.pid"
stderr_path "#{app_path}/shared/log/unicorn.stderr.log"
stdout_path "#{app_path}/shared/log/unicorn.stdout.log"
timeout 60
#The following is an applied setting, so the explanation is omitted.
preload_app true
GC.respond_to?(:copy_on_write_friendly=) && GC.copy_on_write_friendly = true
check_client_connection false
run_once = true
before_fork do |server, worker|
defined?(ActiveRecord::Base) &&
ActiveRecord::Base.connection.disconnect!
if run_once
run_once = false # prevent from firing again
end
old_pid = "#{server.config[:pid]}.oldbin"
if File.exist?(old_pid) && server.pid != old_pid
begin
sig = (worker.nr + 1) >= server.worker_processes ? :QUIT : :TTOU
Process.kill(sig, File.read(old_pid).to_i)
rescue Errno::ENOENT, Errno::ESRCH => e
logger.error e
end
end
end
after_fork do |_server, _worker|
defined?(ActiveRecord::Base) && ActiveRecord::Base.establish_connection
end
config/environments/production.rb (after modification)
# config.assets.js_compressor = :uglifier
First, let's commit and push from GitHub Desktop. Be sure to do it on the master branch at this time.
ec2 server
#Create a new directory with the mkdir command
[ec2-user@ip-172-31-23-189 ~]$ sudo mkdir /var/www/
#Ec2 permissions on the created www directory-Change to user
[ec2-user@ip-172-31-23-189 ~]$ sudo chown ec2-user /var/www/
ec2 server
[ec2-user@ip-172-31-23-189 ~]$ cd /var/www/
[ec2-user@ip-172-31-23-189 www]$ git clone https://github.com/<username>/<Repository name>.git
ec2 server
#Installation
[ec2-user@ip-172-31-25-189 ~]$ sudo yum -y install nginx
#Start configuration file
[ec2-user@ip-172-31-25-189 ~]$ sudo vim /etc/nginx/conf.d/rails.conf
rails.conf
upstream app_server {
#Changed to refer to in shared
server unix:/var/www/<Application name>/shared/tmp/sockets/unicorn.sock;
}
server {
listen 80;
server_name <Fill in Elastic IP>;
#Set the maximum size of files uploaded from the client to 2 giga. The default is 1 mega, so keep it large
client_max_body_size 2g;
#Changed to refer to in current
root /var/www/<Application name>/current/public;
location ^~ /assets/ {
gzip_static on;
expires max;
add_header Cache-Control public;
#Changed to refer to in current
root /var/www/<Application name>/current/public;
}
try_files $uri/index.html $uri @unicorn;
location @unicorn {
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_redirect off;
proxy_pass http://app_server;
}
error_page 500 502 503 504 /500.html;
}
ec2 server
#Change nginx permissions
[ec2-user@ip-172-31-25-189 ~]$ cd /var/lib
[ec2-user@ip-172-31-25-189 lib]$ sudo chmod -R 775 nginx
[ec2-user@ip-172-31-25-189 lib]$ cd ~
[ec2-user@ip-172-31-25-189 ~]$ sudo service nginx restart
#nginx reboot
[ec2-user@ip-172-31-25-189 ~]$ sudo service nginx reload
[ec2-user@ip-172-31-25-189 ~]$ sudo service nginx restart
ec2 server
[ec2-user@ip-172-31-25-189 ~]$ cd
[ec2-user@ip-172-31-25-189 ~]$ sudo dd if=/dev/zero of=/swapfile1 bs=1M count=512
[ec2-user@ip-172-31-25-189 ~]$ sudo chmod 600 /swapfile1
[ec2-user@ip-172-31-25-189 ~]$ sudo mkswap /swapfile1
[ec2-user@ip-172-31-25-189 ~]$ sudo swapon /swapfile1
[ec2-user@ip-172-31-25-189 ~]$ sudo sh -c 'echo "/swapfile1 none swap sw 0 0" >> /etc/fstab'
[ec2-user@ip-172-31-23-189 <Repository name>]$ gem install bundler -v x.x.x
#Introduce the locally confirmed version of bundler
[ec2-user@ip-172-31-23-189 <Repository name>]$ bundle install
#The above command may take several minutes or more.
ec2 server
[ec2-user@ip-172-31-23-189 <Repository name>]$ rake secret
69619d9a75b78f2e1c87ec5e07541b42f23efeb6a54e97da3723de06fe74af29d5718adff77d2b04b2805d3a1e143fa61baacfbf4ca2c6fcc608cff8d5a28e8d
#Copy string
ec2 server
[ec2-user@ip-172-31-23-189 ~]$ sudo vim /etc/environment
/etc/environment
DATABASE_PASSWORD='MySQL root user password'
SECRET_KEY_BASE='The secret you copied earlier_key_base'
After writing, press esc (escape key) and enter: wq to save the contents. Once saved, log out to apply the environment variables.
local
$ ssh -i [The name of the downloaded key].pem ec2-user@[Elastic IP associated with the created EC2 instance]
(Using the downloaded key, ec2-Login as user)
ec2 server
[ec2-user@ip-172-31-23-189 ~]$ env | grep SECRET_KEY_BASE
SECRET_KEY_BASE='secret_key_base'
[ec2-user@ip-172-31-23-189 ~]$ env | grep DATABASE_PASSWORD
DATABASE_PASSWORD='MySQL root user password'
ec2 server
#Production environment database creation
[ec2-user@ip-172-31-23-189 <Repository name>]$ cd /var/www/app name/releases
[ec2-user@ip-172-31-23-189 <Repository name>]$ ll
#A folder with the name of the number representing the date is displayed Example: 20200218063515
cd bottom number#=>Example cd 20200218063515
[ec2-user@ip-172-31-23-189 <Repository name>]$ rails db:create RAILS_ENV=production
# => Created database '<Database name>'
[ec2-user@ip-172-31-23-189 <Repository name>]$ rails db:migrate RAILS_ENV=production
Push all local changes to master
local
#Run in the application directory
$ bundle exec cap production deploy
How to check the error log
On the server side
Check / var / www / <repository name> /current/log/unicorn.stderr.log
with the less or cat command and check if there are any errors (the lower the log, the more up-to-date the log is. Note that it is UTC)
Recommended Posts