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

HYPERCONCERTO株式会社のチーフエンジニア雑記Blog

hyperconcerto株式会社のチーフエンジニアが日々気づいたことを書いています

5回目、vSphereをPowerShellで操作するときのTips

昨年末からPowershellとPowerCLI関係の作業が続いているので、しばらくこの調子でいきたいと思います。

PowershellとBATのお悩み1
タスクスケジューラで実行しているスクリプトからファイルサーバーへ接続できないんですが…

回答
タスクスケジューラやスクリプトの単体実行の場合、特に意識しない限り実行ユーザーは
ローカルコンピュータに作成されたユーザーアカウントで実行されます。
タスクスケジューラの場合はローカルAdministratorが多いのではないでしょうか。
で、そんな状態でファイルサーバーへ接続しようとしても、ADと連携しているファイルサーバーに
ローカルユーザーアカウントが通用するわけもなく接続に失敗します。
このような場合はnet useコマンドで明示的にADユーザーを指定してネットワークドライブを作成します

例:Vドライブとしてマウントする
net use V: \\192.168.0.1\Temp P@ssw0rd1! /user:test-domain\user1

使い終わったらスクリプトの終端部分でネットワークドライブを消します
net use V: /delete

わりと知らない人が多くて現場ではまっているのをよく見かけます。


Powershellのお悩み2
Powershellレジストリ操作はできるのでしょうか

回答
レジストリの書き込み例
UACを無効にする場合
$path1 = "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System"
Set-ItemProperty $path1 -name "ConsentPromptBehaviorAdmin" -value "0"
Set-ItemProperty $path1 -name "PromptOnSecureDesktop" -value "0"

レジストリの内容を取得する場合
$path1 = "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System"
Get-ItemProperty $path1


Powershellのお悩み3
Windows Serverの初期設定スクリプトのサンプルをください

回答
運用自動化の関係でこういう問い合わせが増えています。
下記内容の設定を一発で行うスクリプト例を示します

1.ユーザーを追加
2.Remote Desktopを有効化
3.UAC無効化
4.Windows Firewall無効化

※管理者として実行としないと動かないです

#testuserを管理者権限を付けてパスワード期限を無期限
net user testuser /add
net user testuser P@ssw0rd1!
net localgroup administrators testuser /add
wmic useraccount where "Name='testuser'" set PasswordExpires=FALSE

#Remote Desktop有効化
$path1 = "HKLM:\SYSTEM\CurrentControlSet\Control\Terminal Server"
$path2 = "HKLM:\SYSTEM\CurrentControlSet\Control\Terminal Server\WinStations\RDP-Tcp"
Set-ItemProperty $path1 -name "fDenyTSConnections" -value "0"
Set-ItemProperty $path2 -name "UserAuthentication" -value "0"

#UAC無効化
$path1 = "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System"
Set-ItemProperty $path1 -name "ConsentPromptBehaviorAdmin" -value "0"
Set-ItemProperty $path1 -name "PromptOnSecureDesktop" -value "0"

#Firewall無効化
netsh advfirewall set allprofiles state off

4回目、vSphereをPowerShellで操作するときのTips

PowerCLIの実行速度が遅いんですが…

回答
PowerCLI 6.5 R1なら早いですよ。
実は6.5からは最初から最適化済みのモジュールがインストールされるので実行速度が上がっています。
というわけで調べてみました。

下記コマンドを実行
Measure-Command { get-vm }

6.0の32bit版で最適化無
約3.5秒

6.5の32bit版でインストール直後
約0.8秒

6.0までは32bit版が速かったのですが、6.5からは64bit版の方が速いみたい。

参考
6.5の64bit版でインストール直後
約0.45秒

いままでの6.0は最適化されていないのか?という疑問がありますが、最適化されていません。
詳細は下記記事を参照
https://blogs.vmware.com/PowerCLI/2011/06/how-to-speed-up-the-execution-of-the-first-powercli-cmdlet.html

6.0の最適化自体は下記コマンドで実行できます。
C:\Windows\Microsoft.NET\Framework\v4.0.30319\ngen.exe install “VimService60.XmlSerializers, Version=6.0.0.0, Culture=neutral, PublicKeyToken=10980b081e887e9f”
C:\Windows\Microsoft.NET\Framework64\v4.0.30319\ngen.exe install “VimService60.XmlSerializers, Version=6.0.0.0, Culture=neutral, PublicKeyToken=10980b081e887e9f”

動きとしてはngen.exeでネイティブイメージを生成してグローバルアセンブリに登録するという動きをします。

次はスクリプトの書き方による実行速度の違いを解説します。

●書き方による速度の違い

同じ出力を得ることができますが、いくつかの書き方ができます。

例1
Measure-Command { $ret = get-vm;$ret | where { $_.Name -eq "testvm-01" }}
約2秒

