Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions config/testdata/invalid_empty.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
# The file format version.
file_format: "0.3"

# Configure if the SDK is disabled or not. This is not required to be provided to ensure the SDK isn't disabled, the default value when this is not provided is for the SDK to be enabled.
disabled: false

resource:
attributes:
-
4 changes: 1 addition & 3 deletions config/v0.3.0/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -143,11 +143,9 @@ func WithOpenTelemetryConfiguration(cfg OpenTelemetryConfiguration) Configuratio
// ParseYAML parses a YAML configuration file into an OpenTelemetryConfiguration.
func ParseYAML(file []byte) (*OpenTelemetryConfiguration, error) {
var cfg OpenTelemetryConfiguration
err := yaml.Unmarshal(file, &cfg)
if err != nil {
if err := yaml.Unmarshal(file, &cfg); err != nil {
return nil, err
}

return &cfg, nil
}

Expand Down
15 changes: 14 additions & 1 deletion config/v0.3.0/config_json.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
"errors"
"fmt"
"reflect"
"strings"
)

// MarshalJSON implements json.Marshaler.
Expand Down Expand Up @@ -338,13 +339,25 @@ func (j *Zipkin) UnmarshalJSON(b []byte) error {
return nil
}

func (j *AttributeNameValue) MarshalJSON() ([]byte, error) {
return json.Marshal(j.Value)
}

// UnmarshalJSON implements json.Unmarshaler.
func (j *AttributeNameValue) UnmarshalJSON(b []byte) error {
var raw map[string]interface{}
if err := json.Unmarshal(b, &raw); err != nil {
return err
}
if _, ok := raw["name"]; raw != nil && !ok {
var name string
var ok bool
if _, ok = raw["name"]; raw != nil && !ok {
return errors.New("field name in AttributeNameValue: required")
}
if name, ok = raw["name"].(string); !ok {
return errors.New("yaml: cannot unmarshal field name in AttributeNameValue must be string")
}
if strings.TrimSpace(name) == "" {
return errors.New("field name in AttributeNameValue: required")
}
if _, ok := raw["value"]; raw != nil && !ok {
Expand Down
82 changes: 44 additions & 38 deletions config/v0.3.0/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -390,46 +390,52 @@ func TestParseYAML(t *testing.T) {
wantErr error
wantType interface{}
}{
// {
// name: "valid YAML config",
// input: `valid_empty.yaml`,
// wantErr: nil,
// wantType: &OpenTelemetryConfiguration{
// Disabled: ptr(false),
// FileFormat: ptr("0.1"),
// },
// },
{
name: "valid YAML config",
input: `valid_empty.yaml`,
wantErr: nil,
wantType: &OpenTelemetryConfiguration{
Disabled: ptr(false),
FileFormat: ptr("0.1"),
},
},
{
name: "invalid config",
input: "invalid_bool.yaml",
name: "invalid empty config",
input: "invalid_empty.yaml",
wantErr: errors.New(`yaml: unmarshal errors:
line 2: cannot unmarshal !!str ` + "`notabool`" + ` into bool`),
},
{
name: "invalid nil name",
input: "invalid_nil_name.yaml",
wantErr: errors.New(`yaml: cannot unmarshal field name in NameStringValuePair required`),
},
{
name: "invalid nil value",
input: "invalid_nil_value.yaml",
wantErr: errors.New(`yaml: cannot unmarshal field value in NameStringValuePair required`),
},
{
name: "valid v0.2 config",
input: "v0.2.yaml",
wantErr: errors.New(`yaml: unmarshal errors:
line 81: cannot unmarshal !!map into []config.NameStringValuePair
line 185: cannot unmarshal !!map into []config.NameStringValuePair
line 244: cannot unmarshal !!seq into config.IncludeExclude
line 305: cannot unmarshal !!map into []config.NameStringValuePair
line 408: cannot unmarshal !!map into []config.AttributeNameValue`),
},
{
name: "valid v0.3 config",
input: "v0.3.yaml",
wantType: &v03OpenTelemetryConfig,
},
line 3: cannot unmarshal null values`),
},
// {
// name: "invalid config",
// input: "invalid_bool.yaml",
// wantErr: errors.New(`yaml: unmarshal errors:
// line 2: cannot unmarshal !!str ` + "`notabool`" + ` into bool`),
// },
// {
// name: "invalid nil name",
// input: "invalid_nil_name.yaml",
// wantErr: errors.New(`yaml: cannot unmarshal field name in NameStringValuePair required`),
// },
// {
// name: "invalid nil value",
// input: "invalid_nil_value.yaml",
// wantErr: errors.New(`yaml: cannot unmarshal field value in NameStringValuePair required`),
// },
// {
// name: "valid v0.2 config",
// input: "v0.2.yaml",
// wantErr: errors.New(`yaml: unmarshal errors:
// line 81: cannot unmarshal !!map into []config.NameStringValuePair
// line 185: cannot unmarshal !!map into []config.NameStringValuePair
// line 244: cannot unmarshal !!seq into config.IncludeExclude
// line 305: cannot unmarshal !!map into []config.NameStringValuePair
// line 408: cannot unmarshal !!map into []config.AttributeNameValue`),
// },
// {
// name: "valid v0.3 config",
// input: "v0.3.yaml",
// wantType: &v03OpenTelemetryConfig,
// },
}

for _, tt := range tests {
Expand Down
37 changes: 37 additions & 0 deletions config/v0.3.0/config_yaml.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,25 @@ import (
"reflect"
)

func (c *OpenTelemetryConfiguration) UnmarshalYAML(unmarshal func(interface{}) error) error {
type alias OpenTelemetryConfiguration // Prevents infinite recursion
aux := &alias{}

// Decode into alias
if err := unmarshal(aux); err != nil {
return err
}

// Check for an empty attributes list
if len(aux.Resource.Attributes) == 0 {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is just to demo surfacing an error on an empty resource attributes list. This in effect makes resource attributes required so I don't think this will work.

return fmt.Errorf("error: 'attributes' list cannot be empty")
}

// Assign parsed data back to actual struct
*c = OpenTelemetryConfiguration(*aux)
return nil
}

// UnmarshalYAML implements yaml.Unmarshaler.
func (j *AttributeNameValueType) UnmarshalYAML(unmarshal func(interface{}) error) error {
var v struct {
Expand All @@ -31,6 +50,24 @@ func (j *AttributeNameValueType) UnmarshalYAML(unmarshal func(interface{}) error
return nil
}

// UnmarshalYAML implements yaml.Unmarshaler.
func (j *AttributeNameValue) UnmarshalYAML(unmarshal func(interface{}) error) error {
type alias AttributeNameValue
aux := &alias{}

if err := unmarshal(aux); err != nil {
return err
}

// Check for empty name
if aux.Name == "" {
return fmt.Errorf("error: attribute 'name' cannot be empty")
}

*j = AttributeNameValue(*aux)
return nil
}

// UnmarshalYAML implements yaml.Unmarshaler.
func (j *NameStringValuePair) UnmarshalYAML(unmarshal func(interface{}) error) error {
var raw map[string]interface{}
Expand Down
Loading