From b39c81e4cb0bf856f543db001d98c71ee48533ee Mon Sep 17 00:00:00 2001 From: Fraser Waters Date: Tue, 26 Oct 2021 16:55:52 +0100 Subject: [PATCH] Improve error message and add test for #1440 (#8268) * Improve error message and add test for #1440 * lint * lint * Use %w instead of errors.Wrap --- sdk/go/common/encoding/marshal.go | 12 ++++++++++- tests/integration/integration_test.go | 30 +++++++++++++++++++++++++++ 2 files changed, 41 insertions(+), 1 deletion(-) diff --git a/sdk/go/common/encoding/marshal.go b/sdk/go/common/encoding/marshal.go index 093ad7b40..e0f8bce89 100644 --- a/sdk/go/common/encoding/marshal.go +++ b/sdk/go/common/encoding/marshal.go @@ -16,6 +16,7 @@ package encoding import ( "encoding/json" + "fmt" "path/filepath" yaml "gopkg.in/yaml.v2" @@ -106,5 +107,14 @@ func (m *yamlMarshaler) Unmarshal(data []byte, v interface{}) error { // IDEA: use a "strict" marshaler, so that we can warn on unrecognized keys (avoiding silly mistakes). We should // set aside an officially sanctioned area in the metadata for extensibility by 3rd parties. - return yaml.Unmarshal(data, v) + err := yaml.Unmarshal(data, v) + if err != nil { + // Return type errors directly + if _, ok := err.(*yaml.TypeError); ok { + return err + } + // Other errors will be parse errors due to invalid syntax + return fmt.Errorf("invalid YAML file: %w", err) + } + return nil } diff --git a/tests/integration/integration_test.go b/tests/integration/integration_test.go index dfbce3ada..b302f48e2 100644 --- a/tests/integration/integration_test.go +++ b/tests/integration/integration_test.go @@ -106,6 +106,36 @@ func TestStackTagValidation(t *testing.T) { }) } +// TestStackInitValidation verifies various error scenarios related to init'ing a stack. +func TestStackInitValidation(t *testing.T) { + t.Run("Error_InvalidStackYaml", func(t *testing.T) { + e := ptesting.NewEnvironment(t) + defer func() { + if !t.Failed() { + e.DeleteEnvironment() + } + }() + e.RunCommand("git", "init") + + e.ImportDirectory("stack_project_name") + e.RunCommand("pulumi", "login", "--cloud-url", e.LocalURL()) + + // Starting a yaml value with a quote string and then more data is invalid + invalidYaml := "\"this is invalid\" yaml because of trailing data after quote string" + + // Change the contents of the Description property of Pulumi.yaml. + yamlPath := filepath.Join(e.CWD, "Pulumi.yaml") + err := integration.ReplaceInFile("description: ", "description: "+invalidYaml, yamlPath) + assert.NoError(t, err) + + stdout, stderr := e.RunCommandExpectError("pulumi", "stack", "init", "valid-name") + assert.Equal(t, "", stdout) + assert.Contains(t, stderr, + "error: could not get cloud url: could not load current project: "+ + "invalid YAML file: yaml: line 1: did not find expected key") + }) +} + // TestConfigSave ensures that config commands in the Pulumi CLI work as expected. func TestConfigSave(t *testing.T) { e := ptesting.NewEnvironment(t)