連載
OSSのサーバテスト自動化ツール徹底検証 2016年版 〜Infrataster編――手間取るテストエビデンス作成をどう自動化するか〜:実際に検証済み!OSS徹底比較(6)サーバテスト自動化【後編】(3/6 ページ)
各種オープンソースソフトウェアのうち、特に人気の高いOSSをピックアップ。実際の検証結果をまとめた本連載。前編で解説したサーバテスト自動化ツール「Serverspec」に続き、今回は「Infrataster」を紹介する。
テストスクリプトの作成
1.テスト対象ホストの情報を登録
spec_helper.rbにテスト対象のホストの情報を登録する。登録する情報は以下の通り。
- ホスト名/IPアドレス
- Vagrant上のサーバか?
- ssh接続のホスト名、ユーザーID、パスワードor認証用の秘密鍵ファイル
- mariadb(mysql)への接続情報
さらに、テストスクリプトに記載された順番通りにテストが実施されるように記載する。
$ vi ~/infrataster/spec/spec_helper.rb
Generated by `infrataster init`
require 'infrataster/rspec'
ENV['VAGRANT_CWD'] = File.dirname(__FILE__)
Infrataster::Server.define(
:tissvv096,
'10.255.202.96',
vagrant: false,
ssh: {host_name: 'tissvv096', user: 'maintain', keys: ['/home/maintain/.ssh/id_rsa.pem']},
mysql: {user: 'maintain', password: 'HB-F1XDJ'},
)
Infrataster::Server.define(
:tissvv097,
'10.255.202.97',
vagrant: false,
ssh: {host_name: 'tissvv097', user: 'maintain', keys: ['/home/maintain/.ssh/id_rsa.pem']},
)
RSpec.configure do |config|
treat_symbols_as_metadata_keys_with_true_values = false
config.run_all_when_everything_filtered = true
config.filter_run :focus
# config.order = 'random'
config.order = 'define'
end
2.対話的コンソールを有効にする
作成したテストスクリプトは以下となる。各処理のTIPSは後ほど、機能ごとに説明する。
$ vi infrataster/spec/tissvv096_spec.rb
# Generated by `infrataster init`
require 'spec_helper'
require 'infrataster-plugin-mysql'
require 'infrataster-plugin-firewall'
describe server(:tissvv096) do
mysql_root_pass='FM11AD2+'
wp_dir='/var/www/wordpress'
wp_os_user='root'
wp_os_group='root'
wp_db_name='WordPress'
wp_db_user='wp_admin'
wp_db_pass='HB-F1XDJ'
wp_uniqe_phrse='FX702PFX801PPB100FX860PPB700PB500PB750PAI1000'
wp_version='4.5.2'
hostname='tissvv096'
# yum update check
it 'yum update check' do
result = current_server.ssh_exec('yum check-update 2>&1 > /dev/null; echo $?')
expect(result.chomp).to eq('0')
end
# mariadb-server/httpd/php/php-mysql insall check
%w{ mariadb-server httpd php php-mysql }.each do |pkg|
it "#{pkg} install check" do
result = current_server.ssh_exec("rpm -qa | grep -e '#{pkg}-[0-9]'")
expect(result.chomp).to match /#{pkg}/
end
end
# mariadb service running/enable check
it 'mariadb service running/enable check' do
result = current_server.ssh_exec('systemctl status mariadb')
expect(result).to match /service; enabled/
expect(result).to match /active \(running\)/
end
# mariadb remote login check
describe mysql_query('show databases') do
it 'mariadb remote login check' do
row = results.find {|r| r['Database'] == 'mysql' }
expect(row['Database']).to eq('mysql')
end
end
# mariadb root login check
it 'mariadb root login check' do
result = current_server.ssh_exec("mysqlshow -u root -p#{mysql_root_pass}")
expect(result.chomp).to match /Database/
end
# mariadb root no password login check
it 'mariadb root no password login check' do
result = current_server.ssh_exec('su root -c mysqlshow')
expect(result.chomp).to match /Database/
end
# mysqladmin ping execute check
it 'mysqladmin ping execute check' do
result = current_server.ssh_exec('su root -c "mysqladmin ping"')
expect(result.chomp).to match /mysqld is alive/
end
# mariadb logrotation check
before :all do
@already_rotate = current_server.ssh_exec('su root -c "ls -1 /var/log/mariadb/*.gz | wc -l"').to_i
end
it 'mariadb logrotation check' do
if @already_rotate == 0 then
check_cmd = '/sbin/logrotate -vf /etc/logrotate.d/mariadb'
match_prm = 'running postrotate script'
else
check_cmd = '/sbin/logrotate -vd /etc/logrotate.d/mariadb'
match_prm = 'log does not need rotating'
end
result = current_server.ssh_exec("su root -c \"#{check_cmd}\"")
expect(result).to match /#{match_prm}/
end
after :all do
@already_rotate = nil
end
# WordPress version check
describe http("http://#{hostname}/readme.html") do
it 'WordPress Version check' do
expect(response.body).to match /Version #{wp_version}/
end
end
# mariadb WordPress user login check
it 'mariadb WordPress user login check' do
result = current_server.ssh_exec("mysqlshow -u #{wp_db_user} -p#{wp_db_pass} #{wp_db_name}")
expect(result.chomp).to match /#{wp_db_name}/
end
# WordPress file user/group check
it 'WordPress file user/group check' do
result = current_server.ssh_exec("find #{wp_dir} -not -user #{wp_os_user} -or -not -group #{wp_os_group} | wc -l")
expect(result.chomp).to eq('0')
end
# wp-config.php paramaters check
it 'wp-config.php paramaters check' do
result = current_server.ssh_exec("cat #{wp_dir}/wp-config.php")
expect(result).to match /define\('DB_NAME',.*'#{wp_db_name}'\);/
expect(result).to match /define\('DB_USER',.*'#{wp_db_user}'\);/
expect(result).to match /define\('DB_PASSWORD',.*'#{wp_db_pass}'\);/
expect(result).to match /define\('AUTH_KEY',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('SECURE_AUTH_KEY',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('LOGGED_IN_KEY',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('NONCE_KEY',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('AUTH_SALT',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('SECURE_AUTH_SALT',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('LOGGED_IN_SALT',.*'#{wp_uniqe_phrse}'\);/
expect(result).to match /define\('NONCE_SALT',.*'#{wp_uniqe_phrse}'\);/
end
# wordpress.conf check
it 'wordpress.conf check' do
wordpress_conf = <<"EOT"
<VirtualHost *:80>
ServerName #{hostname}
DocumentRoot #{wp_dir}
<Directory "#{wp_dir}">
AllowOverride All
Options -Indexes
</Directory>
<Files wp-config.php>
order allow,deny
deny from all
</Files>
</VirtualHost>
EOT
result = current_server.ssh_exec("cat /etc/httpd/conf.d/wordpress.conf")
expect(result).to match "#{wordpress_conf}"
end
# httpd.conf ServerName check
it 'httpd.conf ServerName check' do
result = current_server.ssh_exec('cat /etc/httpd/conf/httpd.conf')
expect(result).to match /ServerName #{hostname}/
end
# httpd service running/enable check
it 'httpd service running/enable check' do
result = current_server.ssh_exec('systemctl status httpd')
expect(result).to match /active \(running\)/
expect(result).to match /service; enabled/
end
# WordPress site access check
describe http("http://#{hostname}/wp-admin/install.php") do
it 'WordPress site access check' do
expect(response.body).to match /WordPress/
end
end
# firewall http/ssh/mysql port open check
it 'firewall http/ssh/mysql port open check' do
result = current_server.ssh_exec('firewall-cmd --list-all --zone=public')
expect(result).to match /services:.*http/
expect(result).to match /services:.*ssh/
expect(result).to match /services:.*mysql/
expect(result).to match /ports: $/
end
end
describe server(:tissvv097) do
# firewall open port check
describe firewall(server(:tissvv096)) do
it { is_expected.to be_reachable }
it { is_expected.to be_reachable.dest_port(80).ack(:only) }
end
end
テストスクリプトの実行
1.テストスクリプトの実行
以下のコマンドでInfratasterのテストスクリプトが実行される。結果は標準出力に出力されるため、teeコマンドを利用し、ファイルにも保存している。パラメータに実行するテストスクリプトファイルを指定した場合、そのファイルのみのテストが実行される。指定がない場合、specフォルダ以下の全テストスクリプトファイル(*_spec.rb)が順次実行される。
$ /usr/local/bin/rspec -f d spec/tissvv096_spec.rb | tee tissvv096_test.log
'-f'オプションはログ出力の形式を定義している。使用できるオプションはrspec --helpで表示される。
-f, --format FORMATTER Choose a formatter.
[p]rogress (default - dots)
[d]ocumentation (group and example names)
[h]tml
[j]son
custom formatter class name
今回はエビデンスとして利用するため、'-f d'を使用している。
2.ログ出力
テストスクリプトの実行により、以下の結果が出力される。
Run options: include {:focus=>true}
All examples were filtered out; ignoring {:focus=>true}
server 'tissvv096'
yum update check
mariadb-server install check
httpd install check
php install check
php-mysql install check
mariadb service running/enable check
mariadb root no password login check
mysqladmin ping execute check
mariadb logrotation check
mariadb WordPress user login check
WordPress file user/group check
wp-config.php paramaters check
wordpress.conf check
httpd.conf ServerName check
httpd service running/enable check
firewall http/ssh/mysql port open check
mysql 'show databases' with []
mariadb root login check
http 'http://tissvv096/readme.html' with {:params=>{}, :method=>:get, :headers=>{}}
WordPress Version check
http 'http://tissvv096/wp-admin/install.php' with {:params=>{}, :method=>:get, :headers=>{}}
WordPress site access check
server 'tissvv097'
via firewall
should reach to server 'tissvv096'
should reach to server 'tissvv096' dest_port: 80 (FAILED - 1)
Failures:
1) server 'tissvv097' via firewall should reach to server 'tissvv096' dest_port: 80
Failure/Error: it { is_expected.to be_reachable.dest_port(80).ack(:only) }
expected to reach to server 'tissvv096' dest_port: 80, but did not.
# ./spec/tissvv096_w_fw_spec.rb:168:in `block (3 levels) in <top (required)>'
Finished in 3.48 seconds (files took 0.43954 seconds to load)
21 examples, 1 failure
Failed examples:
rspec ./spec/tissvv096_w_fw_spec.rb:168 # server 'tissvv097' via firewall should reach to server 'tissvv096' dest_port: 80
テスト自体は4秒弱で完了している。1件のテスト項目がエラーとなっているが、原因は次ページのTIPSで別途解説する。
Copyright © ITmedia, Inc. All Rights Reserved.