From 790a2e6574e5f1d7af5fe2883ae3e7ee3da13093 Mon Sep 17 00:00:00 2001 From: tsuyoshiwada Date: Wed, 28 Feb 2018 23:09:54 +0900 Subject: [PATCH 1/4] feat: Supports vim like `j/k` keybind with item selection of `--init` --- Gopkg.lock | 6 +++--- Gopkg.toml | 2 +- vendor/gopkg.in/AlecAivazis/survey.v1/multiselect.go | 4 ++-- vendor/gopkg.in/AlecAivazis/survey.v1/select.go | 8 ++++---- .../gopkg.in/AlecAivazis/survey.v1/terminal/LICENSE.txt | 0 vendor/gopkg.in/AlecAivazis/survey.v1/validate.go | 5 ++++- 6 files changed, 14 insertions(+), 11 deletions(-) create mode 100644 vendor/gopkg.in/AlecAivazis/survey.v1/terminal/LICENSE.txt diff --git a/Gopkg.lock b/Gopkg.lock index 1dc0e963..d07ec387 100644 --- a/Gopkg.lock +++ b/Gopkg.lock @@ -74,8 +74,8 @@ "core", "terminal" ] - revision = "0aa8b6a162b391fe2d95648b7677d1d6ac2090a6" - version = "v1.4.1" + revision = "9f89d9dd66613216993dc300f9f3dbae9c3c9bda" + version = "v1.4.2" [[projects]] name = "gopkg.in/kyokomi/emoji.v1" @@ -92,6 +92,6 @@ [solve-meta] analyzer-name = "dep" analyzer-version = 1 - inputs-digest = "0be1d1c2f1a9b1c1f1d63ad065141425b62687efb378f6657b088ddf993c3882" + inputs-digest = "da532fb70b3049dffe6ae9f73b3f0a742452639096a325ac5d2400be6ad0559e" solver-name = "gps-cdcl" solver-version = 1 diff --git a/Gopkg.toml b/Gopkg.toml index 995c4772..3e1c7751 100644 --- a/Gopkg.toml +++ b/Gopkg.toml @@ -29,7 +29,7 @@ [[constraint]] name = "gopkg.in/AlecAivazis/survey.v1" - version = "1.4.1" + version = "1.4.2" [[constraint]] name = "gopkg.in/kyokomi/emoji.v1" diff --git a/vendor/gopkg.in/AlecAivazis/survey.v1/multiselect.go b/vendor/gopkg.in/AlecAivazis/survey.v1/multiselect.go index 7fd6ca4b..24c4fb35 100644 --- a/vendor/gopkg.in/AlecAivazis/survey.v1/multiselect.go +++ b/vendor/gopkg.in/AlecAivazis/survey.v1/multiselect.go @@ -61,7 +61,7 @@ var MultiSelectQuestionTemplate = ` // OnChange is called on every keypress. func (m *MultiSelect) OnChange(line []rune, pos int, key rune) (newLine []rune, newPos int, ok bool) { - if key == terminal.KeyArrowUp { + if key == terminal.KeyArrowUp || key == 'k' { // if we are at the top of the list if m.selectedIndex == 0 { // go to the bottom @@ -70,7 +70,7 @@ func (m *MultiSelect) OnChange(line []rune, pos int, key rune) (newLine []rune, // decrement the selected index m.selectedIndex-- } - } else if key == terminal.KeyArrowDown { + } else if key == terminal.KeyArrowDown || key == 'j' { // if we are at the bottom of the list if m.selectedIndex == len(m.Options)-1 { // start at the top diff --git a/vendor/gopkg.in/AlecAivazis/survey.v1/select.go b/vendor/gopkg.in/AlecAivazis/survey.v1/select.go index 74cb77c3..eefe5cf0 100644 --- a/vendor/gopkg.in/AlecAivazis/survey.v1/select.go +++ b/vendor/gopkg.in/AlecAivazis/survey.v1/select.go @@ -61,8 +61,8 @@ func (s *Select) OnChange(line []rune, pos int, key rune) (newLine []rune, newPo // if the user pressed the enter key if key == terminal.KeyEnter { return []rune(s.Options[s.selectedIndex]), 0, true - // if the user pressed the up arrow - } else if key == terminal.KeyArrowUp { + // if the user pressed the up arrow or 'k' to emulate vim + } else if key == terminal.KeyArrowUp || key == 'k' { s.useDefault = false // if we are at the top of the list @@ -73,8 +73,8 @@ func (s *Select) OnChange(line []rune, pos int, key rune) (newLine []rune, newPo // otherwise we are not at the top of the list so decrement the selected index s.selectedIndex-- } - // if the user pressed down and there is room to move - } else if key == terminal.KeyArrowDown { + // if the user pressed down or 'j' to emulate vim + } else if key == terminal.KeyArrowDown || key == 'j' { s.useDefault = false // if we are at the bottom of the list if s.selectedIndex == len(s.Options)-1 { diff --git a/vendor/gopkg.in/AlecAivazis/survey.v1/terminal/LICENSE.txt b/vendor/gopkg.in/AlecAivazis/survey.v1/terminal/LICENSE.txt new file mode 100644 index 00000000..e69de29b diff --git a/vendor/gopkg.in/AlecAivazis/survey.v1/validate.go b/vendor/gopkg.in/AlecAivazis/survey.v1/validate.go index a577614a..208eac91 100644 --- a/vendor/gopkg.in/AlecAivazis/survey.v1/validate.go +++ b/vendor/gopkg.in/AlecAivazis/survey.v1/validate.go @@ -8,8 +8,11 @@ import ( // Required does not allow an empty value func Required(val interface{}) error { + // the reflect value of the result + value := reflect.ValueOf(val) + // if the value passed in is the zero value of the appropriate type - if isZero(reflect.ValueOf(val)) { + if isZero(value) && value.Kind() != reflect.Bool { return errors.New("Value is required") } return nil From 40598132fcaecca49b0e38a8c904630ffc0de1ec Mon Sep 17 00:00:00 2001 From: tsuyoshiwada Date: Wed, 28 Feb 2018 23:18:25 +0900 Subject: [PATCH 2/4] chore: Fix release flow (retry) --- .travis.yml | 17 ++++++++++------- scripts/release.sh | 14 ++++++-------- 2 files changed, 16 insertions(+), 15 deletions(-) diff --git a/.travis.yml b/.travis.yml index 0836ac29..bde1d8e2 100644 --- a/.travis.yml +++ b/.travis.yml @@ -6,17 +6,20 @@ go: - 1.9 before_install: - go get github.com/mattn/goveralls - - go get github.com/mitchellh/gox - - go get github.com/tcnksm/ghr before_script: - export TZ=Asia/Tokyo - sudo timedatectl set-timezone Asia/Tokyo - timedatectl script: - make test - - goveralls -service=travis-ci -branches: - only: - - master after_success: - - ./scripts/release.sh + - goveralls -service=travis-ci +before_deploy: + - go get github.com/mitchellh/gox + - go get github.com/tcnksm/ghr +deploy: + provider: script + script: ./scripts/release.sh + on: + tags: true + branch: master diff --git a/scripts/release.sh b/scripts/release.sh index 65660b6e..c4f681e4 100755 --- a/scripts/release.sh +++ b/scripts/release.sh @@ -2,11 +2,9 @@ REPO_ROOT=$(git rev-parse --show-toplevel) -if [[ "$TRAVIS_BRANCH" == "master" ]] && [[ "$TRAVIS_TAG" != "" ]] && [[ "$TRAVIS_PULL_REQUEST" == "" ]]; then - echo "Start release ..." - gox -os="darwin linux windows" -arch="amd64 386" -output="$REPO_ROOT/dist/{{.Dir}}_{{.OS}}_{{.Arch}}" ./cmd/git-chglog - ghr --username git-chglog --token $GITHUB_TOKEN --replace `grep 'Version =' ./cmd/git-chglog/version.go | sed -E 's/.*"(.+)"$$/\1/'` dist/ - echo "Released!" -else - echo "Skip release" -fi +echo "Start release ..." + +gox -os="darwin linux windows" -arch="amd64 386" -output="$REPO_ROOT/dist/{{.Dir}}_{{.OS}}_{{.Arch}}" ./cmd/git-chglog +ghr --username git-chglog --token $GITHUB_TOKEN --replace `grep 'Version =' ./cmd/git-chglog/version.go | sed -E 's/.*"(.+)"$$/\1/'` dist/ + +echo "Released!" From ed6fb2722ea84db8b9349d1bff61285cf5c0878d Mon Sep 17 00:00:00 2001 From: tsuyoshiwada Date: Fri, 2 Mar 2018 00:51:56 +0900 Subject: [PATCH 3/4] feat: Add template for `Keep a changelog` to the `--init` option --- cmd/git-chglog/custom_template_builder.go | 136 +++++++++++++++++ ...est.go => custom_template_builder_test.go} | 34 ++--- cmd/git-chglog/initializer.go | 32 ++-- cmd/git-chglog/initializer_test.go | 4 +- cmd/git-chglog/kac_template_builder.go | 118 +++++++++++++++ cmd/git-chglog/kac_template_builder_test.go | 42 ++++++ cmd/git-chglog/main.go | 2 +- cmd/git-chglog/template_builder.go | 137 +----------------- cmd/git-chglog/variables.go | 8 +- 9 files changed, 344 insertions(+), 169 deletions(-) create mode 100644 cmd/git-chglog/custom_template_builder.go rename cmd/git-chglog/{template_builder_test.go => custom_template_builder_test.go} (85%) create mode 100644 cmd/git-chglog/kac_template_builder.go create mode 100644 cmd/git-chglog/kac_template_builder_test.go diff --git a/cmd/git-chglog/custom_template_builder.go b/cmd/git-chglog/custom_template_builder.go new file mode 100644 index 00000000..90f7752f --- /dev/null +++ b/cmd/git-chglog/custom_template_builder.go @@ -0,0 +1,136 @@ +package main + +import "fmt" + +type customTemplateBuilderImpl struct{} + +// NewCustomTemplateBuilder ... +func NewCustomTemplateBuilder() TemplateBuilder { + return &customTemplateBuilderImpl{} +} + +// Build ... +func (t *customTemplateBuilderImpl) Build(ans *Answer) (string, error) { + // versions + tpl := "{{range .Versions}}\n" + + // version header + tpl += t.versionHeader(ans.Style, ans.Template) + + // commits + tpl += t.commits(ans.Template, ans.CommitMessageFormat) + + // revert + if ans.IncludeReverts { + tpl += t.reverts() + } + + // merges + if ans.IncludeMerges { + tpl += t.merges(ans.Style) + } + + // notes + tpl += t.notes() + + // versions end + tpl += "\n{{end}}" + + return tpl, nil +} + +func (*customTemplateBuilderImpl) versionHeader(style, template string) string { + var ( + tpl string + tagName = "{{.Tag.Name}}" + date = "{{datetime \"2006-01-02\" .Tag.Date}}" + ) + + // parts + switch style { + case styleGitHub: + tpl = "\n" + tagName = "{{if .Tag.Previous}}[{{.Tag.Name}}]({{$.Info.RepositoryURL}}/compare/{{.Tag.Previous.Name}}...{{.Tag.Name}}){{else}}{{.Tag.Name}}{{end}}" + } + + // format + switch template { + case tplStandard: + tpl = fmt.Sprintf("%s## %s (%s)\n", + tpl, + tagName, + date, + ) + case tplCool: + tpl = fmt.Sprintf("%s## %s\n\n> %s\n", + tpl, + tagName, + date, + ) + } + + return tpl +} + +func (*customTemplateBuilderImpl) commits(template, format string) string { + var ( + header string + body string + ) + + switch format { + case fmtSubject.Display: + body = `{{range .Commits}} +* {{.Header}}{{end}} +` + + default: + if format == fmtTypeScopeSubject.Display { + header = "{{if .Scope}}**{{.Scope}}:** {{end}}{{.Subject}}" + } else { + header = "{{.Subject}}" + } + + body = fmt.Sprintf(`### {{.Title}} +{{range .Commits}} +* %s{{end}} +`, header) + } + + return fmt.Sprintf(`{{range .CommitGroups}} +%s{{end}}`, body) +} + +func (*customTemplateBuilderImpl) reverts() string { + return `{{if .RevertCommits}} +### Reverts +{{range .RevertCommits}} +* {{.Revert.Header}}{{end}} +{{end}}` +} + +func (t *customTemplateBuilderImpl) merges(style string) string { + var title string + + switch style { + case styleGitHub: + title = "Pull Requests" + default: + title = "Merges" + } + + return fmt.Sprintf(`{{if .MergeCommits}} +### %s +{{range .MergeCommits}} +* {{.Header}}{{end}} +{{end}}`, title) +} + +func (*customTemplateBuilderImpl) notes() string { + return `{{range .NoteGroups}} +### {{.Title}} +{{range .Notes}} +{{.Body}} +{{end}} +{{end}}` +} diff --git a/cmd/git-chglog/template_builder_test.go b/cmd/git-chglog/custom_template_builder_test.go similarity index 85% rename from cmd/git-chglog/template_builder_test.go rename to cmd/git-chglog/custom_template_builder_test.go index 9d6449e0..a6251800 100644 --- a/cmd/git-chglog/template_builder_test.go +++ b/cmd/git-chglog/custom_template_builder_test.go @@ -6,9 +6,9 @@ import ( "github.com/stretchr/testify/assert" ) -func TestTemplateBuilderDefault(t *testing.T) { +func TestCustomTemplateBuilderDefault(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleGitHub, @@ -25,7 +25,7 @@ func TestTemplateBuilderDefault(t *testing.T) { {{range .CommitGroups}} ### {{.Title}} {{range .Commits}} -* {{if ne .Scope ""}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} +* {{if .Scope}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} {{end}}{{if .RevertCommits}} ### Reverts {{range .RevertCommits}} @@ -43,9 +43,9 @@ func TestTemplateBuilderDefault(t *testing.T) { {{end}}`, out) } -func TestTemplateBuilderNone(t *testing.T) { +func TestCustomTemplateBuilderNone(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleNone, @@ -61,7 +61,7 @@ func TestTemplateBuilderNone(t *testing.T) { {{range .CommitGroups}} ### {{.Title}} {{range .Commits}} -* {{if ne .Scope ""}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} +* {{if .Scope}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} {{end}}{{if .RevertCommits}} ### Reverts {{range .RevertCommits}} @@ -79,9 +79,9 @@ func TestTemplateBuilderNone(t *testing.T) { {{end}}`, out) } -func TestTemplateBuilderCool(t *testing.T) { +func TestCustomTemplateBuilderCool(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleNone, @@ -99,7 +99,7 @@ func TestTemplateBuilderCool(t *testing.T) { {{range .CommitGroups}} ### {{.Title}} {{range .Commits}} -* {{if ne .Scope ""}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} +* {{if .Scope}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} {{end}}{{if .RevertCommits}} ### Reverts {{range .RevertCommits}} @@ -117,9 +117,9 @@ func TestTemplateBuilderCool(t *testing.T) { {{end}}`, out) } -func TestTemplateBuilderSubjectOnly(t *testing.T) { +func TestCustomTemplateBuilderSubjectOnly(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleNone, @@ -152,9 +152,9 @@ func TestTemplateBuilderSubjectOnly(t *testing.T) { {{end}}`, out) } -func TestTemplateBuilderSubject(t *testing.T) { +func TestCustomTemplateBuilderSubject(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleNone, @@ -188,9 +188,9 @@ func TestTemplateBuilderSubject(t *testing.T) { {{end}}`, out) } -func TestTemplateBuilderIgnoreReverts(t *testing.T) { +func TestCustomTemplateBuilderIgnoreReverts(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleNone, @@ -220,9 +220,9 @@ func TestTemplateBuilderIgnoreReverts(t *testing.T) { {{end}}`, out) } -func TestTemplateBuilderIgnoreMerges(t *testing.T) { +func TestCustomTemplateBuilderIgnoreMerges(t *testing.T) { assert := assert.New(t) - builder := NewTemplateBuilder() + builder := NewCustomTemplateBuilder() out, err := builder.Build(&Answer{ Style: styleNone, diff --git a/cmd/git-chglog/initializer.go b/cmd/git-chglog/initializer.go index 920df14b..7356f8b0 100644 --- a/cmd/git-chglog/initializer.go +++ b/cmd/git-chglog/initializer.go @@ -10,13 +10,13 @@ import ( // Initializer ... type Initializer struct { - ctx *InitContext - client gitcmd.Client - fs FileSystem - logger *Logger - questioner Questioner - configBuilder ConfigBuilder - templateBuilder TemplateBuilder + ctx *InitContext + client gitcmd.Client + fs FileSystem + logger *Logger + questioner Questioner + configBuilder ConfigBuilder + templateBuilderFactory TemplateBuilderFactory } // NewInitializer ... @@ -25,15 +25,14 @@ func NewInitializer( fs FileSystem, questioner Questioner, configBuilder ConfigBuilder, - templateBuilder TemplateBuilder, -) *Initializer { + tplBuilderFactory TemplateBuilderFactory) *Initializer { return &Initializer{ - ctx: ctx, - fs: fs, - logger: NewLogger(ctx.Stdout, ctx.Stderr, false, false), - questioner: questioner, - configBuilder: configBuilder, - templateBuilder: templateBuilder, + ctx: ctx, + fs: fs, + logger: NewLogger(ctx.Stdout, ctx.Stderr, false, false), + questioner: questioner, + configBuilder: configBuilder, + templateBuilderFactory: tplBuilderFactory, } } @@ -86,7 +85,8 @@ func (init *Initializer) generateConfig(ans *Answer) error { } func (init *Initializer) generateTemplate(ans *Answer) error { - s, err := init.templateBuilder.Build(ans) + templateBuilder := init.templateBuilderFactory(ans.Template) + s, err := templateBuilder.Build(ans) if err != nil { return err } diff --git a/cmd/git-chglog/initializer_test.go b/cmd/git-chglog/initializer_test.go index 5c4717c4..fb929f19 100644 --- a/cmd/git-chglog/initializer_test.go +++ b/cmd/git-chglog/initializer_test.go @@ -64,7 +64,9 @@ func TestInitializer(t *testing.T) { mockFs, questioner, configBuilder, - tplBuilder, + func(t string) TemplateBuilder { + return tplBuilder + }, ) assert.Equal(ExitCodeOK, init.Run()) diff --git a/cmd/git-chglog/kac_template_builder.go b/cmd/git-chglog/kac_template_builder.go new file mode 100644 index 00000000..f31427cb --- /dev/null +++ b/cmd/git-chglog/kac_template_builder.go @@ -0,0 +1,118 @@ +package main + +import "fmt" + +type kacTemplateBuilderImpl struct{} + +// NewKACTemplateBuilder ... +func NewKACTemplateBuilder() TemplateBuilder { + return &kacTemplateBuilderImpl{} +} + +// Build ... +func (t *kacTemplateBuilderImpl) Build(ans *Answer) (string, error) { + // versions + tpl := "## {{if .Versions}}[Unreleased]{{end}}\n{{range .Versions}}\n" + tpl += t.versionHeader(ans.Style) + + // commits + tpl += t.commits(ans.CommitMessageFormat) + + // revert + if ans.IncludeReverts { + tpl += t.reverts() + } + + // merges + if ans.IncludeMerges { + tpl += t.merges(ans.Style) + } + + // notes + tpl += t.notes() + + // versions end + tpl += "{{end}}" + + // footer (links) + tpl += t.footer(ans.Style) + + return tpl, nil +} + +func (t *kacTemplateBuilderImpl) versionHeader(style string) string { + var ( + tagName = "{{.Tag.Name}}" + date = "{{datetime \"2006-01-02\" .Tag.Date}}" + ) + + switch style { + case styleGitHub: + tagName = "{{if .Tag.Previous}}[{{.Tag.Name}}]{{else}}{{.Tag.Name}}{{end}}" + } + + return fmt.Sprintf("## %s - %s", tagName, date) +} + +func (t *kacTemplateBuilderImpl) commits(format string) string { + var ( + body string + ) + + switch format { + case fmtSubject.Display: + body = `{{range .Commits}} +- {{.Header}}{{end}}` + + default: + body = `### {{.Title}}{{range .Commits}} +- {{if .Scope}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}}` + } + + return fmt.Sprintf(`{{range .CommitGroups}} +%s +{{end}}`, body) +} + +func (t *kacTemplateBuilderImpl) reverts() string { + return `{{if .RevertCommits}} +### Reverts{{range .RevertCommits}} +- {{.Revert.Header}}{{end}} +{{end}}` +} + +func (t *kacTemplateBuilderImpl) merges(style string) string { + var title string + + switch style { + case styleGitHub: + title = "Pull Requests" + default: + title = "Merges" + } + + return fmt.Sprintf(`{{if .MergeCommits}} +### %s{{range .MergeCommits}} +- {{.Header}}{{end}} +{{end}}`, title) +} + +func (*kacTemplateBuilderImpl) notes() string { + return `{{range .NoteGroups}} +### {{.Title}} +{{range .Notes}} +{{.Body}} +{{end}} +{{end}}` +} + +func (*kacTemplateBuilderImpl) footer(style string) string { + if style != styleGitHub { + return "" + } + + return `{{if .Versions}} +[Unreleased]: {{.Info.RepositoryURL}}/compare/{{$latest := index .Versions 0}}{{$latest.Tag.Name}}...HEAD{{range .Versions}}{{if .Tag.Previous}} +[{{.Tag.Name}}]: {{$.Info.RepositoryURL}}/compare/{{.Tag.Previous.Name}}...{{.Tag.Name}}{{end}}{{end}} +{{end}}` +} diff --git a/cmd/git-chglog/kac_template_builder_test.go b/cmd/git-chglog/kac_template_builder_test.go new file mode 100644 index 00000000..2f46d53f --- /dev/null +++ b/cmd/git-chglog/kac_template_builder_test.go @@ -0,0 +1,42 @@ +package main + +import ( + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestKACTemplateBuilderDefault(t *testing.T) { + assert := assert.New(t) + builder := NewKACTemplateBuilder() + + out, err := builder.Build(&Answer{ + Style: styleGitHub, + CommitMessageFormat: fmtTypeScopeSubject.Display, + Template: tplKeepAChangelog, + IncludeMerges: true, + IncludeReverts: true, + }) + + assert.Nil(err) + assert.Equal(`## {{if .Versions}}[Unreleased]{{end}} +{{range .Versions}} +## {{if .Tag.Previous}}[{{.Tag.Name}}]{{else}}{{.Tag.Name}}{{end}} - {{datetime "2006-01-02" .Tag.Date}}{{range .CommitGroups}} +### {{.Title}}{{range .Commits}} +- {{if .Scope}}**{{.Scope}}:** {{end}}{{.Subject}}{{end}} +{{end}}{{if .RevertCommits}} +### Reverts{{range .RevertCommits}} +- {{.Revert.Header}}{{end}} +{{end}}{{if .MergeCommits}} +### Pull Requests{{range .MergeCommits}} +- {{.Header}}{{end}} +{{end}}{{range .NoteGroups}} +### {{.Title}} +{{range .Notes}} +{{.Body}} +{{end}} +{{end}}{{end}}{{if .Versions}} +[Unreleased]: {{.Info.RepositoryURL}}/compare/{{$latest := index .Versions 0}}{{$latest.Tag.Name}}...HEAD{{range .Versions}}{{if .Tag.Previous}} +[{{.Tag.Name}}]: {{$.Info.RepositoryURL}}/compare/{{.Tag.Previous.Name}}...{{.Tag.Name}}{{end}}{{end}} +{{end}}`, out) +} diff --git a/cmd/git-chglog/main.go b/cmd/git-chglog/main.go index fb8e0c21..cae9214d 100644 --- a/cmd/git-chglog/main.go +++ b/cmd/git-chglog/main.go @@ -132,7 +132,7 @@ func main() { fs, ), NewConfigBuilder(), - NewTemplateBuilder(), + templateBuilderFactory, ) os.Exit(initializer.Run()) diff --git a/cmd/git-chglog/template_builder.go b/cmd/git-chglog/template_builder.go index 7154c0f3..963aab7c 100644 --- a/cmd/git-chglog/template_builder.go +++ b/cmd/git-chglog/template_builder.go @@ -1,143 +1,18 @@ package main -import "fmt" - // TemplateBuilder ... type TemplateBuilder interface { Builder } -type templateBuilderImpl struct{} +// TemplateBuilderFactory ... +type TemplateBuilderFactory = func(string) TemplateBuilder -// NewTemplateBuilder ... -func NewTemplateBuilder() TemplateBuilder { - return &templateBuilderImpl{} -} - -// Build ... -func (t *templateBuilderImpl) Build(ans *Answer) (string, error) { - // versions - tpl := "{{range .Versions}}\n" - - // version header - tpl += t.versionHeader(ans.Style, ans.Template) - - // commits - tpl += t.commits(ans.Template, ans.CommitMessageFormat) - - // revert - if ans.IncludeReverts { - tpl += t.reverts() - } - - // merges - if ans.IncludeMerges { - tpl += t.merges(ans.Style) - } - - // notes - tpl += t.notes() - - // versions end - tpl += "\n{{end}}" - - return tpl, nil -} - -func (*templateBuilderImpl) versionHeader(style, template string) string { - var ( - tpl string - tagName string - date = "{{datetime \"2006-01-02\" .Tag.Date}}" - ) - - // parts - switch style { - case styleGitHub: - tpl = "\n" - tagName = "{{if .Tag.Previous}}[{{.Tag.Name}}]({{$.Info.RepositoryURL}}/compare/{{.Tag.Previous.Name}}...{{.Tag.Name}}){{else}}{{.Tag.Name}}{{end}}" - default: - tagName = "{{.Tag.Name}}" - } - - // format +func templateBuilderFactory(template string) TemplateBuilder { switch template { - case tplStandard: - tpl = fmt.Sprintf("%s## %s (%s)\n", - tpl, - tagName, - date, - ) - case tplCool: - tpl = fmt.Sprintf("%s## %s\n\n> %s\n", - tpl, - tagName, - date, - ) - } - - return tpl -} - -func (*templateBuilderImpl) commits(template, format string) string { - var ( - header string - body string - ) - - switch format { - case fmtSubject.Display: - body = `{{range .Commits}} -* {{.Header}}{{end}} -` - + case tplKeepAChangelog: + return NewKACTemplateBuilder() default: - if format == fmtTypeScopeSubject.Display { - header = "{{if ne .Scope \"\"}}**{{.Scope}}:** {{end}}{{.Subject}}" - } else { - header = "{{.Subject}}" - } - - body = fmt.Sprintf(`### {{.Title}} -{{range .Commits}} -* %s{{end}} -`, header) + return NewCustomTemplateBuilder() } - - return fmt.Sprintf(`{{range .CommitGroups}} -%s{{end}}`, body) -} - -func (*templateBuilderImpl) reverts() string { - return `{{if .RevertCommits}} -### Reverts -{{range .RevertCommits}} -* {{.Revert.Header}}{{end}} -{{end}}` -} - -func (t *templateBuilderImpl) merges(style string) string { - var title string - - switch style { - case styleGitHub: - title = "Pull Requests" - default: - title = "Merges" - } - - return fmt.Sprintf(`{{if .MergeCommits}} -### %s -{{range .MergeCommits}} -* {{.Header}}{{end}} -{{end}}`, title) -} - -func (*templateBuilderImpl) notes() string { - return `{{range .NoteGroups}} -### {{.Title}} -{{range .Notes}} -{{.Body}} -{{end}} -{{end}}` } diff --git a/cmd/git-chglog/variables.go b/cmd/git-chglog/variables.go index 0253f10b..bcb63803 100644 --- a/cmd/git-chglog/variables.go +++ b/cmd/git-chglog/variables.go @@ -86,9 +86,11 @@ var ( // Templates var ( - tplStandard = "standard" - tplCool = "cool" - templates = []string{ + tplKeepAChangelog = "keep-a-changelog" + tplStandard = "standard" + tplCool = "cool" + templates = []string{ + tplKeepAChangelog, tplStandard, tplCool, } From 98543fb897a4837cf228e0b490861df27f43261a Mon Sep 17 00:00:00 2001 From: tsuyoshiwada Date: Fri, 2 Mar 2018 02:06:19 +0900 Subject: [PATCH 4/4] test: Pass all the test cases with windows --- cmd/git-chglog/config_test.go | 11 +++++++---- cmd/git-chglog/initializer_test.go | 5 +++-- 2 files changed, 10 insertions(+), 6 deletions(-) diff --git a/cmd/git-chglog/config_test.go b/cmd/git-chglog/config_test.go index ab34c684..a56372f5 100644 --- a/cmd/git-chglog/config_test.go +++ b/cmd/git-chglog/config_test.go @@ -1,6 +1,7 @@ package main import ( + "os" "path/filepath" "testing" @@ -18,7 +19,7 @@ func TestConfigNormalize(t *testing.T) { } err := config.Normalize(&CLIContext{ - ConfigPath: "/test/config.yml", + ConfigPath: filepath.FromSlash("/test/config.yml"), }) assert.Nil(err) @@ -27,14 +28,16 @@ func TestConfigNormalize(t *testing.T) { assert.Equal("/test/CHANGELOG.tpl.md", filepath.ToSlash(config.Template)) // abs template + cwd, _ := os.Getwd() + config = &Config{ - Template: "/CHANGELOG.tpl.md", + Template: filepath.Join(cwd, "CHANGELOG.tpl.md"), } err = config.Normalize(&CLIContext{ - ConfigPath: "/test/config.yml", + ConfigPath: filepath.Join(cwd, "test", "config.yml"), }) assert.Nil(err) - assert.Equal("/CHANGELOG.tpl.md", filepath.ToSlash(config.Template)) + assert.Equal(filepath.Join(cwd, "CHANGELOG.tpl.md"), config.Template) } diff --git a/cmd/git-chglog/initializer_test.go b/cmd/git-chglog/initializer_test.go index fb929f19..95c2b1da 100644 --- a/cmd/git-chglog/initializer_test.go +++ b/cmd/git-chglog/initializer_test.go @@ -3,6 +3,7 @@ package main import ( "bytes" "errors" + "path/filepath" "testing" "github.com/stretchr/testify/assert" @@ -16,13 +17,13 @@ func TestInitializer(t *testing.T) { mockFs := &mockFileSystem{ ReturnMkdirP: func(path string) error { - if path == "/test/config" { + if path == filepath.FromSlash("/test/config") { return nil } return errors.New("") }, ReturnWriteFile: func(path string, content []byte) error { - if path == "/test/config/config.yml" || path == "/test/config/CHANGELOG.tpl.md" { + if path == filepath.FromSlash("/test/config/config.yml") || path == filepath.FromSlash("/test/config/CHANGELOG.tpl.md") { return nil } return errors.New("")