以下の記事に影響を受け、Windows 環境上に Vagrant と Chef、Serverspec を使った Windows Server マシンのテスト駆動開発環境を作った際の手順を自分用のメモとしてまとめました。
- Vagrant+Puppet+Serverspec を使って Windows Server をテスト駆動開発する - 終劇 CPU 100%
- Chef Solo / Vagrant / serverspecでインフラのTDDを行う - Qiita
Vagrant と Chef、Serverspec のインストールと操作は、PowerChef という PowerShell モジュールを作成しましたので、これを使います。
1: PowerChef モジュールのインストール
まず、PowerChef モジュールをローカルマシンにインストールします。
手順 1-1: 'Windows PowerShell' を起動します
スタートメニューから `Windows PowerShell` を起動します
手順 1-2: PowerShellスクリプトの実行セキュリティ・ポリシーを RemoteSigned に変更します
PS> Set-ExecutionPolicy RemoteSigned
PS> Get-ExecutionPolicy
RemoteSigned
→ RemoteSigned と表示されることを確かめます。
手順 1-3: インストールスクリプト(install.ps1
)を使って、GitHub上からモジュールをダウンロードします
PS> Invoke-Expression (New-Object System.Net.WebClient).DownloadString("https://raw.github.com/kukita/PowerChef/master/install.ps1")
→ Installation of 'PowerChef' has finished successfully.
と表示されればインストールの成功です。
2: ホストマシン環境のセットアップ
次に、ローカルマシンをホストマシン環境としてセットアップします。
手順 2-1: PowerChef モジュールをインポートします
PS> Import-Module "PowerChef"
PS> Get-Module
ModuleType Version Name
---------- ------- ----
Manifest 3.1.0.0 Microsoft.PowerShell.Management
Manifest 3.1.0.0 Microsoft.PowerShell.Utility
Manifest 0.5.2 PowerChef
→ PowerChef
が表示されていることを確かめます。
手順 2-2: SetUp-ChefWorkstation
ファンクションを使って、ローカルマシンを WorkStation 環境としてセットアップします
PS> SetUp-ChefWorkstation -PowerChefHomePath "D:\PowerChef"
※30分くらいかかります。最後に WinRM のセキュリティ設定に関して聞かれるので [Y]Yes を選択します。
次のソフトウェアがインストールされます。
- Chocolatey [https://chocolatey.org/]
- Oracle VM VitrualBox [https://www.virtualbox.org/]
- Git for Windows [http://msysgit.github.io/]
- posh-git [https://github.com/dahlbyk/posh-git]
- Chef [http://www.getchef.com/chef/]
- Serverspec [http://serverspec.org/]
- Bento [https://github.com/opscode/bento]
- em-winrm [https://github.com/opscode/em-winrm]
- Oracle Java Runtime [http://java.com/en/download/]
- Vagrant [http://www.vagrantup.com/]
- 7-Zip [http://www.7-zip.org/]
- CwRsync [https://www.itefix.no/i2/cwrsync]
- Berkshelf [http://berkshelf.com/]
手順 2-3: Open-HomeVagrantfile
ファンクションを使って、Vagrant ホームディレクトリの Vagrantfile
を編集します
PS> Open-HomeVagrantfile
→ 仮想化支援機能の有無等ホストマシンのスペックに合わせてファイルを編集しファイルを閉じます。
3: Windows Server 2012 R2 の Box を作成する
Vagrant 上で動作する Windows Server の Box を作成します。
手順 3-1: 'Oracle VM VirtualBox' を起動します
スタートメニューから 'Oracle VM VirtualBox' を起動します
手順 3-2: Show-VeeweeDefinitionVboxList
ファンクションを使って、Bento(Veewee)で定義済みの OS の一覧を表示します
PS> Show-VeeweeDefinitionVboxList
windows-2008r2-standard
windows-2012-standard
windows-2012r2-standard
windows-7-enterprise
windows-8-enterprise
手順 3-3: Invoke-VeeweeVboxBuild
ファンクションを使って、Bento(Veewee)を実行し仮想マシン(VirtualBox のゲストOS)を作製します
PS> Invoke-VeeweeVboxBuild "windows-2012r2-standard"
→ コンソール画面が立ち上がり Windows のインストールがはじまれば成功です。
※ISOイメージのダウンロードで失敗する場合は、手動でダウンロードを行った後、仮想マシンを削除してから再度コマンドを実行してください。
手順 3-4: New-VagrantBox
ファンクションを使って、作成した VirtualBox のゲスト OS をベースに Vagrant の Box を作製します
PS> New-VagrantBox "windows-2012r2-standard"
PS> & vagrant box list
windows-2012r2-standard (virtualbox, 0)
→ windows-2012r2-standard
が表示されれば成功です。このファンクションは任意のゲストOSをBox化することができます。必要がなければ、ベースとして作成した仮想マシンは削除してください。
4: 仮想マシン(VirtualBox のゲスト OS)を作成する
開発/テスト対象となる仮想マシンを作成します。
手順 4-1: New-ChefRepo
ファンクションを使って、"SampleRepo" という名前のリポジトリを作成します
PS> New-ChefRepo "SampleRepo"
PS> Show-ChefRepoList
Name CreationTime LastWriteTime LastAccessTime
---- ------------ -------------- -------------
SampleRepo 2014/XX/XX XX:XX:XX 2014/XX/XX XX:XX:XX 2014/XX/XX XX:XX:XX
→ SampleRepo
が表示されることを確かめます。
手順 4-2: Get-ChefRepoPath
ファンクションを使って、作成した chef-repo のパスを取得しカレントディレクトリを移動します
PS> Get-ChefRepoPath "SampleRepo" | Set-Location
PS> pwd
Path
----
D:\PowerChef\chef-repositories\SampleRepo\chef-repo
→ D:\PowerChef\chef-repositories\SampleRepo\chef-repo
と表示されることを確かめます。
手順 4-3: New-ChefNode
ファンクションを使って、Vagrantfile
を作成します
PS> New-ChefNode -BoxName "windows-2012r2-standard" -OSType "Windows" -VMNumber 10
PS> Show-ChefNodeList
D:\PowerChef\chef-repositories\SampleRepo\chef-repo> Show-ChefNodeList
Name Parent CreationTime LastWriteTime LastAccessTime
---- ------ ------------ ------------- --------------
ip-192-168-56-10 development 2014/XX/XX XX:XX:XX 2014/XX/XX XX:XX:XX 2014/XX/XX XX:XX:XX
→ ip-192-168-56-10
という名前の仮想マシンが作成されたことを確かめます。
手順 4-4: Create-ChefNode
ファンクションを使って、仮想マシン(VirtualBox のゲスト OS)を作成します
PS> Create-ChefNode "ip-192-168-56-10"
PS> Show-ChefNodeStatus "ip-192-168-56-10"
Current machine states:
ip-192-168-56-10 running (virtualbox)
The VM is running. To stop this VM, you can run `vagrant halt` to
shut it down forcefully, or you can run `vagrant suspend` to simply
suspend the virtual machine. In either case, to restart it again,
simply run `vagrant up`.
→ 状態が running
と表示されていることを確かめます。
5: 仮想マシン(VirtualBox のゲスト OS)のテストを行う
手順 5-1: Open-ChefNodeSpecfile
ファンクションを使って、Serverspec の Spec ファイル(default_spec.rb
)を編集します
PS> Open-ChefNodeSpecfile "ip-192-168-56-10"
Testing for files.
の部分に 3 行追記します。
require 'serverspec'
require 'winrm'
include Serverspec::Helper::WinRM
include Serverspec::Helper::Windows
RSpec.configure do |c|
user = 'vagrant'
password = ask("Enter password: ") { |q| q.echo = false }
endpoint = 'http://192.168.56.10:5985/wsman'
c.winrm = ::WinRM::WinRMWebService.new(endpoint, :ssl, :user => user, :pass => password, :basic_auth_only => true)
c.winrm.set_timeout 300 # 5 minutes max timeout for any operation
end
# # Testing for user groups.
# describe group('xxxxxx') do
# it { should exist }
# end
# # Testing for users.
# describe user('xxxxxx') do
# it { should exist }
# it { should belong_to_group 'xxxxxx' }
# it { should_not belong_to_group 'xxxxxx' }
# end
# # Testing for directories.
# describe file('C:\xxxxxx\xxxxxx') do
# it { should be_directory }
# end
# # Testing for files.
# describe file('C:\xxxxxx\xxxxxx') do
# it { should be_file }
# it { should contain /^xxxxxx/ }
# it { should be_readable.by('owner') }
# it { should be_readable.by_user('xxxxxx') }
# it { should_not be_readable.by('others') }
# it { should_not be_readable.by_user('xxxxxx') }
# it { should be_writable.by('owner') }
# it { should be_writable.by_user('xxxxxx') }
# it { should_not be_writable.by('others') }
# it { should_not be_writable.by_user('xxxxxx') }
# it { should be_executable.by('owner') }
# it { should be_executable.by_user('xxxxxx') }
# it { should_not be_executable.by('others') }
# it { should_not be_executable.by_user('xxxxxx') }
# end
describe file('C:/test.txt') do
it { should be_file }
end
# # Testing for enabled services.
# describe service('xxxxxx') do
# it { should be_enabled }
# it { should be_running }
# end
# # Testing for disabled services.
# describe service('xxxxxx') do
# it { should_not be_enabled }
# it { should_not be_running }
# end
# # Testing for open ports.
# describe port(port_number) do
# it { should be_listening.with('tcp') }
# it { should be_listening.with('udp') }Pow
# end
# # Testing for close ports.
# describe port(port_number) do
# it { should_not be_listening }
# end
# # Testing for command returns.
# describe command('xxxxxx') do
# it { should return_stdout /^xxxxxx/ }
# it { should return_exit_status 0 }
# end
手順 5-2: Test-ChefNode
ファンクションを使って、Serverspec を実行します
PS> Test-ChefNode "ip-192-168-56-10"
:
中略
:
1 example, 1 failure
Failed examples:
→ テストに失敗することを確かめます。
6: Chef のレシピを作成して仮想マシン(VirtualBox のゲスト OS)に適用します
手順 6-1: New-Cookbook
ファンクションを使って、"make-testfile" という名前のクックブックを作成します
PS> New-Cookbook "make-testfile"
Maintainer: xxxxxxx xxxxxx ←作成者(メンテナー)の名前を入力します。
MainteinerEmail: xxxxxxxx@xxxxxx.xx ←作成者(メンテナー)のメールアドレスを入力します。
PS> Show-CookbookList
Name Parent CreationTime LastWriteTime LastAccessTime
---- ------ ------------ -------------- -------------
make-testfile site-cookbooks 2014/XX/XX XX:XX:XX 2014/XX/XX XX:XX:XX 2014/XX/XX XX:XX:XX
手順 6-2: Open-CookbookRecipe
ファンクションを使って、クックブックのデフォルトレシピ(default.rb
)を編集します
PS> Open-CookbookRecipe "make-testfile"
次のように編集してファイルを閉じます。
file "C:/test.txt" do
action :create
end
手順 6-3: Start-ChefZero
ファンクションを使って、ローカルマシン上にChef Zero(インメモリー版軽量 Chef Server)を起動します。
PS> Start-ChefZero
PS> & NETSTAT.EXE -anb | Select-String "8889"
→ ポート 8889 番の状態が LISTENING であることを確かめます。
手順 6-4: New-ChefZeroACL
ファンクションを使って、Windows ファイアウォールの設定を行います(Windows 8、Windows Server 2012 以降の環境のみ)
PS> New-ChefZeroACL
手順 6-5: Update-Cookbook
ファンクションを使って、依存関係のあるクックブックをダウンロードし Chef Zero にアップロードします
PS> Update-Cookbook "make-testfile"
PS> & knife cookbook list
→ クックブックの一覧が表示されれば成功です。
手順 6-6: SetUp-ChefNode
ファンクションを使って、作成した仮想マシンを Chef の Node 環境としてセットアップします
PS> SetUp-ChefNode "ip-192-168-56-10"
→ パスワード欄に vagrant
と入力し [OK] ボタンをクリックします。
手順 6-7: knife コマンドを使って、Chef Zero サーバー上に Node として登録されたことを確認します
PS> & knife node list
ip-192-168-56-10
→ ip-192-168-56-10
が表示されれば成功です。
手順 6-8: knife コマンドを使って run_list に作成したクックブックを追加します
PS> & knife node run_list add "ip-192-168-56-10" "make-testfile::default"
PS> & knife node show "ip-192-168-56-10"
手順 6-9: Environment の設定ファイル development.json
を作成します
PS> New-Item -Path ".\environments\development.json" -ItemType "File" -Value @'
{
"name": "development",
"json_class": "Chef::Environment",
"chef_type": "environment",
"default_attributes": {
}
}
'@
手順 6-10: knife コマンドを使って、 Environment を設定します
PS> & knife environment create from file ".\environments\development.json"
手順 6-11: Converge-ChefNode
ファンクションを使って、クックブックを仮想マシンに適用します(仮想マシン上で chef-client を実行します)
PS> Converge-ChefNode "ip-192-168-56-10"
7: 仮想マシン(VirtualBox のゲスト OS)の再テストを行う
手順 7-1: Test-ChefNode
ファンクションを使って、Serverspec を実行します
PS> Test-ChefNode "ip-192-168-56-10"
:
中略
:
1 example, 0 failures
→ テストが通ったことを確認します。
Vagrant + Chef + Serverspec を使って、Windows Server 環境も Infrastructure as Code & TDD してしまうという話でした。
今回、使用した PowerShell のモジュール PowerChef
の詳しい使い方については、以下を参照してください。
以上