19/09/2018, 09:49

Triển khai ứng dụng Rails trên Ubuntu 14.04 với Capistrano, Nginx và Puma

Giới thiệu Rails là một khung ứng dụng web nguồn mở được viết bằng Ruby. Nó theo sau Quy ước về cấu hình triết lý bằng cách đưa ra giả định rằng có cách 'tốt nhất' để làm việc. Điều này cho phép bạn viết ít mã hơn trong khi hoàn thành nhiều hơn mà không cần phải đi qua các tệp cấu hình vô tận. ...

Giới thiệu

Rails là một khung ứng dụng web nguồn mở được viết bằng Ruby. Nó theo sau Quy ước về cấu hình triết lý bằng cách đưa ra giả định rằng có cách 'tốt nhất' để làm việc. Điều này cho phép bạn viết ít mã hơn trong khi hoàn thành nhiều hơn mà không cần phải đi qua các tệp cấu hình vô tận.

Nginx là một máy chủ HTTP hiệu suất cao, proxy ngược và bộ cân bằng tải được biết đến với sự tập trung vào tính đồng thời, tính ổn định, khả năng mở rộng và mức tiêu thụ bộ nhớ thấp. Giống như Nginx, Puma là một máy chủ web cực kỳ nhanh và đồng thời với một bộ nhớ rất nhỏ nhưng được xây dựng cho các ứng dụng web của Ruby.

Capistrano là một công cụ tự động hóa máy chủ từ xa tập trung chủ yếu vào các ứng dụng web của Ruby. Nó được sử dụng để triển khai một cách đáng tin cậy các ứng dụng web cho bất kỳ số lượng máy từ xa nào bằng cách viết các luồng công việc tùy ý qua SSH và tự động hóa các tác vụ phổ biến như biên dịch trước tài sản và khởi động lại máy chủ Rails.

Trong hướng dẫn này, chúng tôi sẽ cài đặt Ruby và Nginx trên một giọt nhỏ DigitalOcean Ubuntu và cấu hình Puma và Capistrano trong ứng dụng web của chúng tôi. Nginx sẽ được sử dụng để nắm bắt các yêu cầu của máy khách và chuyển chúng qua máy chủ web Puma đang chạy Rails. Chúng tôi sẽ sử dụng Capistrano để tự động hóa các tác vụ triển khai phổ biến, vì vậy mỗi lần chúng tôi phải triển khai phiên bản ứng dụng Rails mới cho máy chủ, chúng tôi có thể thực hiện điều đó bằng một vài lệnh đơn giản.

Điều kiện tiên quyết

Để làm theo hướng dẫn này, bạn phải có những điều sau đây:

  • Ubuntu 14.04 x64 Giọt
  • Người dùng không phải root có tên deploy với đặc quyền sudo (Thiết lập máy chủ ban đầu với Ubuntu 14.04 giải thích cách thiết lập điều này.)
  • Ứng dụng Rails được lưu trữ trong kho lưu trữ git từ xa đã sẵn sàng để triển khai

Tùy chọn, để tăng cường bảo mật, bạn có thể tắt đăng nhập root thông qua SSH và thay đổi số cổng SSH như được mô tả trong Thiết lập máy chủ ban đầu với Ubuntu 14.04.

Cảnh báo: Sau khi vô hiệu hóa đăng nhập root, hãy chắc chắn rằng bạn có thể SSH để Droplet của bạn như là deploy người dùng và sử dụng sudo cho người dùng này trước đóng phiên SSH gốc bạn đã mở để thực hiện những thay đổi này.

Tất cả các lệnh trong hướng dẫn này sẽ được chạy như deploy người dùng. Nếu truy cập root là cần thiết cho lệnh, nó sẽ được bắt đầu bằng sudo.

Bước 1 - Cài đặt Nginx

Khi VPS được bảo mật, chúng tôi có thể bắt đầu cài đặt các gói. Cập nhật các tệp chỉ mục gói:

sudo apt-get update

Sau đó, cài đặt Nginx:

sudo apt-get install curl git-core nginx -y

Bước 2 - Cài đặt cơ sở dữ liệu

Cài đặt cơ sở dữ liệu mà bạn sẽ sử dụng trong ứng dụng Rails của bạn. Vì có rất nhiều cơ sở dữ liệu để chọn, chúng tôi sẽ không đề cập đến chúng trong hướng dẫn này. Bạn có thể xem hướng dẫn dành cho những người lớn tại đây:

  • MySQL
  • PostgreSQL
  • MongoDB

