make: add target cl for create changelog entry (#15186)
* make: add target cl for create changelog entry This PR adds `tools/cl-entry` and the `make cl` Makefile target for conveniently creating correctly formatted Changelog entries. * Update tools/cl-entry/main.go Co-authored-by: Luiz Aoqui <luiz@hashicorp.com> * Update tools/cl-entry/main.go Co-authored-by: Luiz Aoqui <luiz@hashicorp.com> Co-authored-by: Luiz Aoqui <luiz@hashicorp.com>
This commit is contained in:
parent
80b6f27efd
commit
87a34102f5
|
@ -409,3 +409,8 @@ missing: ## Check for packages not being tested
|
|||
ec2info: ## Generate AWS EC2 CPU specification table
|
||||
@echo "==> Generating AWS EC2 specifications ..."
|
||||
@go run -modfile tools/go.mod tools/ec2info/main.go
|
||||
|
||||
.PHONY: cl
|
||||
cl: ## Create a new Changelog entry
|
||||
@go run -modfile tools/go.mod tools/cl-entry/main.go
|
||||
|
||||
|
|
|
@ -18,6 +18,12 @@ Use the PR number as the file name. Enterprise private changes should have an en
|
|||
|
||||
The `.txt` files have a markdown-like syntax, with a tag signifying the entry type.
|
||||
|
||||
Use the `tools/cl-entry` command to help generate a changelog entry file.
|
||||
|
||||
```shell
|
||||
make cl
|
||||
```
|
||||
|
||||
Below are some examples of how to generate a CHANGELOG entry with your pull request.
|
||||
|
||||
### Improvement
|
||||
|
|
|
@ -0,0 +1,128 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"regexp"
|
||||
"strconv"
|
||||
"strings"
|
||||
)
|
||||
|
||||
const (
|
||||
pr = `Must have a Pull Request already open.
|
||||
Enter PR # => `
|
||||
|
||||
kind = `Choose type, one of
|
||||
1. bug
|
||||
2. improvement
|
||||
3. security
|
||||
4. breaking-change
|
||||
5. note
|
||||
6. deprecation
|
||||
Enter Kind => `
|
||||
|
||||
note = `Write a note, for example
|
||||
build: Added make target for creating changelog entries
|
||||
Enter Note => `
|
||||
)
|
||||
|
||||
var noteRe = regexp.MustCompile(`[a-z0-9/\s]+: .+`)
|
||||
|
||||
func main() {
|
||||
pr, err := ask(pr)
|
||||
check(err)
|
||||
|
||||
n, err := ask(kind)
|
||||
check(err)
|
||||
|
||||
label, err := label(n)
|
||||
check(err)
|
||||
|
||||
body, err := askStr(note)
|
||||
check(err)
|
||||
|
||||
msg, err := cleanup(body)
|
||||
check(err)
|
||||
|
||||
file, err := write(pr, label, msg)
|
||||
check(err)
|
||||
|
||||
fmt.Println("Created", file)
|
||||
}
|
||||
|
||||
func write(pr int, label, msg string) (string, error) {
|
||||
filename := filepath.Join(".changelog", fmt.Sprintf("%d.txt", pr))
|
||||
sb := new(strings.Builder)
|
||||
sb.WriteString("```release-note:")
|
||||
sb.WriteString(label)
|
||||
sb.WriteString("\n")
|
||||
sb.WriteString(msg)
|
||||
sb.WriteString("\n")
|
||||
sb.WriteString("```\n")
|
||||
s := sb.String()
|
||||
if err := os.WriteFile(filename, []byte(s), 0o644); err != nil {
|
||||
return "", err
|
||||
}
|
||||
return filename, nil
|
||||
}
|
||||
|
||||
func cleanup(note string) (string, error) {
|
||||
note = strings.TrimSpace(note)
|
||||
note = strings.TrimSuffix(note, ".")
|
||||
if !noteRe.MatchString(note) {
|
||||
return "", errors.New("note does not comply with format")
|
||||
}
|
||||
return note, nil
|
||||
}
|
||||
|
||||
func label(n int) (string, error) {
|
||||
var label string
|
||||
switch n {
|
||||
case 1:
|
||||
label = "bug"
|
||||
case 2:
|
||||
label = "improvement"
|
||||
case 3:
|
||||
label = "security"
|
||||
case 4:
|
||||
label = "breaking-change"
|
||||
case 5:
|
||||
label = "note"
|
||||
case 6:
|
||||
label = "deprecation"
|
||||
default:
|
||||
return "", errors.New("not a valid type, must be 1-6")
|
||||
}
|
||||
return label, nil
|
||||
}
|
||||
|
||||
func ask(q string) (int, error) {
|
||||
r := bufio.NewReader(os.Stdin)
|
||||
fmt.Print(q)
|
||||
line, err := r.ReadString('\n')
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i, err := strconv.Atoi(strings.TrimSpace(line))
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
return i, nil
|
||||
}
|
||||
|
||||
func askStr(q string) (string, error) {
|
||||
r := bufio.NewReader(os.Stdin)
|
||||
fmt.Print(q)
|
||||
line, err := r.ReadString('\n')
|
||||
return strings.TrimSpace(line), err
|
||||
}
|
||||
|
||||
func check(err error) {
|
||||
if err != nil {
|
||||
fmt.Fprintf(os.Stderr, "failure: %v\n", err)
|
||||
os.Exit(1)
|
||||
}
|
||||
}
|
|
@ -1,11 +1,11 @@
|
|||
module github.com/hashicorp/nomad/tools
|
||||
|
||||
go 1.18
|
||||
go 1.19
|
||||
|
||||
require (
|
||||
github.com/aws/aws-sdk-go v1.37.26
|
||||
github.com/hashicorp/go-set v0.1.6
|
||||
github.com/shoenig/test v0.4.0
|
||||
github.com/shoenig/test v0.4.4
|
||||
)
|
||||
|
||||
require (
|
||||
|
|
|
@ -13,8 +13,8 @@ github.com/jmespath/go-jmespath/internal/testify v1.5.1/go.mod h1:L3OGu8Wl2/fWfC
|
|||
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
||||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||
github.com/shoenig/test v0.4.0 h1:3X4xG/Chx7mzi0h71Sm6Vo38q0EYaQIBZpYFRcA1HVM=
|
||||
github.com/shoenig/test v0.4.0/go.mod h1:xYtyGBC5Q3kzCNyJg/SjgNpfAa2kvmgA0i5+lQso8x0=
|
||||
github.com/shoenig/test v0.4.4 h1:juucmjQTPYUfO2+rID1wfQqsreSlk+2I8K/bQFsUZ9c=
|
||||
github.com/shoenig/test v0.4.4/go.mod h1:xYtyGBC5Q3kzCNyJg/SjgNpfAa2kvmgA0i5+lQso8x0=
|
||||
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
|
||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||
|
|
Loading…
Reference in New Issue