2017-04-23 13:22:12 +02:00
|
|
|
package goreleaserlib
|
2017-04-21 20:25:32 +02:00
|
|
|
|
|
|
|
import (
|
2017-06-22 05:09:14 +02:00
|
|
|
"fmt"
|
2017-04-21 20:25:32 +02:00
|
|
|
"io/ioutil"
|
|
|
|
"os"
|
2017-06-22 05:38:24 +02:00
|
|
|
"strings"
|
2017-04-21 20:25:32 +02:00
|
|
|
|
2017-06-22 05:09:14 +02:00
|
|
|
"github.com/apex/log"
|
2017-12-06 05:02:52 +02:00
|
|
|
"github.com/apex/log/handlers/cli"
|
2017-04-21 20:25:32 +02:00
|
|
|
"github.com/goreleaser/goreleaser/config"
|
|
|
|
"github.com/goreleaser/goreleaser/context"
|
|
|
|
"github.com/goreleaser/goreleaser/pipeline"
|
2017-09-12 04:45:49 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/archive"
|
2017-12-02 20:41:05 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/artifactory"
|
2017-09-12 04:45:49 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/brew"
|
2017-04-21 20:25:32 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/build"
|
2017-10-16 00:21:35 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/changelog"
|
2017-09-12 04:45:49 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/checksums"
|
2017-04-21 20:25:32 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/defaults"
|
2017-12-09 02:30:02 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/dist"
|
2017-09-12 04:31:00 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/docker"
|
2017-12-10 15:28:01 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/effectiveconfig"
|
2017-04-21 20:25:32 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/env"
|
2017-09-12 04:45:49 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/fpm"
|
2017-04-21 20:25:32 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/git"
|
2017-09-12 04:45:49 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/release"
|
2017-12-13 18:14:01 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/sign"
|
2017-09-12 04:45:49 +02:00
|
|
|
"github.com/goreleaser/goreleaser/pipeline/snapcraft"
|
2017-07-08 17:05:57 +02:00
|
|
|
yaml "gopkg.in/yaml.v2"
|
2017-04-21 20:25:32 +02:00
|
|
|
)
|
|
|
|
|
2017-12-09 01:34:44 +02:00
|
|
|
var (
|
|
|
|
normalPadding = cli.Default.Padding
|
|
|
|
increasedPadding = normalPadding * 2
|
|
|
|
)
|
|
|
|
|
|
|
|
func init() {
|
|
|
|
log.SetHandler(cli.Default)
|
|
|
|
}
|
|
|
|
|
2017-12-02 23:53:19 +02:00
|
|
|
var pipes = []pipeline.Piper{
|
2017-12-10 15:28:01 +02:00
|
|
|
defaults.Pipe{}, // load default configs
|
|
|
|
dist.Pipe{}, // ensure ./dist is clean
|
|
|
|
git.Pipe{}, // get and validate git repo state
|
2017-12-10 15:36:39 +02:00
|
|
|
effectiveconfig.Pipe{}, // writes the actual config (with defaults et al set) to dist
|
2017-12-10 15:28:01 +02:00
|
|
|
changelog.Pipe{}, // builds the release changelog
|
|
|
|
env.Pipe{}, // load and validate environment variables
|
|
|
|
build.Pipe{}, // build
|
|
|
|
archive.Pipe{}, // archive (tar.gz, zip, etc)
|
|
|
|
fpm.Pipe{}, // archive via fpm (deb, rpm, etc)
|
|
|
|
snapcraft.Pipe{}, // archive via snapcraft (snap)
|
|
|
|
checksums.Pipe{}, // checksums of the files
|
2017-12-13 18:14:01 +02:00
|
|
|
sign.Pipe{}, // sign artifacts
|
2017-12-10 15:28:01 +02:00
|
|
|
docker.Pipe{}, // create and push docker images
|
2017-12-10 17:55:55 +02:00
|
|
|
artifactory.Pipe{}, // push to artifactory
|
2017-12-10 15:28:01 +02:00
|
|
|
release.Pipe{}, // release to github
|
|
|
|
brew.Pipe{}, // push to brew tap
|
2017-04-21 20:25:32 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
// Flags interface represents an extractor of cli flags
|
|
|
|
type Flags interface {
|
|
|
|
IsSet(s string) bool
|
|
|
|
String(s string) string
|
2017-07-15 21:49:52 +02:00
|
|
|
Int(s string) int
|
2017-04-21 20:25:32 +02:00
|
|
|
Bool(s string) bool
|
|
|
|
}
|
|
|
|
|
|
|
|
// Release runs the release process with the given flags
|
|
|
|
func Release(flags Flags) error {
|
2017-07-05 04:51:45 +02:00
|
|
|
var file = getConfigFile(flags)
|
2017-04-21 20:25:32 +02:00
|
|
|
var notes = flags.String("release-notes")
|
2017-06-22 05:25:52 +02:00
|
|
|
if flags.Bool("debug") {
|
|
|
|
log.SetLevel(log.DebugLevel)
|
|
|
|
}
|
2017-04-21 20:25:32 +02:00
|
|
|
cfg, err := config.Load(file)
|
|
|
|
if err != nil {
|
|
|
|
// Allow file not found errors if config file was not
|
|
|
|
// explicitly specified
|
|
|
|
_, statErr := os.Stat(file)
|
|
|
|
if !os.IsNotExist(statErr) || flags.IsSet("config") {
|
|
|
|
return err
|
|
|
|
}
|
2017-07-05 04:51:45 +02:00
|
|
|
log.WithField("file", file).Warn("could not load config, using defaults")
|
2017-04-21 20:25:32 +02:00
|
|
|
}
|
|
|
|
var ctx = context.New(cfg)
|
2017-07-15 21:49:52 +02:00
|
|
|
ctx.Parallelism = flags.Int("parallelism")
|
2017-11-04 19:22:29 +02:00
|
|
|
ctx.Debug = flags.Bool("debug")
|
2017-07-15 21:49:52 +02:00
|
|
|
log.Debugf("parallelism: %v", ctx.Parallelism)
|
2017-04-21 20:25:32 +02:00
|
|
|
ctx.Validate = !flags.Bool("skip-validate")
|
|
|
|
ctx.Publish = !flags.Bool("skip-publish")
|
|
|
|
if notes != "" {
|
|
|
|
bts, err := ioutil.ReadFile(notes)
|
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
2017-10-04 16:06:05 +02:00
|
|
|
log.WithField("file", notes).Info("loaded custom release notes")
|
|
|
|
log.WithField("file", notes).Debugf("custon release notes: \n%s", string(bts))
|
2017-04-21 20:25:32 +02:00
|
|
|
ctx.ReleaseNotes = string(bts)
|
|
|
|
}
|
2017-04-29 12:49:22 +02:00
|
|
|
ctx.Snapshot = flags.Bool("snapshot")
|
|
|
|
if ctx.Snapshot {
|
2017-06-22 15:47:34 +02:00
|
|
|
log.Info("publishing disabled in snapshot mode")
|
2017-04-29 12:49:22 +02:00
|
|
|
ctx.Publish = false
|
|
|
|
}
|
2017-07-05 03:53:50 +02:00
|
|
|
ctx.RmDist = flags.Bool("rm-dist")
|
2017-04-21 20:25:32 +02:00
|
|
|
for _, pipe := range pipes {
|
2017-12-09 01:34:44 +02:00
|
|
|
cli.Default.Padding = normalPadding
|
2017-12-02 23:53:19 +02:00
|
|
|
log.Infof("\033[1m%s\033[0m", strings.ToUpper(pipe.String()))
|
2017-12-09 01:34:44 +02:00
|
|
|
cli.Default.Padding = increasedPadding
|
2017-08-20 22:46:30 +02:00
|
|
|
if err := handle(pipe.Run(ctx)); err != nil {
|
2017-04-21 20:25:32 +02:00
|
|
|
return err
|
|
|
|
}
|
|
|
|
}
|
2017-12-09 01:34:44 +02:00
|
|
|
cli.Default.Padding = normalPadding
|
2017-04-21 20:25:32 +02:00
|
|
|
return nil
|
|
|
|
}
|
2017-04-27 11:03:26 +02:00
|
|
|
|
2017-08-20 22:46:30 +02:00
|
|
|
func handle(err error) error {
|
|
|
|
if err == nil {
|
|
|
|
return nil
|
|
|
|
}
|
2017-09-12 04:59:43 +02:00
|
|
|
if pipeline.IsSkip(err) {
|
|
|
|
log.WithField("reason", err.Error()).Warn("skipped")
|
2017-08-20 22:46:30 +02:00
|
|
|
return nil
|
|
|
|
}
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
|
2017-04-27 11:03:26 +02:00
|
|
|
// InitProject creates an example goreleaser.yml in the current directory
|
2017-04-28 13:25:29 +02:00
|
|
|
func InitProject(filename string) error {
|
2017-04-27 11:03:26 +02:00
|
|
|
if _, err := os.Stat(filename); !os.IsNotExist(err) {
|
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
return fmt.Errorf("%s already exists", filename)
|
|
|
|
}
|
|
|
|
|
2017-04-28 13:25:29 +02:00
|
|
|
var ctx = context.New(config.Project{})
|
|
|
|
var pipe = defaults.Pipe{}
|
|
|
|
if err := pipe.Run(ctx); err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
out, err := yaml.Marshal(ctx.Config)
|
|
|
|
if err != nil {
|
|
|
|
return err
|
|
|
|
}
|
|
|
|
|
|
|
|
return ioutil.WriteFile(filename, out, 0644)
|
2017-04-27 11:03:26 +02:00
|
|
|
}
|
2017-07-05 04:51:45 +02:00
|
|
|
|
|
|
|
func getConfigFile(flags Flags) string {
|
|
|
|
var config = flags.String("config")
|
|
|
|
if flags.IsSet("config") {
|
|
|
|
return config
|
|
|
|
}
|
2017-08-28 01:17:09 +02:00
|
|
|
for _, f := range []string{
|
|
|
|
".goreleaser.yml",
|
|
|
|
".goreleaser.yaml",
|
|
|
|
"goreleaser.yml",
|
|
|
|
"goreleaser.yaml",
|
|
|
|
} {
|
2017-07-05 04:51:45 +02:00
|
|
|
_, ferr := os.Stat(f)
|
|
|
|
if ferr == nil || os.IsExist(ferr) {
|
|
|
|
return f
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return config
|
|
|
|
}
|