PowerShell Core 6.0

PowerShell Core 6.0がリリースされました。ダウンロードはGitHubより各プラットフォーム用に公開されています。尚、インストールは全く別の場所に行われますので、既存のWindows PowerShellを残したまま行えるどころか、ZIPファイルでも提供されていますので、インストーラーを実行する必要でさえありません。)

PowerShell CoreはWindows PowerShellのオープンソース、クロスプラットフォーム版で、今後はWindows PowerShellの開発は5.1を最後のバージョンとし、メンテナンス程度になり、こちらの方に注力していくようです。

Windows PowerShellは.NET Frameworkベースになっていますが、PowerShell Coreは、.NET Core、正確には.NET Standardベースのものになっています。そのため、.NET Standardに準拠したライブラリなどは読み込める場合もありますが、Active Directoryなど、一部の機能は使用できませんので、そういった場合はWindows PowerShellと平行して使用することになるかと思います。

PowerShell Coreの何がいいのか?

特にLinuxやWindowsなど複数のプラットフォームを使用している場合において、同様の使用感、及び、スクリプト構文でCUIを利用することができます。尚、execなどの呼び出しに失敗し、挙動がおかしくなる場合があるので、Linux上でpwshに対してchshを行うのはおすすめできません。(目立ったところではSSHのスクリプト実行に失敗したり、Dropboxがゾンビ状態になったりします。)

.NET CoreのモジュールをCUIより呼び出すことが可能なので、例えば以下の要な構文が使えます。

(New-Guid).ToString().ToUpper()

この構文では、New-GuidはPowerShellのCmdletを使用していますが、これは[Guid]::NewGuid()とすることもでき、同じ形式の出力になります。

[Guid]::NewGuid().GetType() -eq (New-Guid).GetType()
True

実際はCmdletの実体は.NETのライブラリなので、内部的には同じような構造になっています。

Cmdletは例えば以下のような構成になっています。

using System.Management.Automation;

namespace cmdlettest
{
    [Cmdlet(VerbsCommon.Get, "Hello")]    
    public class TestModule : PSCmdlet
    {
        [Parameter(Position = 1)]
        public string Message { get; set; } = string.Empty;

        protected override void EndProcessing()
        {
            var output = "Hello World";
            if (Message != string.Empty)
                output += ", " + Message;
            WriteObject(output);
            base.EndProcessing();
        }
    }
}

これをコンパイルし、モジュールとして読み込むことで、Get-Helloのコマンドが使えるようになり、コマンドラインのパーシングなども自動で制御してくれます。もちろん一度コンパイルすると依存として読み込んでいる他のライブラリにプラットフォームの要件がない限りはPowerShell Coreを使用することのできる全ての環境で使用できます。

PowerShell Coreをダウンロードしたらまず行うべきこと

WindowsPSModulePathの導入

Windowsで使用している場合、以下のコマンドでWindowsPSModulePathを導入しておくと便利かも知れません。Windows PowerShellにより提供される一部のライブラリを使用できるようになります。

Install-Module WindowsPSModulePath -Force

ユーザーレベルで入れたい場合は以下のようにもできます。

Install-Module WindowsPSModulePath -CurrentUser -Force

その後、これは以下のコマンドで有効にできます。

Add-WindowsPSModulePath

尚、スタートアップファイルは$PROFILEですので、こちらに格納することによりPowerShell起動時に自動的に読み込まれます。

ヘルプファイルの更新

PowerShell Coreでは詳細なヘルプ情報を参照することができます。(UNIX系シェルでいうmanページのようなものです。)

これらのドキュメントは更新する必要があります。それを行うにはUpdate-Helpコマンドを使用します。このコマンドはAdministrator権限(Windows)、root権限(Linux等)で行う必要があります。(尚、Update-Helpが失敗する場合-Forceオプションをつけてやるとうまく行くかも知れません。)

どうしても更新が失敗する場合(UI Culture系の例外が発生する場合)それを無視する設定が必要になります。(日本語のヘルプはないので、英語のロケールを優先指定します。)

 -Force -ErrorAction SilentlyContinue -UICulture en-US, ja-JP

更新を行うと、例えばGet-Help Get-Processなどで参照できる他、Get-Process -?で行うこともできます。

最後に

PowerShell Coreがリリースされたことにより、Windows以外のプラットフォームでもPowerShellの利便性が享受できるようになります。スクリプトはプラットフォームを超えて動作する他、.NET Coreを使用して独自のCmdletを記述することができます。

スクリプト開発環境も整備されており、Visual Studio及び、Visual Studio Codeでスクリプトのデバッグができるようになっています。(Cmdletに関しても上記のように実体は.NETライブラリなので、.NET Core開発環境で開発可能。)

これまで特にWindowsとLinux間など共通のシェルスクリプト的な使い方ができなかったので、この点が便利です。(Windows上でUNIX系シェルを使用するにしても、WSLはほとんど別環境ですし、bashやCygwinなどもOSとしての作法が違うため、不便さがありました。)

NuGet経由で拡張が可能など、.NET Coreの機能が利用できるなど、便利な使い方ができそうです。

