読者です 読者をやめる 読者になる 読者になる

ConoHaサーバ移行ログ

Nginx Redis MySQL Ruby

LL DiverでConoHaの¥3,000分のクーポンを貰ったのでDigitalOceanで動かしているサーバを一部移行した作業ログ。

OSインストール

  • VPS追加から追加
  • 追加したVPSの設定完了メール確認後、OS再インストール(Debian 7 64bit)
  • 作業ユーザはインストール時に作成
  • パーティションは/dataを切っておく
  • パッケージは以下の通り

f:id:i2bs:20140825012255p:plain

必要なパッケージのインストール

Nginx/Redis/MariaDB/Ruby/Rails等で使うパッケージ等をインストール。

apt-get update
apt-get -y install vim gcc g++ make git libreadline-dev libyaml-dev libssl-dev libpcre3 libpcre3-dev zlib1g zlib1g-dev libncurses5-dev libaio-dev sudo curl iptables iptables-persistent

エディタの変更

デフォルトがnanoなのでvimに変更。

update-alternatives --config editor

sudoの設定

groupadd -g 3000 developer
gpasswd -a work_user developer
visudo
23c23
< %sudo ALL=(ALL:ALL) ALL
---
> %developer  ALL=NOPASSWD:ALL

sshの設定

.sshディレクトリの作成

su - work_user
mkdir -p ~/.ssh

public keyのupload

scp ~/path/to/id_rsa.pub work_user@xxx.xxx.xxx.xxx:~/.ssh/authorized_keys

権限を変更しておく

su - work_user
chmod 700 ~/.ssh
chmod 400 ~/.ssh/authorized_keys

ssh serverの設定変更と再起動

vi /etc/ssh/sshd_config
/etc/init.d/ssh restart
5c5
< Port 22
---
> Port 10022
27c27
< PermitRootLogin yes
---
> PermitRootLogin no
51c51
< #PasswordAuthentication yes
---
> PasswordAuthentication no
71a72,73
>
> ClientAliveInterval 15

iptables

vi /etc/iptables/rules.v4
/etc/init.d/iptables-persistent restart
*filter

# Allows all loopback (lo0) traffic and drop all traffic to 127/8 that doesn't use lo0
-A INPUT -i lo -j ACCEPT
-A INPUT ! -i lo -d 127.0.0.0/8 -j REJECT

# Accepts all established inbound connections
-A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT

# Allows all outbound traffic
# You could modify this to only allow certain traffic
-A OUTPUT -j ACCEPT

# Allows HTTP and HTTPS connections from anywhere (the normal ports for websites)
-A INPUT -p tcp --dport 80 -j ACCEPT
-A INPUT -p tcp --dport 443 -j ACCEPT

# Allows SSH connections
# THE -dport NUMBER IS THE SAME ONE YOU SET UP IN THE SSHD_CONFIG FILE
-A INPUT -p tcp -m state --state NEW --dport 10022 -j ACCEPT

# Now you should read up on iptables rules and consider whether ssh access
# for everyone is really desired. Most likely you will only allow access from certain IPs.

# Allow ping
-A INPUT -p icmp -m icmp --icmp-type 8 -j ACCEPT

# log iptables denied calls (access via 'dmesg' command)
-A INPUT -m limit --limit 5/min -j LOG --log-prefix "iptables denied: " --log-level 7

# Reject all other inbound - default deny unless explicitly allowed policy:
-A INPUT -j REJECT
-A FORWARD -j REJECT

COMMIT

Ruby

git clone https://github.com/sstephenson/rbenv.git /usr/local/rbenv
git clone https://github.com/sstephenson/ruby-build.git /usr/local/ruby-build
cd /usr/local/ruby-build
./install.sh
vi /etc/bash.bashrc
56a57,61
> if [ -d /usr/local/rbenv ]; then
>   export PATH=/usr/local/rbenv/bin
>   eval "$(rbenv init -)"
> fi
>
bash -l
rbenv install -l
rbenv install 2.1.2
rbenv global 2.1.2
gem i bundler
rbenv rehash