Ngoài ra hãy chắc chắn để kiểm tra:

  • Làm thế nào để sử dụng MySQL với Ruby của bạn trên Rails ứng dụng trên Ubuntu 14.04
  • Làm thế nào để sử dụng PostgreSQL với ứng dụng Ruby on Rails của bạn trên Ubuntu 14.04

Bước 3 - Cài đặt RVM và Ruby

Chúng tôi sẽ không cài đặt Ruby trực tiếp. Thay vào đó, chúng ta sẽ sử dụng một trình quản lý phiên bản Ruby. Có rất nhiều người trong số họ để lựa chọn (rbenv, chruby, vv), nhưng chúng tôi sẽ sử dụng RVM cho hướng dẫn này. RVM cho phép bạn dễ dàng cài đặt và quản lý nhiều hồng ngọc trên cùng một hệ thống và sử dụng chính xác theo ứng dụng của bạn. Điều này làm cho cuộc sống dễ dàng hơn nhiều khi bạn phải nâng cấp ứng dụng Rails của bạn để sử dụng một ruby ​​mới hơn.

Trước khi cài đặt RVM, bạn cần nhập khóa RVM GPG:

gpg --keyserver hkp://keys.gnupg.net --recv-keys 409B6B1796C275462A1703113804BB82D39DC0E3

Sau đó cài đặt RVM để quản lý Ruby của chúng tôi:

curl -sSL https://get.rvm.io | bash -s stable

Lệnh này sử dụng curl để tải xuống tập lệnh Cài đặt RVM từ https://get.rvm.io. Các -sSL tùy chọn bao gồm ba lá cờ:

  • -s yêu cầu curl tải xuống tệp trong 'chế độ im lặng'
  • -S nói curl để hiển thị một thông báo lỗi nếu nó không thành công
  • -L yêu cầu curl theo dõi tất cả các chuyển hướng HTTP trong khi truy xuất tập lệnh cài đặt

Sau khi tải xuống, tập lệnh là đường ống đến bash. Các -s tùy chọn vượt qua stable làm đối số cho kịch bản Cài đặt RVM để tải xuống và cài đặt bản phát hành ổn định của RVM.

Chú thích: Nếu lệnh thứ hai thất bại với thông báo "xác thực chữ ký GPG không thành công", điều đó có nghĩa là GPG Key đã thay đổi, chỉ cần sao chép lệnh từ đầu ra lỗi và chạy nó để tải xuống chữ ký. Sau đó chạy lệnh curl để cài đặt RVM.

Chúng ta cần tải kịch bản RVM (như một hàm) để chúng ta có thể bắt đầu sử dụng nó. Sau đó chúng tôi cần chạy requirements lệnh để tự động cài đặt các phụ thuộc và tệp cần thiết cho RVM và Ruby để hoạt động đúng:

source ~/.rvm/scripts/rvm

rvm requirements

Bây giờ chúng ta có thể cài đặt Ruby theo lựa chọn của chúng ta. Chúng tôi sẽ cài đặt phiên bản mới nhất Ruby 2.2.1 (tại thời điểm viết) là Ruby mặc định của chúng tôi:

rvm install 2.2.1

rvm use 2.2.1 --default

Bước 4 - Cài đặt Rails và Bundler

Khi Ruby được thiết lập, chúng ta có thể bắt đầu cài đặt Rubygems. Chúng ta sẽ bắt đầu bằng cách cài đặt gem Rails cho phép ứng dụng Rails của bạn chạy, và sau đó chúng ta sẽ cài đặt bundler có thể đọc ứng dụng của bạn Gemfile và tự động cài đặt tất cả các đá quý cần thiết.

Để cài đặt Rails và Bundler:

gem install rails -V --no-ri --no-rdoc

gem install bundler -V --no-ri --no-rdoc

Ba lá cờ đã được sử dụng:

  • -V (Verbose Output): In thông tin chi tiết về cài đặt Gem
  • --no-ri - (Tài liệu bỏ qua Ri): Không cài đặt Ri Documents, tiết kiệm dung lượng và cài đặt nhanh
  • --no-rdoc - (Bỏ qua RDocs): Không cài đặt RDocs, tiết kiệm dung lượng và tăng tốc cài đặt

Chú thích: Bạn cũng có thể cài đặt phiên bản Rails cụ thể theo yêu cầu của mình bằng cách sử dụng -v cờ:

gem install rails -v '4.2.0' -V --no-ri --no-rdoc 

Bước 5 - Thiết lập Khóa SSH

