diff --git a/modules/mesh-build-go/cmd/mesh-build-go/candidate.go b/modules/mesh-build-go/cmd/mesh-build-go/candidate.go index 4379d3ca4..27f43d778 100644 --- a/modules/mesh-build-go/cmd/mesh-build-go/candidate.go +++ b/modules/mesh-build-go/cmd/mesh-build-go/candidate.go @@ -97,9 +97,10 @@ func (m *Module) candidate(ctx context.Context, workspace string) (string, error // compileError is the first line of the compiler's output that says an error: not the `# package` heading go build // prints above a package's errors, nor Go's progress. func compileError(out string) string { - for _, l := range strings.Split(out, "\n") { + lines := strings.Split(out, "\n") + for i, l := range lines { if l = strings.TrimSpace(l); l != "" && !strings.HasPrefix(l, "#") && !strings.HasPrefix(l, "go: downloading ") { - return l + return withContinuation(l, lines[i+1:]) } } return firstLine(out) diff --git a/modules/mesh-build-go/cmd/mesh-build-go/fetch.go b/modules/mesh-build-go/cmd/mesh-build-go/fetch.go index 8644edd9a..8f66a1a9b 100644 --- a/modules/mesh-build-go/cmd/mesh-build-go/fetch.go +++ b/modules/mesh-build-go/cmd/mesh-build-go/fetch.go @@ -351,15 +351,33 @@ func (m *Module) now() time.Time { return m.clock() } // causeLine is the first line of a go command's output that says something other than Go's own progress: `go: // downloading ...` comes first when Go fetches a module, and `# ` heads a compile error of go build or go vet // (issue 1703: the reason said only the package), and the cause of a failure on a later line. +// +// A cause Go writes over several lines keeps its indented continuation lines, joined by a space: a module graph error +// is "X requires" with the module that fails, and why, on the next line (issue 1966: the composer's reason ended at +// "requires" and hid "golang.org/x/tools@v0.42.0: module lookup disabled"). func causeLine(s string) string { - for _, l := range strings.Split(s, "\n") { + lines := strings.Split(s, "\n") + for i, l := range lines { if l = strings.TrimSpace(l); l != "" && !strings.HasPrefix(l, "go: downloading ") && !strings.HasPrefix(l, "# ") { - return l + return withContinuation(l, lines[i+1:]) } } return firstLine(s) } +// withContinuation is first with each following line Go indented under it, trimmed and joined by a space. +func withContinuation(first string, rest []string) string { + for _, l := range rest { + if !strings.HasPrefix(l, "\t") && !strings.HasPrefix(l, " ") { + break + } + if l = strings.TrimSpace(l); l != "" { + first += " " + l + } + } + return first +} + func firstLine(s string) string { for _, l := range strings.Split(s, "\n") { if l = strings.TrimSpace(l); l != "" { diff --git a/modules/mesh-build-go/cmd/mesh-build-go/fetch_test.go b/modules/mesh-build-go/cmd/mesh-build-go/fetch_test.go index e86e15591..81d7c5d57 100644 --- a/modules/mesh-build-go/cmd/mesh-build-go/fetch_test.go +++ b/modules/mesh-build-go/cmd/mesh-build-go/fetch_test.go @@ -309,9 +309,14 @@ func TestCauseLineSkipsProgressAndThePackageHeading(t *testing.T) { "go: downloading x v1\n# git.example/m/cmd\n./main.go:3:2: undefined: y\n": "./main.go:3:2: undefined: y", "\ngo: example.com/x@v1: reading: 404\n": "go: example.com/x@v1: reading: 404", "go: downloading x v1\n": "go: downloading x v1", + // issue 1966: a module graph error goes on, indented, on the next line; a later error is not taken in. + "a.go:3:8: x@v1 requires\n\ty@v2: module lookup disabled by GOPROXY=off\nb.go:1:1: other\n": "a.go:3:8: x@v1 requires y@v2: module lookup disabled by GOPROXY=off", } { if got := causeLine(in); got != want { t.Errorf("causeLine(%q) = %q, want %q", in, got, want) } + if got := compileError(in); got != want { + t.Errorf("compileError(%q) = %q, want %q", in, got, want) + } } }