privateなcrateどうしてます?
Rustで開発しているとき、crate分割したり、社内用のライブラリを整備したりすると複数のprivateなcrateを扱う必要が出てきます。
publicだったらcrates.ioを使ってしまえばいいのですが、privateなcrateを管理する場合のcrateの扱いはどうしていますでしょうか?
以下使える選択肢をあげて比較してみたいと思います。
crateが同一レポジトリにある場合
単純にpathを使えば参照できるので簡単ですね。
[dependencies]
sample-crate = { path = "../sample-crate" }
crateがレポジトリをまたがる場合
この時は割と悩ましいです。
気にせずpathを使う
全部の開発環境で複数のレポジトリを展開する構造が一致させて運用させます。
pros
- 先ほどと同様で簡単。
cons
- 同じ位置にcloneされると期待しないといけない(社内ツールなど?)
- CI/CDでは使いずらい(元のレポジトリも調達する必要がある)
- コミットごとにライブラリが変わってしまう…。
- どのコミットがライブラリ側のどのコミットを参照していたかわからない
- 作業するレポジトリごとに参照元のレポジトリの状態を管理しないといけない
git submoduleを使う
pathを使うものの亜種で、cargoの機能を使わずに管理します。
pros
- 割と枯れている方法なので導入しやすい。
cons
- git submoduleの管理自体が面倒くさい…。
- ライブラリのバージョンがいくつであるかを追いにくい
- tagで管理すれば問題はないか?
- .gitmodules見ないといけないのは微妙そう
- tagで管理すれば問題はないか?
ファイルをコピペする
管理とは呼べない代物ですね。最悪です。
pros
- 最初だけ楽。最初だけ
cons
- 管理できない
- 無秩序に変更がかかり始め、ライブラリとは一体何だったのだろうか状態になる。
dependenciesでgitを使う
以下のようにgitで依存関係を設定できます。
[dependencies]
sample-crate = { git = "https://github.com/sample-org/sample-crate.git" }
pros
- cargoで管理してくれるので楽
- gitのcommitで指定できるので開発中でも変更しやすい
- tag指定ならどのバージョンに依存しているかが明確
cons
- gitの認証が若干面倒
- commitで頻繁に対象を変えるとcargoのcacheが肥大化しがち
- 巨大なレポジトリなら容量を圧迫する
- gitで対象のcommitやbranch,tagが消えるとそのバージョンが使えなくなる
- tagが消えることはないでしょうが…
Alternate Registryを使う
crates.ioの代わりとなるregistryを用意して、そこから落とす方法です。
既存の3rd-partyなものを使ってもいいし、自前で管理することもできます。
サードパーティーのレジストリのリストがあるのでそこのものを使うか自前で用意してもいいです。
[dependencies]
sample-crate = { version = "0.1", registry = "sample-registry" }
pros
- cargoの仕組みで管理されるので楽
- バージョン管理もcrates.ioのcrateと同じように使える
- 依存関係のバージョンの解決などを行ってくれる
cons
- レジストリのコスト(管理コストまたがサービス利用料)が掛かる
- 認証の手間がある
まとめ
dependenciesでgitを使うのが一番手っ取り早くて楽だと思います。余計なインフラなしに簡単に導入できます。
ただ扱うライブラリが増えてくるならAlternate Registryを使うのがいいと思います。
Registryについての別記事も書いたのでそちらも参照してみてください。
(ちなみに自分は時間がなくて「ファイルをコピペする」の禁じ手をやってしまったものがあるので直したい…。CIで認証がうまくいかなったのだ…。)