Share
Embed
オープンソースになったPowerShellを学ぼう
オープンソースカンファレンス 2017 Hokkaido (CLR/H #105)で発表した資料です。
セッション中の"配列リテラル"の説明に誤りがあり、以下のブログエントリで訂正しています。
* http://blog.shibata.tech/entry/2017/12/09/000500
Takuya Shibata PRO
July 15, 2017
Transcript
72 slides
-
自己紹介 ➢ しばた (素敵なおひげ) ◦Twitter : @stknohg ◦Blog : http://blog.shibata.tech/
➢ 何者? ◦ CLR/HとJAZUG札幌(きたあず)の裏方 ◦Microsoft MVP Cloud and Datacenter Management (2016/07 - ) 2 -
About CLR/H 3 CLR/H は、北海道で IT 関連、特に開発系技術に関する学習と研究を 目的としたコミュニティです。 CLR/H には
”Creation Leads to Revolution with Humanity (or Humor :-)” という意味もあります。 定期的に勉強会およびイベントを開催し、参加者同士の情報交換や 技術研鑽を行っております。 会の成り立ちから、Microsoft .NET テクノロジー関連の話題が多い ですが、それ以外の話題を取り上げることもあります。 本セッションのハッシュタグは #clrh105 #osc17do -
PowerShellとは 6 PowerShellは、WindowsおよびWindows Server用の 自動化プラットフォームおよびスクリプト言語で、 システムの管理を簡素化できます。 他のテキストベースのシェルとは異なり、PowerShell は.NET Frameworkの機能を活用し、豊富なオブジェクト と、Windows環境を制御するための大量の組み込み
機能を提供します。 https://msdn.microsoft.com/en-us/powershell の記述より引用 -
PowerShellの歴史 ➢ 2006年11月、PowerShell 1.0リリース ✓2017年7月15日現在の最新バージョンは 5.1 ➢ PowerShellのエディション(PowerShell 5.1より) 1.
Desktop Edition ✓通常のWindows向け ✓.NET Framework上で動作する 2. Core Edition ✓Nano Server向け ✓.NET Core上で動作する 8 -
PowerShellの歴史 9 PowerShell 1.0 PowerShell 5.1 Desktop Edition Core Edition
PowerShell 5.0 Editionなし Editionなし Windows Windows (Nano Server) Linux Mac -
PowerShell for every system! ➢ 2016年8月18日、突如 PowerShellがオープンソースに ➢ ソースはGitHubで公開 ◦
https://github.com/PowerShell/PowerShell ➢ 同時に.NET Coreを基盤とした クロスプラットフォーム化 ➢ OSS化したPowerShellのバージョンは6.0 ◦ 2017年7月15日現在でBeta 4 11 -
PowerShell for every system! ◦ 対応OS・ディストリビューション (2017年7月15現在) ✓Windows 7 SP1
~ Windows 10 ✓Windows Server 2008 R2 SP1 ~Windows Server 2016 ✓Ubuntu 14.04、16.04 ✓Debian 8 ✓Red Hat Enterprise Linux 7 ✓CentOS 7 ✓OpenSUSE 42.1 ✓Arch Linux ✓Kali Linux ✓AppImage ✓macOS 10.12 12 -
PowerShell 6.0 ➢ 対応OSとエディション ➢ ➢ 現在はCore Editionのみバイナリ配布 ◦ Desktop版がリリースされるかは不明
13 OS Desktop Edition (.NET Framework) Core Edition (.NET Core) Windows ? ※バイナリ未配布 〇 Windows (Nano Server) × 〇(インストーラー無し) Linux × 〇 Mac × 〇 -
これからのPowerShell 14 PowerShell 1.0 PowerShell 6.0 Desktop Edition Core Edition
PowerShell 5.1 Editionなし Core Edition Core Edition Core Edition ? Windows Linux Mac -
これからのPowerShell ➢ コミュニティからのフィードバックを重視 1. GitHubでIssue管理 2. Gitter、Slack上のチャットルーム 3. PowerShell-RFC ◦
GitHubでRFCにより新機能を議論 ✓https://github.com/PowerShell/PowerShell-RFC 4. ドキュメント管理 ◦ GitHubでドキュメント管理。プルリク可能 ✓https://github.com/PowerShell/PowerShell-Docs ✓https://github.com/PowerShell/powerShell-Docs.ja-jp 15 -
インストール ➢ Windows ◦ 既存の環境にPowerShell 6.0を追加インストール できる ◦ MSI、またはZipファイルからインストールする 18
# PowerShell(MSI) Invoke-WebRequest ` -Uri "https://github.com/PowerShell/PowerShell/releases/download/v6.0.0- beta.4/PowerShell-6.0.0-beta.4-win10-win2016-x64.msi" ` -OutFile "$($pwd.Path)¥PowerShell-6.0.0-beta.4.msi" Start-Process ` -FilePath msiexec.exe ` -ArgumentList @("/i", "$($pwd.Path)¥PowerShell-6.0.0-beta.4.msi", "/passive") ` -Wait -PassThru -
インストール ➢ Linux ◦ rpm、debファイルが提供されている ◦ yum、apt-getコマンドでもインストール可能 19 # Bash(apt-get)
curl https://packages.microsoft.com/keys/microsoft.asc | sudo apt-key add - curl https://packages.microsoft.com/config/ubuntu/16.04/prod.list ¥ | sudo tee /etc/apt/sources.list.d/microsoft.list sudo apt-get update sudo apt-get install -y powershell # Bash(yum) curl https://packages.microsoft.com/config/rhel/7/prod.repo ¥ | sudo tee /etc/yum.repos.d/microsoft.repo sudo yum install -y powershell -
インストール ➢ Mac ◦ pkgファイルが提供されている ◦ 公式ではないが、Homebrew Caskからインストール 可能 20
# Bash (Homebrew Cask) brew tap caskroom/cask brew cask install powershell -
オブジェクト、変数 ➢ PowerShellは.NET Frameworkの オブジェクトを使うシェル ➢ すべてのオブジェクトは.NETの型を持つ 21 # 変数定義は
$変数名 $i = 123 # $iは.NET Frameworkの型を持つ $i.GetType().FullName # -> System.Int32 を返す # オブジェクトなのでメソッドやプロパティが使える $i.ToString() -
オブジェクト、変数 ➢ 配列は @() または ,(カンマ演算子) を使う ➢ ハッシュテーブルは @{}
◦ Key = Value形式、各要素は ; で区切る 22 # 配列リテラルは @() $array = @(1, 2, 3) # カンマ演算子を使い以下の様にも書ける $array = 1, 2, 3 # ハッシュテーブルは @{} $hash = @{ Name = "stknohg"; Height = 0xA7 } (@()は演算子となる場合もあるが本セッションでは説明を割愛する) -
変数のスコープ ➢ PowerShellの変数のスコープは ダイナミックスコープ ※レキシカルスコープではないので注意! ➢ スコープ一覧 23 スコープ 内容
Global PowerShellのプロセス全体でグローバル Script スクリプトファイル(.ps1)単位 Local 現在のスコープ、およびその子スコープ Private 現在のスコープのみに限定 番号付きスコープ 相対的なスコープを番号で指定 0 : ローカル、1 ~ : 親スコープ -
フロー制御 PowerShellには一通りの制御構文が用意 されている ➢ If文 24 $grade = 92 if
($grade -ge 90) { "Grade A" } elseif ($grade -ge 80) { "Grade B" } elseif ($grade -ge 70) { "Grade C" } elseif ($grade -ge 60) { "Grade D" } else { "Grade F" } -
フロー制御 ➢ for文、foreach文 25 for ($i = 1; $i -le
5; $i++) { echo ($i * $i) } foreach ($i in 1..5) { echo ($i * $i) } -
フロー制御 ➢ while文、do文 26 $i = 1 while ($i –le
5) { echo ($i * $i) ++$i } $i = 1 do { echo ($i * $i) } while (++$i -le 5) -
フロー制御 ➢ switch文 27 switch ($Host.Name) { "Windows PowerShell ISE
Host" { $result = 1 } "Visual Studio Code Host" { $result = 2 } Default { $result = 3 } } -
演算子 ➢ 主要な演算子は –[演算子] の形式 ➢ 主要な演算子一覧 (他にもたくさんあります) 28 if
($i * 5 –eq 100) { … } 演算子 内容 -eq 等しいか比較(==) -ne 等しくないか比較(!=) -gt, -ge, -lt, -le 大小比較(>, =>, <, <=) -and, -or, -xor, -not 論理比較(&, |, ^, !) -is オブジェクトの型の比較 -like, -match 文字列の比較 -replace, -split 文字列の置換・分割 -contains, -in 配列に要素が含まれるか -
関数・フィルター ➢ 関数 ◦ いわゆる普通の関数 ◦ PowerShellは戻り値の扱いが特殊 ✓文ごとにストリーム(詳細は後述) にオブジェクトを出力する ✓Returnはただの制御構文
29 function Sqrt([int]$Value) { Write-Output "${Value}の平方根は?" return [Math]::Sqrt($Value) } -
関数・フィルター ➢ 高度な関数 ◦ PowerShell 2.0から使用可能 ◦ コマンドレット(詳細は後述) と同等の属性を使える様に した関数
31 function Get-Sqrt { [CmdletBinding()] param ( [Parameter(Mandatory = $true, ValueFromPipeline = $true)] [int]$Value ) Write-Output "${Value}の平方根は?" return [Math]::Sqrt($Value) } -
関数・フィルター ➢ フィルター ◦ パイプラインでの処理に特化した簡易的な関数 ◦ 入力は $_ 32 filter
Sqrt { if ($_ -isnot [int]) { Write-Error "${_}はInt型のみ指定可能です" return } Write-Output "${_}の平方根は?" return [Math]::Sqrt($_) } -
例外処理 ➢ Trap ◦ PowerShell 1.0からある形式 ➢ Try-Catch-Finally ◦ PowerShell
2.0から導入された 33 trap { $j = 2 } $j = 0; $v = 10 / $j try { $j = 0; $v = 10 / $j } catch { $j = 2 } -
Class・Enum ➢ PowerShell 5.0からクラスと列挙型が記述 できる様になった ◦ ただし、C#などのクラスと同等なものを期待する とがっかりするかも… 34 class
Device { [string]$Brand [string]$Model [string]$VendorSku [string]ToString() { return ("{0}|{1}|{2}" ` -f $this.Brand, $this.Model, $this.VendorSku) } } enum MyFlag { Off = 0 On = 1 } -
コマンドレット ➢ PowerShellの内部コマンド ◦Command + Let(小さい) からの造語 ◦Cmdletとも言う ◦[動詞]-[名詞]の命名規則を持つ ➢
PowerShellはオブジェクトを扱うシェルである ため、内部コマンドであるコマンドレットを中心 に組み合わせて使う 35 Write-Output "Hello" -
主要なコマンドレット ➢ Write-Output (echo) ◦ いわゆるecho ◦ ストリーム(詳細は後述) にオブジェクトを出力する ➢
Write-Host ◦ Write-Outputと似てるがこちらはコンソールに 文字を表示するだけ ◦ ストリームには何も出力しない (PowerShell5.0からはちょっと違う) 36 > Write-Output "Hello World!" > Write-Host "Hello World!" -ForegroundColor Green -
主要なコマンドレット ➢ Get-Member (gm) ◦ オブジェクトの型情報およびメンバー情報 (プロパティ・メソッド)を取得する ◦ とりあえずGet-Memberというくらいよく使う ➢
Get-Command (gcm) ◦ PowerShell版の which コマンド ◦ コマンドレットを探すのによく使う 37 > Get-ChildItem | Get-Member > Get-Command Get-* -
主要なコマンドレット ➢ Where-Object (where, ?) ◦ オブジェクトからデータを抽出する ◦ Grepの代わり的なものその1 ◦
➢ Select-String (sls) ◦ ファイルやオブジェクトの文字列を検索する ◦ Grepの代わり的なものその2 38 > Get-ChildItem ` | Where-Object { $_.Name -like "osc*" } > Get-Content .¥sample.txt ` | Select-String "osc" -
主要なコマンドレット ➢ ForEach-Object (foreach, %) ◦ オブジェクトのコレクションに対して反復処理を行う ◦ awkの代わり的なもの ◦
sedっぽく使えないこともない ➢ Select-Object (select) ◦ オブジェクトの特定のプロパティを選択する 39 > Get-ChildItem -File ` | ForEach-Object { ren $_.FullName "$($_.Name).orig" } > Get-ChildItem | Select-Object Name, CreationTime -
エイリアス ➢ エイリアス ◦ 関数やコマンドレットに別名を付けることが可能 ◦ Bashなどのエイリアスとは異なり引数を含むことは できない ➢ エイリアスの衝突
◦ Linux/Macの主要コマンドとPowerShellのエイリアス が衝突する? →Linux/Mac版のPowerShellでは基本的なコマンドと 衝突するエイリアスは除外されている 40 -
エイリアス ➢ 主要なエイリアス一覧 41 エイリアス 実体 Windows Linux/Mac echo Write-Output
〇 〇 ls Get-ChildItem 〇 × dir Get-ChildItem 〇 〇 cd Set-Location 〇 〇 pwd Get-Locatoin 〇 〇 cp Copy-Item 〇 × rm Remove-Item 〇 × mv Move-Item 〇 × ps Get-Process 〇 × wget Invoke-WebRequest 〇 × curl Invoke-WebRequest 〇 × ※エイリアスの一覧は Get-Alias (gal) で確認可能 -
オブジェクトパイプライン ➢ 実行例 ◦ 結果 43 @(1, 2, @(3, 4),
5) | ` % { echo "$($_.GetType())型の値 $($_) が渡されました…"} -
オブジェクトパイプライン 45 function Cmdlet1 { [CmdletBinding()] Param ( [Parameter(Mandatory =
$true, ValueFromPipeline = $true, Position = 0)] $InputObject ) Begin { Write-Host "Command1 Begin($InputObject)..." -ForegroundColor Green } Process { Write-Host "Command1 Process($InputObject)..." -ForegroundColor Green Write-Output $InputObject } End { Write-Host "Command1 End($InputObject)." -ForegroundColor Green } } -
オブジェクトパイプライン ➢ 動作例 46 >@(1..5) | Cmdlet1 | Cmdlet2 Cmdlet1
Cmdlet2 Begin Process End Begin Process End Int[] 配列 1 2 3 4 5 1 2 3 4 5 6 -
(比較) Bashのパイプライン ➢ Pipeシステムコールでプロセスは並列実行 ➢ 入出力はテキスト(バイナリ)をストリーミング ◦ OS毎に異なるバッファサイズ 47 Process1
pipe write read Process2 -
ストリームと標準入出力 ➢ PowerShellのストリーム ◦ PowerShellではオブジェクトを入出力するため、 他のシェルとは異なり標準入出力に相当する 部分はストリームと呼ばれる ➢ ストリームと標準入出力 ◦
ストリームと標準入出力は似ているが別物 ◦ PowerShellと外部のプロセスが連携する場合、 ストリーム(オブジェクト) ⇔ 標準入出力(テキスト) の変換が発生する 48 -
PowerShellのストリーム ストリーム リダイレクト 出力方法 Version 特記事項 Input - - All
標準入力に相当 Standard output 1> Write-Output など All 標準出力に相当 “出力ストリーム” Error output 2> Write-Error All 標準エラー出力に相当 “エラーストリーム” Warning output 3> Write-Waring 3.0以上 Verbose output 4> Write-Verbose 3.0以上 Debug output 5> Write-Debug 3.0以上 Information 6> Write- Information 5.0以上 Write-Hostの結果が ストリームに乗る様に Progress - Write-Progress All 49 -
ストリーム標準入出力 ➢ PowerShell → 外部プロセス ◦ コンソールに表示される文字列を 標準入力へ渡す ◦ $OutputEncoding
で設定されている エンコーディング(デフォルト ASCII)でエンコード ◦ 最後に必ず改行が付く ➢ 外部プロセス → PowerShell ◦ 標準出力を文字列([stirng[]]型)に変換 ◦ [Console]::OutputEncoding で設定されている エンコーディング(デフォルト MS932/UTF8)でエンコード ◦ バイナリ出力も文字列化される 50 -
Monad Manifesto ➢ 2002年にPowerShell Teamの チーフアーキテクト(当時)だったJeffrey Snover さんが書いたドキュメント ◦ http://www.jsnover.com/Docs/MonadManifesto.pdf
➢ PowerShellの基本構成や思想、対象とする問題 領域などについて書かれている ➢ MonadはPowerShell開発時のコードネーム ◦ 関数型言語のアレとは関係ない:) 56 -
Monad Manifestoから見えること ➢ システム管理者(所謂ITPro)、開発者ほど プログラムに習熟していない人を想定していた → コマンドレットの命名規則 → 統一的なパラメータ指定 ➢
Bashなどのシェルを従来型のシェルとし、 そこから新しいアプローチを採ろうとしていた → .NET Frameworkをベースとした統一的な CUIシェル → オブジェクトパイプラインなどの、テキストでは なくオブジェクトを中心した各種機能 57 -
PowerShellとOS管理 ➢UNIX系OS ✓テキストファイル ➢Windows ✓テキストファイル ✓レジストリ ✓WMI ✓Active Directory ✓Win32
API 58 OSを管理するための方法がWindowsと UNIX系OSで決定的に異なる -
JSON ➢ PowerShellにはJSONを扱う組み込み コマンドレットがある ◦jq代わりにPowerShellという選択肢 65 1. ConvertFrom-Json ✓JSONからPowerShellのオブジェクトを生成 2.
ConvertTo-Json ✓PowerShellのオブジェクトをJSONに変換 -
JSON 66 @" { "name": "stknohg", "id": 1, "items": [
123, 456, 789 ] } "@ | ConvertFrom-Json -
JSON 67 @{ id = 1; name = 'stknohg’ items
= @(123, 456, 789) } | ConvertTo-Json -
Pester ➢ PowerShell (5.0以降) に同梱されている OSSのユニットテストフレームワーク ◦ https://github.com/pester/Pester 68 function
Add-Numbers($a, $b) { return $a + $b } Describe "Add-Numbers" { It "adds positive numbers" { Add-Numbers 2 3 | should be 5 } It "ensures that that 2 + 2 does not equal 5" { Add-Numbers 2 2 | should not be 5 } } -
クラウド管理ツールとしてのPowerShell ➢ 各ベンダー・サービスのPowerShell Core対応 1. Azure - AzureRM.NetCore.Preview (プレビュー版) ✓
https://www.powershellgallery.com/packages/AzureRM.NetCore.Preview/ ✓ https://blogs.technet.microsoft.com/jessicadeen/azure/getting-started-with-powershell-core-and-azurerm- modules-on-ubuntu-and-os-x/ 2. AWS - AWSPowerShell.NetCore (Ver. 3.3.113.0) ✓ https://www.powershellgallery.com/packages/AWSPowerShell.NetCore/ ✓ https://aws.amazon.com/jp/blogs/developer/introducing-aws-tools-for-powershell-core-edition/ 3. GCP - CLOUD TOOLS FOR POWERSHELL (Ver. 1.0.0.7) ✓ https://github.com/GoogleCloudPlatform/google-cloud-powershell/ ✓ http://googlecloudplatform-japan.blogspot.jp/2016/12/1-powershell-windows-linux.html 4. Vmware - PowerCLI Core (Ver. 1.10) ✓ https://labs.vmware.com/flings/powercli-core 5. Docker - PowerShell Module for Docker (アルファ版) ✓ https://github.com/Microsoft/Docker-PowerShell 69