From 684617e29ec411f8a8a54cc96d0aaf1f01017047 Mon Sep 17 00:00:00 2001 From: shlomo Date: Mon, 13 Feb 2023 17:37:39 +0200 Subject: [PATCH] fix: default values count even if disabled (#767) --- openapi3/issue767_test.go | 90 +++++++++++++++++++++++++++++++++++++++ openapi3/schema.go | 10 ++--- 2 files changed, 94 insertions(+), 6 deletions(-) create mode 100644 openapi3/issue767_test.go diff --git a/openapi3/issue767_test.go b/openapi3/issue767_test.go new file mode 100644 index 00000000..d498877c --- /dev/null +++ b/openapi3/issue767_test.go @@ -0,0 +1,90 @@ +package openapi3_test + +import ( + "testing" + + "github.com/stretchr/testify/require" + + "github.com/getkin/kin-openapi/openapi3" +) + +func TestIssue767(t *testing.T) { + t.Parallel() + + tests := [...]struct { + name string + schema *openapi3.Schema + value map[string]interface{} + opts []openapi3.SchemaValidationOption + checkErr require.ErrorAssertionFunc + }{ + { + name: "default values disabled should fail with minProps 1", + schema: openapi3.NewSchema().WithProperties(map[string]*openapi3.Schema{ + "foo": {Type: "boolean", Default: true}}).WithMinProperties(1), + value: map[string]interface{}{}, + opts: []openapi3.SchemaValidationOption{ + openapi3.VisitAsRequest(), + }, + checkErr: require.Error, + }, + { + name: "default values enabled should pass with minProps 1", + schema: openapi3.NewSchema().WithProperties(map[string]*openapi3.Schema{ + "foo": {Type: "boolean", Default: true}}).WithMinProperties(1), + value: map[string]interface{}{}, + opts: []openapi3.SchemaValidationOption{ + openapi3.VisitAsRequest(), + openapi3.DefaultsSet(func() {}), + }, + checkErr: require.NoError, + }, + { + name: "default values enabled should pass with minProps 2", + schema: openapi3.NewSchema().WithProperties(map[string]*openapi3.Schema{ + "foo": {Type: "boolean", Default: true}, + "bar": {Type: "boolean"}, + }).WithMinProperties(2), + value: map[string]interface{}{"bar": false}, + opts: []openapi3.SchemaValidationOption{ + openapi3.VisitAsRequest(), + openapi3.DefaultsSet(func() {}), + }, + checkErr: require.NoError, + }, + { + name: "default values enabled should fail with maxProps 1", + schema: openapi3.NewSchema().WithProperties(map[string]*openapi3.Schema{ + "foo": {Type: "boolean", Default: true}, + "bar": {Type: "boolean"}, + }).WithMaxProperties(1), + value: map[string]interface{}{"bar": false}, + opts: []openapi3.SchemaValidationOption{ + openapi3.VisitAsRequest(), + openapi3.DefaultsSet(func() {}), + }, + checkErr: require.Error, + }, + { + name: "default values disabled should pass with maxProps 1", + schema: openapi3.NewSchema().WithProperties(map[string]*openapi3.Schema{ + "foo": {Type: "boolean", Default: true}, + "bar": {Type: "boolean"}, + }).WithMaxProperties(1), + value: map[string]interface{}{"bar": false}, + opts: []openapi3.SchemaValidationOption{ + openapi3.VisitAsRequest(), + }, + checkErr: require.NoError, + }, + } + + for _, test := range tests { + test := test + t.Run(test.name, func(t *testing.T) { + t.Parallel() + err := test.schema.VisitJSON(test.value, test.opts...) + test.checkErr(t, err) + }) + } +} diff --git a/openapi3/schema.go b/openapi3/schema.go index b6be8c1b..4bfbca0b 100644 --- a/openapi3/schema.go +++ b/openapi3/schema.go @@ -1789,12 +1789,10 @@ func (schema *Schema) visitJSONObject(settings *schemaValidationSettings, value reqRO := settings.asreq && propSchema.Value.ReadOnly && !settings.readOnlyValidationDisabled repWO := settings.asrep && propSchema.Value.WriteOnly && !settings.writeOnlyValidationDisabled - if value[propName] == nil { - if dlft := propSchema.Value.Default; dlft != nil && !reqRO && !repWO { - value[propName] = dlft - if f := settings.defaultsSet; f != nil { - settings.onceSettingDefaults.Do(f) - } + if f := settings.defaultsSet; f != nil && value[propName] == nil { + if dflt := propSchema.Value.Default; dflt != nil && !reqRO && !repWO { + value[propName] = dflt + settings.onceSettingDefaults.Do(f) } }