要約
アプリケーション開発時にレジストリや環境変数、設定ファイルといった外部設定値を楽に扱いたい。
単に設定を外に出したいだけなのに、わざわざ技術ごとに違う実装なんて書きたくない。
そんな.NET Framework ライブラリを作ろうとしています。
想定読者
- アプリケーションを1から設計する人
- 動けばいいではなく、長期的な保守コストを考えたい人
- Windows、C#で開発する人 (には限らない話ですが、サンプルコードはこの辺です)
課題
Windowsで動くようなアプリケーションを開発する際、タイムアウト時間といったスペック依存なパラメータや、待ち受けするポートNoといったPC全体の資源を使うパラメータは、後から変更できるよう実装すると思います。
その際使われる主なものを挙げると次があります。
- 設定ファイル
- 環境変数
- コマンドライン引数
- レジストリ (Windowsなら)
- アプリケーション構成ファイル(*.exe.config)
どれも守備範囲が違いますので、自由に選べばよいと思いますが、アプリケーションからするとどれであろうと同じで、アプリケーションの外から値を変更できる「外部設定値」ですよね?
それに対して、実装はそれぞれ違っていて、例えばコマンドライン引数なんかはパーサーを自分で書かないといけなかったり、レジストリはnullチェックが必要だったりと、気軽にパッと使えるものではありません。
また、特にポリシーなく思いつくまま外部設定値の読み込みを実装するとコード上にバラバラに実装されることになり、外部設置値として何が変更可能かわからなくなります。
それに、レジストリのキーや設定ファイルの使い方が微妙に違ったりとか一貫性が保てません。
以上より、アプリケーション開発における外部設定値について、次の課題があると思います。
- アプリケーション側から見ると同じなのに実装方法がまちまち
- ポリシーなく実装するだけでは一覧性や一貫性が無い
解決策
上記の課題を解決できるOSSライブラリがあれば、と思い探していますが、良いものは見つかりません。
需要がないのか、単に探し方が悪いのか・・・
C#の例ですが、次のコードみたいな感じで、優先順位付きで簡単に外部設定を取得することができたらな、と思っています。
// C#
[ApplicationRegistry(
BuiltInAccessors.CommandlineArguments,
BuiltInAccessors.EnvironmenetVariable,
BuiltInAccessors.UserRegistry,
BuiltInAccessors.MachineRegistry)]
)]
public interface ISettings
{
/// <Summary>
/// 待ち受けするポートNo
/// </Summary>
int PortNo { get; }
/// <Summary>
/// バックアップの保存先
/// </Summary>
string BackupFolder { get; }
}
static void Main()
{
int portNo = ApplicationRegistry.Get<ISettings>().PortNo;
}
この例だと、コマンドライン引数→環境変数→レジストリ(HKCU)→レジストリ(HKLM)の順に以下の場所を探します。
無ければ、下へ下へと探索していくという感じです。
- コマンドライン引数: --ISettings-PortNo=(数値) の値
- 環境変数: MYAPP_ISETTINGS_PORTNO の値
- レジストリ: HKCU\Software\MyApp\ISettings の PortNo
- レジストリ: HKLM\Software\MyApp\ISettings の PortNo
また、適当なコマンドで外部設定の仕様をレポート化してくれれば、一覧性の問題も解決できます。
Format-ApplicationRegistry.exe --input MyApp.exe --output "ExternalSettings.html"
レポートの例 その1
プロパティ毎に変更可能な外部設定一覧
![]() |
---|
レポートの例 その2
レジストリやコマンドライン引数等、外部設定の場所ごとの設定値一覧
![]() |
---|
開発中
ということで、自分で作っています。
需要があるかどうかわかりませんが、自分の仕事で使う可能性が高いので。
ちゃんと完成させるか、どこまで汎用性を持たせるかは、やる気次第ですね。
ちなみに、同じ目的で4年位前に一度作っていて、Nugetパッケージも公開していたのですが、
XMLベースということでいまいち煩雑で使いづらく、作り直しています。
そのため今回はバージョン2です。
それなりに完成したら、Qiitaに別の記事を投稿するつもりです。