Nginx

ユーザ追加

groupadd -g 2001 nginx
useradd -u 2001 -g nginx -s `which nologin` -d /usr/local/nginx nginx

Nginxインストール

cd /usr/local/src
wget -c http://nginx.org/download/nginx-1.6.1.tar.gz
tar zxvf nginx-1.6.1.tar.gz
cd nginx-1.6.1
./configure --prefix=/usr/local/nginx --with-http_ssl_module --with-http_gzip_static_module --with-http_stub_status_module
make && make install

Nginx設定

mkdir /usr/local/nginx/conf/conf.d
mkdir /usr/local/nginx/vhosts
mv -i /usr/local/nginx/conf/nginx.conf{,.`date +%Y%m%d`}
cp -pi ~/backup/nginx.conf /usr/local/nginx/conf/nginx.conf # 旧サーバから持ってくる
touch /etc/init.d/nginx
chmod 755 /etc/init.d/nginx
vi /etc/init.d/nginx
#!/bin/bash

# Nginx start stop script
#
# Debian
### BEGIN INIT INFO
# Provides:          nginx
# Required-Start:    $all
# Required-Stop:     $all
# Default-Start:     2 3 4 5
# Default-Stop:      0 1 6
# Short-Description: start and stop Nginx daemon
# Description:       start and stop Nginx daemon
### END INIT INFO
#
# CentOS
# chkconfig: 345 99 1
# description: Nginx start stop script
# processname: nginx

SERVER_ROOT=/usr/local/nginx
NGINX=$SERVER_ROOT/sbin/nginx
PIDFILE=$SERVER_ROOT/logs/nginx.pid

[ -x $NGINX ] || exit 1

if ! $NGINX -t > /dev/null 2>&1 ; then
    echo "Syntax error! Please confirm the config file."
    exit 1
fi

do_start() {
    if [ -f $PIDFILE ] ; then
        if ps -p `cat $PIDFILE` > /dev/null 2>&1 ; then
            echo "Nginx is already running..."
            exit 1
        fi
    fi
    $NGINX || echo "Failed to start Nginx."
}

do_stop() {
    if [ ! -f $PIDFILE ] ; then
        echo "Nginx is not running."
        exit 1
    fi
    if ps -p `cat $PIDFILE` > /dev/null 2>&1 ; then
        kill -QUIT `cat $PIDFILE` || echo "Failed to stop Nginx."
    else
        echo "Nginx is not running."
        exit 1
    fi
}

do_graceful() {
    if [ ! -f $PIDFILE ] ; then
        echo "Nginx is not running."
        exit 1
    fi
    if ps -p `cat $PIDFILE` > /dev/null 2>&1 ; then
        kill -HUP `cat $PIDFILE` || echo "Failed to graceful Nginx."
    else
        echo "Nginx is not running."
        exit 1
    fi
}

case $1 in
    start)
        do_start;;
    stop)
        do_stop;;
    restart)
        do_stop
        sleep 2
        do_start;;
    graceful)
        do_graceful;;
    *)
        echo "Usage: nginx [start|stop|restart|graceful]"
        exit 1;;
esac

exit 0

VirtualHost

mkdir -p /usr/local/nginx/vhosts/example.com/{html,logs,ssl.crt,ssl.key}
cp -pi ~/backup/example.com.conf /usr/local/nginx/conf/conf.d/example.com.conf # 旧サーバから持ってくる
cp -pi ~/backup/server.chained.crt /usr/local/nginx/vhosts/example.com/ssl.crt/. # 旧サーバから持ってくる
cp -pi ~/backup/server.key /usr/local/nginx/vhosts/example.com/ssl.key/. # 旧サーバから持ってくる

Redis

cd /usr/local/src/
wget -c http://download.redis.io/releases/redis-2.8.13.tar.gz
tar zxvf redis-2.8.13.tar.gz
cd redis-2.8.13
make && make install
mkdir -p /data/redis/dump
mkdir /var/log/redis
ln -s /data/redis /usr/local/redis
cp -pi redis.conf /usr/local/redis/.
cp -pi ~/backup/redis.conf /usr/local/redis/redis.conf # 旧サーバから持ってくる

