mirror of
https://github.com/golang/go
synced 2024-11-27 01:21:18 -07:00
cmd/go: return more errors from ReadModFile, loadModFile
Return more errors instead of base.Fatalf, so we can handle them in the callers. For #57001. Change-Id: If3e63d3f64188148f5d750991f9cb1175790d89d Reviewed-on: https://go-review.googlesource.com/c/go/+/499983 Reviewed-by: Bryan Mills <bcmills@google.com> Auto-Submit: Russ Cox <rsc@golang.org> TryBot-Result: Gopher Robot <gobot@golang.org> Run-TryBot: Russ Cox <rsc@golang.org>
This commit is contained in:
parent
40c7be9b0f
commit
c71cbd544e
@ -60,6 +60,7 @@ var Startup struct {
|
||||
type TooNewError struct {
|
||||
What string
|
||||
GoVersion string
|
||||
Toolchain string // for callers if they want to use it, but not printed
|
||||
}
|
||||
|
||||
func (e *TooNewError) Error() string {
|
||||
|
@ -541,7 +541,10 @@ func (mg *ModuleGraph) allRootsSelected() bool {
|
||||
// LoadModGraph need only be called if LoadPackages is not,
|
||||
// typically in commands that care about modules but no particular package.
|
||||
func LoadModGraph(ctx context.Context, goVersion string) (*ModuleGraph, error) {
|
||||
rs := LoadModFile(ctx)
|
||||
rs, err := loadModFile(ctx, nil)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if goVersion != "" {
|
||||
v, _ := rs.rootSelected("go")
|
||||
|
@ -731,12 +731,16 @@ func UpdateWorkFile(wf *modfile.WorkFile) {
|
||||
// it for global consistency. Most callers outside of the modload package should
|
||||
// use LoadModGraph instead.
|
||||
func LoadModFile(ctx context.Context) *Requirements {
|
||||
return loadModFile(ctx, nil)
|
||||
rs, err := loadModFile(ctx, nil)
|
||||
if err != nil {
|
||||
base.Fatal(err)
|
||||
}
|
||||
return rs
|
||||
}
|
||||
|
||||
func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
func loadModFile(ctx context.Context, opts *PackageOpts) (*Requirements, error) {
|
||||
if requirements != nil {
|
||||
return requirements
|
||||
return requirements, nil
|
||||
}
|
||||
|
||||
Init()
|
||||
@ -745,7 +749,7 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
var err error
|
||||
workFile, modRoots, err = loadWorkFile(workFilePath)
|
||||
if err != nil {
|
||||
base.Fatalf("reading go.work: %v", err)
|
||||
return nil, fmt.Errorf("reading go.work: %w", err)
|
||||
}
|
||||
for _, modRoot := range modRoots {
|
||||
sumFile := strings.TrimSuffix(modFilePath(modRoot), ".mod") + ".sum"
|
||||
@ -796,22 +800,23 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
// with no dependencies.
|
||||
requirements.initVendor(nil)
|
||||
}
|
||||
return requirements
|
||||
return requirements, nil
|
||||
}
|
||||
|
||||
var modFiles []*modfile.File
|
||||
var mainModules []module.Version
|
||||
var indices []*modFileIndex
|
||||
var errs []error
|
||||
for _, modroot := range modRoots {
|
||||
gomod := modFilePath(modroot)
|
||||
var fixed bool
|
||||
data, f, err := ReadModFile(gomod, fixVersion(ctx, &fixed))
|
||||
if err != nil {
|
||||
if inWorkspaceMode() {
|
||||
base.Fatalf("go: cannot load module %s listed in go.work file: %v", base.ShortPath(gomod), err)
|
||||
} else {
|
||||
base.Fatalf("go: %v", err)
|
||||
err = fmt.Errorf("cannot load module %s listed in go.work file: %w", base.ShortPath(gomod), err)
|
||||
}
|
||||
errs = append(errs, err)
|
||||
continue
|
||||
}
|
||||
|
||||
modFiles = append(modFiles, f)
|
||||
@ -823,9 +828,12 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
if pathErr, ok := err.(*module.InvalidPathError); ok {
|
||||
pathErr.Kind = "module"
|
||||
}
|
||||
base.Fatalf("go: %v", err)
|
||||
errs = append(errs, err)
|
||||
}
|
||||
}
|
||||
if len(errs) > 0 {
|
||||
return nil, errors.Join(errs...)
|
||||
}
|
||||
|
||||
MainModules = makeMainModules(mainModules, modRoots, modFiles, indices, workFile)
|
||||
setDefaultBuildMod() // possibly enable automatic vendoring
|
||||
@ -835,7 +843,7 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
// We don't need to do anything for vendor or update the mod file so
|
||||
// return early.
|
||||
requirements = rs
|
||||
return rs
|
||||
return rs, nil
|
||||
}
|
||||
|
||||
mainModule := MainModules.mustGetSingleMainModule()
|
||||
@ -855,7 +863,7 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
var err error
|
||||
rs, err = updateRoots(ctx, rs.direct, rs, nil, nil, false)
|
||||
if err != nil {
|
||||
base.Fatal(err)
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
|
||||
@ -880,7 +888,7 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
var err error
|
||||
rs, err = convertPruning(ctx, rs, pruned)
|
||||
if err != nil {
|
||||
base.Fatal(err)
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
} else {
|
||||
@ -889,7 +897,7 @@ func loadModFile(ctx context.Context, opts *PackageOpts) *Requirements {
|
||||
}
|
||||
|
||||
requirements = rs
|
||||
return requirements
|
||||
return requirements, nil
|
||||
}
|
||||
|
||||
// CreateModFile initializes a new module by creating a go.mod file.
|
||||
|
@ -341,7 +341,10 @@ func LoadPackages(ctx context.Context, opts PackageOpts, patterns ...string) (ma
|
||||
}
|
||||
}
|
||||
|
||||
initialRS := loadModFile(ctx, &opts)
|
||||
initialRS, err := loadModFile(ctx, &opts)
|
||||
if err != nil {
|
||||
base.Fatal(err)
|
||||
}
|
||||
|
||||
ld := loadFromRoots(ctx, loaderParams{
|
||||
PackageOpts: opts,
|
||||
|
@ -30,6 +30,7 @@ import (
|
||||
// ReadModFile reads and parses the mod file at gomod. ReadModFile properly applies the
|
||||
// overlay, locks the file while reading, and applies fix, if applicable.
|
||||
func ReadModFile(gomod string, fix modfile.VersionFixer) (data []byte, f *modfile.File, err error) {
|
||||
gomod = base.ShortPath(gomod) // use short path in any errors
|
||||
if gomodActual, ok := fsys.OverlayPath(gomod); ok {
|
||||
// Don't lock go.mod if it's part of the overlay.
|
||||
// On Plan 9, locking requires chmod, and we don't want to modify any file
|
||||
@ -45,14 +46,18 @@ func ReadModFile(gomod string, fix modfile.VersionFixer) (data []byte, f *modfil
|
||||
f, err = modfile.Parse(gomod, data, fix)
|
||||
if err != nil {
|
||||
// Errors returned by modfile.Parse begin with file:line.
|
||||
return nil, nil, fmt.Errorf("errors parsing go.mod:\n%s\n", err)
|
||||
return nil, nil, fmt.Errorf("errors parsing %s:\n%w", gomod, err)
|
||||
}
|
||||
if f.Go != nil && gover.Compare(f.Go.Version, gover.Local()) > 0 && cfg.CmdName != "mod edit" {
|
||||
base.Fatalf("go: %v", &gover.TooNewError{What: base.ShortPath(gomod), GoVersion: f.Go.Version})
|
||||
if f.Go != nil && gover.Compare(f.Go.Version, gover.Local()) > 0 {
|
||||
toolchain := ""
|
||||
if f.Toolchain != nil {
|
||||
toolchain = f.Toolchain.Name
|
||||
}
|
||||
return nil, nil, &gover.TooNewError{What: gomod, GoVersion: f.Go.Version, Toolchain: toolchain}
|
||||
}
|
||||
if f.Module == nil {
|
||||
// No module declaration. Must add module path.
|
||||
return nil, nil, errors.New("no module declaration in go.mod. To specify the module path:\n\tgo mod edit -module=example.com/mod")
|
||||
return nil, nil, fmt.Errorf("error reading %s: missing module declaration. To specify the module path:\n\tgo mod edit -module=example.com/mod", gomod)
|
||||
}
|
||||
|
||||
return data, f, err
|
||||
|
@ -8,7 +8,7 @@ stderr '^go: go.mod requires go >= 1.99999 \(running go 1\..+\)$'
|
||||
# go.mod referenced from go.work too new
|
||||
cp go.work.old go.work
|
||||
! go build .
|
||||
stderr '^go: go.mod requires go >= 1.99999 \(running go 1\..+\)$'
|
||||
stderr '^go: cannot load module go.mod listed in go.work file: go.mod requires go >= 1.99999 \(running go 1\..+\)$'
|
||||
|
||||
# go.work too new
|
||||
cp go.work.new go.work
|
||||
|
@ -3,7 +3,7 @@
|
||||
# Test that go list fails on a go.mod with no module declaration.
|
||||
cd $WORK/gopath/src/mod
|
||||
! go list .
|
||||
stderr '^go: no module declaration in go.mod. To specify the module path:\n\tgo mod edit -module=example.com/mod$'
|
||||
stderr '^go: error reading go.mod: missing module declaration. To specify the module path:\n\tgo mod edit -module=example.com/mod$'
|
||||
|
||||
# Test that go mod init in GOPATH doesn't add a module declaration
|
||||
# with a path that can't possibly be a module path, because
|
||||
|
@ -50,7 +50,7 @@ cd outside
|
||||
stderr 'go: example.com@v0.0.0 \(replaced by \./\.\.\): parsing ..[/\\]go.mod: '$WORK'[/\\]gopath[/\\]src[/\\]go.mod:5: require golang.org/x/text: version "v2.1.1-0.20170915032832-14c0d48ead0c" invalid: should be v0 or v1, not v2'
|
||||
cd ..
|
||||
! go list -m golang.org/x/text
|
||||
stderr $WORK'[/\\]gopath[/\\]src[/\\]go.mod:5: require golang.org/x/text: version "v2.1.1-0.20170915032832-14c0d48ead0c" invalid: should be v0 or v1, not v2'
|
||||
stderr '^go.mod:5: require golang.org/x/text: version "v2.1.1-0.20170915032832-14c0d48ead0c" invalid: should be v0 or v1, not v2'
|
||||
|
||||
# A pseudo-version with fewer than 12 digits of SHA-1 prefix is invalid.
|
||||
cp go.mod.orig go.mod
|
||||
|
Loading…
Reference in New Issue
Block a user