Rails 项目部署

服务器和域名的购买,可自行google解决。

表达惯例:

#开头代表该命令使用 root 权限执行。

$开头代表改命令使用 ruby 用户权限执行。

从 root 切换至 ruby 用户,使用 su - ruby-的作用可以确保 ruby 用户的环境变量的正确加载。
如果命令中有xxx,请替换为自己的项目名称。

服务器搭建环境

本地执行:

$ ssh root@yourserver_ip
输入密码确保登录成功

准备工作

更新源,并安装必需的用户

# apt-get update
# apt-get install -y git-core curl zlib1g-dev build-essential libssl-dev \
   libreadline-dev libyaml-dev libsqlite3-dev sqlite3 libxml2-dev libxslt1-dev \
   libcurl4-openssl-dev python-software-properties libffi-dev imagemagick libmagickwand-dev

创建新用户 ruby

# adduser ruby(不要使用 useradd)

随便输入一个复杂密码即可,因为后续我们只使用ruby用户的sshkey登录方式。

在 ruby 用户下安装Rbenv + ruby

# su - ruby

Ruby的安装推荐使用RbenvRvm

我使用Rbenv https://github.com/rbenv/rbenv

$ git clone git@github.com:rbenv/rbenv.git ~/.rbenv
$ git clone git@github.com:rbenv/ruby-build.git ~/.rbenv/plugins/ruby-build
$ git clone git@github.com:AndorChen/rbenv-china-mirror.git ~/.rbenv/plugins/rbenv-china-mirror

$ echo 'export path="$home/.rbenv/bin:$path"' >> ~/.bashrc
$ echo 'eval "$(rbenv init -)"' >> ~/.bashrc
$ echo 'source ~/.bashrc' >> ~/.bash_profile
$ source ~/.bash_profile

$ rbenv install 3.0.1
$ rbenv global 3.0.1
$ rbenv rehash

安装 Rails 依赖 gem 和 bundler

$ gem sources --add https://gems.ruby-china.com/ --remove https://rubygems.org/
$ gem update --system
$ gem install bundler
$ bundle config mirror.https://rubygems.org https://gems.ruby-china.com

准备发布目录

# chown ruby:ruby /home/ruby

准备免密登录

$ ssh-keygen
$ vim ~/.ssh/authorized_keys (然后复制本机的 id_rsa.pub 内容写入。)

然后本地新开终端窗口,测试输入:

(本地执行)
$ ssh ruby@yourserver_ip

这里一定要成功免密登录,如果有问题请自行 google 解决。

准备 github clone 权限

$ cat ~/.ssh/id_rsa.pub

将输出的内容复制到 github 仓库中 deploy key 里,保证发布环境主机能 clone 你的仓库。

github 选择账户 -> settings -> SSH and GPG keys -> New SSH key

当然在测试之前你还需要设置 git 的 username 和 useremail:

$ git config --global user.name "example"
$ git config --global user.email example@163.com

然后测试确保能够克隆代码

准备 postgresql

# apt update
# apt install -y postgresql postgresql-contrib
# apt install -y postgresql libpq-dev

然后运行 sudo -u postgres psql -c "SELECT version();"

会输出相关版本信息,例如:

PostgreSQL 12.2 (Ubuntu 12.2-4) on x86_64-pc-linux-gnu, compiled by gcc (Ubuntu 9.3.0-8ubuntu1) 9.3.0, 64-bit

postgresql_user 设置(最简单的就是把 /etc/postgresql/xxx(版本号)/main/pg_hba.conf 里面的 MD5 与 peer 统一改为 trust)

然后修改 postgres 用户的密码,改成 database.yml 文件中一样的。

然后重启下:# service postgresql restart

安装 Nodejs (用来编译 assets 使用)

# curl -sL https://deb.nodesource.com/setup_14.x | sudo -E bash -

如果你需要另外的 Node.js 版本,例如12.x,将setup_14.x修改为setup_12.x

# apt install nodejs

现在切换到本地,

首先你的config/puma.rb最简单应该长这样:

port 3000

if ENV['RAILS_ENV'] == 'production'
  app_root = '/home/ruby/xxx/shared'
  pidfile "#{app_root}/tmp/pids/puma.pid"
  state_path "#{app_root}/tmp/pids/puma.state"
  bind "unix://#{app_root}/tmp/sockets/puma.sock"
  activate_control_app "unix://#{app_root}/tmp/sockets/pumactl.sock"
  daemonize true
  workers 2
  threads 8, 16
  prune_bundler

  stdout_redirect "#{app_root}/log/puma_access.log", "#{app_root}/log/puma_error.log", true
else
  plugin :tmp_restart
end

然后你的config/deploy/production.rb最简单应该长这样:

set :domain, '服务器ip或者域名'
set :deploy_to, '/home/ruby/xxx'
set :repository,  '你的仓库地址'
set :branch, 'master'
set :user, 'ruby'

然后在本地终端执行:$ mina deploy,静等执行完毕,根据提示,需要你修改服务器上的application.ymldatabase.yml

(服务器执行)
$ vim /home/ruby/xxx/shared/config/application.yml
$ vim /home/ruby/xxx/shared/config/database.yml

第一次搞部署肯定会有很多问题,可以先进行一次冒烟测试,

(本地执行)
$ mina first_deploy

如果一切正常,进入正式发布流程:

(本地执行)
$ mina deploy

每个人发布时都可能会遇到问题,需要自己 google 去解决。

发布成功之后,开始配置nginx

# echo "deb http://nginx.org/packages/mainline/ubuntu `lsb_release -cs` nginx" \
    | sudo tee /etc/apt/sources.list.d/nginx.list

# curl -o /tmp/nginx_signing.key https://nginx.org/keys/nginx_signing.key
# mv /tmp/nginx_signing.key /etc/apt/trusted.gpg.d/nginx_signing.asc
# apt update
# apt install nginx

nginx -v

保证 nginx 版本大于1.20.1

/etc/nginx/conf.d/ 创建 xxx.conf,

里面的内容最简单可以长这样:

upstream xxx {
  server unix:///home/ruby/xxx/shared/tmp/sockets/puma.sock fail_timeout=0;
}

server {
  listen 80;
  server_name domain.com;
  root /home/ruby/xxx/current/public;

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

  location /cable {
    proxy_http_version 1.1;
    proxy_set_header Upgrade $http_upgrade;
    proxy_set_header Connection "Upgrade";
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_pass http://xxx;
  }

  location ~ ^/(uploads)/  {
    expires max;
    break;
  }


  try_files $uri/index.html $uri @xxx;
  location @xxx{
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header Host $http_host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_redirect off;
    proxy_pass http://xxx;
  }

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

# nginx -s reload (重启 nginx)

本地浏览器打开http://yourserverdomain来检查是否发布成功。

服务器安全

采用 ufw 来作为防火墙,简单而不失安全。

ufw 配置,打开2280443端口。

# ufw allow 22/tcp
# ufw allow 80/tcp
# ufw allow 433/tcp
# ufw enable

这样可以防止大部分的入侵。

https ssl 支持

这里直接抄作业,看大佬文章 https://ruby-china.org/topics/31983

上一篇:Rails (PSU)


下一篇:苹果 M1 支持 Linux 最新进展;英特尔发布“GSC”Linux 驱动程序;Linux 基金会研究揭示开源趋势 | 开源日报