ラベル test-kitchen の投稿を表示しています。 すべての投稿を表示
ラベル test-kitchen の投稿を表示しています。 すべての投稿を表示

2014年6月10日火曜日

[Chef]expectコマンドを使ってAndroidSDKをインストールするレシピを作成してみた

このエントリーをはてなブックマークに追加 はてなブックマーク - [Chef]expectコマンドを使ってAndroidSDKをインストールするレシピを作成してみた

Chefを利用してAndroidSDK本体のインストール及び特定AndroidSDKインストールを自動化させたいと思っていました。

が、指定したAndroidSDKのインストールの途中で利用許諾の承認が必要であり、単純にexecuteコマンドを利用してインストールが出来ませんでした。

調査するとexpectコマンドを使うと対話形式の入力が必要な処理を自動化出来るとのことで実際に実施する事が出来たいのでそのメモを記載します。

そもそもexpectコマンドとは?

  • telnetやsshなどパスワード入力を求められるような処理を自動化出来る
  • 同様にインストール時に許諾への同意などが必要なものも自動化させる事が出来る

前提

  • Chef、Berkshelfなどはインストール済み
  • ホストはMac OSX 10.9.3
  • test-kitchenを利用。ドライバはvagrantを利用。

Chefやtest-kitchenの詳細は過去のブログを参考の事。

Berkshelf version3+Knife soloでnginx環境をVagrantに作ってみた話

[Chef]Berkshelfを利用したJenkinsクックブックを作成してserverspec+Kitchenでテストした話

参考

こちらのクックブックを参考にさせて頂きました。

gildegoma/chef-android-sdk

Github

置きました。

toshihirock/AndroidSDK

  • Ubuntuのテストはしてません
  • URLやAndroidSDKのバージョンは適宜変更してください。(そのうちattribute化したい。。。)

準備

クックブック作成します。

$knife cookbook create android -o .

AndroidSDKを利用する為にJavaのインストールが必要ですが、サードパーティのクックブックを利用 します。 また、AndroidSDKのダウンロード、展開の為にopscodeのarkというクックブックを利用します。

サードパーティのクックブックを使う為にBerksheflを利用する準備をします。

$berks init .

利用するためにmetadata.rbに追記を行います。

$cd android
$vi metadata.rb

name             'android'
maintainer       'YOUR_COMPANY_NAME'
maintainer_email 'YOUR_EMAIL'
license          'All rights reserved'
description      'Installs/Configures android'
long_description IO.read(File.join(File.dirname(__FILE__), 'README.md'))
version          '0.1.0'

depends "ark"
depends "java"

また、test-kitchenを使ってプロビジョニングを行うのでその為のファイルを作成します。

$kitchen init

既にBerkshlefで.kitchen.ymlが作成済みの場合にはコンフリクトしますが、yを入力して鵣川書きします。

今回、試験ははCentOSのみに今回はするため、.kitchen.ymlの一部をコメントアウトします。

$vi .kitchen.yml

編集。

platforms:
  #- name: ubuntu-12.04
  - name: centos-6.4

AndroidSDK本体のダウンロード、展開

まずはAndroidSDK本体のダウンロード、展開までのレシピを書きます。 本来はURLやパスはattributesの値とすべきですが、とりあえずベタ書きします。

$vi recipes/default.rb

編集。

include_recipe 'java'

%w{unzip expect}.each do |pkg|
  package pkg do
    action :install
  end
end

ark 'android' do
  url 'http://dl.google.com/android/adt/22.6.2/adt-bundle-linux-x86_64-20140321.zip'
  path '/usr/local/android'
end

URLはAndroidのサイトをみて確認してください。(ビット数に応じてダウンロードするzipが違いますが、今回は判定処理は割愛して64bitで確認)

試験環境の準備

VMの起動。

$kitchen create

VMにChefやBerkshelfのインストール、及びレシピの適用を行います。

$kitchen setup

状態を確認します。

$kitchne list

SSH接続して確認してみます。

$kitchen login
$ll /usr/local
lrwxrwxrwx. 1 root root   20 Jun  9 14:30 android -> /usr/local/android-1

expectコマンドを使ってみる

Chefのコードを書く前に正しく動作出来るかVMでコマンドを実行して確認してみます。

$kitchen login
$sudo su
$cd /usr/local/android/sdk/tools
$vi expectTest.sh

確認用のシェルスクリプトを編集します。

#!/bin/bash

expect -c '

spawn /usr/local/android/sdk/tools/android update sdk --no-ui --filter android-17
set timeout 1800
expect {
  -regexp "Do you accept the license.*" {
    exp_send "y\r"
    exp_continue
  }
}
'

ざっくり説明します。

  • spawn:実際に実行させたいコマンド
  • set timeout:expectの実行を許容する時間。短すぎるとコマンドの途中で強制終了してしまう。
  • regrexp:どの文字列が表示されたら入力を自動的に行うかの正規表現。今回の場合、利用規約のDo you accept …という文字列が表示された時に入力を行う事を示す。
  • exp_send:regrexpで合致する文字列が表示された時に自動入力する文字列。
  • exp_continue:これを指定しないと自動入力したあと復帰出来ないっぽいです。

実行権限を付与して、実行してみます。

