From 2c77719cd64eea2f341b461e2cc0e5438cc433de Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bj=C3=B8rn=20Erik=20Pedersen?= Date: Thu, 13 Feb 2025 11:00:02 +0100 Subject: [PATCH] modules: Add GOAUTH to module config Closes #13385 --- docs/content/en/hugo-modules/configuration.md | 4 ++ modules/client.go | 53 ++++++++++++------- modules/client_test.go | 39 ++++++++++++++ modules/config.go | 6 +++ 4 files changed, 83 insertions(+), 19 deletions(-) diff --git a/docs/content/en/hugo-modules/configuration.md b/docs/content/en/hugo-modules/configuration.md index 0bc1b47d8..58a3e36f1 100644 --- a/docs/content/en/hugo-modules/configuration.md +++ b/docs/content/en/hugo-modules/configuration.md @@ -22,6 +22,7 @@ proxy = 'direct' replacements = '' vendorClosest = false workspace = 'off' +auth = '' {{< /code-toggle >}} noProxy @@ -36,6 +37,9 @@ private proxy : (`string`) Defines the proxy server to use to download remote modules. Default is `direct`, which means "git clone" and similar. +auth +: (`string`) {{< new-in 0.144.0 >}} Configures `GOAUTH` when running the Go command for module operations. This is a semicolon-separated list of authentication commands for go-import and HTTPS module mirror interactions. This is useful for private repositories. See `go help goauth` for more information. + vendorClosest : (`bool`) When enabled, we will pick the vendored module closest to the module using it. The default behavior is to pick the first. Note that there can still be only one dependency of a given module path, so once it is in use it cannot be redefined. Default is `false`. diff --git a/modules/client.go b/modules/client.go index d16af2d35..011d43014 100644 --- a/modules/client.go +++ b/modules/client.go @@ -32,6 +32,7 @@ import ( "github.com/gohugoio/hugo/common/herrors" "github.com/gohugoio/hugo/common/hexec" "github.com/gohugoio/hugo/common/loggers" + "github.com/gohugoio/hugo/config" hglob "github.com/gohugoio/hugo/hugofs/glob" @@ -41,8 +42,6 @@ import ( "github.com/gohugoio/hugo/hugofs/files" - "github.com/gohugoio/hugo/config" - "golang.org/x/mod/module" "github.com/gohugoio/hugo/common/hugio" @@ -79,21 +78,6 @@ func NewClient(cfg ClientConfig) *Client { goModFilename = n } - var env []string - mcfg := cfg.ModuleConfig - - config.SetEnvVars(&env, - "PWD", cfg.WorkingDir, - "GO111MODULE", "on", - "GOPROXY", mcfg.Proxy, - "GOPRIVATE", mcfg.Private, - "GONOPROXY", mcfg.NoProxy, - "GOPATH", cfg.CacheDir, - "GOWORK", mcfg.Workspace, // Requires Go 1.18, see https://tip.golang.org/doc/go1.18 - // GOCACHE was introduced in Go 1.15. This matches the location derived from GOPATH above. - "GOCACHE", filepath.Join(cfg.CacheDir, "pkg", "mod"), - ) - logger := cfg.Logger if logger == nil { logger = loggers.NewDefault() @@ -109,8 +93,8 @@ func NewClient(cfg ClientConfig) *Client { ccfg: cfg, logger: logger, noVendor: noVendor, - moduleConfig: mcfg, - environ: env, + moduleConfig: cfg.ModuleConfig, + environ: cfg.toEnv(), GoModulesFilename: goModFilename, } } @@ -785,6 +769,37 @@ func (c ClientConfig) shouldIgnoreVendor(path string) bool { return c.IgnoreVendor != nil && c.IgnoreVendor.Match(path) } +func (cfg ClientConfig) toEnv() []string { + mcfg := cfg.ModuleConfig + var env []string + keyVals := []string{ + "PWD", cfg.WorkingDir, + "GO111MODULE", "on", + "GOPATH", cfg.CacheDir, + "GOWORK", mcfg.Workspace, // Requires Go 1.18, see https://tip.golang.org/doc/go1.18 + // GOCACHE was introduced in Go 1.15. This matches the location derived from GOPATH above. + "GOCACHE", filepath.Join(cfg.CacheDir, "pkg", "mod"), + } + + if mcfg.Proxy != "" { + keyVals = append(keyVals, "GOPROXY", mcfg.Proxy) + } + if mcfg.Private != "" { + keyVals = append(keyVals, "GOPRIVATE", mcfg.Private) + } + if mcfg.NoProxy != "" { + keyVals = append(keyVals, "GONOPROXY", mcfg.NoProxy) + } + if mcfg.Auth != "" { + // GOAUTH was introduced in Go 1.24, see https://tip.golang.org/doc/go1.24. + keyVals = append(keyVals, "GOAUTH", mcfg.Auth) + } + + config.SetEnvVars(&env, keyVals...) + + return env +} + type goBinaryStatus int type goModule struct { diff --git a/modules/client_test.go b/modules/client_test.go index 6320e3338..1b4b1161a 100644 --- a/modules/client_test.go +++ b/modules/client_test.go @@ -216,3 +216,42 @@ func TestGetModlineSplitter(t *testing.T) { gosumSplitter := getModlineSplitter(false) c.Assert(gosumSplitter("github.com/BurntSushi/toml v0.3.1"), qt.DeepEquals, []string{"github.com/BurntSushi/toml", "v0.3.1"}) } + +func TestClientConfigToEnv(t *testing.T) { + c := qt.New(t) + + ccfg := ClientConfig{ + WorkingDir: "/mywork", + CacheDir: "/mycache", + } + + env := ccfg.toEnv() + + c.Assert(env, qt.DeepEquals, []string{"PWD=/mywork", "GO111MODULE=on", "GOPATH=/mycache", "GOWORK=", filepath.FromSlash("GOCACHE=/mycache/pkg/mod")}) + + ccfg = ClientConfig{ + WorkingDir: "/mywork", + CacheDir: "/mycache", + ModuleConfig: Config{ + Proxy: "https://proxy.example.org", + Private: "myprivate", + NoProxy: "mynoproxy", + Workspace: "myworkspace", + Auth: "myauth", + }, + } + + env = ccfg.toEnv() + + c.Assert(env, qt.DeepEquals, []string{ + "PWD=/mywork", + "GO111MODULE=on", + "GOPATH=/mycache", + "GOWORK=myworkspace", + filepath.FromSlash("GOCACHE=/mycache/pkg/mod"), + "GOPROXY=https://proxy.example.org", + "GOPRIVATE=myprivate", + "GONOPROXY=mynoproxy", + "GOAUTH=myauth", + }) +} diff --git a/modules/config.go b/modules/config.go index 78ec3b6b3..1a833b301 100644 --- a/modules/config.go +++ b/modules/config.go @@ -295,6 +295,12 @@ type Config struct { // Configures GOPRIVATE when running the Go command for module operations. Private string + // Configures GOAUTH when running the Go command for module operations. + // This is a semicolon-separated list of authentication commands for go-import and HTTPS module mirror interactions. + // This is useful for private repositories. + // See `go help goauth` for more information. + Auth string + // Defaults to "off". // Set to a work file, e.g. hugo.work, to enable Go "Workspace" mode. // Can be relative to the working directory or absolute.