diff options
| author | Michael Matloob <matloob@golang.org> | 2026-04-07 17:15:10 -0400 |
|---|---|---|
| committer | Gopher Robot <gobot@golang.org> | 2026-04-09 09:24:43 -0700 |
| commit | 28c56bb5fb438d46d921a37f2e172ecf198f75c2 (patch) | |
| tree | b9e1f71e10f66af1ea310d1d7abe8f4aed9b9172 /src | |
| parent | f6d825cd3a7f98fbb48880b791b4c2be8cecddf3 (diff) | |
| download | go-28c56bb5fb438d46d921a37f2e172ecf198f75c2.tar.xz | |
cmd/go: build pkgsite doc command in same go command invocation
Instead of running go run. This is enabled by Ian Alexander's work to
remove global state in the loader package.
This also fixes an issue where we can't build and run the pkgsite binary
because, with our GOPROXY setting, if pkgsite module is available in the
module cache at the requested version, but the pkgsite/cmd/internal/doc
module isn't we'll give up trying to fetch the doc module. Now that the
build and execution are separated, we can make sure the GOPROXY setting
is only supplied to the running pkgsite binary, but not to the
operations that build it.
Fixes #78457
Change-Id: Id2a754fee12b68240243773f81e7d00b6a6a6964
Reviewed-on: https://go-review.googlesource.com/c/go/+/763760
Reviewed-by: Michael Matloob <matloob@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Michael Matloob <matloob@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Diffstat (limited to 'src')
| -rw-r--r-- | src/cmd/go/internal/doc/doc.go | 8 | ||||
| -rw-r--r-- | src/cmd/go/internal/doc/pkgsite.go | 59 | ||||
| -rw-r--r-- | src/cmd/go/internal/doc/pkgsite_bootstrap.go | 4 |
3 files changed, 58 insertions, 13 deletions
diff --git a/src/cmd/go/internal/doc/doc.go b/src/cmd/go/internal/doc/doc.go index 4376e3344e..d961c2a215 100644 --- a/src/cmd/go/internal/doc/doc.go +++ b/src/cmd/go/internal/doc/doc.go @@ -222,16 +222,16 @@ func do(ctx context.Context, writer io.Writer, flagSet *flag.FlagSet, args []str mod, err := runCmd(append(os.Environ(), "GOWORK=off"), "go", "list", "-m") if err == nil && mod != "" && mod != "command-line-arguments" { // If there's a module, go to the module's doc page. - return doPkgsite(mod, "") + return doPkgsite(ctx, mod, "") } gowork, err := runCmd(nil, "go", "env", "GOWORK") if err == nil && gowork != "" { // Outside a module, but in a workspace, go to the home page // with links to each of the modules' pages. - return doPkgsite("", "") + return doPkgsite(ctx, "", "") } // Outside a module or workspace, go to the documentation for the standard library. - return doPkgsite("std", "") + return doPkgsite(ctx, "std", "") } // If args are provided, we need to figure out which page to open on the pkgsite @@ -296,7 +296,7 @@ func do(ctx context.Context, writer io.Writer, flagSet *flag.FlagSet, args []str if err != nil { return err } - return doPkgsite(path, fragment) + return doPkgsite(ctx, path, fragment) } return nil } diff --git a/src/cmd/go/internal/doc/pkgsite.go b/src/cmd/go/internal/doc/pkgsite.go index 2c135cdc34..a2398ef397 100644 --- a/src/cmd/go/internal/doc/pkgsite.go +++ b/src/cmd/go/internal/doc/pkgsite.go @@ -7,17 +7,21 @@ package doc import ( + "context" "errors" "fmt" "net" "net/url" "os" "os/exec" - "os/signal" "path/filepath" "strings" + "cmd/go/internal/base" "cmd/go/internal/cfg" + "cmd/go/internal/load" + "cmd/go/internal/modload" + "cmd/go/internal/work" ) // pickUnusedPort finds an unused port by trying to listen on port 0 @@ -36,7 +40,49 @@ func pickUnusedPort() (int, error) { return port, nil } -func doPkgsite(urlPath, fragment string) error { +// buildPkgsite builds a pkgsite binary whose build may be cached. +func buildPkgsite(ctx context.Context) string { + loader := modload.NewLoader() + + // Set the builder to have no module root so we can build a pkg@version pattern. + loader.ForceUseModules = true + loader.RootMode = modload.NoRoot + loader.AllowMissingModuleImports() + modload.Init(loader) + + work.BuildInit(loader) + b := work.NewBuilder("", loader.VendorDirOrEmpty) + defer func() { + if err := b.Close(); err != nil { + base.Fatal(err) + } + }() + + const version = "v0.0.0-20251223195805-1a3bd3c788fe" + pkgVers := "golang.org/x/pkgsite/cmd/internal/doc@" + version + pkgOpts := load.PackageOpts{MainOnly: true} + pkgs, err := load.PackagesAndErrorsOutsideModule(loader, ctx, pkgOpts, []string{pkgVers}) + if err != nil { + base.Fatal(err) + } + if len(pkgs) == 0 { + base.Fatalf("go: internal error: no packages loaded for %s", pkgVers) + } + if len(pkgs) > 1 { + base.Fatalf("go: internal error: pattern %s matches multiple packages", pkgVers) + } + p := pkgs[0] + p.Internal.OmitDebug = true + p.Internal.ExeName = p.DefaultExecName() + load.CheckPackageErrors([]*load.Package{p}) + + a := b.LinkAction(loader, work.ModeBuild, work.ModeBuild, p) + a.CacheExecutable = true + b.Do(ctx, a) + return a.BuiltTarget() +} + +func doPkgsite(ctx context.Context, urlPath, fragment string) error { port, err := pickUnusedPort() if err != nil { return fmt.Errorf("failed to find port for documentation server: %v", err) @@ -57,7 +103,7 @@ func doPkgsite(urlPath, fragment string) error { // Turn off the default signal handler for SIGINT (and SIGQUIT on Unix) // and instead wait for the child process to handle the signal and // exit before exiting ourselves. - signal.Ignore(signalsToIgnore...) + base.StartSigHandlers() // Prepend the local download cache to GOPROXY to get around deprecation checks. env := os.Environ() @@ -77,11 +123,8 @@ func doPkgsite(urlPath, fragment string) error { env = append(env, "GOPROXY="+gomodcache+","+goproxy) } - const version = "v0.0.0-20251223195805-1a3bd3c788fe" - cmd := exec.Command(goCmd(), "run", "golang.org/x/pkgsite/cmd/internal/doc@"+version, - "-gorepo", cfg.GOROOT, - "-http", addr, - "-open", path) + pkgsite := buildPkgsite(ctx) + cmd := exec.Command(pkgsite, "-gorepo", cfg.GOROOT, "-http", addr, "-open", path) cmd.Env = env cmd.Stdout = os.Stderr cmd.Stderr = os.Stderr diff --git a/src/cmd/go/internal/doc/pkgsite_bootstrap.go b/src/cmd/go/internal/doc/pkgsite_bootstrap.go index 3c9f546957..cb72492cb5 100644 --- a/src/cmd/go/internal/doc/pkgsite_bootstrap.go +++ b/src/cmd/go/internal/doc/pkgsite_bootstrap.go @@ -8,4 +8,6 @@ package doc -func doPkgsite(string, string) error { return nil } +import "context" + +func doPkgsite(context.Context, string, string) error { return nil } |
