在 Ubuntu Server 16.04 上配置 Apache 和 Passenger 部署 Sinatra 应用

Phusion Passenger 是什么?

  • 开始被设计成 Apache 的 module,用来部署 Ruby on Rails,叫mod_rails
  • 后来不断发展成独立的 Ruby Web Server,改名Passenger

下面是关于 Passenger 的一些历史。

Sinatra 是一个基于 Ruby 的 DSL,方便开发者快速创建 Web 应用。官方文档里有更详细的说明。

Hello Sinatra

  1. 安装 rvm
$ gpg --keyserver hkp://keys.gnupg.net --recv-keys 409B6B1796C275462A1703113804BB82D39DC0E3

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

$ rvm -v
rvm 1.28.0 (latest) by Wayne E. Seguin <[email protected]>, Michal Papis <[email protected]> [https://rvm.io/]
  1. 安装 Ruby
$ rvm install 2.3.3

$ ruby -v
ruby 2.3.3p222 (2016-11-21 revision 56859) [x86_64-linux]
  1. 安装 Sinatra
$ gem install sinatra
  1. 码一段代码
$ vi hello_sinatra.rb
require 'sinatra'

get '/' do
'Hello, Sinatra'
end
  1. 测试
$ ruby hello_sinatra.rb
[2017-02-13 01:32:47] INFO WEBrick 1.3.1
[2017-02-13 01:32:47] INFO ruby 2.3.3 (2016-11-21) [x86_64-linux]
== Sinatra (v1.4.8) has taken the stage on 4567 for development with backup from WEBrick
[2017-02-13 01:32:47] INFO WEBrick::HTTPServer#start: pid=7962 port=4567

访问 http://localhost:4567,能看到输出Hello, Sinatra

配置 Apache 和 Passenger

安装 Apache

$ sudo apt-get install apache2

安装 Passenger

按照官网上提供的安装向导,生成具体的安装步骤

  • relevant integration mode
    • Apache
    • Passenger open source
  • operating system / installation method
    • Debian, Ubuntu (With APT)
    • Ubuntu 16.04 LTS (Xenial)
# Step 1: install Passenger packages

## Install our PGP key and add HTTPS support for APT
$ sudo apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 561F9B9CAC40B2F7
$ sudo apt-get install -y apt-transport-https ca-certificates

## Add our APT repository
$ sudo sh -c 'echo deb https://oss-binaries.phusionpassenger.com/apt/passenger xenial main > /etc/apt/sources.list.d/passenger.list'
$ sudo apt-get update

## Install Passenger + Apache module
$ sudo apt-get install -y libapache2-mod-passenger

# Step 2: enable the Passenger Apache module and restart Apache

$ sudo a2enmod passenger
$ sudo apache2ctl restart

# Step 3: check installation

$ sudo /usr/bin/passenger-config validate-install
* Checking whether this Phusion Passenger install is in PATH... ✓
* Checking whether there are no other Phusion Passenger installations... ✓

$ sudo /usr/sbin/passenger-memory-stats
Version: 5.0.8
Date : 2015-05-28 08:46:20 +0200

---------- Apache processes ----------
PID PPID VMSize Private Name
--------------------------------------
3918 1 190.1 MB 0.1 MB /usr/sbin/apache2
...

----- Passenger processes ------
PID VMSize Private Name
--------------------------------
12517 83.2 MB 0.6 MB Passenger watchdog
12520 266.0 MB 3.4 MB Passenger core
12531 149.5 MB 1.4 MB Passenger ust-router
...

# Step 4: update regularly

$ sudo apt-get update
$ sudo apt-get upgrade

Sinatra 部署文件夹

/var/www下,新建hello-sinatra文件夹,结构如下。

hello-sinatra/
├── config.ru
├── hello.rb
├── logs/
├── pids/
├── public/
└── tmp/
└── restart.txt

文件hello.rb的内容为

require 'sinatra/base'

class HelloSinatra < Sinatra::Base
get '/' do
'Hello, Sinatra'
end
end

文件config.ru的内容为

require File.expand_path('../hello.rb', __FILE__)
use Rack::ShowExceptions # 访问未定义的路由时,在网页上显示异常信息
run HelloSinatra.new

配置 Apache 的 vhost

/etc/apache2/sites-available里拷贝一份默认的 vhost 模板。

$ sudo cp 000-default.conf hello-sinatra.conf

/etc/apache2/sites-enabled下,新建一个符号链接到hello-sinatra.conf

$ sudo ln -s ../sites-available/hello-sinatra.conf .
$ sudo vi hello-sinatra.conf
<VirtualHost *:80>
DocumentRoot /var/www/hello-sinatra/public # !!

ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined

PassengerRuby /home/aaron67/.rvm/gems/ruby-2.3.3/wrappers/ruby # !!

<Directory /var/www/hello-sinatra/public> # !!
Allow from all
Options -MultiViews
</Directory>
</VirtualHost>

两点注意:

  • DocumentRootDirectory里的路径要写到public文件夹
  • PassengerRuby的值,通过下面的命令查看
$ passenger-config about ruby-command
passenger-config was invoked through the following Ruby interpreter:
Command: /home/aaron67/.rvm/gems/ruby-2.3.3/wrappers/ruby
Version: ruby 2.3.3p222 (2016-11-21 revision 56859) [x86_64-linux]
To use in Apache: PassengerRuby /home/aaron67/.rvm/gems/ruby-2.3.3/wrappers/ruby # <== 看这里
To use in Nginx : passenger_ruby /home/aaron67/.rvm/gems/ruby-2.3.3/wrappers/ruby
To use with Standalone: /home/aaron67/.rvm/gems/ruby-2.3.3/wrappers/ruby /usr/bin/passenger start

重启 Apache 服务。

$ sudo service apache2 restart

测试

浏览器访问服务器地址,显示的是 Apache 默认的欢迎页面(文件位置在/var/www/html/index.html)。

这是由于000-default.confhello-sinatra.conf配置了不同的DocumentRoot,但没配置不同的ServerName

vhost配置文件 ServerName DocumentRoot
000-default.conf /var/www/html
hello-sinatra.conf /var/www/hello-sinatra

更多关于 Apache Name-based Virtual Hosts 的内容,可以阅读官方文档

测试用的虚拟机没有域名绑定,所以简单的直接禁用掉默认 site 就好。

$ sudo a2dissite 000-default
Site 000-default disabled.
To activate the new configuration, you need to run:
service apache2 reload

重新加载或重启 Apache 服务使配置生效。

14869289421368

一个错误

查看 Apache 的日志文件/var/log/apache2/error.log,刚才的访问会输出如下错误。

App 9888 stdout:
App 9888 stderr: [passenger_native_support.so] trying to compile for the current user (nobody) and Ruby interpreter...
App 9888 stderr: (set PASSENGER_COMPILE_NATIVE_SUPPORT_BINARY=0 to disable)
App 9888 stderr: Warning: compilation did not succeed. To learn why, read this file:
App 9888 stderr: /tmp/passenger_native_support-1ozcjtk.log
App 9888 stderr: [passenger_native_support.so] finding downloads for the current Ruby interpreter...
App 9888 stderr: (set PASSENGER_DOWNLOAD_NATIVE_SUPPORT_BINARY=0 to disable)
App 9888 stderr: # tar xzf rubyext-ruby-2.3.3-x86_64-linux.tar.gz
App 9888 stderr: # rm -f rubyext-ruby-2.3.3-x86_64-linux.tar.gz
App 9888 stderr: Checking whether downloaded binary is usable...
App 9888 stderr: # /home/aaron67/.rvm/gems/ruby-2.3.3/wrappers/ruby -I. test.rb
App 9888 stderr: Binary is usable.
App 9888 stderr: # current user is: nobody
App 9888 stderr: # mkdir -p /nonexistent/.passenger/native_support/5.1.2/ruby-2.3.3-x86_64-linux
App 9888 stderr: Encountered permission error, but no more directories to try. Giving up.
App 9888 stderr: -------------------------------
App 9888 stderr: [passenger_native_support.so] will not be used (cannot compile or download)
App 9888 stderr: --> Passenger will still operate normally.
App 9924 stdout:

看起来像是目录权限问题,修改/var/www/hello-sinatra文件夹的 owner 成当前用户。

$ sudo chown -R aaron67:aaron67 /var/www/hello-sinatra/

重启服务,搞定。

参考