github.skymusic.top/goreleaser/goreleaser@v0.92.0/internal/pipe/build/build_test.go (about)

     1  package build
     2  
     3  import (
     4  	"errors"
     5  	"os"
     6  	"path/filepath"
     7  	"testing"
     8  
     9  	"github.com/goreleaser/goreleaser/internal/artifact"
    10  	"github.com/goreleaser/goreleaser/internal/testlib"
    11  	"github.com/goreleaser/goreleaser/internal/tmpl"
    12  	api "github.com/goreleaser/goreleaser/pkg/build"
    13  	"github.com/goreleaser/goreleaser/pkg/config"
    14  	"github.com/goreleaser/goreleaser/pkg/context"
    15  	"github.com/stretchr/testify/assert"
    16  )
    17  
    18  var fakeArtifact = artifact.Artifact{
    19  	Name: "fake",
    20  }
    21  
    22  type fakeBuilder struct {
    23  	fail bool
    24  }
    25  
    26  func (*fakeBuilder) WithDefaults(build config.Build) config.Build {
    27  	return build
    28  }
    29  
    30  var errFailedBuild = errors.New("fake builder failed")
    31  
    32  func (f *fakeBuilder) Build(ctx *context.Context, build config.Build, options api.Options) error {
    33  	if f.fail {
    34  		return errFailedBuild
    35  	}
    36  	ctx.Artifacts.Add(fakeArtifact)
    37  	return nil
    38  }
    39  
    40  func init() {
    41  	api.Register("fake", &fakeBuilder{})
    42  	api.Register("fakeFail", &fakeBuilder{
    43  		fail: true,
    44  	})
    45  }
    46  
    47  func TestPipeDescription(t *testing.T) {
    48  	assert.NotEmpty(t, Pipe{}.String())
    49  }
    50  
    51  func TestBuild(t *testing.T) {
    52  	var config = config.Project{
    53  		Builds: []config.Build{
    54  			{
    55  				Lang:   "fake",
    56  				Binary: "testing.v{{.Version}}",
    57  				Flags:  []string{"-n"},
    58  				Env:    []string{"BLAH=1"},
    59  			},
    60  		},
    61  	}
    62  	var ctx = &context.Context{
    63  		Artifacts: artifact.New(),
    64  		Git: context.GitInfo{
    65  			CurrentTag: "v1.2.3",
    66  			Commit:     "123",
    67  		},
    68  		Version: "1.2.3",
    69  		Config:  config,
    70  	}
    71  	error := doBuild(ctx, ctx.Config.Builds[0], "darwin_amd64")
    72  	assert.NoError(t, error)
    73  }
    74  
    75  func TestRunPipe(t *testing.T) {
    76  	var config = config.Project{
    77  		Builds: []config.Build{
    78  			{
    79  				Lang:    "fake",
    80  				Binary:  "testing",
    81  				Flags:   []string{"-v"},
    82  				Ldflags: []string{"-X main.test=testing"},
    83  				Targets: []string{"whatever"},
    84  			},
    85  		},
    86  	}
    87  	var ctx = context.New(config)
    88  	ctx.Git.CurrentTag = "2.4.5"
    89  	assert.NoError(t, Pipe{}.Run(ctx))
    90  	assert.Equal(t, ctx.Artifacts.List(), []artifact.Artifact{fakeArtifact})
    91  }
    92  
    93  func TestRunFullPipe(t *testing.T) {
    94  	folder, back := testlib.Mktmp(t)
    95  	defer back()
    96  	var pre = filepath.Join(folder, "pre")
    97  	var post = filepath.Join(folder, "post")
    98  	var config = config.Project{
    99  		Builds: []config.Build{
   100  			{
   101  				Lang:    "fake",
   102  				Binary:  "testing",
   103  				Flags:   []string{"-v"},
   104  				Ldflags: []string{"-X main.test=testing"},
   105  				Hooks: config.Hooks{
   106  					Pre:  "touch " + pre,
   107  					Post: "touch " + post,
   108  				},
   109  				Targets: []string{"whatever"},
   110  			},
   111  		},
   112  	}
   113  	var ctx = context.New(config)
   114  	ctx.Git.CurrentTag = "2.4.5"
   115  	assert.NoError(t, Pipe{}.Run(ctx))
   116  	assert.Equal(t, ctx.Artifacts.List(), []artifact.Artifact{fakeArtifact})
   117  	assert.True(t, exists(pre), pre)
   118  	assert.True(t, exists(post), post)
   119  }
   120  
   121  func TestRunFullPipeFail(t *testing.T) {
   122  	folder, back := testlib.Mktmp(t)
   123  	defer back()
   124  	var pre = filepath.Join(folder, "pre")
   125  	var post = filepath.Join(folder, "post")
   126  	var config = config.Project{
   127  		Builds: []config.Build{
   128  			{
   129  				Lang:    "fakeFail",
   130  				Binary:  "testing",
   131  				Flags:   []string{"-v"},
   132  				Ldflags: []string{"-X main.test=testing"},
   133  				Hooks: config.Hooks{
   134  					Pre:  "touch " + pre,
   135  					Post: "touch " + post,
   136  				},
   137  				Targets: []string{"whatever"},
   138  			},
   139  		},
   140  	}
   141  	var ctx = context.New(config)
   142  	ctx.Git.CurrentTag = "2.4.5"
   143  	assert.EqualError(t, Pipe{}.Run(ctx), errFailedBuild.Error())
   144  	assert.Empty(t, ctx.Artifacts.List())
   145  	assert.True(t, exists(pre), pre)
   146  	assert.False(t, exists(post), post)
   147  }
   148  
   149  func TestRunPipeFailingHooks(t *testing.T) {
   150  	var config = config.Project{
   151  		Builds: []config.Build{
   152  			{
   153  				Lang:    "fake",
   154  				Binary:  "hooks",
   155  				Hooks:   config.Hooks{},
   156  				Targets: []string{"whatever"},
   157  			},
   158  		},
   159  	}
   160  	t.Run("pre-hook", func(t *testing.T) {
   161  		var ctx = context.New(config)
   162  		ctx.Git.CurrentTag = "2.3.4"
   163  		ctx.Config.Builds[0].Hooks.Pre = "exit 1"
   164  		ctx.Config.Builds[0].Hooks.Post = "echo post"
   165  		assert.EqualError(t, Pipe{}.Run(ctx), `pre hook failed: `)
   166  	})
   167  	t.Run("post-hook", func(t *testing.T) {
   168  		var ctx = context.New(config)
   169  		ctx.Git.CurrentTag = "2.3.4"
   170  		ctx.Config.Builds[0].Hooks.Pre = "echo pre"
   171  		ctx.Config.Builds[0].Hooks.Post = "exit 1"
   172  		assert.EqualError(t, Pipe{}.Run(ctx), `post hook failed: `)
   173  	})
   174  }
   175  
   176  func TestDefaultNoBuilds(t *testing.T) {
   177  	var ctx = &context.Context{
   178  		Config: config.Project{},
   179  	}
   180  	assert.NoError(t, Pipe{}.Default(ctx))
   181  }
   182  
   183  func TestDefaultExpandEnv(t *testing.T) {
   184  	assert.NoError(t, os.Setenv("BAR", "FOOBAR"))
   185  	var ctx = &context.Context{
   186  		Config: config.Project{
   187  			Builds: []config.Build{
   188  				{
   189  					Env: []string{
   190  						"FOO=bar_$BAR",
   191  					},
   192  				},
   193  			},
   194  		},
   195  	}
   196  	assert.NoError(t, Pipe{}.Default(ctx))
   197  	var env = ctx.Config.Builds[0].Env[0]
   198  	assert.Equal(t, "FOO=bar_FOOBAR", env)
   199  }
   200  
   201  func TestDefaultEmptyBuild(t *testing.T) {
   202  	var ctx = &context.Context{
   203  		Config: config.Project{
   204  			ProjectName: "foo",
   205  			Builds: []config.Build{
   206  				{},
   207  			},
   208  		},
   209  	}
   210  	assert.NoError(t, Pipe{}.Default(ctx))
   211  	var build = ctx.Config.Builds[0]
   212  	assert.Equal(t, ctx.Config.ProjectName, build.Binary)
   213  	assert.Equal(t, ".", build.Main)
   214  	assert.Equal(t, []string{"linux", "darwin"}, build.Goos)
   215  	assert.Equal(t, []string{"amd64", "386"}, build.Goarch)
   216  	assert.Equal(t, []string{"6"}, build.Goarm)
   217  	assert.Len(t, build.Ldflags, 1)
   218  	assert.Equal(t, "-s -w -X main.version={{.Version}} -X main.commit={{.Commit}} -X main.date={{.Date}}", build.Ldflags[0])
   219  }
   220  
   221  func TestDefaultPartialBuilds(t *testing.T) {
   222  	var ctx = &context.Context{
   223  		Config: config.Project{
   224  			Builds: []config.Build{
   225  				{
   226  					Binary: "bar",
   227  					Goos:   []string{"linux"},
   228  					Main:   "./cmd/main.go",
   229  				},
   230  				{
   231  					Binary:  "foo",
   232  					Ldflags: []string{"-s -w"},
   233  					Goarch:  []string{"386"},
   234  				},
   235  			},
   236  		},
   237  	}
   238  	assert.NoError(t, Pipe{}.Default(ctx))
   239  	t.Run("build0", func(t *testing.T) {
   240  		var build = ctx.Config.Builds[0]
   241  		assert.Equal(t, "bar", build.Binary)
   242  		assert.Equal(t, "./cmd/main.go", build.Main)
   243  		assert.Equal(t, []string{"linux"}, build.Goos)
   244  		assert.Equal(t, []string{"amd64", "386"}, build.Goarch)
   245  		assert.Equal(t, []string{"6"}, build.Goarm)
   246  		assert.Len(t, build.Ldflags, 1)
   247  		assert.Equal(t, "-s -w -X main.version={{.Version}} -X main.commit={{.Commit}} -X main.date={{.Date}}", build.Ldflags[0])
   248  	})
   249  	t.Run("build1", func(t *testing.T) {
   250  		var build = ctx.Config.Builds[1]
   251  		assert.Equal(t, "foo", build.Binary)
   252  		assert.Equal(t, ".", build.Main)
   253  		assert.Equal(t, []string{"linux", "darwin"}, build.Goos)
   254  		assert.Equal(t, []string{"386"}, build.Goarch)
   255  		assert.Equal(t, []string{"6"}, build.Goarm)
   256  		assert.Len(t, build.Ldflags, 1)
   257  		assert.Equal(t, "-s -w", build.Ldflags[0])
   258  	})
   259  }
   260  
   261  func TestDefaultFillSingleBuild(t *testing.T) {
   262  	_, back := testlib.Mktmp(t)
   263  	defer back()
   264  
   265  	var ctx = &context.Context{
   266  		Config: config.Project{
   267  			ProjectName: "foo",
   268  			SingleBuild: config.Build{
   269  				Main: "testreleaser",
   270  			},
   271  		},
   272  	}
   273  	assert.NoError(t, Pipe{}.Default(ctx))
   274  	assert.Len(t, ctx.Config.Builds, 1)
   275  	assert.Equal(t, ctx.Config.Builds[0].Binary, "foo")
   276  }
   277  
   278  func TestExtWindows(t *testing.T) {
   279  	assert.Equal(t, ".exe", extFor("windows_amd64"))
   280  	assert.Equal(t, ".exe", extFor("windows_386"))
   281  }
   282  
   283  func TestExtOthers(t *testing.T) {
   284  	assert.Empty(t, "", extFor("linux_amd64"))
   285  	assert.Empty(t, "", extFor("linuxwin_386"))
   286  	assert.Empty(t, "", extFor("winasdasd_sad"))
   287  }
   288  
   289  func TestTemplate(t *testing.T) {
   290  	var ctx = context.New(config.Project{})
   291  	ctx.Git = context.GitInfo{
   292  		CurrentTag: "v1.2.3",
   293  		Commit:     "123",
   294  	}
   295  	ctx.Version = "1.2.3"
   296  	ctx.Env = map[string]string{"FOO": "123"}
   297  	binary, err := tmpl.New(ctx).
   298  		Apply(`-s -w -X main.version={{.Version}} -X main.tag={{.Tag}} -X main.date={{.Date}} -X main.commit={{.Commit}} -X "main.foo={{.Env.FOO}}"`)
   299  	assert.NoError(t, err)
   300  	assert.Contains(t, binary, "-s -w")
   301  	assert.Contains(t, binary, "-X main.version=1.2.3")
   302  	assert.Contains(t, binary, "-X main.tag=v1.2.3")
   303  	assert.Contains(t, binary, "-X main.commit=123")
   304  	assert.Contains(t, binary, "-X main.date=")
   305  	assert.Contains(t, binary, `-X "main.foo=123"`)
   306  }
   307  
   308  //
   309  // Helpers
   310  //
   311  
   312  func exists(file string) bool {
   313  	_, err := os.Stat(file)
   314  	return !os.IsNotExist(err)
   315  }