зеркало из https://github.com/golang/build.git
internal/task: read nested module's own go.mod files
As of the last change, it becomes easy to read the nested module's own go.mod file and determine whether it had a toolchain directive. Before, it was reusing the top-level go.mod file's decision for nested modules. I didn't realize earlier there is a way to use the lower-level 'go mod edit' command to drop a toolchain directive, but it turns out there is. Switch to it now - it's equivalent but fits slightly better in context. Fixes golang/go#68873. Change-Id: I1ea4bfd9e5deb4e72843887d7f8d68a4b2a67f3e Reviewed-on: https://go-review.googlesource.com/c/build/+/622396 Reviewed-by: Dmitri Shuralyov <dmitshur@google.com> Auto-Submit: Dmitri Shuralyov <dmitshur@golang.org> Reviewed-by: Michael Knyszek <mknyszek@google.com> LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
This commit is contained in:
Родитель
fa508ab9e9
Коммит
d28f1065dd
|
@ -71,7 +71,6 @@ type TagRepo struct {
|
|||
Name string // Gerrit project name, e.g., "tools".
|
||||
ModPath string // Module path, e.g., "golang.org/x/tools".
|
||||
Deps []*TagDep // Dependency modules.
|
||||
HasToolchain bool // Whether the go.mod file has a toolchain directive when the workflow started.
|
||||
StartVersion string // The version of the module when the workflow started. Empty string means repo hasn't begun release version tagging yet.
|
||||
NewerVersion string // The version of the module that will be tagged, or the empty string when the repo is being updated only and not tagged.
|
||||
}
|
||||
|
@ -192,7 +191,6 @@ func (x *TagXReposTasks) readRepo(ctx *wf.TaskContext, project string) (*TagRepo
|
|||
result := &TagRepo{
|
||||
Name: project,
|
||||
ModPath: mf.Module.Mod.Path,
|
||||
HasToolchain: mf.Toolchain != nil,
|
||||
StartVersion: currentTag,
|
||||
}
|
||||
|
||||
|
@ -385,10 +383,6 @@ func (x *TagXReposTasks) UpdateGoMod(ctx *wf.TaskContext, repo TagRepo, deps []T
|
|||
for _, dep := range deps {
|
||||
script.WriteString(" " + dep.ModPath + "@" + dep.NewerVersion)
|
||||
}
|
||||
if !repo.HasToolchain {
|
||||
// Don't introduce a toolchain directive if it wasn't already there.
|
||||
script.WriteString(" toolchain@none")
|
||||
}
|
||||
script.WriteString("\n")
|
||||
|
||||
// Tidy the root module and nested modules.
|
||||
|
@ -418,10 +412,11 @@ func (x *TagXReposTasks) UpdateGoMod(ctx *wf.TaskContext, repo TagRepo, deps []T
|
|||
if d.Name() == "go.mod" && !d.IsDir() { // A go.mod file.
|
||||
dir := pathpkg.Dir(path)
|
||||
dropToolchain := ""
|
||||
if !repo.HasToolchain {
|
||||
if had, err := hasToolchain(rootFS, path); err != nil {
|
||||
return err
|
||||
} else if !had {
|
||||
// Don't introduce a toolchain directive if it wasn't already there.
|
||||
// TODO(go.dev/issue/68873): Read the nested module's go.mod. For now, re-use decision from the top-level module.
|
||||
dropToolchain = " && go get toolchain@none"
|
||||
dropToolchain = " && go mod edit -toolchain=none"
|
||||
}
|
||||
script.WriteString(fmt.Sprintf("(cd %v && touch go.sum && go mod tidy%s)\n", dir, dropToolchain))
|
||||
outputs = append(outputs, dir+"/go.mod", dir+"/go.sum")
|
||||
|
@ -439,6 +434,20 @@ func (x *TagXReposTasks) UpdateGoMod(ctx *wf.TaskContext, repo TagRepo, deps []T
|
|||
return buildToOutputs(ctx, x.CloudBuild, build)
|
||||
}
|
||||
|
||||
// hasToolchain parses the specified go.mod file, and
|
||||
// reports whether it has a toolchain directive in it.
|
||||
func hasToolchain(fsys fs.FS, goModPath string) (has bool, _ error) {
|
||||
b, err := fs.ReadFile(fsys, goModPath)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
f, err := modfile.Parse(goModPath, b, nil)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
return f.Toolchain != nil, nil
|
||||
}
|
||||
|
||||
func buildToOutputs(ctx *wf.TaskContext, buildClient CloudBuildClient, build CloudBuild) (map[string]string, error) {
|
||||
if _, err := AwaitCondition(ctx, 10*time.Second, func() (string, bool, error) {
|
||||
return buildClient.Completed(ctx, build)
|
||||
|
|
|
@ -255,8 +255,15 @@ case "$1" in
|
|||
done
|
||||
;;
|
||||
"mod")
|
||||
ls go.mod go.sum >/dev/null
|
||||
echo "tidied! $*" >> go.mod
|
||||
case "$2" in
|
||||
"tidy")
|
||||
ls go.mod go.sum >/dev/null
|
||||
echo "tidied! $*" >> go.mod
|
||||
;;
|
||||
"edit")
|
||||
echo "edited! $*" >> go.mod
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
*)
|
||||
echo unexpected command $@
|
||||
|
@ -307,10 +314,11 @@ func TestTagXRepos(t *testing.T) {
|
|||
mod.Tag("v1.0.0", mod1)
|
||||
tools := NewFakeRepo(t, "tools")
|
||||
tools1 := tools.Commit(map[string]string{
|
||||
"go.mod": "module golang.org/x/tools\nrequire golang.org/x/mod v1.0.0\ngo 1.18\nrequire golang.org/x/sys v0.1.0\nrequire golang.org/x/build v0.0.0\n",
|
||||
"go.sum": "\n",
|
||||
"gopls/go.mod": "module golang.org/x/tools/gopls\nrequire golang.org/x/mod v1.0.0\n",
|
||||
"gopls/go.sum": "\n",
|
||||
"go.mod": "module golang.org/x/tools\nrequire golang.org/x/mod v1.0.0\ngo 1.18\nrequire golang.org/x/sys v0.1.0\nrequire golang.org/x/build v0.0.0\n",
|
||||
"go.sum": "\n",
|
||||
"gopls/go.mod": "module golang.org/x/tools/gopls\nrequire golang.org/x/mod v1.0.0\n",
|
||||
"gopls/go.sum": "\n",
|
||||
"withtoolchain/go.mod": "module golang.org/x/tools/withtoolchain\ngo 1.23.1\ntoolchain go1.23.2\n",
|
||||
})
|
||||
tools.Tag("v1.1.5", tools1)
|
||||
build := NewFakeRepo(t, "build")
|
||||
|
@ -364,12 +372,22 @@ func TestTagXRepos(t *testing.T) {
|
|||
if !strings.Contains(string(goMod), "tidied!") {
|
||||
t.Error("tools go.mod should be tidied")
|
||||
}
|
||||
if !strings.Contains(string(goMod), "edited! mod edit -toolchain=none") {
|
||||
t.Error("tools go.mod should be edited with -toolchain=none")
|
||||
}
|
||||
goplsMod, err := deps.gerrit.ReadFile(ctx, "tools", tag.Revision, "gopls/go.mod")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if !strings.Contains(string(goplsMod), "tidied!") || strings.Contains(string(goplsMod), "upgraded") {
|
||||
t.Errorf("gopls go.mod should be tidied and not upgraded:\n%s", goplsMod)
|
||||
if !strings.Contains(string(goplsMod), "tidied!") || !strings.Contains(string(goplsMod), "edited!") || strings.Contains(string(goplsMod), "upgraded") {
|
||||
t.Errorf("gopls go.mod should be tidied+edited and not upgraded:\n%s", goplsMod)
|
||||
}
|
||||
withtoolchainMod, err := deps.gerrit.ReadFile(ctx, "tools", tag.Revision, "withtoolchain/go.mod")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if !strings.Contains(string(withtoolchainMod), "tidied!") || strings.Contains(string(withtoolchainMod), "edited!") {
|
||||
t.Errorf("withtoolchain go.mod should be tidied and not edited:\n%s", withtoolchainMod)
|
||||
}
|
||||
|
||||
tags, err = deps.gerrit.ListTags(ctx, "build")
|
||||
|
|
Загрузка…
Ссылка в новой задаче