Windows Package Manager (winget) で非公式リポジトリを使おうと検討したはなし

2021.06.11

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

しばたです。

先月開催されたMicrosoft Build 2021でVer.1.0がリリースされたWindows Package Manager (winget)ですが、その運用について色々検討した結果を本記事でざっくばらんに共有します。

なお、本記事ではwingetの基本的な使い方については解説しませんのでご了承ください。
(以前DevelopsIOで紹介してますので概念的な話についてはこちらをご覧ください)

wingetのデフォルトリポジトリ

wingetでは対象となるソフトウェアをGitHub(microsoft/winget-pkgs)上で管理していますが、GitHubではマニフェストのみ管理されリポジトリはAzure環境上に独自形式のデータを持つかたちとなっています。

winget source listコマンドで利用しているリポジトリ一覧を確認でき、デフォルトリポジトリ(winget)はhttps://winget.azureedge.net/cacheであることが分かります。

C:\> winget source list
Name   Argument
-----------------------------------------
winget https://winget.azureedge.net/cache

このリポジトリの構造は非公開なのですが、有志で解析してる人がそこそこおりStack Overflowでも議論されていたりします。

興味のあるかたは上記記事もご覧ください。

非公式リポジトリ (REST Repository) の現状

そしてwingetにはwinget source addコマンドでユーザー独自のリポジトリを追加する機能があるのですが、残念ながら現時点ではコマンドだけ用意されているが実際に利用することができない状態となっています。

C:\> winget source add --help
Windows Package Manager v1.0.11451
Copyright (c) Microsoft Corporation. All rights reserved.

Add a new source. A source provides the data for you to discover and install packages. Only add a new source if you trust it as a secure location.

usage: winget source add [-n] <name> [-a] <arg> [[-t] <type>]

The following arguments are available:
  -n,--name  Name of the source
  -a,--arg   Argument given to the source
  -t,--type  Type of the source

More help can be found at: https://aka.ms/winget-command-source

現時点の開発マイルストーンではREST APIをベースとした非公式リポジトリ(REST Repository)を作成可能にする予定であるものの正式リリースには至っていません。

ちなみにこのREST Repositoryのリファレンス実装はこちらになります。

現在絶賛開発中の様で今後変わるかもしれませんが、ざっとソースを見た感じ、

  • Azure上に構築する前提
  • Function Apps + Cosmos DB

となっています。

私の動機と妥協案

動機

私が非公式リポジトリについて調べているのは、個人でちょっと管理したいアプリや公式リポジトリに展開できない構造となってるアプリをお手軽に自分用の非公式リポジトリに置きたいという動機があります。

例えばAWSから提供されているAWS CLI 用の Session Manager pluginは常に最新バージョンのバイナリしかダウンロードできず、各バージョン毎のバイナリへのリンクが必須となる公式リポジトリには登録できない類のソフトウェアになります。
こういったソフトウェアのインストールを省力化するために自分用リポジトリで管理できたら嬉しいなと考えていました。

先行ツールであるScoopでは自分のGitHubリポジトリに独自のバケット(≒リポジトリ)をお手軽に作成できます。

これくらいの気軽さでwingetでも自分用リポジトリも欲しい感じでした。

ただ、残念ながら結果は前節の通り現状ではAzure上に重厚なREST API Serverを構築しなければならず非常にめんどうくさい感じです。
(将来的にはAzure環境以外で使える実装や軽量サーバーも登場する可能性はあると思いますが、もうしばらく待たなければならないでしょう)

妥協案

ということで、自分用リポジトリを作ることは諦めて、妥協案として以下のGitHubリポジトリを運用することにしました。

wingetではリポジトリを参照する他にローカルディレクトリにあるマニフェストファイルを参照してアプリケーションの管理を行う--manifest (-m)オプションがあります。

# --manifest -m オプションを指定するとローカルにあるマニフェストを参照してアプリケーションをインストールする
winget install -m <Path to manifest files.>

予め自分で作ったマニフェストをGitHubに登録しておきローカルにClone、--manifest (-m)オプションでCloneしたパスを指定することで自分用リポジトリの代替とします。

# 前述のSession Manager pluginをインストールする例
git clone https://github.com/stknohg/winget-manifests.git

winget install -m .\manifests\Amazon.SessionManagerPlugin\

あまりスマートではありませんが、私の場合は自分で管理したいソフトウェアもそう多くありませんし運用もお手軽なのでこれでやりたいことは実現できています。

おまけ : マニフェストの作成方法

wingetで管理するソフトウェアのマニフェストの仕様は以下に公開されています。

現時点での仕様(v1.0)では3種類のYAMLファイルにアプリケーション情報、インストール形式などを記述します。

この仕様を全部覚えるのは正直つらいので私は公式で提供されているwinget-createを使ってマニフェストを生成しています。
このツール(wingetcreate)を使うとウィザード形式でマニフェストを生成できますので非常に便利です。

# winget から wingetcreate をインストールする
winget install wingetcreate

# wingetcreate を起動するとウィザード形式でマニフェストを作成できる
wingetcreate new

(ウィザード形式でインストールバイナリのURL等を指定しマニフェストを生成できる)

アプリケーションによってはウィザードから生成された後にパラメーターの微調整が必要ですが大きな問題にはならないしょう。

最後に

ざっとこんな感じです。

もし私と同じ様にwingetで非公式リポジトリの利用を検討されている方がいれば参考にしてみてください。