Skip to content

Commit

Permalink
Fix properties update validation
Browse files Browse the repository at this point in the history
The properties validation was validating the envelope instead of the
actual properties. This lead to issues of us not being able to
accurately update required fields, even if this was allowed by previous
checks.

Signed-off-by: Juan Antonio Osorio <[email protected]>
  • Loading branch information
JAORMX committed Nov 15, 2024
1 parent 5ff3184 commit 72e4300
Show file tree
Hide file tree
Showing 2 changed files with 58 additions and 3 deletions.
22 changes: 19 additions & 3 deletions internal/util/schemaupdate/schemaupdate.go
Original file line number Diff line number Diff line change
Expand Up @@ -97,14 +97,30 @@ func validateObjectSchemaUpdate(oldSchemaMap, newSchemaMap map[string]any) error
}

func validateProperties(oldSchemaMap, newSchemaMap map[string]any) error {
dst, err := deepcopy.Anything(newSchemaMap)
oldProperties, hasOldProperties := oldSchemaMap["properties"]
newProperties, hasNewProperties := newSchemaMap["properties"]

if !hasNewProperties || !hasOldProperties {
return fmt.Errorf("cannot remove properties from object type rule schema")
}

oldPropertiesMap, ok := oldProperties.(map[string]any)
if !ok {
return fmt.Errorf("invalid old properties field")
}
newPropertiesMap, ok := newProperties.(map[string]any)
if !ok {
return fmt.Errorf("invalid new properties field")
}

dst, err := deepcopy.Anything(newPropertiesMap)
if err != nil {
return fmt.Errorf("failed to deepcopy old schema: %v", err)
}

castedDst := dst.(map[string]any)

err = mergo.Merge(&castedDst, &oldSchemaMap, mergo.WithOverride, mergo.WithSliceDeepCopy)
err = mergo.Merge(&castedDst, &oldPropertiesMap, mergo.WithOverride, mergo.WithSliceDeepCopy)
if err != nil {
return fmt.Errorf("failed to merge old and new schema: %v", err)
}
Expand All @@ -119,7 +135,7 @@ func validateProperties(oldSchemaMap, newSchemaMap map[string]any) error {

// The new schema should be a superset of the old schema
// if it's not, we may break profiles using this rule type
if !cmp.Equal(newSchemaMap, castedDst, opts...) {
if !cmp.Equal(newPropertiesMap, castedDst, opts...) {
return fmt.Errorf("cannot remove properties from rule schema")
}

Expand Down
39 changes: 39 additions & 0 deletions internal/util/schemaupdate/schemaupdate_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,28 @@ func TestValidateSchemaUpdate(t *testing.T) {
},
wantErr: true,
},
{
name: "removing required fields is allowed",
args: args{
oldRuleSchemaDef: `{
"type": "object",
"properties": {
"foo": {
"type": "string"
}
},
"required": ["foo"]
}`,
newRuleSchemaDef: `{
"type": "object",
"properties": {
"foo": {
"type": "string"
}
}
}`,
},
},
{
name: "old schema should error if new schema deletes fields",
args: args{
Expand Down Expand Up @@ -299,6 +321,23 @@ func TestValidateSchemaUpdate(t *testing.T) {
},
wantErr: true,
},
{
name: "Removing the properties map is not allowed",
args: args{
oldRuleSchemaDef: `{
"type": "object",
"properties": {
"foo": {
"type": "string"
}
}
}`,
newRuleSchemaDef: `{
"type": "object"
}`,
},
wantErr: true,
},
}
for _, tt := range tests {
tt := tt
Expand Down

0 comments on commit 72e4300

Please sign in to comment.