desktop.ini Manager 公開

Desktop Ini Manager

現在公開中のバージョンはv3.4.2だが、v3.5.0をプレリリース予定

3.5でTabを追加して、フォルダー比較とGrepをTAB化して、履歴を残せる様にした。

AIコーディングで開発したが、この手のアプリをあっさり開発出来るのはかなり凄いと思った。

元々、業務で使うので、WM(WinMerge)やBC(Beyond Compare)を使って差分を確認していた。

今回DIM(desktop.ini Manager)を作った切っ掛けは、フリーランスで様々な現場を渡り歩いていると、色々なソリューションに対応する必要があるが、ある程度出来上がっているソリューションの改修が主で、今はWindows11対応のカスタマイズを行っている

開発言語はC#で、VisualStudio2022で開発しているのだが、運用としては、VPN-PCがあり、ここに メインリモートリポジトリがある。

このPCは外部アクセス出来ない為、VisualStudioが動かせない

そこで、許可されたUSBメモリーを使いローカルリポジトリを開発PC側にコピーしてそこで開発する流れとなる。

この開発が面倒なのは、開発中にVPN側のリモートリポジトリが更新されてしまうため、ローカル開発のベースのブランチの内容が常に変化してしまうので、開発中のコードは最終的にもう一度最新の状態にしたブランチに乗せ直して確認しなくてはならない。

この手順で、色々問題があって、VPN側で共有している定数や定義の中身まで変わる事があり、その通達が有るのか無いのか遅いのかやってないのか非常に粗暴な更新が成されるため、一度、前提にしていた、定義がリモート側で削除されていて、Mergeも面倒だったのでファイルコピーで変更ファイルのみ上書きで更新した。

当然、ローカルではビルドが成功するが、リモートに上げたブランチでビルドエラーが発生した。

原因は、前提にしていたClassや定義が削除されていたからなのだが、最終チェックを強く義務づけられる始末。

と言う事で、この辺りの面倒な手順をいかにスムーズに行うか既存のツールでは作業フローにのせられなく、オリジナルで、俺が、俺の為に、俺専用のツールを作る事にした。

リポジトリの容量は約2GB弱、約4万ファイルある。

AOSPの開発経験がある俺にとっては大した容量ではないのだが、それでも個人開発のレベルはゆうに超えており、複数のソリューションにプロジェクトが約300程ぶら下がっている。

対応するのはその1つのプロジェクトに集約出来るが希にプロジェクトを跨がって共通のリソースやAPIをコールして開発する

最初は、アプリのタイトル通り、desktop.iniを設定して、フォルダーアイコンを視覚的に自分の担当する機会の多いプロジェクトに付けるつもりで、開発していたが、使ううちに、色々と開発手順を全て1アプリで出来れば便利だと思って、一本に面倒を全部詰め込んでみた。

当初の開発動機がフォルダーアイコンの変更だったのでdesktop.ini Managerとしたわけだが、完成してみると、ソリューションマネージャーと言っても過言はないのだが、初心を名前に込めてそのままのアプリ名で完成させた。

まず、最初の問題はVPN側のリポジトリをローカルのリポジトリにコピーする際に、差分を確認する必要があり、影響する部分が変更されたか、コンフリクトの確認も最初に行い、同じファイルが無いかをチェックする必要があり、WMやBCの出番になる。

そこで、ファイルの羅列ならMFTが速いだろうと思い、MFTベースで実装したのだが、確かにMFT速かったが、管理者権限に昇格させる必要があって、これは前回開発したResourceHackerReplacerで知見があったので、問題はなかったが、MFT便利そうで意外に制約が多く広範囲に使えなかった。

それは当然で、CloudやNASのMFTはないので、その場合はフォールバックで、自前のファイル走査を走らせる様にして作って見た。