MariaDB

ユーザ作成

groupadd -g 2008 mysql
useradd -u 2008 -g mysql -d /home/mysql -m -s /bin/bash mysql

インストール

cd /usr/local/src
wget -c https://downloads.mariadb.org/interstitial/mariadb-10.0.12/bintar-centos5-amd64/mariadb-10.0.12-linux-x86_64.tar.gz/from/http://ftp.yz.yamagata-u.ac.jp/pub/dbms/mariadb -O mariadb-10.0.12-linux-x86_64.tar.gz
tar zxvf mariadb-10.0.12-linux-x86_64.tar.gz
mv -i mariadb-10.0.12-linux-x86_64 /data/.
ln -s /data/mariadb-10.0.12-linux-x86_64 /usr/local/mysql

初期化

cd /usr/local/mysql
scripts/mysql_install_db --user=mysql
chown -R root .
chown -R mysql data

設定

cp -pi ~/backup/my.cnf /etc/my.cnf
echo 'export PATH=$PATH:/usr/local/mysql/bin' >> /etc/bash.bashrc
bash -l
/etc/init.d/mysql start
mysql_secure_installation
echo /usr/local/mysql/lib > /etc/ld.so.conf.d/mariadb.conf
ldconfig

App

mkdir -p /data/rails
ln -s /data/rails /usr/local/rails
cd /usr/local/rails
git clone git@bitbucket.org:user/repo.git

Ruby 2.1.1インストール

Ruby

rbenv + ruby-buildでRuby 2.1.1をインストールしようとしたらビルドが失敗したのでメモ。
結論から言うとreadlineのバージョンを下げてインストールできた。

$ cd ~/.rbenv;git pull
$ cd plugins/ruby-build;git pull
$ rbenv install 2.1.1
Downloading ruby-2.1.1.tar.gz...
-> http://dqw8nmjcqpjn7.cloudfront.net/e57fdbb8ed56e70c43f39c79da1654b2
Installing ruby-2.1.1...

BUILD FAILED

Inspect or clean up the working tree at /var/folders/mb/3kb7lflx1j999k3cjdkp2gfw0000gn/T/ruby-build.20140506005126.60566
Results logged to /var/folders/mb/3kb7lflx1j999k3cjdkp2gfw0000gn/T/ruby-build.20140506005126.60566.log

Last 10 log lines:
compiling ossl_x509crl.c
compiling ossl_x509ext.c
1 warning generated.
compiling ossl_x509name.c
compiling ossl_x509req.c
compiling ossl_x509revoked.c
compiling ossl_x509store.c
installing default openssl libraries
linking shared-object openssl.bundle
make: *** [build-ext] Error 2
$ brew uninstall readline
$ cd /usr/local
$ git checkout 0181c8a Library/Formula/readline.rb
$ brew install readline
==> Downloading https://downloads.sf.net/project/machomebrew/Bottles/readline-6.2.4.mavericks.bottle.2.tar.gz
######################################################################## 100.0%
==> Pouring readline-6.2.4.mavericks.bottle.2.tar.gz
==> Caveats
$ RUBY_CONFIGURE_OPTS="--with-readline-dir=$(brew --prefix readline) --with-openssl-dir=$(brew --prefix openssl)" rbenv install 2.1.1
$ rbenv global 2.1.1
$ ruby -v
ruby 2.1.1p76 (2014-02-24 revision 45161) [x86_64-darwin13.0]

Building Ruby 2.x on OS X Mavericks Suddenly Fails · Issue #550 · sstephenson/ruby-build · GitHub

Apache Solrインストール

Solr

環境

JDKインストール

tar zxvf jdk-7u45-linux-x64.gz
mv -i jdk1.7.0_45 /usr/local/.
ln -s /usr/local/jdk1.7.0_45 /usr/local/java
export JAVA_HOME=/usr/local/java
export PATH=$PATH:$JAVA_HOME/bin

