@@ -125,22 +125,48 @@ type workspaceInformation struct {
125
125
hasGopackagesDriver bool
126
126
127
127
// `go env` variables that need to be tracked by gopls.
128
- environmentVariables
129
-
130
- // userGo111Module is the user's value of GO111MODULE.
131
128
//
132
- // TODO(rfindley): is there really value in memoizing this variable? It seems
133
- // simpler to make this a function/method.
134
- userGo111Module go111module
135
-
136
- // The value of GO111MODULE we want to run with.
137
- effectiveGo111Module string
129
+ // TODO(rfindley): eliminate this in favor of goEnv, or vice-versa.
130
+ environmentVariables
138
131
139
132
// goEnv is the `go env` output collected when a view is created.
140
133
// It includes the values of the environment variables above.
141
134
goEnv map [string ]string
142
135
}
143
136
137
+ // effectiveGO111MODULE reports the value of GO111MODULE effective in the go
138
+ // command at this go version, accounting for default values at different go
139
+ // versions.
140
+ func (w workspaceInformation ) effectiveGO111MODULE () go111module {
141
+ // Off by default until Go 1.12.
142
+ go111module := w .GO111MODULE ()
143
+ if go111module == "off" || (w .goversion < 12 && go111module == "" ) {
144
+ return off
145
+ }
146
+ // On by default as of Go 1.16.
147
+ if go111module == "on" || (w .goversion >= 16 && go111module == "" ) {
148
+ return on
149
+ }
150
+ return auto
151
+ }
152
+
153
+ // GO111MODULE returns the value of GO111MODULE to use for running the go
154
+ // command. It differs from the user's environment in order to allow for the
155
+ // more forgiving default value "auto" when using recent go versions.
156
+ //
157
+ // TODO(rfindley): it is probably not worthwhile diverging from the go command
158
+ // here. The extra forgiveness may be nice, but breaks the invariant that
159
+ // running the go command from the command line produces the same build list.
160
+ //
161
+ // Put differently: we shouldn't go out of our way to make GOPATH work, when
162
+ // the go command does not.
163
+ func (w workspaceInformation ) GO111MODULE () string {
164
+ if w .goversion >= 16 && w .go111module == "" {
165
+ return "auto"
166
+ }
167
+ return w .go111module
168
+ }
169
+
144
170
type go111module int
145
171
146
172
const (
@@ -149,8 +175,15 @@ const (
149
175
on
150
176
)
151
177
178
+ // environmentVariables holds important environment variables captured by a
179
+ // call to `go env`.
152
180
type environmentVariables struct {
153
- gocache , gopath , goroot , goprivate , gomodcache , go111module string
181
+ gocache , gopath , goroot , goprivate , gomodcache string
182
+
183
+ // Don't use go111module directly, because we choose to use a different
184
+ // default (auto) on Go 1.16 and later, to avoid spurious errors. Use
185
+ // the workspaceInformation.GO111MODULE method instead.
186
+ go111module string
154
187
}
155
188
156
189
// workspaceMode holds various flags defining how the gopls workspace should
@@ -804,20 +837,11 @@ func (s *Session) getWorkspaceInformation(ctx context.Context, folder span.URI,
804
837
return nil , err
805
838
}
806
839
807
- go111module := os .Getenv ("GO111MODULE" )
808
- if v , ok := options .Env ["GO111MODULE" ]; ok {
809
- go111module = v
810
- }
811
840
// Make sure to get the `go env` before continuing with initialization.
812
- envVars , env , err := s .getGoEnv (ctx , folder .Filename (), goversion , go111module , options .EnvSlice ())
841
+ envVars , env , err := s .getGoEnv (ctx , folder .Filename (), goversion , options .EnvSlice ())
813
842
if err != nil {
814
843
return nil , err
815
844
}
816
- // If using 1.16, change the default back to auto. The primary effect of
817
- // GO111MODULE=on is to break GOPATH, which we aren't too interested in.
818
- if goversion >= 16 && go111module == "" {
819
- go111module = "auto"
820
- }
821
845
// The value of GOPACKAGESDRIVER is not returned through the go command.
822
846
gopackagesdriver := os .Getenv ("GOPACKAGESDRIVER" )
823
847
// TODO(rfindley): this looks wrong, or at least overly defensive. If the
@@ -838,26 +862,12 @@ func (s *Session) getWorkspaceInformation(ctx context.Context, folder span.URI,
838
862
839
863
return & workspaceInformation {
840
864
hasGopackagesDriver : hasGopackagesDriver ,
841
- effectiveGo111Module : go111module ,
842
- userGo111Module : go111moduleForVersion (go111module , goversion ),
843
865
goversion : goversion ,
844
866
environmentVariables : envVars ,
845
867
goEnv : env ,
846
868
}, nil
847
869
}
848
870
849
- func go111moduleForVersion (go111module string , goversion int ) go111module {
850
- // Off by default until Go 1.12.
851
- if go111module == "off" || (goversion < 12 && go111module == "" ) {
852
- return off
853
- }
854
- // On by default as of Go 1.16.
855
- if go111module == "on" || (goversion >= 16 && go111module == "" ) {
856
- return on
857
- }
858
- return auto
859
- }
860
-
861
871
// findWorkspaceRoot searches for the best workspace root according to the
862
872
// following heuristics:
863
873
// - First, look for a parent directory containing a gopls.mod file
@@ -938,7 +948,7 @@ func defaultCheckPathCase(path string) error {
938
948
}
939
949
940
950
// getGoEnv gets the view's various GO* values.
941
- func (s * Session ) getGoEnv (ctx context.Context , folder string , goversion int , go111module string , configEnv []string ) (environmentVariables , map [string ]string , error ) {
951
+ func (s * Session ) getGoEnv (ctx context.Context , folder string , goversion int , configEnv []string ) (environmentVariables , map [string ]string , error ) {
942
952
envVars := environmentVariables {}
943
953
vars := map [string ]* string {
944
954
"GOCACHE" : & envVars .gocache ,
@@ -984,13 +994,12 @@ func (s *Session) getGoEnv(ctx context.Context, folder string, goversion int, go
984
994
}
985
995
986
996
// Old versions of Go don't have GOMODCACHE, so emulate it.
997
+ //
998
+ // TODO(rfindley): consistent with the treatment of go111module, we should
999
+ // provide a wrapper method rather than mutating this value.
987
1000
if envVars .gomodcache == "" && envVars .gopath != "" {
988
1001
envVars .gomodcache = filepath .Join (filepath .SplitList (envVars .gopath )[0 ], "pkg/mod" )
989
1002
}
990
- // GO111MODULE does not appear in `go env` output until Go 1.13.
991
- if goversion < 13 {
992
- envVars .go111module = go111module
993
- }
994
1003
return envVars , env , err
995
1004
}
996
1005
0 commit comments