Monday, September 29, 2008

前回 Add-Contentコマンドレットの-Pathパラメータ を紹介しました。

今回はAdd-Contentコマンドレットの-literalPathパラメータについてまとめた(http://pswiki.hiros-dot.net/) のでご紹介します。

-literalPath <string[]>

内容を追加する先のパスを指定します。ただし-pathパラメータと異なり、ワイルドカードを指定することができません。パスにワイルドーカード文字を含めてもワイルドカードとして認識されないためエラーが発生します。パスにエスケープ文字が含まれている場合は単一引用符で囲む必要があります。(PowerShellでは`(アクサングラーブ文字)がエスケープ文字として扱われます。)

注意)ワイルドカードは指定できない

Add-Content -literalPath "Test*.txt" -Value "abc"

はエラーになります。-pathパラメータはワイルドカードを使用して複数ファイルへの書き込みが可能ですが-literalPathはできません。ただしカンマ区切りによる複数ファイルの指定は可能です。

–––––––––– -literalPathパラメータの使用例1 ––––––––––
Add-Content -literalPath "test.txt" -Value "ABC"

このコマンドを実行すると、カレントディレクトリに存在する test.txt というファイルに"ABC"という文字列を追記します。ファイルが存在しない場合は新規で作成され"ABC"という文字列を書き込みます。

–––––––––– -literalPathパラメータの使用例2 ––––––––––
Add-Content -literalPath "test1.txt","test2.txt" -Value "ABC"

このコマンドを実行すると、test1.txt と test2.txtの2つのファイルに文字列"ABC"を追記します。ファイルが存在しない場合は新規で作成され"ABC"という文字列を書き込みます。

–––––––––– -literalPathパラメータの使用例3 ––––––––––
Add-Content -literalPath 'tes`t.txt' -Value "ABC"

このコマンドを実行すると、カレントディレクトリに存在する tes`t.txt というファイルに"ABC"という文字列を追記します。ファイルが存在しない場合には新規で作成されます。
この例のように、パスにエスケープ文字が含まれている場合は単一引用符(')で括って指定します。

–––––––––– -literalPathパラメータの使用例4 ––––––––––
Add-Content -literalPath "tes[]t.txt" -Value "ABC"

このコマンドを実行すると、カレントディレクトリに存在する tes[]t.txt というファイルに"ABC"という文字列を追記します。ファイルが存在しない場合には新規で作成されます。
この例のようにパスにワイルドカードパターンが含まれていても文字として取り扱います。

–––––––––– -literalPathパラメータのNG例1 ––––––––––
Add-Content -literalPath "Test*.txt" -Value "abc"

このコマンドレットは、パスにワイルドカード(*)が含まれているためにエラーとなります。これは*をワイルドカードではなく文字として認識し、ファイル名として取り扱おうとしたことが原因となります。

まとめ

-literalPathパラメータの特徴は、なんといってもワイルドカード文字をワイルドカードとしてではなく文字として取り扱うことでしょう。

パスにワイルドカードが含まれている場合には-literalPathパラメータを使用するということを是非覚えておいてください。

Monday, September 29, 2008 11:51:55 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Exchane Server 2007のPowerShellで使用可能なコマンドレット一覧

http://technet.microsoft.com/ja-jp/library/bb123703.aspx

にあります。全部で393個あるようです。(数え間違えていなければ...)

忘れないようにメモ。

Monday, September 29, 2008 1:05:45 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Sunday, September 28, 2008

現在、PowerShell WikiでAdd-Contentコマンドレットの使用方法についてまとめています。(サイト自体は今年の7月に立ち上げていたのですがこれから始動といったところです)

では、本題です。


Add-Contentコマンドレットは

指定した項目やファイルに内容を追加することができます。内容を指定するには、コマンドに内容を入力するか、内容が入力されているオブジェクトを指定します。指定した項目やファイルが存在しない場合は、新規で作成され、指定した値が追記されます。


基本構文

Add-Content -Path "パス文字列" -Value "追記する値"

です。実際には数多くのパラメータがありますが、後日紹介していきたいと思います。

今回取り上げるのは-Pathパラメータです。


-Pathパラメータは

内容を追加する先のパスを指定します。パスにはワイルドカードを指定することができます。また、カンマで区切ることで複数のファイルを指定することができます。

エスケープ文字を含むパスを指定することはできません。エスケープ文字を含むパスを指定したい場合は-literalPathパラメータを使用します。(PowerShellでは`(アクサングラーブ文字)がエスケープ文字として扱われます。)


使用例

–––––––––– -Pathパラメータの使用例1 ––––––––––

Add-Content -Path "test.txt" -Value "ABC"

このコマンドを実行すると、カレントディレクトリに存在する test.txt というファイルに"ABC"という文字列を追記します。
ファイルが存在しない場合は新規で作成され"ABC"という文字列を書き込みます。

–––––––––– -Pathパラメータの使用例2 ––––––––––
Add-Content -Path "test1.txt","test2.txt" -Value "ABC"

このコマンドを実行すると、test1.txt と test2.txtの2つのファイルに文字列"ABC"を追記します。
ファイルが存在しない場合は新規で作成され"ABC"という文字列を書き込みます。

–––––––––– -Pathパラメータの使用例3 ––––––––––
Add-Content -Path "*.txt" -Value "ABC"


このコマンドを実行すると、カレントディレクトリにある拡張子が*.txtのファイルに"ABC"という文字列を追記します。


–––––––––– -PathパラメータのNG例1 ––––––––––

Add-Content -Path "tes`t.txt" -Value "ABC"

このコマンドレットはパスにエスケープ文字`tが含まれているため「パスに無効な文字が含まれています。」のエラーが発生します。
エスケープ文字が含まれているパスを指定したい場合には-Pathパラメータの代わりに-literalPathパラメータを使用します。

–––––––––– -PathパラメータのNG例2 ––––––––––
Add-Content -Path "tes[t.txt" -Value "ABC"

このコマンドレットはパスに[が含まれているため「指定されたワイルドカード パターンは無効です」のエラーが発生します。-Pathパラメータでは"["をワイルドカードととして認識します。この例で使用されている文字"["は正規表現で使用される文字であり"]"と対で使用しなければなりません。このようなファイル名を使用したい場合は-Pathパラメータの代わりに-literalPathパラメータを使用します。


まとめ

-Pathパラメータはワイルドカードを使用して、複数ファイルへ一気に同じ文字列を追記できるところがすごいですね。

ワイルドカードを使用できる分、-PathパラメータのNG例2のようにワイルドカード構成する文字を含むパスは指定できないという制限がありますが、-literalPathパラメータを使用すればこの問題は回避できます。

-Pathと-literalPathパラメータを使い分けるポイントとなりますね。

Sunday, September 28, 2008 11:48:54 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Friday, September 26, 2008

Hey, Scripting Guy! で紹介されたPowerShellトピックをまとめてみました。

ただし、2008年3月~2008年5月を除ききます。この期間中にも公開されていると思うのですが、リンク先を見つけられませんでした。

何か情報をお持ちの方おりましたら、連絡いただけると助かります。

どうでしょうか? この一覧を見るとPowerShellに魅力を感じませんか?

Friday, September 26, 2008 11:52:08 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Tuesday, September 23, 2008

PowerShellで配列を作成するには、実は2種類の方法があります。

一般的なのは、値をカンマ(,)で区切って代入する方法。

PS > $a = 1,2,3,4,5

もう1つは@を使用する方法です。

PS > $a = @(1,2,3,4,5)

この@を使用すると、区切り文字はカンマではなくセミコロン(;)も使用することが可能です。

PS > $a = @(1;2;3;4;5)

是非、試してみてください。

Tuesday, September 23, 2008 10:52:38 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback

PowerShellで配列を作成する場合は

$a =1,2,3,4,5

のようにカンマで区切って記述します。この場合は1から5までの値を持つ1次元配列が作成されます。

各要素へアクセスするには

変数名[要素番号]

でアクセスでき

PS > $a[3]
4

上記のように記述した場合は、要素番号が3(要素番号は0から始まる)の値にアクセスできます。

実は要素番号には-1を指定することが可能で、

PS > $a[-1]

と記述した場合と

PS > $a[4]

と記述した場合は同じ要素を指し示します。

最後の要素の値を取得するには、要素番号に-1ということを覚えておけば、要素数がわからなくても最後の要素の値を取得できますので活用してみてください。

Tuesday, September 23, 2008 12:04:19 AM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Wednesday, September 10, 2008

今回は.NETアセンブリのロードについて説明したいと思います。

PowerShellは.NET Frameworkを基盤としており、あらかじめロードされているアセンブリがいくつかあります。

しかし、実際にやりたいことを実現するためには、ロード済みのアセンブリだけでは足りない場合があり、こういった場合は目的とするアセンブリをロードして、PowerShell上から使用できる様にする必要があります。

ロード方法ですが

[reflection.assembly]::LoadWithPartialName

を使用します。

たとえば Microsoft.VisualBasic 名前空間を使用できるようにするには

[reflection.assembly]::LoadWithPartialName("Microsoft.VisualBasic")

のようにしますが、このまま実行した場合は結果がAssemblyオブジェクトとして返されコンソールに表示されていまいます。

スクリプトの中からロードする場合には、出力されると邪魔な場合もありますので先頭に[void」を付加して

[void][reflection.assembly]::LoadWithPartialName("Microsoft.VisualBasic")

とすることをおすすめします。メッセージが必要な方は[void]は付加しないでください。

 

dllファイルのアセンブリのロードについても紹介しておきましょう。

この場合は

[reflection.assembly]::LoadFrom(dllファイル名)

を使用します。

こちらも同様にロード時にメッセージが出力されるので、回避したい方は先頭に[void]を付加してください。

せっかくなので1つサンプルを紹介します。

下記は Microsoft.VisualBasic をロードしてStrConvメソッドを使用できるようにして、ひらがなとカタカナを相互変換できるようにするものです。

PS C:\Work> [void][reflection.assembly]::LoadWithPartialName("Microsoft.VisualBasic")
PS C:\Work>
PS C:\Work> $vbHiragana = [Microsoft.VisualBasic.VbStrConv]::Hiragana
PS C:\Work> $vbKatakana = [Microsoft.VisualBasic.VbStrConv]::Katakana

上記を入力し終えたら、「ひらがな」から「カタカナ」へ変換してみましょう。

PS C:\Work> [Microsoft.VisualBasic.Strings]::StrConv("あいうえお", $vbKatakana)
アイウエオ

ついでに「カタカナ」から「ひらがな」へも変換してみましょう。

PS C:\Work>  [Microsoft.VisualBasic.Strings]::StrConv("アイウエオ", $vbHiragana)
あいうえお

このようにアセンブリをロードし、ぜひPowerShellで.NET Frameworkを有効活用してみてください。

Wednesday, September 10, 2008 11:18:54 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Tuesday, September 09, 2008

VB.NETやC#からPowerShellのコマンドレットを使用する その2

今回紹介する例は Creating a Console Application that Runs a Specified Script を参考にしたものです。
(というか使用しているコマンドレットを変更し、自分なりの解説をしてみただけ...です)

前回、VB.NETやC#からコマンドレットを実行するには、invokeメソッドを使用することについて説明したわけですが、このメソッドは3つのオーバーロードメソッドがあります。

このオーバーロードメソッドの中に引数が3つあるタイプのもを使用すると、実行するスクリプトへ値を渡したり、エラーを受け取ったりすることが可能です。

今回実験するコードは
VB.NETやC#からGet-Serviceコマンドレットを使用して、サービス名が"WMI","Messenger","HIRO"というデータを取得するというものです。
このときサービス名が"HIRO"というものは存在せずエラーが発生することを想定しています。

まずは、Get-Serviceでサービス名が"WMI","Messenger","HIRO"のデータを取り出す方法ですが、PowerShellでは

PS > $SrvNames = "WMI","Messenger","HIRO"PS > $SrvNames | Get-Service -Name { $_ } 

のように記述します。

VB.NETやC#で実現するには、前回説明したように事前に参照設定に System.Windows.Management 追加し、Imports(VB.NET)やUsing(C#)で名前空間を追加してから行ってください。

ではコードの説明です。
(1)Get-Serviceコマンドレットで取得するサービス名をString型の配列で事前準備しておきます。
(2)実行するスクリプトを準備します
(3)スクリプト実行用のinvokerを準備します
(4)スクリプト実行時に発生するエラーを格納する変数を準備します
(5)For Eachでinvokeメソッドで取り出した結果を処理します。(この辺の説明は前回を参照)
   ここで使用しているinvokeメソッドですが、第1引数に実行するスクリプト、第2引数にスクリプトへ渡す値、第3引数にエラーを受け取る変数 をそれぞれ指定しています。
   第2引数に渡した値は、変数 script の$SrvNamesに渡されます。
(6)受け取ったエラーをFor Eachで出力します。

VB.NET

VB.NET
Imports System.Management.Automation

Module Module1

    Sub Main()
        Dim serviceNames As String() = {"WMI", "Messenger", "HIRO"}・・・・・(1)
        Dim script As String = "$input | Get-Service -name {$_}"・・・・・(2)
        Dim invoker As New RunspaceInvoke・・・・・(3)

        Dim errors As System.Collections.IList = Nothing・・・・・(4)
        For Each result As PSObject In invoker.Invoke(script, serviceNames, errors)
            Console.WriteLine("{0,-15}{1}", _・・・・・(5)
                              result.Members("Status").Value, _
                              result.Members("Name").Value)
        Next

        For Each er In errors・・・・・(6)
            Console.WriteLine(er.ToString())
        Next

        Console.ReadLine()
    End Sub

End Module

C#

using System.Management.Automation;

namespace Sample2
{
    class Program
    {
        static void Main(string[] args)
        {
            string[] serviceNames = new string[] {"WMI", "Messenger", "HIRO" };・・・・・(1)
            string script = "$input | Get-Service -name {$_}";・・・・・(2)

            RunspaceInvoke invoker = new RunspaceInvoke();・・・・・(3)
            System.Collections.IList errors = null;・・・・・(4)

            foreach (PSObject result in invoker.Invoke(script, serviceNames, out errors))・・・・・(5)
            {
                Console.WriteLine("{0,-15}{1}",
                                  result.Members["Status"].Value,
                                  result.Members["Name"].Value);
            }

            foreach (PSObject err in errors)・・・・・(6)
            {
                System.Console.WriteLine("    error: {0}", err.ToString());
            }

            Console.ReadLine();
        }
    }
} 
Tuesday, September 09, 2008 1:30:15 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Monday, September 08, 2008

VB.NETやC#からPowerShellを利用するには、System.Management.Automation.dllを使用します。

これは通常、システムディレクトリの下の windowspowershell\v1.0\SDK にあります。

この dll を参照設定で追加し、

VB.NETなら


Imports System.Management.Automation

C#なら


Using System.Management.Automation;

を追加します。

VB.NETでPowerShellのGet-Commandコマンドレットを使用する方法について見てみましょう。 

VB.NET内でPowerShellのコマンドレットを実行するには RunspaceInvokeクラスのInvokeメソッドを使用します。

最初にRunspaceInvokeクラスのインスタンスを作成します。 (1)

次にInvokeメソッドを利用して、PowerShellのコマンドレットを実行するのですが、このInvokeメソッドはPSObject型の値を返してきます。

Get-Commandコマンドレットは、複数の値(PSObject型のコレクション)を返すのでFor Eachを使用して1つずつ変数resultへ取り出します。(2)

resultへ代入された個々の値へアクセスするにはMembersプロパティを使用します。(3)

この例ではNameの値を取り出すことになります。

VB.NETのソース

Imports System.Management.Automation

Module Module1

    Sub Main()
        Dim invoker As RunspaceInvoke = New RunspaceInvoke() 

        For Each result As PSObject In invoker.Invoke("Get-Command") 
            Console.WriteLine(result.Members("Name").Value)
        Next

        Console.ReadLine()
    End Sub

End Module 

C# のソース

using System.Management.Automation;

namespace Sample1_CS
{
    class Program
    {
        static void Main(string[] args)
        {
            RunspaceInvoke invoker = new RunspaceInvoke();

            foreach (PSObject result in invoker.Invoke("Get-Command"))
            {
                Console.WriteLine(result.Members["Name"].Value);
            }

            Console.ReadLine();
        }
    }
} 

 

ちなみに、Get-Dateコマンドレットのように結果を1つしか返さないようなコマンドレットの場合は

invoker.Invoke("Get-Date")(0).Members("DateTime").Value

 

のように値を取得することもできます。

Monday, September 08, 2008 12:54:44 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback
Sunday, September 07, 2008

PowerShellでスタティックなメンバーを取り扱うにはコロンを2つ続けて::と記述します。

スタティックなメンバーとは何か?

これは、オブジェクトのインスタンスを作成しなくても呼び出しが可能なプロパティやメソッドのことです。

Get-Memberコマンドレットを使用するとスタティックなプロパティとメソッドを使用することが可能です。

このとき、パラメータとして-staticを使用します。

では、一例としてGet-Memberを使用して、[Text.Encodin]のスタティックプロパティ/メソッドを調べてみましょう。
PS > [Text.Encoding] | Get-member -static
TypeName: System.Text.Encoding
Name MemberType Definition
---- ---------- ----------
Convert Method static System.Byte[] Convert(Encoding srcEncoding, Encoding ...
Equals Method static System.Boolean Equals(Object objA, Object objB)
GetEncoding Method static System.Text.Encoding GetEncoding(Int32 codepage), ...
GetEncodings Method static System.Text.EncodingInfo[] GetEncodings()
get_ASCII Method static System.Text.Encoding get_ASCII()
get_BigEndianUnicode Method static System.Text.Encoding get_BigEndianUnicode()
get_Default Method static System.Text.Encoding get_Default()
get_Unicode Method static System.Text.Encoding get_Unicode()
get_UTF32 Method static System.Text.Encoding get_UTF32()
get_UTF7 Method static System.Text.Encoding get_UTF7()
get_UTF8 Method static System.Text.Encoding get_UTF8()
ReferenceEquals Method static System.Boolean ReferenceEquals(Object objA, Object objB)
ASCII Property static System.Text.Encoding ASCII {get;}
BigEndianUnicode Property static System.Text.Encoding BigEndianUnicode {get;}
Default Property static System.Text.Encoding Default {get;}
Unicode Property static System.Text.Encoding Unicode {get;}
UTF32 Property static System.Text.Encoding UTF32 {get;}
UTF7 Property static System.Text.Encoding UTF7 {get;}
UTF8 Property static System.Text.Encoding UTF8 {get;}

 

エンコーディングとしてShift-Jisを取得する場合は GetEncodingメソッドを使用します。

この場合は下記のように記述します。

$enc = [Text.Encoding]::GetEncoding("Shift-Jis") 

 

 スタティックなメンバーを使用したい場合は::を使用、調査するときはGet-Memberコマンドレットと-staticパラメータをを活用してみてください。

Sunday, September 07, 2008 11:49:40 PM (Tokyo Standard Time, UTC+09:00)  #    Comments [0]  |  Trackback

Theme design by Jelle Druyts

Pick a theme: