Go Wiki: GOPATH
GOPATH変数
標準ライブラリ以外の依存関係を使用するGo開発は、Goモジュールを使用して行われます。Goモジュールを使用する場合、GOPATH変数(デフォルトはUnixでは$HOME/go
、Windowsでは%USERPROFILE%\go
)は、以下の目的で使用されます。
go install
コマンドは、バイナリを$GOBIN
にインストールします。これはデフォルトで$GOPATH/bin
です。go get
コマンドは、ダウンロードしたモジュールを$GOMODCACHE
にキャッシュします。これはデフォルトで$GOPATH/pkg/mod
です。go get
コマンドは、ダウンロードしたチェックサムデータベースの状態を$GOPATH/pkg/sumdb
にキャッシュします。
GOPATH変数の詳細については、goコマンドドキュメントを参照してください。このページの残りの部分では、現在非推奨となっているGOPATH開発モードについて説明します。
GOPATH開発モード
Goモジュール以前は、依存関係を使用するGo開発は、短く「GOPATHモード」とも呼ばれる「GOPATH開発モード」を使用していました。GOPATHモードでは、go
コマンドはGOPATH変数を次の目的で使用しました。
go install
コマンドは、バイナリを$GOBIN
にインストールしました。これはデフォルトで$GOPATH/bin
です。go install
コマンドは、import "example.com/y/z"
のコンパイル済みパッケージファイルを$GOPATH/pkg/example.com/y/z.a
にインストールしました。go get
コマンドは、import "example.com/y/z"
を満たすソースコードを$GOPATH/src/example.com/y/z
にダウンロードしました。
GOPATH開発モードの非推奨化と削除
Goモジュールは、Goエコシステム全体にパッケージバージョンの概念を追加するためのGOPATH開発モードの代替です。
GOPATH開発モードからGoモジュールへの移行は、多くのGoリリースにまたがり、段階的に行われてきました。
-
Go 1.11 (2018年8月) では、
GO111MODULE
変数が導入され、デフォルトはauto
でした。GO111MODULE=off
の場合、go
コマンドは常にGOPATHモードを使用しました。GO111MODULE=on
の場合、go
コマンドは常にモジュールモードを使用しました。GO111MODULE=auto
(またはGO111MODULE
を設定しないまま)の場合、go
コマンドは現在のディレクトリに基づいてモードを決定しました。現在のディレクトリが$GOPATH/src
の外であり、ルートにgo.mod
ファイルがあるソースツリー内にある場合、go
コマンドはGoモジュールモードを使用しました。それ以外の場合、go
コマンドはGOPATHモードを使用しました。このルールにより、$GOPATH/src
で実行されるすべてのコマンドがauto
モードで影響を受けないようにし、ユーザーが他のディレクトリでモジュールを試せるようにしました。 -
Go 1.13 (2019年8月) では、
GO111MODULE=auto
モードが調整され、$GOPATH/src
の制限が解除されました。$GOPATH/src
内のディレクトリにgo.mod
ファイルがある場合、そのディレクトリまたはその下のディレクトリで実行されるコマンドはモジュールモードを使用するようになりました。これにより、ユーザーはインポートベースの階層でチェックアウトされたコードを整理し続けることができますが、個々のチェックアウトにはモジュールを使用できます。 -
Go 1.16 (2021年2月) では、デフォルトが
GO111MODULE=on
に変更され、常にモジュールモードが使用されます。つまり、GOPATHモードはデフォルトで完全に無効になります。もう1つのリリースでGOPATHモードを使用する必要があるユーザーは、GO111MODULE=auto
またはGO111MODULE=off
を明示的に設定できます。 -
Go 1.NN (???) では、
GO111MODULE
設定とGOPATHモードが完全に削除され、常にモジュールモードが使用されます。
GOPATH開発モードの削除は、GOPATH変数の削除を意味するわけではないことに注意してください。これは、このページの上部に記載されている目的のために引き続き使用されます。
FAQ
GOPATH変数は削除されるのですか?
いいえ。GOPATH変数(環境内またはgo env -w
で設定)は削除されません。このページの上部に記載されているように、デフォルトのバイナリインストール場所、モジュールキャッシュ場所、およびチェックサムデータベースキャッシュ場所を決定するために引き続き使用されます。
GOPATH/src/import/pathでコードを記述できますか?
はい。多くのGo開発者は、この規約が提供する構造を高く評価しており、モジュールリポジトリをチェックアウトしています。モジュールを開始するために必要なコードは、go.mod
ファイルだけです。go mod init
を参照してください。
別のリポジトリで行われた変更に対して、GOPATH/srcの1つのリポジトリをコンパイルするにはどうすればよいですか?
別のモジュールをビルドするときに、公開されていないあるモジュールの変更を使用する場合は、他のモジュールのgo.mod
にreplace
行を追加できます。
たとえば、golang.org/x/website
とgolang.org/x/tools
を$GOPATH/src/golang.org/x/website
と$GOPATH/src/golang.org/x/tools
にチェックアウトした場合、website
のローカルビルドでtools
の変更を自動的に使用するようにするには、$GOPATH/src/golang.org/x/website/go.mod
にこれを追加します。
replace golang.org/x/tools => ../tools
もちろん、replace
ディレクティブは$GOPATH
について何も知りません。同じ行は、2つを$HOME/mycode/website
と$HOME/mycode/tools
にチェックアウトした場合でも正常に機能します。
なぜGOPATH開発モードは削除されるのですか?
その核心において、GOPATH開発モードは基本的に、これらの種類のreplace
行をすべて自動的に提供するため、依存関係のためにビルドするコードは、コンピュータにチェックアウトしたコードです。つまり、ビルドは、忘れてしまった可能性のある古いチェックアウトの影響を受けます。つまり、同じトップレベルリポジトリの同じバージョンから開始した場合でも、あるマシンで取得するビルドは別のマシンとは異なる可能性があります。そして、取得するビルドは、同じプロジェクトの別の開発者が取得するビルドとは異なる可能性があります。Goモジュールは、これらの再現性の問題をすべて解決します。これらの問題の根本的な原因は、GOPATHモードにはパッケージのバージョンの概念がないことです。
再現性に加えて、Goモジュールはプロキシと安全なダウンロードを処理するための明確な方法を提供します。プロジェクトをgit clone
して依存関係を取得すると、それらの依存関係は、元の開発者が使用したのと同じビットであることを確認するために(go.sum
ファイルを使用して)暗号的にチェックされます。信頼できる部分は、トップレベルのgit clone
だけです。ここでも、これはGoモジュールがGOPATHモードとは対照的に、パッケージバージョンの概念を持っている場合にのみ可能です。
そして、Go自体の将来の進化のために、モジュールは、特定のファイルツリーが記述されているGo言語のバージョンを明確にマークします。これにより、問題のある機能(たとえば、多くの人が"1"
を生成すると考えているが、実際には"\x01"
(Ctrl-A)を生成するstring(1)
など)を、古いプログラムのビルドを維持しながら(古いバージョンのGo用に書かれたとして明示的にマークされているため)Goの後のバージョンで無効にすることができます。
このような例は他にもあります。
これらはすべて、今日のGOPATH開発モードでは不可能です。エコシステムを前進させ、GOPATHモードを廃止することなく、Goモジュールのこれらの重要な特性に本当に依存し始めることはできません。
(次のような質問もあるかもしれません。なぜこれらのことをGOPATHモードに追加しないのですか?答えは、実行した結果がGoモジュールであるということです。)
GOPATH開発モードを非推奨にすることが決定されたのはいつですか?
当初の計画では、Go 1.13でGOPATHモードを非推奨にすることでしたが、できるだけ多くのGoユーザーにとってモジュールをさらに堅牢にするために時間をかける必要があったため、非推奨はそのリリースから延期されました。issue #41330とgolang-toolsグループでの議論では、GOPATHを非推奨にするための残りのブロッカーは特定されなかったため、上記のタイムラインに記載されているように、Go 1.16でスケジュールされ、将来のリリースで削除される予定です。
GOPATH開発モードからGoモジュールへの移行についてさらに質問がある場合はどうすればよいですか?
リソースのリストについては、golang.org/helpを参照してください。それらが適切でない場合は、ここに問題を提出してください。私たちは皆がGoモジュールを採用することに成功することを望んでいます。
このコンテンツは、Go Wikiの一部です。