diff --git a/.drone.yml b/.drone.yml index 6204acb..1d29e76 100644 --- a/.drone.yml +++ b/.drone.yml @@ -3,6 +3,11 @@ type: docker name: default steps: +- name: test + image: golang:1.16 + commands: + - go test ./... + - name: build image: golang:1.16 commands: diff --git a/CHANGELOG.md b/CHANGELOG.md index 20ee285..67657b4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,25 @@ # Changelog +## [v1.3.3](https://github.com/drone/drone-cli/tree/v1.3.3) (2021-08-26) + +[Full Changelog](https://github.com/drone/drone-cli/compare/v1.3.2...v1.3.3) + +**Fixed bugs:** + +- Fix `--stream` combined with `--format` for `jsonnet` [\#195](https://github.com/drone/drone-cli/pull/195) ([julienduchesne](https://github.com/julienduchesne)) + +## [v1.3.2](https://github.com/drone/drone-cli/tree/v1.3.2) (2021-08-25) + +[Full Changelog](https://github.com/drone/drone-cli/compare/v1.3.1...v1.3.2) + +**Fixed bugs:** + +- \(fix\) re-enable format option for jsonnet command [\#193](https://github.com/drone/drone-cli/pull/193) ([tphoney](https://github.com/tphoney)) + +**Merged pull requests:** + +- \(maint\) release prep for v1.3.2 [\#194](https://github.com/drone/drone-cli/pull/194) ([tphoney](https://github.com/tphoney)) + ## [v1.3.1](https://github.com/drone/drone-cli/tree/v1.3.1) (2021-08-20) [Full Changelog](https://github.com/drone/drone-cli/compare/v1.3.0...v1.3.1) @@ -10,6 +30,10 @@ - \(DRON-113\) use ghodss/yaml for yaml printing [\#189](https://github.com/drone/drone-cli/pull/189) ([tphoney](https://github.com/tphoney)) - fixes issue were cli required an additional parameter in order to com… [\#188](https://github.com/drone/drone-cli/pull/188) ([eoinmcafee00](https://github.com/eoinmcafee00)) +**Merged pull requests:** + +- release prep v1.3.1 [\#192](https://github.com/drone/drone-cli/pull/192) ([eoinmcafee00](https://github.com/eoinmcafee00)) + \* *This Changelog was automatically generated by [github_changelog_generator](https://github.com/github-changelog-generator/github-changelog-generator)* diff --git a/drone/jsonnet/jsonnet.go b/drone/jsonnet/jsonnet.go index 29d3702..97f13bb 100644 --- a/drone/jsonnet/jsonnet.go +++ b/drone/jsonnet/jsonnet.go @@ -41,9 +41,8 @@ var Command = cli.Command{ Usage: "Write output as a YAML stream.", }, cli.BoolFlag{ - Name: "format", - Hidden: true, - Usage: "Write output as formatted YAML", + Name: "format", + Usage: "Write output as formatted YAML", }, cli.BoolFlag{ Name: "stdout", @@ -61,17 +60,30 @@ var Command = cli.Command{ } func generate(c *cli.Context) error { - source := c.String("source") - target := c.String("target") - - data, err := ioutil.ReadFile(source) + result, err := convert(c.String("source"), c.Bool("string"), c.Bool("format"), c.Bool("stream"), c.StringSlice("extVar")) if err != nil { return err } + // the user can optionally write the yaml to stdout. This is useful for debugging purposes without mutating an existing file. + if c.Bool("stdout") { + io.WriteString(os.Stdout, result) + return nil + } + + target := c.String("target") + return ioutil.WriteFile(target, []byte(result), 0644) +} + +func convert(source string, stringOutput bool, format bool, stream bool, vars []string) (string, error) { + data, err := ioutil.ReadFile(source) + if err != nil { + return "", err + } + vm := jsonnet.MakeVM() vm.MaxStack = 500 - vm.StringOutput = c.Bool("string") + vm.StringOutput = stringOutput vm.ErrorFormatter.SetMaxStackTraceSize(20) vm.ErrorFormatter.SetColorFormatter( color.New(color.FgRed).Fprintf, @@ -81,26 +93,38 @@ func generate(c *cli.Context) error { RegisterNativeFuncs(vm) // extVars - vars := c.StringSlice("extVar") for _, v := range vars { name, value, err := getVarVal(v) if err != nil { - return err + return "", err } vm.ExtVar(name, value) } + formatDoc := func(doc []byte) ([]byte, error) { + // enable yaml output + if format { + formatted, yErr := yaml.JSONToYAML(doc) + if yErr != nil { + return nil, fmt.Errorf("failed to convert to YAML: %v", yErr) + } + return formatted, nil + } + return doc, nil + } + buf := new(bytes.Buffer) - if c.Bool("stream") { + if stream { docs, err := vm.EvaluateSnippetStream(source, string(data)) if err != nil { - return err + return "", err } for _, doc := range docs { - formatted, yErr := yaml.JSONToYAML([]byte(doc)) - if yErr != nil { - return fmt.Errorf("failed to convert to YAML: %v", yErr) + formatted, err := formatDoc([]byte(doc)) + if err != nil { + return "", err } + buf.WriteString("---") buf.WriteString("\n") buf.Write(formatted) @@ -108,22 +132,16 @@ func generate(c *cli.Context) error { } else { result, err := vm.EvaluateSnippet(source, string(data)) if err != nil { - return err + return "", err } - formatted, yErr := yaml.JSONToYAML([]byte(result)) - if yErr != nil { - return fmt.Errorf("failed to convert to YAML: %v", yErr) + formatted, err := formatDoc([]byte(result)) + if err != nil { + return "", err } buf.Write(formatted) } - // the user can optionally write the yaml to stdout. This is useful for debugging purposes without mutating an existing file. - if c.Bool("stdout") { - io.Copy(os.Stdout, buf) - return nil - } - - return ioutil.WriteFile(target, buf.Bytes(), 0644) + return buf.String(), nil } // https://github.com/google/go-jsonnet/blob/master/cmd/jsonnet/cmd.go#L149 diff --git a/drone/jsonnet/jsonnet_test.go b/drone/jsonnet/jsonnet_test.go new file mode 100644 index 0000000..0dce888 --- /dev/null +++ b/drone/jsonnet/jsonnet_test.go @@ -0,0 +1,37 @@ +package jsonnet + +import ( + "os" + "path/filepath" + "testing" + + "github.com/stretchr/testify/assert" +) + +func TestConvert(t *testing.T) { + testcases := []struct { + name string + jsonnetFile, yamlFile string + stringOutput, format, stream bool + extVars []string + }{ + { + name: "Stream + Format", + jsonnetFile: "stream_format.jsonnet", + yamlFile: "stream_format.yaml", + format: true, stream: true, + }, + } + + for _, tc := range testcases { + tc := tc + t.Run(tc.name, func(t *testing.T) { + expected, err := os.ReadFile(filepath.Join("./testdata", tc.yamlFile)) + assert.NoError(t, err) + + result, err := convert(filepath.Join("./testdata", tc.jsonnetFile), tc.stringOutput, tc.format, tc.stream, tc.extVars) + assert.NoError(t, err) + assert.Equal(t, string(expected), result) + }) + } +} diff --git a/drone/jsonnet/testdata/stream_format.jsonnet b/drone/jsonnet/testdata/stream_format.jsonnet new file mode 100644 index 0000000..3252c6c --- /dev/null +++ b/drone/jsonnet/testdata/stream_format.jsonnet @@ -0,0 +1,27 @@ +local pipeline(name) = + { + kind: 'pipeline', + type: 'docker', + name: name, + platform: { + os: 'linux', + arch: 'amd64', + }, + steps: [ + { + name: 'test', + image: 'golang:1.16', + commands: ['go test ./...'], + }, + { + name: 'build', + image: 'golang:1.16', + commands: ['go build ./...'], + }, + ], + }; + +[ + pipeline('first'), + pipeline('second'), +] diff --git a/drone/jsonnet/testdata/stream_format.yaml b/drone/jsonnet/testdata/stream_format.yaml new file mode 100644 index 0000000..1728a3f --- /dev/null +++ b/drone/jsonnet/testdata/stream_format.yaml @@ -0,0 +1,32 @@ +--- +kind: pipeline +name: first +platform: + arch: amd64 + os: linux +steps: +- commands: + - go test ./... + image: golang:1.16 + name: test +- commands: + - go build ./... + image: golang:1.16 + name: build +type: docker +--- +kind: pipeline +name: second +platform: + arch: amd64 + os: linux +steps: +- commands: + - go test ./... + image: golang:1.16 + name: test +- commands: + - go build ./... + image: golang:1.16 + name: build +type: docker diff --git a/go.mod b/go.mod index 2a49864..c55c96b 100644 --- a/go.mod +++ b/go.mod @@ -20,6 +20,7 @@ require ( github.com/mattn/go-colorable v0.1.4 github.com/mattn/go-isatty v0.0.11 github.com/pkg/browser v0.0.0-20180916011732-0a3d74bf9ce4 + github.com/stretchr/testify v1.4.0 github.com/urfave/cli v1.20.0 go.starlark.net v0.0.0-20201118183435-e55f603d8c79 golang.org/x/net v0.0.0-20190603091049-60506f45cf65