Tomcat配置

cd /usr/local/src/
wget -c http://ftp.yz.yamagata-u.ac.jp/pub/network/apache/tomcat/tomcat-7/v7.0.47/bin/apache-tomcat-7.0.47.tar.gz
tar zxvf apache-tomcat-7.0.47.tar.gz
mv -i apache-tomcat-7.0.47 /usr/local/.
ln -s /usr/local/apache-tomcat-7.0.47 /usr/local/apache-tomcat

Solr配置

wget -c http://mirrors.go-parts.com/apache/lucene/solr/4.6.0/solr-4.6.0.tgz
tar zxvf solr-4.6.0.tgz

cd /usr/local/apache-tomcat
cp -rpi /usr/local/src/solr-4.6.0/example/solr .
cp -rpi /usr/local/src/solr-4.6.0/contrib solr/.
cp -rpi /usr/local/src/solr-4.6.0/dist solr/.
cp -pi /usr/local/src/solr-4.6.0/example/lib/ext/* lib/.
cp -pi solr/dist/solr-4.6.0.war webapps/solr.war

Tomcat設定

mkdir -p conf/Catalina/localhost
vi conf/Catalina/localhost/solr.xml
<?xml version="1.0" encoding="utf-8"?>
<Context docBase="solr" debug="0"
crossContext="true">
<Environment name="solr/home" type="java.lang.String" 
value="/usr/local/apache-tomcat/solr" override="true"/>
</Context>
vi conf/server.xml
    <Connector port="8080" protocol="HTTP/1.1"
               connectionTimeout="20000"
               redirectPort="8443" useBodyEncodingForURI="true" />

Tomcat起動

./bin/startup.sh

PostgreSQLインストール(Clientのみ)

PostgreSQL

PostgreSQL Clientのインストールメモ。

cd /usr/local/src
wget -c http://ftp.postgresql.org/pub/source/v9.2.4/postgresql-9.2.4.tar.gz
tar zxvf postgresql-9.2.4.tar.gz
cd postgresql-9.2.4
./configure --prefix=/usr/local/pgsql --with-openssl
make
make -C src/bin install
make -C src/include install
make -C src/interfaces install
export PATH=$PATH:/usr/local/pgsql/bin

Heroku Postgresに接続してみる。

psql "dbname=[DBNAME] host=[HOSTNAME] user=[USERNAME] password=[PASSWORD] port=5432 sslmode=require"

JenkinsでRailsのテストが失敗してた

Ruby

Railsアプリのbundle updateをしてローカルでテストを実行してリポジトリにpushした後、Jenkinsで結果を確認してたら以下のメッセージが出て失敗してた。。。

libmysqlclient.so.18: cannot open shared object file: No such file or directory

確かにない。

# ls -l `cat /etc/ld.so.conf.d/mysql.conf`
lrwxrwxrwx 1 root root      24 May  8 20:37 libmysqlclient.so.16 -> libmysqlclient.so.16.0.0
-rwxr-xr-x 1 root root 1584456 Apr 26 03:44 libmysqlclient.so.16.0.0
lrwxrwxrwx 1 root root      26 May  8 20:37 libmysqlclient_r.so.16 -> libmysqlclient_r.so.16.0.0
-rwxr-xr-x 1 root root 1595208 Apr 26 03:44 libmysqlclient_r.so.16.0.0

今までは問題なく動いてたのになんでだろう。

# echo "/usr/local/mysql/lib" > /etc/ld.so.conf.d/mysql.conf
# ldconfig
# bundle exec rake db:migrate

Gradleインストール

Java

homebrewでもインストールできる。

cd /tmp
wget -c http://services.gradle.org/distributions/gradle-1.6-bin.zip
unzip gradle-1.6-bin.zip

mkdir -p ~/src
mv -i gradle-1.6 ~/src/.

export GRADLE_HOME=$HOME/src/gradle-1.6
export PATH=$PATH:$GRADLE_HOME/bin
export GRADLE_OPTS="-Dorg.gradle.daemon=true"
gradle -v

Gradle Download
Gradle User Guide

Rails4へのアップデート

Ruby

現在仕事で作っているRailsアプリの一つをRails3.2.13から4.0.0にアップデートしたのでメモ。

パッケージのアップデート
Gemfile

coffee-railsは使っていないので書いてませんが、使ってる場合は4.0.0にする必要があるみたいです。
protected_attributesはStrong Parametersを使う前に他の部分のテストを実行する為に入れてます。
他のgemは変更してません。

gem "rails", "4.0.0"
gem "sass-rails",   "~> 4.0.0"
gem "uglifier", ">= 1.3.0"
gem "protected_attributes" # => 一時的に追加
config/application.rb

rails4からactive_resourceは標準では無くなったのでコメントアウトしておきます。

# Pick the frameworks you want:
require "active_record/railtie"
require "action_controller/railtie"
require "action_mailer/railtie"
# require "active_resource/railtie" # => コメントアウト
require "sprockets/railtie"
# require "rails/test_unit/railtie"
アップデート
bundle update
bundle exec rake rails:update

以下のファイルが更新/新規追加されます。
基本的には上書きして設定をマージしました。

  • config/boot.rb
  • config/routes.rb
  • config/application.rb
  • config/environment.rb
  • config/environments/development.rb
  • config/environments/production.rb
  • config/environments/test.rb
  • config/initializers/filter_parameter_logging.rb (新規)
  • config/initializers/inflections.rb
  • config/initializers/secret_token.rb
  • config/initializers/session_store.rb
  • config/initializers/wrap_parameters.rb
  • config/locales/en.yml
  • bin/bundle (新規)
  • bin/rails (新規)
  • bin/rake (新規)
主に設定したところ

config/application.rb:

基本的にはautoload/time_zone/i18nあたりの設定をしました。
filter_parametersはconfig/initializers/filter_parameter_logging.rbに書くようになったみたいです。

config/initializers/filter_parameter_logging.rb:

Rails.application.config.filter_parameters += [:password, :password_confirmation]

config/environments/*.rb:

action_mailerの設定とかその他環境ごとの設定。

config/initializers/session_store.rb:

sessionはmemcacheに設定しているので再設定。

テスト

config/routes.rbでmatchを使っている場合は直しておく。
また、メソッド違い(GETとかPOSTとか)で同じURLに:asで同じ名前をつけている場合はそれも直しておく。
テストを実行して通らないところは直しておく。

bundle exec rake spec
bundle exec rake cucumber

テストが通ったらGemfileからgem "protected_attributes"を削除してbundleしておく。

Views

link_toconfirmがまだ残っていたみたいなのでdata: {confirm: "text"}に変更。

DEPRECATION WARNING: :confirm option is deprecated and will be removed from Rails 4.1. Use 'data: { confirm: 'Text' }' instead.
Model
  • scopeをlambda記法に修正
  • attr_accessibleを削除
Controller
  • Strong Parametersとspecの修正/追加
class UsersController < ApplicationController
  def create
    @user = User.new(user_params)
    @user.save
  end

  def update
    @user = User.find(params[:id])
    @user.update_attributes(user_params)
  end

  private
  def user_params
    params.require(:user).permit(:name, :email)
  end
end
  • *_filter*_actionに変更

これは*_filterのままでも動作しますが、一応。

class ApplicationController < ActionController::Base
  protect_from_forgery
  before_action :current_user
end
  • update_attributesupdateに変更

これも非推奨でもなく動作もしますが、一応。

class UsersController < ApplicationController
  def update
    @user = User.find(params[:id])
    @user.update(user_params)
  end

  private
  def user_params
    params.require(:user).permit(:name, :email)
  end
end
テスト
bundle exec rake spec
bundle exec rake cucumber
参考

http://www.engineyard.co.jp/blog/2013/rails-4-changes/ http://www.engineyard.co.jp/blog/2013/new-in-rails-4/ http://akasata.com/articles/303