at backyard

Color my life with the chaos of trouble.

go installの挙動がおかしいと思ったら案の定cacheでした

Goでpackageをinstallする際に特定のブランチを指定して、下記のようにインストールしていた。

# go install <package>@<branch>
go install github.com/shinshin86/go-leet@add-package-leet

上のパッケージは実際にあるもので、下記になる。
(Goのパッケージ周りに関する理解がまだ追いついていなくて、学習がてら作成したようなPull Requestとなっている。)

github.com

で、このブランチで最初Go的には誤っている内容でコミットをしてしまった。

main パッケージに関する問題で、この時点で go install を行うと、下記のようにエラーになった。

$ go install github.com/shinshin86/go-leet@add-package-leet
package github.com/shinshin86/go-leet is not a main package

で、上の問題は修正してもう一度コミットしたのだが、結果が変わらない。
ローカルで go buildするとビルドには成功するし、調べてもソースコード自体は問題なさそうだ。

そのため、これはgo install 時のキャッシュが悪さをしているのではないかと思い、キャッシュを削除するコマンドを探したのだが、今回のケースに該当するものが見つけられなかった。

go cleanあたりに該当するものがありそうで試行錯誤していたのだが結局ダメで、下記のディレクトリ内にある該当するパッケージをすべて手で削除することでキャッシュをクリアできた。 (installコマンドを実行した分のパッケージがこのディレクトリ内には格納されていて、それらをすべて削除した)

open $GOPATH/pkg/mod/github.com/shinshin86/

これで良いのかはわからない。良い方法ありましたらコメントいただけると幸いです。

go clean --modcacheを用いてキャッシュをクリアする

go clean --modcache を用いた場合、installされたモジュールを削除してくれるようだ。

pkg.go.dev

実際に go clean --modcache を実行すると、上で書いたディレクトリが削除されることを確認している。

ただ、この後に go install <package>@<branch> とやると、ダウンロードはされるのだが、修正前のversionがやはりダウンロードされてしまう。
該当するディレクトリに行き、ソースコードを見ると修正前のソースコードがある。

ちなみに今回は go install <package>@<branch> という形で特定のブランチを示した形としたが、これは go install <package>@latest というように最新を指定した場合でも同様の挙動となる。

この状態で上のやり方で直接ディレクトリを削除しに行ってから、再度同じようにinstallすると、今度は最新のものが反映される。

さらには go install <package> としてバージョンを指定しない場合はディレクトリを直接削除することなく、修正後の最新がインストールされるようだ。

これはもしかしてバグなのでは?と思って、Goのリポジトリにissueをあげてみた。
( go install <package>@latest とした場合はその時点で最新のpackageがインストールされるべきなのでは?と思ったからだ)

github.com

そしてこちらのイシュー内ですぐにコメントを頂いたのだが、Goでは参照のためにパッケージのキャッシュを短期間行うらしい(詳細はイシュー内のコメント参照)。
よって、これは仕様通りの挙動ということだった(と私はコメント受けて認識している)。

参照すべきドキュメントも教えてくれた。

下記のドキュメントについてはページ内で proxy と検索すべし、と教えていただいている。

go.dev

proxy.golang.org

これらのドキュメントについてはまだ読み込めていないのだが、後日また確認してみようと思う。

キャッシュを無視して最新のgoのパッケージをインストールする方法

後日調べた結果、

GOPROXY=direct go install <package>@latest

というように、環境変数 GOPROXY に対して direct を指定することでcacheを無視してインストールすることができた。

これでGitHubにあげたけど、キャッシュのせいで本当に最新のものがインストールできない、という事態は回避できる。