Vì chúng tôi muốn thiết lập các triển khai trơn tru, chúng tôi sẽ sử dụng Khóa SSH để ủy quyền. Đầu tiên, hãy bắt tay với GitHub, Bitbucket hoặc bất kỳ Git Remote nào khác, nơi mà codebase cho ứng dụng Rails của bạn được lưu trữ:

ssh -T git@github.com

ssh -T git@bitbucket.org

Đừng lo lắng nếu bạn nhận được Permission denied (publickey) thông điệp. Bây giờ, tạo khóa SSH (Cặp khóa công khai / riêng tư) cho máy chủ của bạn:

ssh-keygen -t rsa 

Thêm khóa công cộng mới được tạo (~/.ssh/id_rsa.pub) vào các khóa triển khai của kho lưu trữ của bạn:

  • Hướng dẫn cho Github
  • Hướng dẫn cho Bitbucket

Nếu tất cả các bước đã được hoàn thành chính xác, bây giờ bạn sẽ có thể clone kho lưu trữ git của bạn (qua Giao thức SSH, không phải HTTP) mà không cần nhập mật khẩu của bạn:

git clone git@example.com:username/appname.git

Nếu bạn cần một ứng dụng mẫu để thử nghiệm, bạn có thể chia rẽ ứng dụng thử nghiệm sau đây được tạo cụ thể cho hướng dẫn này: Ứng dụng Rails mẫu trên GitHub

Các git clone lệnh sẽ tạo một thư mục có cùng tên với ứng dụng của bạn. Ví dụ: một thư mục có tên testapp_rails sẽ được tạo ra.

Chúng tôi đang nhân bản chỉ để kiểm tra xem các khóa triển khai của chúng tôi có đang hoạt động hay không, chúng tôi không cần sao chép hoặc kéo kho lưu trữ của mình mỗi lần chúng tôi đẩy các thay đổi mới. Chúng tôi sẽ để Capistrano xử lý tất cả những điều đó cho chúng tôi. Bây giờ bạn có thể xóa thư mục nhân bản này nếu bạn muốn.

Mở một thiết bị đầu cuối trên máy cục bộ của bạn. Nếu bạn không có Khóa SSH cho máy tính cục bộ của mình, hãy tạo một Khóa SSH cho nó. Trong phiên đầu cuối địa phương của bạn:

ssh-keygen -t rsa 

Thêm Khóa SSH cục bộ của bạn vào Phím được ủy quyền tệp (nhớ thay thế số cổng bằng số cổng tùy chỉnh của bạn):

cat ~/.ssh/id_rsa.pub | ssh -p your_port_num deploy@your_server_ip 'cat >> ~/.ssh/authorized_keys'

Bước 6 - Thêm cấu hình triển khai trong ứng dụng Rails

Trên máy cục bộ của bạn, tạo các tệp cấu hình cho Nginx và Capistrano trong ứng dụng Rails của bạn. Bắt đầu bằng cách thêm các dòng này vào Gemfile trong ứng dụng Rails:

Gemfile

group :development do
    gem 'capistrano',         require: false
    gem 'capistrano-rvm',     require: false
    gem 'capistrano-rails',   require: false
    gem 'capistrano-bundler', require: false
    gem 'capistrano3-puma',   require: false
end

gem 'puma'

Sử dụng bundler để cài đặt những viên đá quý bạn vừa chỉ định trong Gemfile. Nhập lệnh sau để nhóm ứng dụng Rails của bạn:

bundle

Sau khi đóng gói, hãy chạy lệnh sau để định cấu hình Capistrano:

cap install

Điều này sẽ tạo ra:

  • Capfile trong thư mục gốc của ứng dụng Rails của bạn
  • deploy.rb tập tin trong config danh mục
  • deploy thư mục trong config danh mục

Thay thế nội dung của bạn Capfile với những điều sau đây:

Capfile

# Load DSL and Setup Up Stages
require 'capistrano/setup'
require 'capistrano/deploy'

require 'capistrano/rails'
require 'capistrano/bundler'
require 'capistrano/rvm'
require 'capistrano/puma'

# Loads custom tasks from `lib/capistrano/tasks' if you have any defined.
Dir.glob('lib/capistrano/tasks/*.rake').each { |r| import r }

Điều này Capfile tải một số tác vụ được xác định trước vào các tệp cấu hình Capistrano của bạn để làm cho các triển khai của bạn không gặp rắc rối, chẳng hạn như tự động:

  • Chọn đúng Ruby
  • Pre-compiling Assets
  • Nhân bản kho lưu trữ Git của bạn đến đúng vị trí
  • Cài đặt các phụ thuộc mới khi Gemfile của bạn đã thay đổi

