mirror of
https://github.com/goreleaser/goreleaser.git
synced 2024-12-31 01:53:50 +02:00
refactor: split go mod into 2 pipes (#2502)
Signed-off-by: Carlos Alexandro Becker <caarlos0@gmail.com>
This commit is contained in:
parent
28ef87b4b0
commit
f7c865c4d9
3
internal/pipe/gomod/doc.go
Normal file
3
internal/pipe/gomod/doc.go
Normal file
@ -0,0 +1,3 @@
|
||||
// Package gomod provides go modules utilities, such as template variables and the ability to proxy the module from
|
||||
// proxy.golang.org.
|
||||
package gomod
|
163
internal/pipe/gomod/gomod proxy.go
Normal file
163
internal/pipe/gomod/gomod proxy.go
Normal file
@ -0,0 +1,163 @@
|
||||
// Package gomod provides go modules utilities, such as template variables and the ability to proxy the module from
|
||||
// proxy.golang.org.
|
||||
package gomod
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"github.com/apex/log"
|
||||
"github.com/goreleaser/goreleaser/internal/tmpl"
|
||||
"github.com/goreleaser/goreleaser/pkg/config"
|
||||
"github.com/goreleaser/goreleaser/pkg/context"
|
||||
)
|
||||
|
||||
// ProxyPipe for gomod proxy.
|
||||
type ProxyPipe struct{}
|
||||
|
||||
func (ProxyPipe) String() string { return "proxying go module" }
|
||||
|
||||
func (ProxyPipe) Skip(ctx *context.Context) bool {
|
||||
return ctx.ModulePath == "" || !ctx.Config.GoMod.Proxy || ctx.Snapshot
|
||||
}
|
||||
|
||||
// Run the ProxyPipe.
|
||||
func (ProxyPipe) Run(ctx *context.Context) error {
|
||||
for i := range ctx.Config.Builds {
|
||||
build := &ctx.Config.Builds[i]
|
||||
if err := proxyBuild(ctx, build); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
const goModTpl = `
|
||||
module {{ .BuildID }}
|
||||
|
||||
require {{ .ModulePath }} {{ .Tag }}
|
||||
`
|
||||
|
||||
const mainGoTpl = `
|
||||
// +build main
|
||||
package main
|
||||
|
||||
import _ "{{ .Main }}"
|
||||
`
|
||||
|
||||
// ErrProxy happens when something goes wrong while proxying the current go module.
|
||||
type ErrProxy struct {
|
||||
err error
|
||||
details string
|
||||
}
|
||||
|
||||
func newErrProxy(err error) error {
|
||||
return ErrProxy{
|
||||
err: err,
|
||||
}
|
||||
}
|
||||
|
||||
func newDetailedErrProxy(err error, details string) error {
|
||||
return ErrProxy{
|
||||
err: err,
|
||||
details: details,
|
||||
}
|
||||
}
|
||||
|
||||
func (e ErrProxy) Error() string {
|
||||
out := fmt.Sprintf("failed to proxy module: %v", e.err)
|
||||
if e.details != "" {
|
||||
return fmt.Sprintf("%s: %s", out, e.details)
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
func (e ErrProxy) Unwrap() error {
|
||||
return e.err
|
||||
}
|
||||
|
||||
func proxyBuild(ctx *context.Context, build *config.Build) error {
|
||||
mainPackage := path.Join(ctx.ModulePath, build.Main)
|
||||
if strings.HasSuffix(build.Main, ".go") {
|
||||
pkg := path.Dir(build.Main)
|
||||
log.Warnf("guessing package of '%s' to be '%s', if this is incorrect, setup 'build.%s.main' to be the correct package", build.Main, pkg, build.ID)
|
||||
mainPackage = path.Join(ctx.ModulePath, pkg)
|
||||
}
|
||||
template := tmpl.New(ctx).WithExtraFields(tmpl.Fields{
|
||||
"Main": mainPackage,
|
||||
"BuildID": build.ID,
|
||||
})
|
||||
|
||||
log.Infof("proxying %s@%s to build %s", ctx.ModulePath, ctx.Git.CurrentTag, mainPackage)
|
||||
|
||||
mod, err := template.Apply(goModTpl)
|
||||
if err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
main, err := template.Apply(mainGoTpl)
|
||||
if err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
dir := filepath.Join(ctx.Config.Dist, "proxy", build.ID)
|
||||
|
||||
log.Debugf("creating needed files")
|
||||
|
||||
if err := os.MkdirAll(dir, 0o755); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
if err := os.WriteFile(filepath.Join(dir, "main.go"), []byte(main), 0o666); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
if err := os.WriteFile(filepath.Join(dir, "go.mod"), []byte(mod), 0o666); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
if err := copyGoSum("go.sum", filepath.Join(dir, "go.sum")); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
log.Debugf("tidying")
|
||||
cmd := exec.CommandContext(ctx, ctx.Config.GoMod.GoBinary, "mod", "tidy")
|
||||
cmd.Dir = dir
|
||||
cmd.Env = append(ctx.Config.GoMod.Env, os.Environ()...)
|
||||
if out, err := cmd.CombinedOutput(); err != nil {
|
||||
return newDetailedErrProxy(err, string(out))
|
||||
}
|
||||
|
||||
build.UnproxiedMain = build.Main
|
||||
build.UnproxiedDir = build.Dir
|
||||
build.Main = mainPackage
|
||||
build.Dir = dir
|
||||
return nil
|
||||
}
|
||||
|
||||
func copyGoSum(src, dst string) error {
|
||||
r, err := os.OpenFile(src, os.O_RDONLY, 0o666)
|
||||
if err != nil {
|
||||
if errors.Is(err, os.ErrNotExist) {
|
||||
return nil
|
||||
}
|
||||
return err
|
||||
}
|
||||
defer r.Close()
|
||||
|
||||
w, err := os.Create(dst)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer w.Close()
|
||||
|
||||
_, err = io.Copy(w, r)
|
||||
return err
|
||||
}
|
@ -1,21 +1,11 @@
|
||||
// Package gomod provides go modules utilities, such as template variables and the ability to proxy the module from
|
||||
// proxy.golang.org.
|
||||
package gomod
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"github.com/apex/log"
|
||||
"github.com/goreleaser/goreleaser/internal/pipe"
|
||||
"github.com/goreleaser/goreleaser/internal/tmpl"
|
||||
"github.com/goreleaser/goreleaser/pkg/config"
|
||||
"github.com/goreleaser/goreleaser/pkg/context"
|
||||
)
|
||||
|
||||
@ -24,7 +14,7 @@ const (
|
||||
go116NotAGoModuleError = "command-line-arguments"
|
||||
)
|
||||
|
||||
// Pipe for env.
|
||||
// Pipe for gomod.
|
||||
type Pipe struct{}
|
||||
|
||||
func (Pipe) String() string { return "loading go mod information" }
|
||||
@ -49,149 +39,5 @@ func (Pipe) Run(ctx *context.Context) error {
|
||||
}
|
||||
|
||||
ctx.ModulePath = result
|
||||
|
||||
if !ctx.Config.GoMod.Proxy {
|
||||
// TODO: check this on Skip?
|
||||
return pipe.Skip("proxying not enabled")
|
||||
}
|
||||
|
||||
if ctx.Snapshot {
|
||||
return pipe.ErrSnapshotEnabled
|
||||
}
|
||||
|
||||
return setupProxy(ctx)
|
||||
}
|
||||
|
||||
func setupProxy(ctx *context.Context) error {
|
||||
for i := range ctx.Config.Builds {
|
||||
build := &ctx.Config.Builds[i]
|
||||
if err := proxyBuild(ctx, build); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
const goModTpl = `
|
||||
module {{ .BuildID }}
|
||||
|
||||
require {{ .ModulePath }} {{ .Tag }}
|
||||
`
|
||||
|
||||
const mainGoTpl = `
|
||||
// +build main
|
||||
package main
|
||||
|
||||
import _ "{{ .Main }}"
|
||||
`
|
||||
|
||||
// ErrProxy happens when something goes wrong while proxying the current go module.
|
||||
type ErrProxy struct {
|
||||
err error
|
||||
details string
|
||||
}
|
||||
|
||||
func newErrProxy(err error) error {
|
||||
return ErrProxy{
|
||||
err: err,
|
||||
}
|
||||
}
|
||||
|
||||
func newDetailedErrProxy(err error, details string) error {
|
||||
return ErrProxy{
|
||||
err: err,
|
||||
details: details,
|
||||
}
|
||||
}
|
||||
|
||||
func (e ErrProxy) Error() string {
|
||||
out := fmt.Sprintf("failed to proxy module: %v", e.err)
|
||||
if e.details != "" {
|
||||
return fmt.Sprintf("%s: %s", out, e.details)
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
func (e ErrProxy) Unwrap() error {
|
||||
return e.err
|
||||
}
|
||||
|
||||
func proxyBuild(ctx *context.Context, build *config.Build) error {
|
||||
mainPackage := path.Join(ctx.ModulePath, build.Main)
|
||||
if strings.HasSuffix(build.Main, ".go") {
|
||||
pkg := path.Dir(build.Main)
|
||||
log.Warnf("guessing package of '%s' to be '%s', if this is incorrect, setup 'build.%s.main' to be the correct package", build.Main, pkg, build.ID)
|
||||
mainPackage = path.Join(ctx.ModulePath, pkg)
|
||||
}
|
||||
template := tmpl.New(ctx).WithExtraFields(tmpl.Fields{
|
||||
"Main": mainPackage,
|
||||
"BuildID": build.ID,
|
||||
})
|
||||
|
||||
log.Infof("proxying %s@%s to build %s", ctx.ModulePath, ctx.Git.CurrentTag, mainPackage)
|
||||
|
||||
mod, err := template.Apply(goModTpl)
|
||||
if err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
main, err := template.Apply(mainGoTpl)
|
||||
if err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
dir := filepath.Join(ctx.Config.Dist, "proxy", build.ID)
|
||||
|
||||
log.Debugf("creating needed files")
|
||||
|
||||
if err := os.MkdirAll(dir, 0o755); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
if err := os.WriteFile(filepath.Join(dir, "main.go"), []byte(main), 0o666); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
if err := os.WriteFile(filepath.Join(dir, "go.mod"), []byte(mod), 0o666); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
if err := copyGoSum("go.sum", filepath.Join(dir, "go.sum")); err != nil {
|
||||
return newErrProxy(err)
|
||||
}
|
||||
|
||||
log.Debugf("tidying")
|
||||
cmd := exec.CommandContext(ctx, ctx.Config.GoMod.GoBinary, "mod", "tidy")
|
||||
cmd.Dir = dir
|
||||
cmd.Env = append(ctx.Config.GoMod.Env, os.Environ()...)
|
||||
if out, err := cmd.CombinedOutput(); err != nil {
|
||||
return newDetailedErrProxy(err, string(out))
|
||||
}
|
||||
|
||||
build.UnproxiedMain = build.Main
|
||||
build.UnproxiedDir = build.Dir
|
||||
build.Main = mainPackage
|
||||
build.Dir = dir
|
||||
return nil
|
||||
}
|
||||
|
||||
func copyGoSum(src, dst string) error {
|
||||
r, err := os.OpenFile(src, os.O_RDONLY, 0o666)
|
||||
if err != nil {
|
||||
if errors.Is(err, os.ErrNotExist) {
|
||||
return nil
|
||||
}
|
||||
return err
|
||||
}
|
||||
defer r.Close()
|
||||
|
||||
w, err := os.Create(dst)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer w.Close()
|
||||
|
||||
_, err = io.Copy(w, r)
|
||||
return err
|
||||
}
|
||||
|
258
internal/pipe/gomod/gomod_proxy_test.go
Normal file
258
internal/pipe/gomod/gomod_proxy_test.go
Normal file
@ -0,0 +1,258 @@
|
||||
package gomod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"runtime"
|
||||
"testing"
|
||||
|
||||
"github.com/goreleaser/goreleaser/internal/testlib"
|
||||
"github.com/goreleaser/goreleaser/pkg/config"
|
||||
"github.com/goreleaser/goreleaser/pkg/context"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
func TestGoModProxy(t *testing.T) {
|
||||
t.Run("goreleaser", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
GoBinary: "go",
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
Main: ".",
|
||||
Dir: ".",
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.161.1"
|
||||
|
||||
ctx.ModulePath = "github.com/goreleaser/goreleaser"
|
||||
|
||||
fakeGoModAndSum(t, ctx.ModulePath)
|
||||
require.NoError(t, ProxyPipe{}.Run(ctx))
|
||||
requireGoMod(t, ctx.ModulePath, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, ctx.ModulePath)
|
||||
require.Equal(t, ctx.ModulePath, ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, ".", ctx.Config.Builds[0].UnproxiedMain)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, ".", ctx.Config.Builds[0].UnproxiedDir)
|
||||
require.Equal(t, ctx.ModulePath, ctx.ModulePath)
|
||||
})
|
||||
|
||||
t.Run("nfpm", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
GoBinary: "go",
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
Main: "./cmd/nfpm",
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v2.3.1"
|
||||
|
||||
ctx.ModulePath = "github.com/goreleaser/nfpm/v2"
|
||||
fakeGoModAndSum(t, ctx.ModulePath)
|
||||
require.NoError(t, ProxyPipe{}.Run(ctx))
|
||||
requireGoMod(t, ctx.ModulePath, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, ctx.ModulePath+"/cmd/nfpm")
|
||||
require.Equal(t, ctx.ModulePath+"/cmd/nfpm", ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, ctx.ModulePath, ctx.ModulePath)
|
||||
})
|
||||
|
||||
// this repo does not have a go.sum file, which is ok, a project might not have any dependencies
|
||||
t.Run("no go.sum", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
GoBinary: "go",
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.0.1"
|
||||
|
||||
ctx.ModulePath = "github.com/goreleaser/example-mod-proxy"
|
||||
fakeGoMod(t, ctx.ModulePath)
|
||||
require.NoError(t, ProxyPipe{}.Run(ctx))
|
||||
requireGoMod(t, ctx.ModulePath, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, ctx.ModulePath)
|
||||
require.Equal(t, ctx.ModulePath, ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, ctx.ModulePath, ctx.ModulePath)
|
||||
})
|
||||
|
||||
t.Run("no perms", func(t *testing.T) {
|
||||
for file, mode := range map[string]os.FileMode{
|
||||
"go.mod": 0o500,
|
||||
"go.sum": 0o500,
|
||||
"main.go": 0o500,
|
||||
"../../../go.sum": 0o300,
|
||||
} {
|
||||
t.Run(file, func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
GoBinary: "go",
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.161.1"
|
||||
|
||||
ctx.ModulePath = "github.com/goreleaser/goreleaser"
|
||||
|
||||
fakeGoModAndSum(t, ctx.ModulePath)
|
||||
require.NoError(t, ProxyPipe{}.Run(ctx)) // should succeed at first
|
||||
|
||||
// change perms of a file and run again, which should now fail on that file.
|
||||
require.NoError(t, os.Chmod(filepath.Join(dist, "proxy", "foo", file), mode))
|
||||
require.ErrorAs(t, ProxyPipe{}.Run(ctx), &ErrProxy{})
|
||||
})
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("goreleaser with main.go", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
GoBinary: "go",
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
Main: "main.go",
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.161.1"
|
||||
|
||||
ctx.ModulePath = "github.com/goreleaser/goreleaser"
|
||||
|
||||
fakeGoModAndSum(t, ctx.ModulePath)
|
||||
require.NoError(t, ProxyPipe{}.Run(ctx))
|
||||
requireGoMod(t, ctx.ModulePath, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, ctx.ModulePath)
|
||||
require.Equal(t, ctx.ModulePath, ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, ctx.ModulePath, ctx.ModulePath)
|
||||
})
|
||||
}
|
||||
|
||||
func TestProxyDescription(t *testing.T) {
|
||||
require.NotEmpty(t, ProxyPipe{}.String())
|
||||
}
|
||||
|
||||
func TestSkip(t *testing.T) {
|
||||
t.Run("skip false gomod.proxy", func(t *testing.T) {
|
||||
require.True(t, ProxyPipe{}.Skip(context.New(config.Project{})))
|
||||
})
|
||||
|
||||
t.Run("skip snapshot", func(t *testing.T) {
|
||||
ctx := context.New(config.Project{
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
})
|
||||
ctx.ModulePath = "github.com/goreleaser/goreleaser"
|
||||
ctx.Snapshot = true
|
||||
require.True(t, ProxyPipe{}.Skip(ctx))
|
||||
})
|
||||
|
||||
t.Run("skip not a go module", func(t *testing.T) {
|
||||
ctx := context.New(config.Project{
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
})
|
||||
ctx.ModulePath = ""
|
||||
require.True(t, ProxyPipe{}.Skip(ctx))
|
||||
})
|
||||
|
||||
t.Run("dont skip", func(t *testing.T) {
|
||||
ctx := context.New(config.Project{
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
})
|
||||
ctx.ModulePath = "github.com/goreleaser/goreleaser"
|
||||
require.False(t, ProxyPipe{}.Skip(ctx))
|
||||
})
|
||||
}
|
||||
|
||||
func requireGoMod(tb testing.TB, module, version string) {
|
||||
tb.Helper()
|
||||
|
||||
mod, err := os.ReadFile("dist/proxy/foo/go.mod")
|
||||
require.NoError(tb, err)
|
||||
require.Contains(tb, string(mod), fmt.Sprintf(`module foo
|
||||
|
||||
go 1.17
|
||||
|
||||
require %s %s
|
||||
`, module, version))
|
||||
}
|
||||
|
||||
func requireMainGo(tb testing.TB, module string) {
|
||||
tb.Helper()
|
||||
|
||||
main, err := os.ReadFile("dist/proxy/foo/main.go")
|
||||
require.NoError(tb, err)
|
||||
require.Equal(tb, fmt.Sprintf(`
|
||||
// +build main
|
||||
package main
|
||||
|
||||
import _ "%s"
|
||||
`, module), string(main))
|
||||
}
|
||||
|
||||
func fakeGoModAndSum(tb testing.TB, module string) {
|
||||
tb.Helper()
|
||||
|
||||
fakeGoMod(tb, module)
|
||||
require.NoError(tb, os.WriteFile("go.sum", []byte("\n"), 0o666))
|
||||
}
|
||||
|
||||
func fakeGoMod(tb testing.TB, module string) {
|
||||
tb.Helper()
|
||||
require.NoError(tb, os.WriteFile("go.mod", []byte(fmt.Sprintf("module %s\n", module)), 0o666))
|
||||
}
|
@ -1,10 +1,8 @@
|
||||
package gomod
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"runtime"
|
||||
"testing"
|
||||
|
||||
"github.com/goreleaser/goreleaser/internal/testlib"
|
||||
@ -16,19 +14,7 @@ import (
|
||||
func TestRun(t *testing.T) {
|
||||
ctx := context.New(config.Project{})
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
testlib.AssertSkipped(t, Pipe{}.Run(ctx))
|
||||
require.Equal(t, "github.com/goreleaser/goreleaser", ctx.ModulePath)
|
||||
}
|
||||
|
||||
func TestRunSnapshot(t *testing.T) {
|
||||
ctx := context.New(config.Project{
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
})
|
||||
ctx.Snapshot = true
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
testlib.AssertSkipped(t, Pipe{}.Run(ctx))
|
||||
require.NoError(t, Pipe{}.Run(ctx))
|
||||
require.Equal(t, "github.com/goreleaser/goreleaser", ctx.ModulePath)
|
||||
}
|
||||
|
||||
@ -54,206 +40,3 @@ func TestRunCommandError(t *testing.T) {
|
||||
func TestDescription(t *testing.T) {
|
||||
require.NotEmpty(t, Pipe{}.String())
|
||||
}
|
||||
|
||||
func TestGoModProxy(t *testing.T) {
|
||||
t.Run("goreleaser", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
Main: ".",
|
||||
Dir: ".",
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.161.1"
|
||||
|
||||
mod := "github.com/goreleaser/goreleaser"
|
||||
|
||||
fakeGoModAndSum(t, mod)
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
require.NoError(t, Pipe{}.Run(ctx))
|
||||
requireGoMod(t, mod, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, mod)
|
||||
require.Equal(t, mod, ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, ".", ctx.Config.Builds[0].UnproxiedMain)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, ".", ctx.Config.Builds[0].UnproxiedDir)
|
||||
require.Equal(t, mod, ctx.ModulePath)
|
||||
})
|
||||
|
||||
t.Run("nfpm", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
Main: "./cmd/nfpm",
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v2.3.1"
|
||||
|
||||
mod := "github.com/goreleaser/nfpm/v2"
|
||||
fakeGoModAndSum(t, mod)
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
require.NoError(t, Pipe{}.Run(ctx))
|
||||
requireGoMod(t, mod, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, mod+"/cmd/nfpm")
|
||||
require.Equal(t, mod+"/cmd/nfpm", ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, mod, ctx.ModulePath)
|
||||
})
|
||||
|
||||
// this repo does not have a go.sum file, which is ok, a project might not have any dependencies
|
||||
t.Run("no go.sum", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.0.1"
|
||||
|
||||
mod := "github.com/goreleaser/example-mod-proxy"
|
||||
fakeGoMod(t, mod)
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
require.NoError(t, Pipe{}.Run(ctx))
|
||||
requireGoMod(t, mod, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, mod)
|
||||
require.Equal(t, mod, ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, mod, ctx.ModulePath)
|
||||
})
|
||||
|
||||
t.Run("no perms", func(t *testing.T) {
|
||||
for file, mode := range map[string]os.FileMode{
|
||||
"go.mod": 0o500,
|
||||
"go.sum": 0o500,
|
||||
"main.go": 0o500,
|
||||
"../../../go.sum": 0o300,
|
||||
} {
|
||||
t.Run(file, func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.161.1"
|
||||
|
||||
mod := "github.com/goreleaser/goreleaser"
|
||||
|
||||
fakeGoModAndSum(t, mod)
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
require.NoError(t, Pipe{}.Run(ctx)) // should succeed at first
|
||||
|
||||
// change perms of a file and run again, which should now fail on that file.
|
||||
require.NoError(t, os.Chmod(filepath.Join(dist, "proxy", "foo", file), mode))
|
||||
require.ErrorAs(t, Pipe{}.Run(ctx), &ErrProxy{})
|
||||
})
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("goreleaser with main.go", func(t *testing.T) {
|
||||
dir := testlib.Mktmp(t)
|
||||
dist := filepath.Join(dir, "dist")
|
||||
ctx := context.New(config.Project{
|
||||
Dist: dist,
|
||||
GoMod: config.GoMod{
|
||||
Proxy: true,
|
||||
},
|
||||
Builds: []config.Build{
|
||||
{
|
||||
ID: "foo",
|
||||
Goos: []string{runtime.GOOS},
|
||||
Goarch: []string{runtime.GOARCH},
|
||||
Main: "main.go",
|
||||
},
|
||||
},
|
||||
})
|
||||
ctx.Git.CurrentTag = "v0.161.1"
|
||||
|
||||
mod := "github.com/goreleaser/goreleaser"
|
||||
|
||||
fakeGoModAndSum(t, mod)
|
||||
require.NoError(t, Pipe{}.Default(ctx))
|
||||
require.NoError(t, Pipe{}.Run(ctx))
|
||||
requireGoMod(t, mod, ctx.Git.CurrentTag)
|
||||
requireMainGo(t, mod)
|
||||
require.Equal(t, mod, ctx.Config.Builds[0].Main)
|
||||
require.Equal(t, filepath.Join(dist, "proxy", "foo"), ctx.Config.Builds[0].Dir)
|
||||
require.Equal(t, mod, ctx.ModulePath)
|
||||
})
|
||||
}
|
||||
|
||||
func requireGoMod(tb testing.TB, module, version string) {
|
||||
tb.Helper()
|
||||
|
||||
mod, err := os.ReadFile("dist/proxy/foo/go.mod")
|
||||
require.NoError(tb, err)
|
||||
require.Contains(tb, string(mod), fmt.Sprintf(`module foo
|
||||
|
||||
go 1.17
|
||||
|
||||
require %s %s
|
||||
`, module, version))
|
||||
}
|
||||
|
||||
func requireMainGo(tb testing.TB, module string) {
|
||||
tb.Helper()
|
||||
|
||||
main, err := os.ReadFile("dist/proxy/foo/main.go")
|
||||
require.NoError(tb, err)
|
||||
require.Equal(tb, fmt.Sprintf(`
|
||||
// +build main
|
||||
package main
|
||||
|
||||
import _ "%s"
|
||||
`, module), string(main))
|
||||
}
|
||||
|
||||
func fakeGoModAndSum(tb testing.TB, module string) {
|
||||
tb.Helper()
|
||||
|
||||
fakeGoMod(tb, module)
|
||||
require.NoError(tb, os.WriteFile("go.sum", []byte("\n"), 0o666))
|
||||
}
|
||||
|
||||
func fakeGoMod(tb testing.TB, module string) {
|
||||
tb.Helper()
|
||||
require.NoError(tb, os.WriteFile("go.mod", []byte(fmt.Sprintf("module %s\n", module)), 0o666))
|
||||
}
|
||||
|
@ -48,6 +48,7 @@ var BuildPipeline = []Piper{
|
||||
snapshot.Pipe{}, // snapshot version handling
|
||||
dist.Pipe{}, // ensure ./dist is clean
|
||||
gomod.Pipe{}, // setup gomod-related stuff
|
||||
gomod.ProxyPipe{}, // proxy gomod if needed
|
||||
effectiveconfig.Pipe{}, // writes the actual config (with defaults et al set) to dist
|
||||
changelog.Pipe{}, // builds the release changelog
|
||||
build.Pipe{}, // build
|
||||
|
Loading…
Reference in New Issue
Block a user