この記事はほぼ自分用メモです。
概要
- GOPATH, GOROOT, go mod を理解できてなくていろんなところでつまずく
- goenv 使わない限り GOROOT は気にしなくてもよさそうだから、とにかく GOPATH と go mod を理解したい
- 以下の記述はこれらのページを参照して自分用に整理したものなので、不明点・曖昧箇所があった場合はこちらを参照すること
Go Module が導入された理由
Go 1.11 以前のモード(のちに GOPATH mode
と呼ばれる)は、いろんなプロジェクトのコードを全部 GOPATH
以下で管理していたため、ソースコードを好きな場所に置けなかったり、プロジェクト毎に異なるバージョンのパッケージを使うことができない問題(GOPATH汚染問題)があったため、これを解消するために導入された。
モジュールとパッケージの違い
- パッケージは特定の物理ディレクトリ内全部
- モジュールは go.mod ファイルのあるディレクトリ以下の全パッケージを内包し、バージョン毎に異なるモジュールと見なされる
歴史と経過
- GO 1.11 で導入された (
GO111MODULE
のデフォルトはauto
) - Go 1.16 で大幅変更
-
go install
動作変更(ビルド・インストール用となる) -
go get
はgo.mod
編集用となる -
GO111MODULE
のデフォルトがon
に変更 -
go build
,go test
ではgo.mod
が変更されなくなった
-
- Go 1.18 からは
go get
からバイナリインストール機能が削除された
Go Module と mode
- GOPATH mode: 全てのソースコードとバイナリが
GOPATH
下に入り、パッケージは最新バージョンのみ使える。 - module-aware mode: バイナリのみ
GOPATH
下に入り、ソースコードは任意のディレクトリに置ける。パッケージはバージョン指定して使える。
GO111MODULE 環境変数による切り替え
- on: module-aware mode になる
- off: GOPATH mode になる
- auto: go.mod が存在するディレクトリでのみ module-aware mode になる
今更 GOPATH mode を使う理由はないので、GO111MODULE
は on
にするか、そもそも定義しなくてよい(Go 1.16 以降はデフォルト on
になったため)。
go.mod の役割
- モジュール名が記述される (
module github.com/tmishina/myapp
) - 使う go バージョンと依存モジュール情報などを含む
go install と go get
-
go install <package>@<version>
で任意のモジュールをインストールできる。このとき、go.mod は変更されない- 例:
go install golang.org/x/tools/gopls@latest
- 例:
-
go get
は、現時点では忘れてよい。Go 1.18 からダウンロードする機能はなくなる。
開発時の基本な流れ
-
go mod init github.com/tmishina/myapp
を実行してgo.mod
生成 - ソースを書く(
import
記述がソースコード内に現れる) -
go mod tidy
実行することで、不要モジュール削除・不足モジュール追加が自動的に行われる(よって通常の開発プロセスにおいてはgo install
もgo get
も実行不要)