しかし、4万ファイルあるとMFTなら一瞬でフォルダーツリーを構築できるのだが、自前のファイル走査では数分かかって再帰分析するのでちょっと使い物にならないと思ったので、普段、構成を確認するために使うTreeコマンドを思いたち、これなら直ぐにTreeが取得出来ると思ったのだが、Treeコマンドは、システム属性を付けたフォルダーを落としてしまう。

desktop.iniを仕掛けたフォルダーを見てくれないので、次はDIRコマンドを試して見た。

これが中々早く、属性などの影響もなく中々高速にツリーの構築が出来、まずはDIR版としてMFTは全て削除した。

それで、一通り作ってみて、最適化を重ね、使えるレベルにはした物のWM/BCにはまだまだ及ばない

そこで、これらのツールはどうやってツリーを作っているのか興味があったので、各サイトから情報などを集め、FFFE(FindFirstFileEx)を使っているようなので、FFFEをツリーのエンジンにすることに切り替えてみた。

これが中々の早さで、FFFEで一回のスキャンで必要な情報とIndexを作成し、それを書く機能で使う様にしたら、激早でWM/BCの速度には至らない物の遜色無い速度でツリーを表示することに成功した。

後はNASのフォルダーのツリー構造の取得で、FFFEでもここではSMBとの通信が絡むため急ブレーキ状態になるのだが、BCはNASでも秒でフォルダー構造を表示していたのに驚いて、その方法を探ってみた

すると、NASの場合はルート以下のレベル1のフォルダーをまずは表示して、バックグランドでファイルを走査するUIを止めない設計をしていると言う事が書かれていたので、それを真似した。

ただ、ルートだけをツリービューに表示すると後から枝を付けられないので、ダミーのサブフォルダーも同時に追加する様にして、ここはほぼBCレベルの速度でツリーを構築出来る様になった。

アプリもFFFEエディションとしてBlanchを切り直してDIR版は開発を閉じ、現行はFFFE版にした。

フォルダー比較で俺にとって必要な比較はコードのある部分で、binとかobjは各環境で作り直されるので、最初から見ない様にして、いつも比較対象にしている内容に絞り込む事でかなり高速に比較出来る様になった。

利点としてはResourceフォルダーの画像やアイコンもサムネイル表示でリスト上でも確認出来て、これは既存のツールにはない、自作としてオリジナルな利便性を盛り込み、Stubで動かしている各設定ファイルとして定義しているJSONが山ほどあるのだが、この辺の差分も確認する必要があった。

フォルダー比較の次はDIFFビューを追加して中身の確認をするのだが、Mergeツールには既存の優秀なエディターがあるので、読み取り専用のDIFF VIEWを作れば事足りるので、読み取り専用に特化して実装し、必要があれば外部のDIFF VIEWにファイルを送る事で対応する割り切った設計にしている。

画像も同様にDIFF VIEWに左右並べられるようにした。

後はバイナリファイルはDIFF VIEWではそもそも扱わない切り捨てを行った。

バイナリの差分を見たところで、結局どちらを採用するかしかなく、俺にはノイズなので切り捨てた。

後は、このDIFF VIEWだが、従来の概念だと、リスト上の差分ファイルを選択して確認し、また、リストに戻り、差分ファイルを選択する行き来を余儀なくされる。

俺はこれが面倒で時間の無駄だと思ったので、DIFF VIEW上で次の差分、次の差分とそのまま比較内容を取り込める様にして連続で差分ファイルのみを確認できるUIにした

これで、数の多いStubの設定ファイルも連続で見られ、画像のリソースも確認出来るので、これは今まだこう言う機能を実装してないのが不思議なくらい置き去りにされた機能だと思ったほど便利だった。

次にメイン画面でソリューションエクスプローラーとフィジカルツリーの2つを同時に確認したいと思ったので実装した。

これは、VisualStudioなどのソリューションエクスプローラーは実体のフォルダー構成とは違っていて、IDE内で自由に纏めているため、実体のファイルを探すのに結構戸惑うことがあり、IDEのソリューションエクスプローラーと同じ表示になるようにして作ってみた。