例2
Measure-Command { get-vm | where { $_.Name -eq "testvm-01" }}
約1.9秒

例3
Measure-Command { get-vm -name testvm-01 }
約0.5秒

例1はfor文で拾う時用ですね。
当然ですが、Get-VMの-Name引き数で指定したほうが速いです。


ループの場合

下記のような書き方にすると遅くなることが多いです。

あかん例
foreach ($tempList in $VMList){
Get-VM -Name $tempList
}

改善した例
$ret = Get-VM
foreach ($tempList in $VMList){
$ret | where { $_.Name -eq $tempList }
}

$VMListに入っている数が数個ならいいのですが10個を超えるとかなり遅くなります。

基本的にPowerShellは実行速度が結構遅いので、書き方に注意が必要です。
Where-Object句自体がちょっと遅い気がします。

その他の遅いと苦情を言われるパターン
PowerCLIのモジュールを使うps1ファイルの場合ですが、PowerCLI自体のモジュールのロードが遅いです。
数分かかることもありますので、頻繁に実行するのならプロセスを上げたままで処理するなどの工夫が必要です。

3回目、vSphereをPowerShellで操作するときのTips

特定のOSを使用しているGeustOSの一覧を作りたい!

回答
EOL対応とかセキュリティ対応でいますぐ出してよ!ってよく言われるあれです。
構成管理をさぼってると非常に大変な作業でして、いちいちログインして確認するのは非現実的なので
、vCenterからGUIから確認することが多いと思います。
しかし、台数が多いと大変なので自動化してみます。
前回のGet-VMGuestコマンドで取得できますが、このコマンドはVM名を引数として渡さないと動きません。
一気に表示する場合は下記のようなコマンドになります。
※表示に時間がかかるので実行時には注意してください。

Get-VM | Get-VMGuest

さらにGet-VMGuestの中身からWhere-ObjectコマンドでWindows Server 2012に該当するものだけを抽出すると下記のようになります。

Get-VM | Get-VMGuest | Where-Object {$_.OSFullName -like "*Microsoft Windows Server 2012*"}

このコマンドだと下記の表示になってわかりにくいです。


State IPAddress OSFullName

          • --------- ----------

Running {10.0.0.1} Microsoft Windows Server 2012 (64 ビット)
Running {10.0.0.2} Microsoft Windows Server 2012 (64 ビット)
Running {10.0.0.3} Microsoft Windows Server 2012 (64 ビット)

改良したコマンド
Get-VM | Get-VMGuest | Where-Object {$_.OSFullName -like "*Microsoft Windows Server 2012*"} | SELECT VmName,HostName,IPAddress,OSFullName

VmName HostName IPAddress OSFullName

            • -------- --------- ----------

TestVM1 WINAD1 {10.0.0.1} Microsoft Window...
TestVM2 WINSRV2 {10.0.0.2} Microsoft Window...

見切れてますのできちんとした形で見る場合はCSV形式で書き出しましょう

CSV書き出しと電源状態の表示を追加したコマンド
Get-VM | Get-VMGuest | Where-Object {$_.OSFullName -like "*Microsoft Windows Server 2012*"} | SELECT VmName,HostName,IPAddress,OSFullName,State | Export-Csv C:\Temp\test.txt -Encoding Default


作成から1ヵ月以上経過しているスナップショットを持っているか調べる方法はないのでしょうか?

回答
VMware社の推奨では48時間を超えてスナップショットを保持しないでくださいというガイドラインがあります。
指定した期間を経過していたら表示するコマンドがあったら便利ですが、用意されて内容です。
しかし、PowerCLIでちょっと作りこまないと多分無理です。
ちょっと頑張って任意の日数で抽出するスクリプトを作ってみました。

※モジュールの読み込みコマンドを入れてないのでPowerCLIの窓から呼び出してください。

ShowSnapshotInfo.ps1

$VIServer = "192.168.0.1"
$UserName = "administrator@vsphere.local"
$Password = "P@ssw0rd1!"
$LimitDay = 7

$vCenter_ret = Connect-VIServer -Server $VIServer -User $UserName -Password $Password

$i = 0

$ret_get_vm = Get-VM
$LimitDay = $LimitDay * -1
$tempLimitDay = (Get-Date).AddDays($LimitDay)

foreach($temp_Results1 in $ret_get_vm){
$ret_SnapShot = Get-Snapshot -vm $temp_Results1.Name

foreach($temp_Results2 in $ret_SnapShot){
$tempSnapShotDay = $temp_Results2.Created
if ($tempSnapShotDay.Date -lt $tempLimitDay.Date){
#CSV形式へ変換
$OutString = $temp_Results1.Name + "," + $temp_Results2.Name + "," + $temp_Results2.Created
#結果出力
$OutString
}
}
}