Thay thế nội dung của config/deploy.rb với những điều sau đây, cập nhật các trường được đánh dấu màu đỏ với thông số ứng dụng của bạn và Giọt:

config/deploy.rb

# Change these
server 'your_server_ip', port: your_port_num, roles: [:web, :app, :db], primary: true

set :repo_url,        'git@example.com:username/appname.git'
set :application,     'appname'
set :user,            'deploy'
set :puma_threads,    [4, 16]
set :puma_workers,    0

# Don't change these unless you know what you're doing
set :pty,             true
set :use_sudo,        false
set :stage,           :production
set :deploy_via,      :remote_cache
set :deploy_to,       "/home/#{fetch(:user)}/apps/#{fetch(:application)}"
set :puma_bind,       "unix://#{shared_path}/tmp/sockets/#{fetch(:application)}-puma.sock"
set :puma_state,      "#{shared_path}/tmp/pids/puma.state"
set :puma_pid,        "#{shared_path}/tmp/pids/puma.pid"
set :puma_access_log, "#{release_path}/log/puma.error.log"
set :puma_error_log,  "#{release_path}/log/puma.access.log"
set :ssh_options,     { forward_agent: true, user: fetch(:user), keys: %w(~/.ssh/id_rsa.pub) }
set :puma_preload_app, true
set :puma_worker_timeout, nil
set :puma_init_active_record, true  # Change to false when not using ActiveRecord

## Defaults:
# set :scm,           :git
# set :branch,        :master
# set :format,        :pretty
# set :log_level,     :debug
# set :keep_releases, 5

## Linked Files & Directories (Default None):
# set :linked_files, %w{config/database.yml}
# set :linked_dirs,  %w{bin log tmp/pids tmp/cache tmp/sockets vendor/bundle public/system}

namespace :puma do
  desc 'Create Directories for Puma Pids and Socket'
  task :make_dirs do
    on roles(:app) do
      execute "mkdir #{shared_path}/tmp/sockets -p"
      execute "mkdir #{shared_path}/tmp/pids -p"
    end
  end

  before :start, :make_dirs
end

namespace :deploy do
  desc "Make sure local git is in sync with remote."
  task :check_revision do
    on roles(:app) do
      unless `git rev-parse HEAD` == `git rev-parse origin/master`
        puts "WARNING: HEAD is not the same as origin/master"
        puts "Run `git push` to sync changes."
        exit
      end
    end
  end

  desc 'Initial Deploy'
  task :initial do
    on roles(:app) do
      before 'deploy:restart', 'puma:start'
      invoke 'deploy'
    end
  end

  desc 'Restart application'
  task :restart do
    on roles(:app), in: :sequence, wait: 5 do
      invoke 'puma:restart'
    end
  end

  before :starting,     :check_revision
  after  :finishing,    :compile_assets
  after  :finishing,    :cleanup
  after  :finishing,    :restart
end

# ps aux | grep puma    # Get puma pid
# kill -s SIGUSR2 pid   # Restart puma
# kill -s SIGTERM pid   # Stop puma

Điều này deploy.rb tập tin chứa một số mặc định sane làm việc out-of-the-box để giúp bạn quản lý các bản phát hành ứng dụng của bạn và tự động thực hiện một số tác vụ khi bạn triển khai:

  • Sử dụng production làm môi trường mặc định cho ứng dụng Rails của bạn
  • Tự động quản lý nhiều bản phát hành ứng dụng của bạn
  • Sử dụng các tùy chọn SSH tối ưu
  • Kiểm tra xem điều khiển từ xa git của bạn có cập nhật không
  • Quản lý nhật ký ứng dụng của bạn
  • Tải trước ứng dụng trong bộ nhớ khi quản lý nhân viên Puma
  • Bắt đầu (hoặc khởi động lại) máy chủ Puma sau khi hoàn thành triển khai
  • Mở ổ cắm đến máy chủ Puma tại một vị trí cụ thể trong bản phát hành của bạn

Bạn có thể thay đổi tất cả các tùy chọn tùy thuộc vào yêu cầu của bạn. Bây giờ, Nginx cần phải được cấu hình. Tạo nên config/nginx.conf trong thư mục dự án Rails của bạn và thêm thông tin sau vào nó (một lần nữa, thay thế bằng các tham số của bạn):

config/nginx.conf

upstream puma {
  server unix:///home/deploy/apps/appname/shared/tmp/sockets/appname-puma.sock;
}