また、右クリックでエクスプローラーで表示させたり、ファイルリストをエディターに送るなどの機能を追加して、目的のファイルへ、快適にアクセス出来る機能を追加した。

あとは、バッチファイルも多様していたので、Launcherとしてバッチファイルも実行して、%d、%f、%nの引数を持たせ フルディレクトリ、フルパスファイル名、ファイル名のみをバッチの引数として使う事で、色々と便利なバッチを作成してDIM上で実行出来る様にした

次に、Grep機能だが、既存のGrepにVS-CODEを活用していたのだが、VS-CODEのGrepは非常に優秀なんだが、ルートからヒットするので、手を入れなくてもいプロジェクトの中も対象になってしまう。

設定で、複数のパスを定義できるとは思うが、それをやるくらいなら折角フォルダーリストを構築していうので、GREPしたいフォルダーをチェックして簡単に複数のツリーの違うフォルダーを巡回出来る様にした。

後は、GREPの結果もエディターに送れる様にし、肝心なのは同じリストに次のキーワードを追記し続ける仕様にした。

別々のキーワードを1つのリストに表示する試みは既存のGREPツールでも見かけない画期的なGREPなので、Scoped Code Grepとして実装したので、これが以外に便利だとわかった。

これで大体の機能は盛り込めたが、ソリューションツリーを構築するので、ついでにコマンドでVisualStudioを開かなくてもビルド出来る様にした。

そして、フォルダー比較のリストを眺めていると、変更ファイルだけをパス構造のままZIPに出来れば便利だと思った。

同期する対象もSource、Targetとして、双方向でロボコピーの様な同期機能を実装していたので、その同期先をZIPにすれば良いだけだと思い必要なファイルだけで簡単に構造を持たせたZIPを作成出来る様にした。

この構造を維持したZIPが出来るツールは探したが見つからず、GITのコマンドでHEADの変更ファイルを構造を保ってZIPにするコマンドはあるが、差分ファイルのみで、同時に同一ファイルを含めたい場合に対応出来ないし、フォルダーを跨がってZIPを作る発想は意外に見つからなかったので便利になった。

それまでは空のフォルダー構成を作成為て、そのフォルダーにファイルをコピーしてルートからZIP化することでやっていた事がサクッと無駄なく出来る様になった。

ザックリとはここまでの機能を実装して完成、実運用でも想定通り素早く目的の対応ができるツールに仕立て上げた。

速度もBC/WMと比較しても遜色無く、DIMは俺の作業に特化した分、より効率が上がっている。

BC/WMが悪いわけでは無く、機能など長年のノウハウの元開発を続け、世界中で利用されている事は賞讃に値するのだが、俺の今やりたい事に特化したDIMはリスペクトとは別の次元で便利になっている。

最初はフォルダーにマーキングするのが目的だったが、結局フォルダー比較にGrep機能を足して、IDEのビルドも実行出来る統合アプリとして使える為、VisualStudioを開かず開発が出来る様になった。

ただ、コーディングルールでnuGetを使っている為、最後はIDEで開いてフォーマットを調整したりチェッカーを走らせるので、それは最後の最後、一回だけで済ませるようにし、普段はVS-CODEやMIFESでサクサクコーディングしてテストしたり出来る様になった。

元々、フリーランスでいきなり巨大なツリーを見てチケットに対応する必要があり、即戦力を期待されている。

しかし、ドメイン理解があるはずのプロパー自体もチケットをこなすにはどこを見たら良いとか細かく説明できないし、仕様書の場所を投げられるが、内容が更新されてないとかで結局自力でコードを見て理解するしかない

そのためにはF11の連打で腱鞘炎になってしまう

ある意味DIMは腱鞘炎防止レストみたいなものになった

今対応しているのがC#なので、過去AndroidやJavaなどのWEB系も今後、対応する事になったら別バージョンを開発するが、今は今の現場専用のこのDIMで十分な仕上がりで、誰よりも早くチケットを消化して快適な開発ワークを満喫している。

コメント