Disconnect-VIServer -Server $VIServer -Confirm:$false


使い方
vCenterのIPアドレスや認証情報を環境に合わせて修正してください。
変数$LimitDayに対して検知したいスナップショットの古さを指定してください。
1か月の場合は下記のようになります。
$LimitDay = 30

出力はVM名、スナップショット名、スナップショット日付
となります。

スクリプトは全数に対してGet-VMを投げているのでVMの数が多い環境では非常に時間がかかります。

スクリプトに対する安全性やバグについては保証しません。

2回目、vSphereをPowerShellで操作するときのTips

スクリプトをファイルにまとめて実行すると、Dissconnect-VIServerでログオフの確認メッセージが出て自動化できない!

回答

  • Confirm:$failseを付けると確認メッセージが出ません。

具体的には下記のように書くといいです。
※-Serverオプションはつけなくても動きますが、うまくいかない環境もあるようなので付けました。
※-Serverオプションに指定するアドレスはvCenterのアドレスです

Disconnect-VIServer -Server 192.168.0.1 -Confirm:$false


Get-VMコマンドで取得できる項目を知りたい。Get-VMコマンドで表示される項目が少なすぎる

回答
Get-VM | Get-Member
で戻り値が持っているプロパティなどが見れます。
モリーの割当量を見たい場合はMemoryGBを参照します。

ちなみにGet-VMGuestコマンドの方がGuest OSの細かな情報が取れます。
例えばOSの情報とかIPアドレスなど

例:
Get-VMGuest -VM PC1

詳しくはPowerCLIのリファレンスを参照してください

PowerCLIのTipsその1

だいぶ時間が空いてしまいましたが、2017年1回目の更新を行いたいと思います。

仮想化関係が得意ですと発表してしまっているので、仮想化関係の記事を書こうとここ最近悩んでいました。
しかし、なかなかネタが思いつきません。

最近vSphereのスクリプト開発が多かったので、PowerShellやPowerCLI関係の事を書きたいと思います。

1回目、vSphereをPowerShellで操作するときのTips

PowerCLIのウインドウからならGet-VMとかのコマンドが通るけど、PowerShellのウインドウから実行できないのはどうして?
PowerCLIってPowerShellベースじゃないの?
スクリプトファイルでの実行できないよ!

回答
PowerCLIはPowerShellに対してVMwareが提供するモジュールを組み込んだものです。
ですので、手動でモジュールを組み込めばコマンドが通ります。

基本コマンドを使えるようにするには下記モジュールを読み込みます
Import-Module VMware.VimAutomation.Core

読み込めたらConnect-VIServerが通るはずです。

他のモジュールはこの中に入っているので、使いたいプロダクトに合わせて読み込んでください。
C:\Program Files (x86)\VMware\Infrastructure\PowerCLI\Modules

全てのモジュールを読み込む場合は初期化スクリプトを呼び出してください
& 'C:\Program Files (x86)\VMware\Infrastructure\PowerCLI\Scripts\Initialize-PowerCLIEnvironment.ps1'


PowerCLI6.5RC1がリリースされているので補足
PowerCLI6.5RC1の段階ではHorizonViewに関するコマンドは提供されていませんが、ViewAPIがサポートされるようになったので一応は操作可能です。
ViewAPIを使った操作は結構大変なので、VMware.Hv.HelperというGitHubで公開されているモジュールを使ったほうが良いでしょう。
ただしデスクトッププールなどの一般的な操作のみサポートされています。
(細かな操作はViewAPIを使う必要があります)

ヘッドホンアンプの箱を特注しました

前回はヘッドホンアンプの基板を基板工場で作ってもらい、部品実装をするところまで進みました。
今回は基板を入れる箱の特注をお届けしようと思います。

箱はタカチ電機様に加工までお願いしました

最初からクライマックスですけれど、完成した箱の写真です。
f:id:hyperconcerto:20161107172530p:plain

諸事情によりフロントパネルはあえて撮影していません。(すみません…)

加工依頼の流れ

ここが一番気になるところでしょう。
基板作成はできても筐体加工は無理っていうのは結構あると思います。
穴あけだけでも10mm超えるとボール盤じゃないと辛い部分もありますし、金属カスやバリ取りの手間を考えたら専門家にお任せしたほうがいいかなと思います。
そもそもドリルの刃って結構しますし…

1.タカチ電機様のWebサイトから箱を選定します
2.同Webサイトに箱のCADデータがあるはずなのでダウンロードします(私が使った箱はCADデータありませんでした)
3.もしCADデータが無いのなら問い合わせをします
4.加工指示をCADデータに書き込みます※1
5.DWG形式かDXF形式で保存します
6.タカチ電機様や代理店に加工依頼を行います※2
7.支払い方法を指定して、支払いを済ませます
8.届くのを待ちます