server {
  listen 80 default_server deferred;
  # server_name example.com;

  root /home/deploy/apps/appname/current/public;
  access_log /home/deploy/apps/appname/current/log/nginx.access.log;
  error_log /home/deploy/apps/appname/current/log/nginx.error.log info;

  location ^~ /assets/ {
    gzip_static on;
    expires max;
    add_header Cache-Control public;
  }

  try_files $uri/index.html $uri @puma;
  location @puma {
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header Host $http_host;
    proxy_redirect off;

    proxy_pass http://puma;
  }

  error_page 500 502 503 504 /500.html;
  client_max_body_size 10M;
  keepalive_timeout 10;
}

Giống như tệp trước, điều này nginx.conf chứa các giá trị mặc định hoạt động ngoài hộp với các cấu hình trong deploy.rb tập tin. Điều này lắng nghe lưu lượng trên cổng 80 và chuyển yêu cầu tới ổ cắm Puma của bạn, ghi nhật ký nginx vào bản phát hành 'hiện tại' của ứng dụng, nén tất cả nội dung và lưu trữ chúng trong trình duyệt hết hạn, phục vụ các trang HTML ở nơi công cộng thư mục dưới dạng tệp tĩnh và đặt tối đa mặc định Client Body Size và Request Timeout giá trị.

Bước 7 - Triển khai ứng dụng Rails của bạn

Nếu bạn đang sử dụng ứng dụng Rails của riêng mình, hãy cam kết những thay đổi bạn vừa thực hiện và đẩy chúng từ xa từ Máy cục bộ của bạn:

git add -A

git commit -m "Set up Puma, Nginx & Capistrano"

git push origin master

Chú thích: Nếu đây là lần đầu tiên sử dụng GitHub từ hệ thống này, bạn có thể phải đưa ra các lệnh sau với tên người dùng và địa chỉ email GitHub của bạn:

git config --global user.name 'Your Name'

git config --global user.email you@example.com 

Một lần nữa, từ máy cục bộ của bạn, thực hiện triển khai đầu tiên của bạn:

cap production deploy:initial

Điều này sẽ đẩy ứng dụng Rails của bạn vào Droplet, cài đặt tất cả các đá quý cần thiết cho ứng dụng của bạn và khởi động máy chủ web Puma. Điều này có thể mất từ ​​5-15 phút tùy thuộc vào số lượng Đá quý mà ứng dụng của bạn sử dụng. Bạn sẽ thấy thông báo gỡ lỗi khi quá trình này xảy ra.

Nếu mọi thứ suôn sẻ, chúng tôi đã sẵn sàng kết nối máy chủ web Puma của bạn với proxy ngược Nginx.

Trên các giọt, liên kết biểu tượng nginx.conf đến sites-enabled danh mục:

sudo rm /etc/nginx/sites-enabled/default

sudo ln -nfs "/home/deploy/apps/appname/current/config/nginx.conf" "/etc/nginx/sites-enabled/appname"

Khởi động lại dịch vụ Nginx:

sudo service nginx restart

Bây giờ bạn có thể trỏ trình duyệt web của bạn đến IP máy chủ của bạn và xem ứng dụng Rails của bạn đang hoạt động!

Triển khai bình thường

Bất cứ khi nào bạn thực hiện các thay đổi đối với ứng dụng của mình và muốn triển khai bản phát hành mới cho máy chủ, hãy thực hiện các thay đổi, chuyển sang git từ xa như bình thường và chạy deploy chỉ huy:

git add -A

git commit -m "Deploy Message"

git push origin master

cap production deploy

Chú thích: Nếu bạn thực hiện thay đổi cho config/nginx.conf , bạn sẽ phải tải lại hoặc khởi động lại dịch vụ Nginx trên máy chủ sau khi triển khai ứng dụng của mình:

sudo service nginx restart 

Phần kết luận

Được rồi, do đó, bây giờ bạn sẽ chạy một ứng dụng Rails trên Droplet của bạn với Puma như Web Server của bạn cũng như Nginx và Capistrano được cấu hình với các thiết lập cơ bản. Bây giờ bạn hãy xem các tài liệu khác có thể giúp bạn tối ưu hóa cấu hình của mình để tận dụng tối đa ứng dụng Rails của mình:

  • Cấu hình Puma
  • Puma DSL trong Capistrano
  • Biên soạn trước tài sản địa phương ở Capistrano
  • Tự động khởi động lại nhân viên Puma dựa trên RAM
  • Tối ưu hóa Nginx cho tải lưu lượng truy cập cao
0