ReSharperが指摘してくれるコードスタイルのあれこれ

ReSharper(と同様のエンジンを内蔵しているRider)が指摘してくれるものにはいろいろな種類のものがあるのですがそのいくつかに関する考察。

Collection Initializerへの置き換え

次のようなコードがあったとします。

var list = new List();
list.Add(new Something() {unit = "One", value = 5});
list.Add(new Something() {unit = "Two", value = 6});

ReShaperは次のような置き換えを提案してきます。

var list = new List
{
    new Something() {unit = "One", value = 5},
    new Something() {unit = "Two", value = 6}
};

これは確かに冗長になりがちなのでシンプルな書き換えにするのにはいい方法。

Foreach文のLINQ式への置き換え

時々出てくるパターンとしてリストの中を辿りつつ内容に対して処理を行うパターン。foreachで辿るようなパターン、例えば次のようなパターンがあったとします。

foreach (var item in list)
{
     if (item.unit == "Two")
        result += item.value;
}

これは以下のように置き換えることを提案してきます。

var result = list.Where(item => item.unit == "Two").Sum(item => item.value);

処理が複雑になると可読性が失われたり、デバッグが複雑になったりすることがあるのでその点は注意です。

メソッドのstatic化

次のようなクラスがあったとします。

internal class Hoge
{
    private int _value;

    public int Foo(int v)
    {
        _value += v;
        return _value;
    }

    public int Bar(int v)
    {
        v -= 1;
        return v;
    }
}

ReSharperはこのうち、public int Bar(int v)をstatic化するように提案してきます。

internal class Hoge
{
    private int _value;

    public int Foo(int v)
    {
        _value += v;
        return _value;
    }

    public static int Bar(int v)
    {
        v -= 1;
        return v;
    }
}

これはインスタンス化を行うとその分、要求されるメモリが増えるので、必要がないものにおいてはVM内で共有したほうがいい、ということですね。

ただ、staticメソッドのインスタンス化はそのメンバを呼び出したタイミングで行われたり、ガーベジコレクションの挙動が普通とは異なってくるはず(というか、スコープから外れない場合は残存し続けるので、長期的に残り続ける挙動を示すはずです)のでその部分では注意が必要です。

JetBrains All Products Pack

最近JetBrainsのAll Products Packを購入したのでいろいろと。

まずはそれぞれのツールに関していろいろと書いてみる。

Rider

まずいちばん使っているのがこのRider。C#のIDEです。現段階で使っているのは.NET Core 2.0の機能を使いたいので、EAP版です。

ちなみにRiderはUnityと組み合わせ使うことも可能です。Linux版のUnity Editorと組み合わせて使用する場合に便利です。

機能面ではVisual StudioResharperを組み合わせたものに近いです。(Windows Formなどのビジュアルエディターはありませんが……。)

尚、Reshaperに関しても上位版であるResharper Ultimateが、All Products Packに含まれています。

プライベートではマルチプラットフォーム開発なので、あまり使う機会はなかったりしますが。(ただし、使う場合Visual Studio Communityでもちゃんと動作します。)

DataGrip

次によく使うのがDataGripです。DataGripはデータベース用のIDEです。

いろいろなデータベースをサポートしていて、SQL文を発行したり、内容を調べたりすることができます。

Gogland

GoglandはGoogleにより開発されている、Go用のIDEです。現在EAPで無料で使用できます。正式版では名前が変わるかも知れないようです。

IntelliJ IDEA Ultimate

IntelliJ IDEA UltimateJavaのIDEです。(正確にはJVMな言語は多くが対応しています。KotlinもJetBrainsが開発していますし、もちろん対応しています。)

尚、IntelliJ IDEA Ultimateにはオープンソース版のIntelliJ IDEA Communityも存在します。これ一本でJavaのアプリ、Androidのアプリなどを開発したりできます。プラグインを通してGoやPythonなどの他の言語も開発することができるようですが、挙動など言語特化のIDEがより言語に特化した動作をするようになっているようです。

個人的にはJavaはあまり使わないので、XSLTの編集などに使ったりする場合が多いです。

PyCharm Professional

PyCharm ProfessionalPythonのIDEです。。こちらもPyCharm Communityというオープンソース版の他、PyCharm Eduという教育目的に特化した特別版も存在します。

PhpStorm

PhpStormPHPのIDEです。あまり新規にPHPは少なくとも自分で書くことは少ないのですが、レガシーなコードはあるのでその保守に使用しています。

CLion

CLionはC/C++のIDEです。Linux上で時々C/C++を扱ったりするので、その場合に活用しているツールです。

RubyMine

RubyMineRubyのIDE。Rubyのコードは現在PHPよりも少ないのであまり出番はないですが……。

MPS

イマイチ使い方がよくわかっていないのが、このMPS。IDEというよりはメタ言語みたいなのですが……。

JetBrainsのAll Products Packは開発機材として個人的に買う場合は、そこまでは高くはないのですが(ビジネスとして買う場合はそれなりに高くなりますが……)それなりの額にはなりますが、今のところはその値打ちはあるように感じています。特に複数の言語を使う必要がある場合同じ使用感で複数の言語を扱えますので。