※1 DXF形式かDWG形式のようなので、対応しているCADを使ってください
※2 今回はマルツエレック様経由で対応して頂きました

加工指示の具体的内容ですが、どの位置にどのような穴を開けるかといった内容がメインになります。
また、ネジ穴付きのスタッドなども指定すれば加工してくれますので基板固定に悩む必要はありません。

気になるお値段ですが…
具体的なそのものずばりな金額は避けますが、今回の場合だと加工費は文字入れと穴あけで箱の1.3倍ぐらいでした。
箱2個ちょっとで済むので結構リーズナブルではないかと思います。

またヘッドホンアンプを作ってみました

引っ越したり色々あったので更新がとても遅くなりました。

前回作ったヘッドホンアンプはICをつなぐだけでできるのであまり面白くありません。
個人的には気に入ってなかったりします。
実はあの作例のだいぶ前から電流増幅部分をICではなく、単体の素子で作りこんだアンプを作っていました。

1~2代目は分解されてしまったので写真無し

1代目は4極ヘッドホン用に小規模な回路で試作しました。
色々妥協した設計でしたのであっさり動きましたが、面白くないので大電流動作させようと設計変更しましたがここから泥沼へ…

2代目は大電流でヘッドホンを駆動しようとしましたが、熱暴走する上に動作が不安定なのでやめました。

3代目(一部分解済み)
f:id:hyperconcerto:20161018220348j:plain
熱暴走するならヒートシンクつけたらいいのでは?と安直な考えで生まれたのが3代目です。
写真には写っていませんが、この基板の2倍の大きさがある電源が付いています。
回路構成を極力統一化してトラブルを防ごうとしましたが、手配線特有のばらつきは解消できず片耳側だけ音が歪むという致命的な問題がありました。
増幅回路の安定化手法に関するナレッジについては収穫がありましたので4代目の設計に入りました

4代目
f:id:hyperconcerto:20161018220025j:plain
変なこだわり?は捨ててシンプルに作ろうというわけで、電源はACアダプターにして消費電流も控えめに設計しました。増幅回路の形式によって解消できない暴走が起きるので、いままでと違う増幅回路にしました。
細かい話をすると、ヘッドホンの入力側って見た目は電線なんですが複雑な作用をします。
その影響を断ち切る構造が必要なので大幅な設計変更をしました。
今回はまったく同じ回路を4つ並べて配線間違いのリスクを減らしました。
これも4極ヘッドホン用に作りました。
今もACアダプターをつなぐと動きます。
しかし変なこだわりは捨てられず、特殊な増幅ICを使っているので汎用性がありませんでした。

5代目
f:id:hyperconcerto:20161018220018j:plain
4代目の結果を受けてさらに簡素化して、普通の増幅ICを使えるようにしたのものです。抜群の回路安定性で不安定な高周波増幅ICを使っても動作します。
いい加減動くと思ったので、手配線せずに基板屋さんで製造してもらいました。
(部品実装は自分でやりました)
これは普通の3極ヘッドホン用に作りました。

基板製造!?って驚く方が多いと思いますが、基板製造委託って今はそれほど難しくないんです。
回路CAD使えたら注文は簡単ですし、回路CADもオープンソースの物があります。
私はKiCADを使っています。
製造のほうは海外へ注文すればかなりお安くできます。(納期確認とかデータ不備について英語で対応できればですが…経験談)
少ない枚数(5枚以下)でも作ってくれるので、自作派の方は検討しても良いかもしれません。

5代目を聞き比べ
iPhoneにつなぐことを想定して作っていましたので、iPhone6 Plusで試してみました。直結より音の広がりが良いです。というかiPhoen6 Plusはかなり音が良いと思います。
数万円するDACと同じぐらいだし、ノイズもないので音楽プレーヤーとしても優秀だと思います。
ついでにiPhone7 Plusと6で比べてみました。7からイヤホン端子がなくなりましたので、劣化を気にしていたのですが、やはり劣化してました。音が平らで広がりがかなり弱くなりました…

最後に
自分で作ったアンプだと思い込みでまともに聞こえている可能性があります。不安になったのでまともな特性なのか調べてみました。
f:id:hyperconcerto:20161018225001p:plain
このグラフは各周波数でどの程度の音量(正確には電圧)なのか測定したグラフです。
下が周波数で、20kHzまでが人間が聞き取れる周波数だそうです。
イコライザーアンプなどはこの特性を意図的に変化させるように作られています。
今回のアンプは標準的な特性ですので問題はなさそうです。(多分…)

こんな事してますが、専門分野はWindows Serverなどです。

むき出しの基板だと使いにくいので箱を作らないといけませんが、工作のセンスないんです。
穴あけるだけは簡単ですが・・・