$chmod a+x expectTest.sh
$./expectTest.sh

Chefのレシピでexpectコマンドを実行する

成功すればこれをChefのレシピに落とし込みます。

$exit
$vi recipes/default.rb

レシピに追記します。

script 'Install Android SDK' do
  android_version="android-17"
  interpreter 'expect'
  not_if { ::File.exists?("/usr/local/android/sdk/#{android_version}") }
  code <<-EOF
    spawn /usr/local/android/sdk/tools/android update sdk --no-ui --filter #{android_version}
    set timeout 1800
    expect {
      -regexp "Do you accept the license.*" {
        exp_send "y\r"
        exp_continue
      }
    }
  EOF
end

テストも書きます。今回はserverspecを利用します。 Gemfileに追加します。

$echo "gem \'serverspec\'" >> Gemfile

$mkdir -p test/integration/default/serverspec/localhost/
$vi test/integration/default/serverspec/localhost/default_spec.rb

テストを書きます。

require 'serverspec'
include Serverspec::Helper::Exec
include Serverspec::Helper::DetectOS

describe command('which java') do
  it { should return_exit_status 0 }
end

describe command('ls /usr/local/android/sdk/platforms/android-17') do
  it { should return_exit_status 0 }
end

色々実験したので一度、VM環境を削除します。

$kitchen destroy

その後、VMの作成、Chefの適用、serverspecのテストを実施します。

$kitchen test

問題なく完了すればOKです。

2014年6月5日木曜日

[chef]test-kitchenのテストをAWSのEC2で実施する

このエントリーをはてなブックマークに追加 はてなブックマーク - [chef]test-kitchenのテストをAWSのEC2で実施する

前回のブログでJenkinsのレシピを作成し、Vagrantを利用してローカル環境のVMでtest-kitchenを利用してserverspecのテストを実行するようにしました。

今回、kitchen-ec2を使ってその環境をローカルでなく、AWSのEC2を利用してテストするようにします。

参考

Chefのテストツール kitchen-ec2を使う – 導入、チュートリアル

test-kitchen/kitchen-ec2

前提

  • AWSのアカウントがあること
  • AWS のアクセスキー/シークレットアクセスキーが存在すること。
  • EC2のキーペアを作成済みである事
  • VagrantやChefなどがインストール済みである事

環境の準備

必要なものをインストールします。

$gem install test-kitchen
$gem install kitchen-ec2

対象レシピのディレクトリに移動し、.kitchen.ymlを変更します。 既に.kitchen.ymlが存在する場合には上書きするかの確認が表示されますが、必要に応じてバックアップを取得しておいてください。

$cd {repo_dir}
$kitchen init --driver=kitchen-ec2

.kitchen.ymlの編集

.kitchen.ymlを編集します。

---
driver:
  name: ec2
  aws_access_key_id: <%= ENV['AWS_ACCESS_KEY'] %>
  aws_secret_access_key: <%= ENV['AWS_SECRET_KEY'] %>
  aws_ssh_key_id: <%= ENV['AWS_SSH_KEY_ID'] %>
  ssh_key: <%= ENV['SSH_KEY'] %>
  security_group_ids: ["Vagrant"]
  region: ap-northeast-1
  availability_zone: ap-northeast-1a
  require_chef_omnibus: true

provisioner:
  name: chef_solo

platforms:
  - name: ubuntu-12.04
    driver:
      image_id: ami-0596ef04
      username: ubuntu
      flavor_id: t1.micro
  - name: centos-6.4
    driver:
      image_id: ami-99fa7098
      username: root
      flavor_id: t1.micro

suites:
  - name: default
    run_list:
      - recipe[jenkins::default]
    attributes:

ポイントだけ記載します。

  • aws_access_key_id:AWSのアクセスキー
  • aws_secret_access_key:AWSのシークレットアクセスキー
  • aws_ssh_key_id:キーペアの名称
  • ssh_key:キーペア(pem)のファイルパス
  • security_group_ids:設定するセキュリティグループ

詳細は test-kitchen/kitchen-ec2を確認ください。

上記のように環境変数から読み込む設定の場合、~/.bashrcなどに以下のように記載します。

export AWS_ACCESS_KEY="xxx"
export AWS_SECRET_KEY="xxxxxxxx" 
export AWS_SSH_KEY_ID="hogeKeyPair" 
export SSH_KEY="~/.ssh/hogeKeyPair.pem" 

image_idについては自分で作成したAMIでも大丈夫ですし、aws marketplaceのものも利用出来るようです。

aws marketplaceのものを利用する場合、利用承諾をしていないとインスタンス起動時にエラーとなります。その場合には、利用承諾用URLが表示されるのでリンクがエラー文に表示されるのでそこから利用承諾を行うと以降の起動が成功します。

テストの実行

テストの実行は以下のコマンドで可能です。

$kitchen test

上記で

  • インスタンスの作成
  • AWSへのChefのインストール、レシピの適用
  • テストの実行
  • インスタンスの削除

をplatformsに書かれたOSの数分実行されます。

それぞれを個別にやるには

  • kitchen create
  • kitchen coverage
  • kitche verify
  • kitchen destroy

というコマンドが対応しています。

インスタンスの各状態はkitchen listコマンドで確認が出来ます。