github.com/emreu/go-swagger@v0.22.1/generator/model_test.go (about) 1 // Copyright 2015 go-swagger maintainers 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package generator 16 17 import ( 18 "bytes" 19 "fmt" 20 "io/ioutil" 21 "log" 22 "os" 23 "regexp" 24 "strconv" 25 "strings" 26 "testing" 27 "text/template" 28 29 "github.com/go-openapi/loads" 30 "github.com/go-openapi/swag" 31 "github.com/stretchr/testify/assert" 32 ) 33 34 type templateTest struct { 35 t testing.TB 36 template *template.Template 37 } 38 39 func (tt *templateTest) assertRender(data interface{}, expected string) bool { 40 buf := bytes.NewBuffer(nil) 41 err := tt.template.Execute(buf, data) 42 if !assert.NoError(tt.t, err) { 43 return false 44 } 45 return assert.Equal(tt.t, expected, buf.String()) 46 } 47 48 func TestGenerateModel_Sanity(t *testing.T) { 49 // just checks if it can render and format these things 50 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 51 if assert.NoError(t, err) { 52 definitions := specDoc.Spec().Definitions 53 54 //k := "Comment" 55 //schema := definitions[k] 56 for k, schema := range definitions { 57 opts := opts() 58 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 59 60 // log.Printf("trying model: %s", k) 61 if assert.NoError(t, err) { 62 //b, _ := json.MarshalIndent(genModel, "", " ") 63 //fmt.Println(string(b)) 64 rendered := bytes.NewBuffer(nil) 65 66 err := templates.MustGet("model").Execute(rendered, genModel) 67 if assert.NoError(t, err, "Unexpected error while rendering models for fixtures/codegen/todolist.models.yml: %v", err) { 68 _, err := opts.LanguageOpts.FormatContent(strings.ToLower(k)+".go", rendered.Bytes()) 69 assert.NoError(t, err) 70 //if assert.NoError(t, err) { 71 //fmt.Println(string(formatted)) 72 //} else { 73 //fmt.Println(rendered.String()) 74 ////break 75 //} 76 77 //assert.EqualValues(t, strings.TrimSpace(string(expected)), strings.TrimSpace(string(formatted))) 78 } 79 } 80 } 81 } 82 } 83 84 func TestGenerateModel_DocString(t *testing.T) { 85 templ := template.Must(template.New("docstring").Funcs(FuncMap).Parse(string(assets["docstring.gotmpl"]))) 86 tt := templateTest{t, templ} 87 88 var gmp GenSchema 89 gmp.Title = "The title of the property" 90 gmp.Description = "The description of the property" 91 var expected = `The title of the property 92 // 93 // The description of the property` 94 tt.assertRender(gmp, expected) 95 96 gmp.Title = "" 97 expected = `The description of the property` 98 tt.assertRender(gmp, expected) 99 100 gmp.Description = "" 101 gmp.Name = "theModel" 102 expected = `the model` 103 tt.assertRender(gmp, expected) 104 } 105 106 func TestGenerateModel_PropertyValidation(t *testing.T) { 107 templ := template.Must(template.New("propertyValidationDocString").Funcs(FuncMap).Parse(string(assets["validation/structfield.gotmpl"]))) 108 tt := templateTest{t, templ} 109 110 var gmp GenSchema 111 gmp.Required = true 112 tt.assertRender(gmp, ` 113 // Required: true`) 114 var fl float64 = 10 115 var in1 int64 = 20 116 var in2 int64 = 30 117 gmp.Maximum = &fl 118 gmp.ExclusiveMaximum = true 119 gmp.Minimum = &fl 120 gmp.ExclusiveMinimum = true 121 gmp.MaxLength = &in1 122 gmp.MinLength = &in1 123 gmp.Pattern = "\\w[\\w- ]+" 124 gmp.MaxItems = &in2 125 gmp.MinItems = &in2 126 gmp.UniqueItems = true 127 128 tt.assertRender(gmp, ` 129 // Required: true 130 // Maximum: < 10 131 // Minimum: > 10 132 // Max Length: 20 133 // Min Length: 20 134 // Pattern: \w[\w- ]+ 135 // Max Items: 30 136 // Min Items: 30 137 // Unique: true`) 138 139 gmp.Required = false 140 gmp.ExclusiveMaximum = false 141 gmp.ExclusiveMinimum = false 142 tt.assertRender(gmp, ` 143 // Maximum: 10 144 // Minimum: 10 145 // Max Length: 20 146 // Min Length: 20 147 // Pattern: \w[\w- ]+ 148 // Max Items: 30 149 // Min Items: 30 150 // Unique: true`) 151 152 } 153 154 func TestGenerateModel_SchemaField(t *testing.T) { 155 tt := templateTest{t, templates.MustGet("model").Lookup("structfield")} 156 157 var gmp GenSchema 158 gmp.Name = "some name" 159 gmp.OriginalName = "some name" 160 gmp.resolvedType = resolvedType{GoType: "string", IsPrimitive: true, IsEmptyOmitted: true} 161 gmp.Title = "The title of the property" 162 gmp.CustomTag = "mytag:\"foobar,foobaz\"" 163 164 tt.assertRender(gmp, `// The title of the property 165 `+"SomeName string `json:\"some name,omitempty\" mytag:\"foobar,foobaz\"`\n") 166 167 var fl float64 = 10 168 var in1 int64 = 20 169 var in2 int64 = 30 170 171 gmp.Description = "The description of the property" 172 gmp.Required = true 173 gmp.Maximum = &fl 174 gmp.ExclusiveMaximum = true 175 gmp.Minimum = &fl 176 gmp.ExclusiveMinimum = true 177 gmp.MaxLength = &in1 178 gmp.MinLength = &in1 179 gmp.Pattern = "\\w[\\w- ]+" 180 gmp.MaxItems = &in2 181 gmp.MinItems = &in2 182 gmp.UniqueItems = true 183 gmp.ReadOnly = true 184 tt.assertRender(gmp, `// The title of the property 185 // 186 // The description of the property 187 // Required: true 188 // Read Only: true 189 // Maximum: < 10 190 // Minimum: > 10 191 // Max Length: 20 192 // Min Length: 20 193 // Pattern: \w[\w- ]+ 194 // Max Items: 30 195 // Min Items: 30 196 // Unique: true 197 `+"SomeName string `json:\"some name\" mytag:\"foobar,foobaz\"`\n") 198 } 199 200 var schTypeGenDataSimple = []struct { 201 Value GenSchema 202 Expected string 203 }{ 204 {GenSchema{resolvedType: resolvedType{GoType: "string", IsPrimitive: true}}, "string"}, 205 {GenSchema{resolvedType: resolvedType{GoType: "string", IsPrimitive: true, IsNullable: true}}, "*string"}, 206 {GenSchema{resolvedType: resolvedType{GoType: "bool", IsPrimitive: true}}, "bool"}, 207 {GenSchema{resolvedType: resolvedType{GoType: "int32", IsPrimitive: true}}, "int32"}, 208 {GenSchema{resolvedType: resolvedType{GoType: "int64", IsPrimitive: true}}, "int64"}, 209 {GenSchema{resolvedType: resolvedType{GoType: "float32", IsPrimitive: true}}, "float32"}, 210 {GenSchema{resolvedType: resolvedType{GoType: "float64", IsPrimitive: true}}, "float64"}, 211 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.Base64", IsPrimitive: true}}, "strfmt.Base64"}, 212 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.Date", IsPrimitive: true}}, "strfmt.Date"}, 213 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.DateTime", IsPrimitive: true}}, "strfmt.DateTime"}, 214 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.URI", IsPrimitive: true}}, "strfmt.URI"}, 215 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.Email", IsPrimitive: true}}, "strfmt.Email"}, 216 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.Hostname", IsPrimitive: true}}, "strfmt.Hostname"}, 217 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.IPv4", IsPrimitive: true}}, "strfmt.IPv4"}, 218 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.IPv6", IsPrimitive: true}}, "strfmt.IPv6"}, 219 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.UUID", IsPrimitive: true}}, "strfmt.UUID"}, 220 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.UUID3", IsPrimitive: true}}, "strfmt.UUID3"}, 221 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.UUID4", IsPrimitive: true}}, "strfmt.UUID4"}, 222 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.UUID5", IsPrimitive: true}}, "strfmt.UUID5"}, 223 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.ISBN", IsPrimitive: true}}, "strfmt.ISBN"}, 224 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.ISBN10", IsPrimitive: true}}, "strfmt.ISBN10"}, 225 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.ISBN13", IsPrimitive: true}}, "strfmt.ISBN13"}, 226 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.CreditCard", IsPrimitive: true}}, "strfmt.CreditCard"}, 227 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.SSN", IsPrimitive: true}}, "strfmt.SSN"}, 228 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.HexColor", IsPrimitive: true}}, "strfmt.HexColor"}, 229 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.RGBColor", IsPrimitive: true}}, "strfmt.RGBColor"}, 230 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.Duration", IsPrimitive: true}}, "strfmt.Duration"}, 231 {GenSchema{resolvedType: resolvedType{GoType: "strfmt.Password", IsPrimitive: true}}, "strfmt.Password"}, 232 {GenSchema{resolvedType: resolvedType{GoType: "io.ReadCloser", IsStream: true}}, "io.ReadCloser"}, 233 {GenSchema{resolvedType: resolvedType{GoType: "interface{}", IsInterface: true}}, "interface{}"}, 234 {GenSchema{resolvedType: resolvedType{GoType: "[]int32", IsArray: true}}, "[]int32"}, 235 {GenSchema{resolvedType: resolvedType{GoType: "[]string", IsArray: true}}, "[]string"}, 236 {GenSchema{resolvedType: resolvedType{GoType: "map[string]int32", IsMap: true}}, "map[string]int32"}, 237 {GenSchema{resolvedType: resolvedType{GoType: "models.Task", IsComplexObject: true, IsNullable: true, IsAnonymous: false}}, "*models.Task"}, 238 } 239 240 func TestGenSchemaType(t *testing.T) { 241 tt := templateTest{t, templates.MustGet("model").Lookup("schemaType")} 242 for _, v := range schTypeGenDataSimple { 243 tt.assertRender(v.Value, v.Expected) 244 } 245 } 246 func TestGenerateModel_Primitives(t *testing.T) { 247 tt := templateTest{t, templates.MustGet("model").Lookup("schema")} 248 for _, v := range schTypeGenDataSimple { 249 v.Value.IncludeValidator = true 250 v.Value.IncludeModel = true 251 val := v.Value 252 val.ReceiverName = "o" 253 if val.IsComplexObject { 254 continue 255 } 256 val.Name = "theType" 257 exp := v.Expected 258 if val.IsInterface || val.IsStream { 259 tt.assertRender(&val, "type TheType "+exp+"\n \n") 260 continue 261 } 262 tt.assertRender(&val, "type TheType "+exp+"\n // Validate validates this the type\nfunc (o theType) Validate(formats strfmt.Registry) error {\n return nil\n}\n") 263 } 264 } 265 266 func TestGenerateModel_Zeroes(t *testing.T) { 267 for _, v := range schTypeGenDataSimple { 268 //t.Logf("Zero for %s: %s", v.Value.GoType, v.Value.Zero()) 269 switch v.Value.GoType { 270 // verifying Zero for primitive 271 case "string": 272 assert.Equal(t, `""`, v.Value.Zero()) 273 case "bool": 274 assert.Equal(t, `false`, v.Value.Zero()) 275 case "int32", "int64", "float32", "float64": 276 assert.Equal(t, `0`, v.Value.Zero()) 277 // verifying Zero for primitive formatters 278 case "strfmt.Date", "strfmt.DateTime", "strfmt.OjbectId": // akin to structs 279 rex := regexp.MustCompile(regexp.QuoteMeta(v.Value.GoType) + `{}`) 280 assert.True(t, rex.MatchString(v.Value.Zero())) 281 k := v.Value 282 k.IsAliased = true 283 k.AliasedType = k.GoType 284 k.GoType = "myAliasedType" 285 rex = regexp.MustCompile(regexp.QuoteMeta(k.GoType+"("+k.AliasedType) + `{}` + `\)`) 286 assert.True(t, rex.MatchString(k.Zero())) 287 //t.Logf("Zero for %s: %s", k.GoType, k.Zero()) 288 case "strfmt.Duration": // akin to integer 289 rex := regexp.MustCompile(regexp.QuoteMeta(v.Value.GoType) + `\(\d*\)`) 290 assert.True(t, rex.MatchString(v.Value.Zero())) 291 k := v.Value 292 k.IsAliased = true 293 k.AliasedType = k.GoType 294 k.GoType = "myAliasedType" 295 rex = regexp.MustCompile(regexp.QuoteMeta(k.GoType+"("+k.AliasedType) + `\(\d*\)` + `\)`) 296 assert.True(t, rex.MatchString(k.Zero())) 297 //t.Logf("Zero for %s: %s", k.GoType, k.Zero()) 298 case "strfmt.Base64": // akin to []byte 299 rex := regexp.MustCompile(regexp.QuoteMeta(v.Value.GoType) + `\(\[\]byte.*\)`) 300 assert.True(t, rex.MatchString(v.Value.Zero())) 301 k := v.Value 302 k.IsAliased = true 303 k.AliasedType = k.GoType 304 k.GoType = "myAliasedType" 305 rex = regexp.MustCompile(regexp.QuoteMeta(k.GoType+"("+k.AliasedType) + `\(\[\]byte.*\)` + `\)`) 306 assert.True(t, rex.MatchString(k.Zero())) 307 // t.Logf("Zero for %s: %s", k.GoType, k.Zero()) 308 case "interface{}": 309 assert.Equal(t, `nil`, v.Value.Zero()) 310 case "io.ReadCloser": 311 continue 312 default: 313 switch { 314 case strings.HasPrefix(v.Value.GoType, "[]") || strings.HasPrefix(v.Value.GoType, "map["): // akin to slice or map 315 assert.True(t, strings.HasPrefix(v.Value.Zero(), "make(")) 316 317 case strings.HasPrefix(v.Value.GoType, "models."): 318 assert.True(t, strings.HasPrefix(v.Value.Zero(), "new(")) 319 320 default: // akin to string 321 rex := regexp.MustCompile(regexp.QuoteMeta(v.Value.GoType) + `\(".*"\)`) 322 assert.True(t, rex.MatchString(v.Value.Zero())) 323 k := v.Value 324 k.IsAliased = true 325 k.AliasedType = k.GoType 326 k.GoType = "myAliasedType" 327 rex = regexp.MustCompile(regexp.QuoteMeta(k.GoType+"("+k.AliasedType) + `\(".*"\)` + `\)`) 328 assert.True(t, rex.MatchString(k.Zero())) 329 //t.Logf("Zero for %s: %s", k.GoType, k.Zero()) 330 } 331 } 332 } 333 } 334 func TestGenerateModel_Nota(t *testing.T) { 335 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 336 if assert.NoError(t, err) { 337 definitions := specDoc.Spec().Definitions 338 k := "Nota" 339 schema := definitions[k] 340 opts := opts() 341 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 342 if assert.NoError(t, err) { 343 buf := bytes.NewBuffer(nil) 344 err := templates.MustGet("model").Execute(buf, genModel) 345 if assert.NoError(t, err) { 346 res := buf.String() 347 assertInCode(t, "type Nota map[string]int32", res) 348 } 349 } 350 } 351 } 352 353 func TestGenerateModel_NotaWithRef(t *testing.T) { 354 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 355 if assert.NoError(t, err) { 356 definitions := specDoc.Spec().Definitions 357 k := "NotaWithRef" 358 schema := definitions[k] 359 opts := opts() 360 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 361 if assert.NoError(t, err) { 362 buf := bytes.NewBuffer(nil) 363 err := templates.MustGet("model").Execute(buf, genModel) 364 if assert.NoError(t, err) { 365 ff, err := opts.LanguageOpts.FormatContent("nota_with_ref.go", buf.Bytes()) 366 if assert.NoError(t, err) { 367 res := string(ff) 368 assertInCode(t, "type NotaWithRef map[string]Notable", res) 369 } 370 } 371 } 372 } 373 } 374 375 func TestGenerateModel_NotaWithMeta(t *testing.T) { 376 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 377 if assert.NoError(t, err) { 378 definitions := specDoc.Spec().Definitions 379 k := "NotaWithMeta" 380 schema := definitions[k] 381 opts := opts() 382 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 383 if assert.NoError(t, err) { 384 buf := bytes.NewBuffer(nil) 385 err := templates.MustGet("model").Execute(buf, genModel) 386 if assert.NoError(t, err) { 387 ff, err := opts.LanguageOpts.FormatContent("nota_with_meta.go", buf.Bytes()) 388 if assert.NoError(t, err) { 389 res := string(ff) 390 assertInCode(t, "type NotaWithMeta map[string]NotaWithMetaAnon", res) 391 assertInCode(t, "type NotaWithMetaAnon struct {", res) 392 assertInCode(t, "Comment *string `json:\"comment\"`", res) 393 assertInCode(t, "Count int32 `json:\"count,omitempty\"`", res) 394 } 395 } 396 } 397 } 398 } 399 400 func TestGenerateModel_RunParameters(t *testing.T) { 401 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 402 if assert.NoError(t, err) { 403 definitions := specDoc.Spec().Definitions 404 k := "RunParameters" 405 schema := definitions[k] 406 opts := opts() 407 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 408 if assert.NoError(t, err) { 409 assert.False(t, genModel.IsAdditionalProperties) 410 assert.True(t, genModel.IsComplexObject) 411 assert.False(t, genModel.IsMap) 412 assert.False(t, genModel.IsAnonymous) 413 buf := bytes.NewBuffer(nil) 414 err := templates.MustGet("model").Execute(buf, genModel) 415 if assert.NoError(t, err) { 416 res := buf.String() 417 assertInCode(t, "type "+k+" struct {", res) 418 assertInCode(t, "BranchName string `json:\"branch_name,omitempty\"`", res) 419 assertInCode(t, "CommitSha string `json:\"commit_sha,omitempty\"`", res) 420 assertInCode(t, "Refs interface{} `json:\"refs,omitempty\"`", res) 421 } 422 } 423 } 424 } 425 426 func TestGenerateModel_NotaWithName(t *testing.T) { 427 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 428 if assert.NoError(t, err) { 429 definitions := specDoc.Spec().Definitions 430 k := "NotaWithName" 431 schema := definitions[k] 432 opts := opts() 433 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 434 if assert.NoError(t, err) { 435 assert.True(t, genModel.IsAdditionalProperties) 436 assert.False(t, genModel.IsComplexObject) 437 assert.False(t, genModel.IsMap) 438 assert.False(t, genModel.IsAnonymous) 439 buf := bytes.NewBuffer(nil) 440 err := templates.MustGet("model").Execute(buf, genModel) 441 if assert.NoError(t, err) { 442 res := buf.String() 443 assertInCode(t, "type "+k+" struct {", res) 444 assertInCode(t, k+" map[string]int32 `json:\"-\"`", res) 445 assertInCode(t, "Name *string `json:\"name\"`", res) 446 assertInCode(t, k+") UnmarshalJSON", res) 447 assertInCode(t, k+") MarshalJSON", res) 448 assertInCode(t, "json.Marshal(stage1)", res) 449 assertInCode(t, "stage1.Name = m.Name", res) 450 assertInCode(t, "json.Marshal(m."+k+")", res) 451 assertInCode(t, "json.Unmarshal(data, &stage1)", res) 452 assertInCode(t, "json.Unmarshal(data, &stage2)", res) 453 assertInCode(t, "json.Unmarshal(v, &toadd)", res) 454 assertInCode(t, "result[k] = toadd", res) 455 assertInCode(t, "m."+k+" = result", res) 456 for _, p := range genModel.Properties { 457 assertInCode(t, "delete(stage2, \""+p.Name+"\")", res) 458 } 459 460 } 461 } 462 } 463 } 464 465 func TestGenerateModel_NotaWithRefRegistry(t *testing.T) { 466 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 467 if assert.NoError(t, err) { 468 definitions := specDoc.Spec().Definitions 469 k := "NotaWithRefRegistry" 470 schema := definitions[k] 471 opts := opts() 472 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 473 if assert.NoError(t, err) { 474 buf := bytes.NewBuffer(nil) 475 err := templates.MustGet("model").Execute(buf, genModel) 476 if assert.NoError(t, err) { 477 ff, err := opts.LanguageOpts.FormatContent("nota_with_ref_registry.go", buf.Bytes()) 478 if assert.NoError(t, err) { 479 res := string(ff) 480 assertInCode(t, "type "+k+" map[string]map[string]map[string]Notable", res) 481 } 482 } 483 } 484 } 485 } 486 487 func TestGenerateModel_WithCustomTag(t *testing.T) { 488 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 489 if assert.NoError(t, err) { 490 definitions := specDoc.Spec().Definitions 491 k := "WithCustomTag" 492 schema := definitions[k] 493 opts := opts() 494 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 495 if assert.NoError(t, err) { 496 buf := bytes.NewBuffer(nil) 497 err := templates.MustGet("model").Execute(buf, genModel) 498 if assert.NoError(t, err) { 499 res := buf.String() 500 assertInCode(t, "mytag:\"foo,bar\"", res) 501 } 502 } 503 } 504 } 505 506 func TestGenerateModel_NotaWithMetaRegistry(t *testing.T) { 507 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 508 if assert.NoError(t, err) { 509 definitions := specDoc.Spec().Definitions 510 k := "NotaWithMetaRegistry" 511 schema := definitions[k] 512 opts := opts() 513 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 514 if assert.NoError(t, err) { 515 buf := bytes.NewBuffer(nil) 516 err := templates.MustGet("model").Execute(buf, genModel) 517 if assert.NoError(t, err) { 518 ff, err := opts.LanguageOpts.FormatContent("nota_with_meta_registry.go", buf.Bytes()) 519 if assert.NoError(t, err) { 520 res := string(ff) 521 assertInCode(t, "type "+k+" map[string]map[string]map[string]NotaWithMetaRegistryAnon", res) 522 assertInCode(t, "type NotaWithMetaRegistryAnon struct {", res) 523 assertInCode(t, "Comment *string `json:\"comment\"`", res) 524 assertInCode(t, "Count int32 `json:\"count,omitempty\"`", res) 525 } 526 } 527 } 528 } 529 } 530 531 func TestGenerateModel_WithMap(t *testing.T) { 532 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 533 if assert.NoError(t, err) { 534 definitions := specDoc.Spec().Definitions 535 schema := definitions["WithMap"] 536 opts := opts() 537 genModel, err := makeGenDefinition("WithMap", "models", schema, specDoc, opts) 538 if assert.NoError(t, err) { 539 assert.False(t, genModel.HasAdditionalProperties) 540 prop := getDefinitionProperty(genModel, "data") 541 assert.True(t, prop.HasAdditionalProperties) 542 assert.True(t, prop.IsMap) 543 assert.False(t, prop.IsComplexObject) 544 buf := bytes.NewBuffer(nil) 545 err := templates.MustGet("model").Execute(buf, genModel) 546 if assert.NoError(t, err) { 547 res := buf.String() 548 assertInCode(t, "type WithMap struct {", res) 549 assertInCode(t, "Data map[string]string `json:\"data,omitempty\"`", res) 550 } 551 } 552 } 553 } 554 555 func TestGenerateModel_WithMapInterface(t *testing.T) { 556 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 557 if assert.NoError(t, err) { 558 definitions := specDoc.Spec().Definitions 559 schema := definitions["WithMapInterface"] 560 opts := opts() 561 genModel, err := makeGenDefinition("WithMapInterface", "models", schema, specDoc, opts) 562 if assert.NoError(t, err) { 563 assert.False(t, genModel.HasAdditionalProperties) 564 prop := getDefinitionProperty(genModel, "extraInfo") 565 assert.True(t, prop.HasAdditionalProperties) 566 assert.True(t, prop.IsMap) 567 assert.False(t, prop.IsComplexObject) 568 assert.Equal(t, "map[string]interface{}", prop.GoType) 569 assert.True(t, prop.Required) 570 assert.True(t, prop.HasValidations) 571 // NOTE(fredbi): NeedsValidation now deprecated 572 //assert.False(t, prop.NeedsValidation) 573 buf := bytes.NewBuffer(nil) 574 err := templates.MustGet("model").Execute(buf, genModel) 575 if assert.NoError(t, err) { 576 res := buf.String() 577 assertInCode(t, "type WithMapInterface struct {", res) 578 assertInCode(t, "ExtraInfo map[string]interface{} `json:\"extraInfo\"`", res) 579 } 580 } 581 } 582 } 583 584 func TestGenerateModel_WithMapRef(t *testing.T) { 585 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 586 if assert.NoError(t, err) { 587 definitions := specDoc.Spec().Definitions 588 k := "WithMapRef" 589 schema := definitions[k] 590 opts := opts() 591 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 592 if assert.NoError(t, err) { 593 assert.False(t, genModel.HasAdditionalProperties) 594 prop := getDefinitionProperty(genModel, "data") 595 assert.True(t, prop.HasAdditionalProperties) 596 assert.True(t, prop.IsMap) 597 assert.False(t, prop.IsComplexObject) 598 buf := bytes.NewBuffer(nil) 599 err := templates.MustGet("model").Execute(buf, genModel) 600 if assert.NoError(t, err) { 601 res := buf.String() 602 assertInCode(t, "type "+k+" struct {", res) 603 assertInCode(t, "Data map[string]Notable `json:\"data,omitempty\"`", res) 604 } 605 } 606 } 607 } 608 609 func TestGenerateModel_WithMapComplex(t *testing.T) { 610 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 611 if assert.NoError(t, err) { 612 definitions := specDoc.Spec().Definitions 613 k := "WithMapComplex" 614 schema := definitions[k] 615 opts := opts() 616 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 617 if assert.NoError(t, err) { 618 assert.False(t, genModel.HasAdditionalProperties) 619 prop := getDefinitionProperty(genModel, "data") 620 assert.True(t, prop.HasAdditionalProperties) 621 assert.True(t, prop.IsMap) 622 assert.False(t, prop.IsComplexObject) 623 buf := bytes.NewBuffer(nil) 624 err := templates.MustGet("model").Execute(buf, genModel) 625 if assert.NoError(t, err) { 626 res := buf.String() 627 assertInCode(t, "type "+k+" struct {", res) 628 assertInCode(t, "Data map[string]"+k+"DataAnon `json:\"data,omitempty\"`", res) 629 } 630 } 631 } 632 } 633 634 func TestGenerateModel_WithMapRegistry(t *testing.T) { 635 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 636 if assert.NoError(t, err) { 637 definitions := specDoc.Spec().Definitions 638 schema := definitions["WithMapRegistry"] 639 opts := opts() 640 genModel, err := makeGenDefinition("WithMap", "models", schema, specDoc, opts) 641 if assert.NoError(t, err) { 642 assert.False(t, genModel.HasAdditionalProperties) 643 prop := getDefinitionProperty(genModel, "data") 644 assert.True(t, prop.HasAdditionalProperties) 645 assert.True(t, prop.IsMap) 646 assert.False(t, prop.IsComplexObject) 647 buf := bytes.NewBuffer(nil) 648 err := templates.MustGet("model").Execute(buf, genModel) 649 if assert.NoError(t, err) { 650 res := buf.String() 651 assertInCode(t, "type WithMap struct {", res) 652 assertInCode(t, "Data map[string]map[string]map[string]string `json:\"data,omitempty\"`", res) 653 } 654 } 655 } 656 } 657 658 func TestGenerateModel_WithMapRegistryRef(t *testing.T) { 659 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 660 if assert.NoError(t, err) { 661 definitions := specDoc.Spec().Definitions 662 k := "WithMapRegistryRef" 663 schema := definitions[k] 664 opts := opts() 665 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 666 if assert.NoError(t, err) { 667 assert.False(t, genModel.HasAdditionalProperties) 668 prop := getDefinitionProperty(genModel, "data") 669 assert.True(t, prop.HasAdditionalProperties) 670 assert.True(t, prop.IsMap) 671 assert.False(t, prop.IsComplexObject) 672 buf := bytes.NewBuffer(nil) 673 err := templates.MustGet("model").Execute(buf, genModel) 674 if assert.NoError(t, err) { 675 res := buf.String() 676 assertInCode(t, "type "+k+" struct {", res) 677 assertInCode(t, "Data map[string]map[string]map[string]Notable `json:\"data,omitempty\"`", res) 678 } 679 } 680 } 681 } 682 683 func TestGenerateModel_WithMapComplexRegistry(t *testing.T) { 684 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 685 if assert.NoError(t, err) { 686 definitions := specDoc.Spec().Definitions 687 k := "WithMapComplexRegistry" 688 schema := definitions[k] 689 opts := opts() 690 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 691 if assert.NoError(t, err) { 692 assert.False(t, genModel.HasAdditionalProperties) 693 prop := getDefinitionProperty(genModel, "data") 694 assert.True(t, prop.HasAdditionalProperties) 695 assert.True(t, prop.IsMap) 696 assert.False(t, prop.IsComplexObject) 697 buf := bytes.NewBuffer(nil) 698 err := templates.MustGet("model").Execute(buf, genModel) 699 if assert.NoError(t, err) { 700 res := buf.String() 701 assertInCode(t, "type "+k+" struct {", res) 702 assertInCode(t, "Data map[string]map[string]map[string]"+k+"DataAnon `json:\"data,omitempty\"`", res) 703 } 704 } 705 } 706 } 707 708 func TestGenerateModel_WithAdditional(t *testing.T) { 709 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 710 if assert.NoError(t, err) { 711 definitions := specDoc.Spec().Definitions 712 k := "WithAdditional" 713 schema := definitions[k] 714 opts := opts() 715 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 716 if assert.NoError(t, err) && assert.NotEmpty(t, genModel.ExtraSchemas) { 717 assert.False(t, genModel.HasAdditionalProperties) 718 assert.False(t, genModel.IsMap) 719 assert.False(t, genModel.IsAdditionalProperties) 720 assert.True(t, genModel.IsComplexObject) 721 722 sch := genModel.ExtraSchemas[0] 723 assert.True(t, sch.HasAdditionalProperties) 724 assert.False(t, sch.IsMap) 725 assert.True(t, sch.IsAdditionalProperties) 726 assert.False(t, sch.IsComplexObject) 727 728 if assert.NotNil(t, sch.AdditionalProperties) { 729 prop := findProperty(genModel.Properties, "data") 730 assert.False(t, prop.HasAdditionalProperties) 731 assert.False(t, prop.IsMap) 732 assert.False(t, prop.IsAdditionalProperties) 733 assert.True(t, prop.IsComplexObject) 734 buf := bytes.NewBuffer(nil) 735 err := templates.MustGet("model").Execute(buf, genModel) 736 if assert.NoError(t, err) { 737 res := buf.String() 738 assertInCode(t, "type "+k+" struct {", res) 739 assertInCode(t, "Data *"+k+"Data `json:\"data,omitempty\"`", res) 740 assertInCode(t, "type "+k+"Data struct {", res) 741 assertInCode(t, k+"Data map[string]string `json:\"-\"`", res) 742 assertInCode(t, "Name *string `json:\"name\"`", res) 743 assertInCode(t, k+"Data) UnmarshalJSON", res) 744 assertInCode(t, k+"Data) MarshalJSON", res) 745 assertInCode(t, "json.Marshal(stage1)", res) 746 assertInCode(t, "stage1.Name = m.Name", res) 747 assertInCode(t, "json.Marshal(m."+k+"Data)", res) 748 assertInCode(t, "json.Unmarshal(data, &stage1)", res) 749 assertInCode(t, "json.Unmarshal(data, &stage2)", res) 750 assertInCode(t, "json.Unmarshal(v, &toadd)", res) 751 assertInCode(t, "result[k] = toadd", res) 752 assertInCode(t, "m."+k+"Data = result", res) 753 for _, p := range sch.Properties { 754 assertInCode(t, "delete(stage2, \""+p.Name+"\")", res) 755 } 756 } 757 } 758 } 759 } 760 } 761 762 func TestGenerateModel_JustRef(t *testing.T) { 763 tt := templateTest{t, templates.MustGet("model").Lookup("schema")} 764 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 765 if assert.NoError(t, err) { 766 definitions := specDoc.Spec().Definitions 767 schema := definitions["JustRef"] 768 opts := opts() 769 genModel, err := makeGenDefinition("JustRef", "models", schema, specDoc, opts) 770 if assert.NoError(t, err) { 771 assert.NotEmpty(t, genModel.AllOf) 772 assert.True(t, genModel.IsComplexObject) 773 assert.Equal(t, "JustRef", genModel.Name) 774 assert.Equal(t, "JustRef", genModel.GoType) 775 buf := bytes.NewBuffer(nil) 776 err = tt.template.Execute(buf, genModel) 777 assert.NoError(t, err) 778 res := buf.String() 779 assertInCode(t, "type JustRef struct {", res) 780 assertInCode(t, "Notable", res) 781 } 782 } 783 } 784 785 func TestGenerateModel_WithRef(t *testing.T) { 786 tt := templateTest{t, templates.MustGet("model").Lookup("schema")} 787 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 788 if assert.NoError(t, err) { 789 definitions := specDoc.Spec().Definitions 790 schema := definitions["WithRef"] 791 opts := opts() 792 genModel, err := makeGenDefinition("WithRef", "models", schema, specDoc, opts) 793 if assert.NoError(t, err) { 794 assert.True(t, genModel.IsComplexObject) 795 assert.Equal(t, "WithRef", genModel.Name) 796 assert.Equal(t, "WithRef", genModel.GoType) 797 buf := bytes.NewBuffer(nil) 798 err = tt.template.Execute(buf, genModel) 799 assert.NoError(t, err) 800 res := buf.String() 801 assertInCode(t, "type WithRef struct {", res) 802 assertInCode(t, "Notes *Notable `json:\"notes,omitempty\"`", res) 803 } 804 } 805 } 806 807 func TestGenerateModel_WithNullableRef(t *testing.T) { 808 tt := templateTest{t, templates.MustGet("model").Lookup("schema")} 809 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 810 if assert.NoError(t, err) { 811 definitions := specDoc.Spec().Definitions 812 schema := definitions["WithNullableRef"] 813 opts := opts() 814 genModel, err := makeGenDefinition("WithNullableRef", "models", schema, specDoc, opts) 815 if assert.NoError(t, err) { 816 assert.True(t, genModel.IsComplexObject) 817 assert.Equal(t, "WithNullableRef", genModel.Name) 818 assert.Equal(t, "WithNullableRef", genModel.GoType) 819 prop := getDefinitionProperty(genModel, "notes") 820 assert.True(t, prop.IsNullable) 821 assert.True(t, prop.IsComplexObject) 822 buf := bytes.NewBuffer(nil) 823 err = tt.template.Execute(buf, genModel) 824 assert.NoError(t, err) 825 res := buf.String() 826 assertInCode(t, "type WithNullableRef struct {", res) 827 assertInCode(t, "Notes *Notable `json:\"notes,omitempty\"`", res) 828 } 829 } 830 } 831 832 func TestGenerateModel_Scores(t *testing.T) { 833 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 834 if assert.NoError(t, err) { 835 definitions := specDoc.Spec().Definitions 836 k := "Scores" 837 schema := definitions[k] 838 opts := opts() 839 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 840 if assert.NoError(t, err) { 841 buf := bytes.NewBuffer(nil) 842 err := templates.MustGet("model").Execute(buf, genModel) 843 if assert.NoError(t, err) { 844 ff, err := opts.LanguageOpts.FormatContent("scores.go", buf.Bytes()) 845 if assert.NoError(t, err) { 846 res := string(ff) 847 assertInCode(t, "type Scores []float32", res) 848 } 849 } 850 } 851 } 852 } 853 854 func TestGenerateModel_JaggedScores(t *testing.T) { 855 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 856 if assert.NoError(t, err) { 857 definitions := specDoc.Spec().Definitions 858 k := "JaggedScores" 859 schema := definitions[k] 860 opts := opts() 861 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 862 if assert.NoError(t, err) { 863 buf := bytes.NewBuffer(nil) 864 err := templates.MustGet("model").Execute(buf, genModel) 865 if assert.NoError(t, err) { 866 ff, err := opts.LanguageOpts.FormatContent("jagged_scores.go", buf.Bytes()) 867 if assert.NoError(t, err) { 868 res := string(ff) 869 assertInCode(t, "type JaggedScores [][][]float32", res) 870 } 871 } 872 } 873 } 874 } 875 876 func TestGenerateModel_Notables(t *testing.T) { 877 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 878 if assert.NoError(t, err) { 879 definitions := specDoc.Spec().Definitions 880 k := "Notables" 881 schema := definitions[k] 882 opts := opts() 883 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 884 if assert.NoError(t, err) && assert.Equal(t, "[]*Notable", genModel.GoType) { 885 buf := bytes.NewBuffer(nil) 886 err := templates.MustGet("model").Execute(buf, genModel) 887 if assert.NoError(t, err) { 888 ff, err := opts.LanguageOpts.FormatContent("notables.go", buf.Bytes()) 889 if assert.NoError(t, err) { 890 res := string(ff) 891 assertInCode(t, "type Notables []*Notable", res) 892 } 893 } 894 } 895 } 896 } 897 898 func TestGenerateModel_Notablix(t *testing.T) { 899 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 900 if assert.NoError(t, err) { 901 definitions := specDoc.Spec().Definitions 902 k := "Notablix" 903 schema := definitions[k] 904 opts := opts() 905 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 906 if assert.NoError(t, err) { 907 buf := bytes.NewBuffer(nil) 908 err := templates.MustGet("model").Execute(buf, genModel) 909 if assert.NoError(t, err) { 910 ff, err := opts.LanguageOpts.FormatContent("notablix.go", buf.Bytes()) 911 if assert.NoError(t, err) { 912 res := string(ff) 913 assertInCode(t, "type Notablix [][][]*Notable", res) 914 } 915 } 916 } 917 } 918 } 919 920 func TestGenerateModel_Stats(t *testing.T) { 921 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 922 if assert.NoError(t, err) { 923 definitions := specDoc.Spec().Definitions 924 k := "Stats" 925 schema := definitions[k] 926 opts := opts() 927 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 928 if assert.NoError(t, err) { 929 buf := bytes.NewBuffer(nil) 930 err := templates.MustGet("model").Execute(buf, genModel) 931 if assert.NoError(t, err) { 932 ff, err := opts.LanguageOpts.FormatContent("stats.go", buf.Bytes()) 933 if assert.NoError(t, err) { 934 res := string(ff) 935 assertInCode(t, "type Stats []*StatsItems0", res) 936 assertInCode(t, "type StatsItems0 struct {", res) 937 assertInCode(t, "Points []int64 `json:\"points\"`", res) 938 } 939 } 940 } 941 } 942 } 943 944 func TestGenerateModel_Statix(t *testing.T) { 945 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 946 if assert.NoError(t, err) { 947 definitions := specDoc.Spec().Definitions 948 k := "Statix" 949 schema := definitions[k] 950 opts := opts() 951 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 952 // spew.Dump(genModel) 953 if assert.NoError(t, err) { 954 buf := bytes.NewBuffer(nil) 955 err := templates.MustGet("model").Execute(buf, genModel) 956 if assert.NoError(t, err) { 957 ff, err := opts.LanguageOpts.FormatContent("statix.go", buf.Bytes()) 958 if assert.NoError(t, err) { 959 res := string(ff) 960 assertInCode(t, "type Statix [][][]*StatixItems0", res) 961 assertInCode(t, "type StatixItems0 struct {", res) 962 assertInCode(t, "Points []int64 `json:\"points\"`", res) 963 } /*else { 964 fmt.Println(buf.String()) 965 }*/ 966 } 967 } 968 } 969 } 970 971 func TestGenerateModel_WithItems(t *testing.T) { 972 tt := templateTest{t, templates.MustGet("model").Lookup("schema")} 973 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 974 if assert.NoError(t, err) { 975 definitions := specDoc.Spec().Definitions 976 schema := definitions["WithItems"] 977 opts := opts() 978 genModel, err := makeGenDefinition("WithItems", "models", schema, specDoc, opts) 979 if assert.NoError(t, err) { 980 assert.Nil(t, genModel.Items) 981 assert.True(t, genModel.IsComplexObject) 982 prop := getDefinitionProperty(genModel, "tags") 983 assert.NotNil(t, prop.Items) 984 assert.True(t, prop.IsArray) 985 assert.False(t, prop.IsComplexObject) 986 buf := bytes.NewBuffer(nil) 987 err := tt.template.Execute(buf, genModel) 988 if assert.NoError(t, err) { 989 res := buf.String() 990 assertInCode(t, "type WithItems struct {", res) 991 assertInCode(t, "Tags []string `json:\"tags\"`", res) 992 } 993 } 994 } 995 } 996 997 func TestGenerateModel_WithComplexItems(t *testing.T) { 998 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 999 if assert.NoError(t, err) { 1000 definitions := specDoc.Spec().Definitions 1001 k := "WithComplexItems" 1002 schema := definitions[k] 1003 opts := opts() 1004 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1005 if assert.NoError(t, err) { 1006 assert.Nil(t, genModel.Items) 1007 assert.True(t, genModel.IsComplexObject) 1008 prop := getDefinitionProperty(genModel, "tags") 1009 assert.NotNil(t, prop.Items) 1010 assert.True(t, prop.IsArray) 1011 assert.False(t, prop.IsComplexObject) 1012 buf := bytes.NewBuffer(nil) 1013 err := templates.MustGet("model").Execute(buf, genModel) 1014 if assert.NoError(t, err) { 1015 b, err := opts.LanguageOpts.FormatContent("with_complex_items.go", buf.Bytes()) 1016 if assert.NoError(t, err) { 1017 res := string(b) 1018 assertInCode(t, "type WithComplexItems struct {", res) 1019 assertInCode(t, "type WithComplexItemsTagsItems0 struct {", res) 1020 assertInCode(t, "Tags []*WithComplexItemsTagsItems0 `json:\"tags\"`", res) 1021 } 1022 } 1023 } 1024 } 1025 } 1026 1027 func TestGenerateModel_WithItemsAndAdditional(t *testing.T) { 1028 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1029 if assert.NoError(t, err) { 1030 definitions := specDoc.Spec().Definitions 1031 k := "WithItemsAndAdditional" 1032 schema := definitions[k] 1033 opts := opts() 1034 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1035 if assert.NoError(t, err) { 1036 assert.Nil(t, genModel.Items) 1037 assert.True(t, genModel.IsComplexObject) 1038 prop := getDefinitionProperty(genModel, "tags") 1039 assert.True(t, prop.IsComplexObject) 1040 buf := bytes.NewBuffer(nil) 1041 err := templates.MustGet("model").Execute(buf, genModel) 1042 if assert.NoError(t, err) { 1043 b, err := opts.LanguageOpts.FormatContent("with_complex_items.go", buf.Bytes()) 1044 if assert.NoError(t, err) { 1045 res := string(b) 1046 assertInCode(t, "type "+k+" struct {", res) 1047 assertInCode(t, "type "+k+"TagsTuple0 struct {", res) 1048 // this would fail if it accepts additionalItems because it would come out as []interface{} 1049 assertInCode(t, "Tags *"+k+"TagsTuple0 `json:\"tags,omitempty\"`", res) 1050 assertInCode(t, "P0 *string `json:\"-\"`", res) 1051 assertInCode(t, k+"TagsTuple0Items []interface{} `json:\"-\"`", res) 1052 } 1053 } 1054 } 1055 } 1056 } 1057 1058 func TestGenerateModel_WithItemsAndAdditional2(t *testing.T) { 1059 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1060 if assert.NoError(t, err) { 1061 definitions := specDoc.Spec().Definitions 1062 k := "WithItemsAndAdditional2" 1063 schema := definitions[k] 1064 opts := opts() 1065 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1066 if assert.NoError(t, err) { 1067 assert.Nil(t, genModel.Items) 1068 assert.True(t, genModel.IsComplexObject) 1069 prop := getDefinitionProperty(genModel, "tags") 1070 assert.True(t, prop.IsComplexObject) 1071 buf := bytes.NewBuffer(nil) 1072 err := templates.MustGet("model").Execute(buf, genModel) 1073 if assert.NoError(t, err) { 1074 b, err := opts.LanguageOpts.FormatContent("with_complex_items.go", buf.Bytes()) 1075 if assert.NoError(t, err) { 1076 res := string(b) 1077 assertInCode(t, "type "+k+" struct {", res) 1078 assertInCode(t, "type "+k+"TagsTuple0 struct {", res) 1079 // this would fail if it accepts additionalItems because it would come out as []interface{} 1080 assertInCode(t, "P0 *string `json:\"-\"`", res) 1081 assertInCode(t, "Tags *"+k+"TagsTuple0 `json:\"tags,omitempty\"`", res) 1082 assertInCode(t, k+"TagsTuple0Items []int32 `json:\"-\"`", res) 1083 1084 } 1085 } 1086 } 1087 } 1088 } 1089 1090 func TestGenerateModel_WithComplexAdditional(t *testing.T) { 1091 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1092 if assert.NoError(t, err) { 1093 definitions := specDoc.Spec().Definitions 1094 k := "WithComplexAdditional" 1095 schema := definitions[k] 1096 opts := opts() 1097 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1098 if assert.NoError(t, err) { 1099 assert.Nil(t, genModel.Items) 1100 assert.True(t, genModel.IsComplexObject) 1101 prop := getDefinitionProperty(genModel, "tags") 1102 assert.True(t, prop.IsComplexObject) 1103 buf := bytes.NewBuffer(nil) 1104 err := templates.MustGet("model").Execute(buf, genModel) 1105 if assert.NoError(t, err) { 1106 b, err := opts.LanguageOpts.FormatContent("with_complex_additional.go", buf.Bytes()) 1107 if assert.NoError(t, err) { 1108 res := string(b) 1109 assertInCode(t, "type WithComplexAdditional struct {", res) 1110 assertInCode(t, "type WithComplexAdditionalTagsTuple0 struct {", res) 1111 assertInCode(t, "Tags *WithComplexAdditionalTagsTuple0 `json:\"tags,omitempty\"`", res) 1112 assertInCode(t, "P0 *string `json:\"-\"`", res) 1113 assertInCode(t, "WithComplexAdditionalTagsTuple0Items []*WithComplexAdditionalTagsItems `json:\"-\"`", res) 1114 } 1115 } 1116 } 1117 } 1118 } 1119 1120 func TestGenerateModel_SimpleTuple(t *testing.T) { 1121 tt := templateTest{t, templates.MustGet("model")} 1122 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1123 if assert.NoError(t, err) { 1124 definitions := specDoc.Spec().Definitions 1125 k := "SimpleTuple" 1126 schema := definitions[k] 1127 opts := opts() 1128 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1129 if assert.NoError(t, err) && assert.Len(t, genModel.ExtraSchemas, 1) { 1130 // NOTE: with PR#1592, an extra schema is added here because of the allOf tuple element. 1131 // This uncovers another issue with special AllOfs (e.g. allOf [ ..., x-nullable:true ]) 1132 // TODO(fredbi): fix liftSpecialAllOf() to revert to: assert.Empty(t, genModel.ExtraSchemas) 1133 assert.True(t, genModel.IsTuple) 1134 assert.False(t, genModel.IsComplexObject) 1135 assert.False(t, genModel.IsArray) 1136 assert.False(t, genModel.IsAnonymous) 1137 assert.Equal(t, k, genModel.Name) 1138 assert.Equal(t, k, genModel.GoType) 1139 assert.Len(t, genModel.Properties, 5) 1140 buf := bytes.NewBuffer(nil) 1141 err = tt.template.Execute(buf, genModel) 1142 assert.NoError(t, err) 1143 res := buf.String() 1144 assertInCode(t, "swagger:model "+k, res) 1145 assertInCode(t, "type "+k+" struct {", res) 1146 assertInCode(t, "P0 *int64 `json:\"-\"`", res) 1147 assertInCode(t, "P1 *string `json:\"-\"`", res) 1148 assertInCode(t, "P2 *strfmt.DateTime `json:\"-\"`", res) 1149 assertInCode(t, "P3 *Notable `json:\"-\"`", res) 1150 // NOTE: with PR#1592, an extra schema is added here because of the allOf tuple element. 1151 // This uncovers another issue with special AllOfs (e.g. allOf [ ..., x-nullable:true ]) 1152 // TODO(fredbi): fix liftSpecialAllOf() to revert to: assert.Empty(t, genModel.ExtraSchemas) 1153 //assertInCode(t, "P4 *Notable `json:\"-\"`", res) 1154 assertInCode(t, "P4 *SimpleTupleItems4 `json:\"-\"`", res) 1155 assertInCode(t, k+") UnmarshalJSON", res) 1156 assertInCode(t, k+") MarshalJSON", res) 1157 assertInCode(t, "json.Marshal(data)", res) 1158 assert.NotRegexp(t, regexp.MustCompile("lastIndex"), res) 1159 1160 for i, p := range genModel.Properties { 1161 m := "m.P" + strconv.Itoa(i) 1162 r := "&dataP" + strconv.Itoa(i) 1163 var rr string 1164 if !p.IsNullable { 1165 rr = "dataP" + strconv.Itoa(i) 1166 } else { 1167 rr = r 1168 } 1169 assertInCode(t, fmt.Sprintf("buf = bytes.NewBuffer(stage1[%d])", i), res) 1170 assertInCode(t, fmt.Sprintf("dec.Decode(%s)", r), res) 1171 assertInCode(t, "P"+strconv.Itoa(i)+",", res) 1172 assertInCode(t, fmt.Sprintf("%s = %s", m, rr), res) 1173 } 1174 } 1175 } 1176 } 1177 1178 func TestGenerateModel_TupleWithExtra(t *testing.T) { 1179 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1180 if assert.NoError(t, err) { 1181 definitions := specDoc.Spec().Definitions 1182 k := "TupleWithExtra" 1183 schema := definitions[k] 1184 opts := opts() 1185 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1186 if assert.NoError(t, err) && assert.Empty(t, genModel.ExtraSchemas) { 1187 assert.True(t, genModel.IsTuple) 1188 assert.False(t, genModel.IsComplexObject) 1189 assert.False(t, genModel.IsArray) 1190 assert.False(t, genModel.IsAnonymous) 1191 assert.True(t, genModel.HasAdditionalItems) 1192 assert.NotNil(t, genModel.AdditionalItems) 1193 assert.Equal(t, k, genModel.Name) 1194 assert.Equal(t, k, genModel.GoType) 1195 assert.Len(t, genModel.Properties, 4) 1196 buf := bytes.NewBuffer(nil) 1197 err := templates.MustGet("model").Execute(buf, genModel) 1198 if assert.NoError(t, err) { 1199 ff, err := opts.LanguageOpts.FormatContent("tuple_with_extra.go", buf.Bytes()) 1200 if assert.NoError(t, err) { 1201 res := string(ff) 1202 assertInCode(t, "swagger:model "+k, res) 1203 assertInCode(t, "type "+k+" struct {", res) 1204 assertInCode(t, "P0 *int64 `json:\"-\"`", res) 1205 assertInCode(t, "P1 *string `json:\"-\"`", res) 1206 assertInCode(t, "P2 *strfmt.DateTime `json:\"-\"`", res) 1207 assertInCode(t, "P3 *Notable `json:\"-\"`", res) 1208 assertInCode(t, k+"Items []float64 `json:\"-\"`", res) 1209 assertInCode(t, k+") UnmarshalJSON", res) 1210 assertInCode(t, k+") MarshalJSON", res) 1211 1212 for i, p := range genModel.Properties { 1213 m := "m.P" + strconv.Itoa(i) 1214 r := "&dataP" + strconv.Itoa(i) 1215 var rr string 1216 if !p.IsNullable { 1217 rr = "dataP" + strconv.Itoa(i) 1218 } else { 1219 rr = r 1220 } 1221 assertInCode(t, fmt.Sprintf("lastIndex = %d", i), res) 1222 assertInCode(t, fmt.Sprintf("buf = bytes.NewBuffer(stage1[%d])", i), res) 1223 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1224 assertInCode(t, fmt.Sprintf("dec.Decode(%s)", r), res) 1225 assertInCode(t, "P"+strconv.Itoa(i)+",", res) 1226 assertInCode(t, fmt.Sprintf("%s = %s", m, rr), res) 1227 } 1228 assertInCode(t, "var lastIndex int", res) 1229 assertInCode(t, "var toadd float64", res) 1230 assertInCode(t, "for _, val := range stage1[lastIndex+1:]", res) 1231 assertInCode(t, "buf = bytes.NewBuffer(val)", res) 1232 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1233 assertInCode(t, "dec.Decode(&toadd)", res) 1234 assertInCode(t, "json.Marshal(data)", res) 1235 assertInCode(t, "for _, v := range m."+k+"Items", res) 1236 } 1237 } 1238 } 1239 } 1240 } 1241 1242 func TestGenerateModel_TupleWithComplex(t *testing.T) { 1243 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1244 if assert.NoError(t, err) { 1245 definitions := specDoc.Spec().Definitions 1246 k := "TupleWithComplex" 1247 schema := definitions[k] 1248 opts := opts() 1249 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1250 if assert.NoError(t, err) { //&& assert.Empty(t, genModel.ExtraSchemas) { 1251 assert.True(t, genModel.IsTuple) 1252 assert.False(t, genModel.IsComplexObject) 1253 assert.False(t, genModel.IsArray) 1254 assert.False(t, genModel.IsAnonymous) 1255 assert.True(t, genModel.HasAdditionalItems) 1256 assert.NotNil(t, genModel.AdditionalItems) 1257 assert.Equal(t, k, genModel.Name) 1258 assert.Equal(t, k, genModel.GoType) 1259 assert.Len(t, genModel.Properties, 4) 1260 buf := bytes.NewBuffer(nil) 1261 err := templates.MustGet("model").Execute(buf, genModel) 1262 if assert.NoError(t, err) { 1263 ff, err := opts.LanguageOpts.FormatContent("tuple_with_extra.go", buf.Bytes()) 1264 if assert.NoError(t, err) { 1265 res := string(ff) 1266 assertInCode(t, "swagger:model "+k, res) 1267 assertInCode(t, "type "+k+" struct {", res) 1268 assertInCode(t, "P0 *int64 `json:\"-\"`", res) 1269 assertInCode(t, "P1 *string `json:\"-\"`", res) 1270 assertInCode(t, "P2 *strfmt.DateTime `json:\"-\"`", res) 1271 assertInCode(t, "P3 *Notable `json:\"-\"`", res) 1272 assertInCode(t, k+"Items []*TupleWithComplexItems `json:\"-\"`", res) 1273 assertInCode(t, k+") UnmarshalJSON", res) 1274 assertInCode(t, k+") MarshalJSON", res) 1275 1276 for i, p := range genModel.Properties { 1277 m := "m.P" + strconv.Itoa(i) 1278 r := "&dataP" + strconv.Itoa(i) 1279 var rr string 1280 if !p.IsNullable { 1281 rr = "dataP" + strconv.Itoa(i) 1282 } else { 1283 rr = r 1284 } 1285 assertInCode(t, fmt.Sprintf("lastIndex = %d", i), res) 1286 assertInCode(t, fmt.Sprintf("buf = bytes.NewBuffer(stage1[%d])", i), res) 1287 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1288 assertInCode(t, fmt.Sprintf("dec.Decode(%s)", r), res) 1289 assertInCode(t, "P"+strconv.Itoa(i)+",", res) 1290 assertInCode(t, fmt.Sprintf("%s = %s", m, rr), res) 1291 } 1292 1293 assertInCode(t, "var lastIndex int", res) 1294 assertInCode(t, "var toadd *TupleWithComplexItems", res) 1295 assertInCode(t, "for _, val := range stage1[lastIndex+1:]", res) 1296 assertInCode(t, "buf = bytes.NewBuffer(val)", res) 1297 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1298 assertInCode(t, "dec.Decode(toadd)", res) 1299 assertInCode(t, "json.Marshal(data)", res) 1300 assertInCode(t, "for _, v := range m."+k+"Items", res) 1301 } 1302 } 1303 } 1304 } 1305 } 1306 1307 func TestGenerateModel_WithTuple(t *testing.T) { 1308 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1309 if assert.NoError(t, err) { 1310 definitions := specDoc.Spec().Definitions 1311 k := "WithTuple" 1312 schema := definitions[k] 1313 opts := opts() 1314 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1315 if assert.NoError(t, err) && assert.NotEmpty(t, genModel.ExtraSchemas) && assert.NotEmpty(t, genModel.Properties) { 1316 assert.False(t, genModel.IsTuple) 1317 assert.True(t, genModel.IsComplexObject) 1318 assert.False(t, genModel.IsArray) 1319 assert.False(t, genModel.IsAnonymous) 1320 1321 sch := genModel.ExtraSchemas[0] 1322 assert.True(t, sch.IsTuple) 1323 assert.False(t, sch.IsComplexObject) 1324 assert.False(t, sch.IsArray) 1325 assert.False(t, sch.IsAnonymous) 1326 assert.Equal(t, k+"FlagsTuple0", sch.Name) 1327 assert.False(t, sch.HasAdditionalItems) 1328 assert.Nil(t, sch.AdditionalItems) 1329 1330 prop := genModel.Properties[0] 1331 assert.False(t, genModel.IsTuple) 1332 assert.True(t, genModel.IsComplexObject) 1333 assert.False(t, prop.IsArray) 1334 assert.False(t, prop.IsAnonymous) 1335 assert.Equal(t, k+"FlagsTuple0", prop.GoType) 1336 assert.Equal(t, "flags", prop.Name) 1337 buf := bytes.NewBuffer(nil) 1338 err := templates.MustGet("model").Execute(buf, genModel) 1339 if assert.NoError(t, err) { 1340 ff, err := opts.LanguageOpts.FormatContent("with_tuple.go", buf.Bytes()) 1341 if assert.NoError(t, err) { 1342 res := string(ff) 1343 assertInCode(t, "swagger:model "+k+"Flags", res) 1344 assertInCode(t, "type "+k+"FlagsTuple0 struct {", res) 1345 assertInCode(t, "P0 *int64 `json:\"-\"`", res) 1346 assertInCode(t, "P1 *string `json:\"-\"`", res) 1347 assertInCode(t, k+"FlagsTuple0) UnmarshalJSON", res) 1348 assertInCode(t, k+"FlagsTuple0) MarshalJSON", res) 1349 assertInCode(t, "json.Marshal(data)", res) 1350 assert.NotRegexp(t, regexp.MustCompile("lastIndex"), res) 1351 1352 for i, p := range sch.Properties { 1353 m := "m.P" + strconv.Itoa(i) 1354 r := "&dataP" + strconv.Itoa(i) 1355 var rr string 1356 if !p.IsNullable { 1357 rr = "dataP" + strconv.Itoa(i) 1358 } else { 1359 rr = r 1360 } 1361 assertInCode(t, fmt.Sprintf("buf = bytes.NewBuffer(stage1[%d])", i), res) 1362 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1363 assertInCode(t, fmt.Sprintf("dec.Decode(%s)", r), res) 1364 assertInCode(t, "P"+strconv.Itoa(i)+",", res) 1365 assertInCode(t, fmt.Sprintf("%s = %s", m, rr), res) 1366 } 1367 } 1368 } 1369 } 1370 } 1371 } 1372 1373 func TestGenerateModel_WithTupleWithExtra(t *testing.T) { 1374 tt := templateTest{t, templates.MustGet("model")} 1375 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1376 if assert.NoError(t, err) { 1377 definitions := specDoc.Spec().Definitions 1378 k := "WithTupleWithExtra" 1379 schema := definitions[k] 1380 opts := opts() 1381 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 1382 if assert.NoError(t, err) && assert.NotEmpty(t, genModel.ExtraSchemas) && assert.NotEmpty(t, genModel.Properties) { 1383 assert.False(t, genModel.IsTuple) 1384 assert.True(t, genModel.IsComplexObject) 1385 assert.False(t, genModel.IsArray) 1386 assert.False(t, genModel.IsAnonymous) 1387 1388 sch := genModel.ExtraSchemas[0] 1389 assert.True(t, sch.IsTuple) 1390 assert.False(t, sch.IsComplexObject) 1391 assert.False(t, sch.IsArray) 1392 assert.False(t, sch.IsAnonymous) 1393 assert.Equal(t, k+"FlagsTuple0", sch.Name) 1394 assert.True(t, sch.HasAdditionalItems) 1395 assert.NotEmpty(t, sch.AdditionalItems) 1396 1397 prop := genModel.Properties[0] 1398 assert.False(t, genModel.IsTuple) 1399 assert.True(t, genModel.IsComplexObject) 1400 assert.False(t, prop.IsArray) 1401 assert.False(t, prop.IsAnonymous) 1402 assert.Equal(t, k+"FlagsTuple0", prop.GoType) 1403 assert.Equal(t, "flags", prop.Name) 1404 buf := bytes.NewBuffer(nil) 1405 err := tt.template.Execute(buf, genModel) 1406 if assert.NoError(t, err) { 1407 ff, err := opts.LanguageOpts.FormatContent("with_tuple.go", buf.Bytes()) 1408 if assert.NoError(t, err) { 1409 res := string(ff) 1410 assertInCode(t, "swagger:model "+k+"Flags", res) 1411 assertInCode(t, "type "+k+"FlagsTuple0 struct {", res) 1412 assertInCode(t, "P0 *int64 `json:\"-\"`", res) 1413 assertInCode(t, "P1 *string `json:\"-\"`", res) 1414 assertInCode(t, k+"FlagsTuple0Items []float32 `json:\"-\"`", res) 1415 assertInCode(t, k+"FlagsTuple0) UnmarshalJSON", res) 1416 assertInCode(t, k+"FlagsTuple0) MarshalJSON", res) 1417 assertInCode(t, "json.Marshal(data)", res) 1418 1419 for i, p := range sch.Properties { 1420 m := "m.P" + strconv.Itoa(i) 1421 r := "&dataP" + strconv.Itoa(i) 1422 var rr string 1423 if !p.IsNullable { 1424 rr = "dataP" + strconv.Itoa(i) 1425 } else { 1426 rr = r 1427 } 1428 assertInCode(t, fmt.Sprintf("lastIndex = %d", i), res) 1429 assertInCode(t, fmt.Sprintf("buf = bytes.NewBuffer(stage1[%d])", i), res) 1430 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1431 assertInCode(t, fmt.Sprintf("dec.Decode(%s)", r), res) 1432 assertInCode(t, "P"+strconv.Itoa(i)+",", res) 1433 assertInCode(t, fmt.Sprintf("%s = %s", m, rr), res) 1434 } 1435 1436 assertInCode(t, "var lastIndex int", res) 1437 assertInCode(t, "var toadd float32", res) 1438 assertInCode(t, "for _, val := range stage1[lastIndex+1:]", res) 1439 assertInCode(t, "buf = bytes.NewBuffer(val)", res) 1440 assertInCode(t, "dec := json.NewDecoder(buf)", res) 1441 assertInCode(t, "dec.Decode(&toadd)", res) 1442 assertInCode(t, "json.Marshal(data)", res) 1443 assertInCode(t, "for _, v := range m."+k+"FlagsTuple0Items", res) 1444 } 1445 } 1446 } 1447 } 1448 } 1449 1450 func TestGenerateModel_WithAllOfAndDiscriminator(t *testing.T) { 1451 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1452 if assert.NoError(t, err) { 1453 definitions := specDoc.Spec().Definitions 1454 schema := definitions["Cat"] 1455 opts := opts() 1456 genModel, err := makeGenDefinition("Cat", "models", schema, specDoc, opts) 1457 if assert.NoError(t, err) && assert.Len(t, genModel.AllOf, 2) { 1458 assert.True(t, genModel.IsComplexObject) 1459 assert.Equal(t, "Cat", genModel.Name) 1460 assert.Equal(t, "Cat", genModel.GoType) 1461 buf := bytes.NewBuffer(nil) 1462 err := templates.MustGet("model").Execute(buf, genModel) 1463 if assert.NoError(t, err) { 1464 ct, err := opts.LanguageOpts.FormatContent("cat.go", buf.Bytes()) 1465 if assert.NoError(t, err) { 1466 res := string(ct) 1467 assertInCode(t, "type Cat struct {", res) 1468 assertInCode(t, "Pet", res) 1469 assertInCode(t, "HuntingSkill *string `json:\"huntingSkill\"`", res) 1470 } 1471 } 1472 } 1473 } 1474 } 1475 1476 func TestGenerateModel_WithAllOfAndDiscriminatorAndArrayOfPolymorphs(t *testing.T) { 1477 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1478 if assert.NoError(t, err) { 1479 definitions := specDoc.Spec().Definitions 1480 schema := definitions["PetWithPets"] 1481 opts := opts() 1482 genModel, err := makeGenDefinition("PetWithPets", "models", schema, specDoc, opts) 1483 if assert.NoError(t, err) && assert.Len(t, genModel.AllOf, 2) { 1484 assert.True(t, genModel.IsComplexObject) 1485 assert.Equal(t, "PetWithPets", genModel.Name) 1486 assert.Equal(t, "PetWithPets", genModel.GoType) 1487 buf := bytes.NewBuffer(nil) 1488 err := templates.MustGet("model").Execute(buf, genModel) 1489 if assert.NoError(t, err) { 1490 ct, err := opts.LanguageOpts.FormatContent("PetWithPets.go", buf.Bytes()) 1491 if assert.NoError(t, err) { 1492 res := string(ct) 1493 assertInCode(t, "type PetWithPets struct {", res) 1494 assertInCode(t, "UnmarshalPetSlice", res) 1495 } 1496 } 1497 } 1498 } 1499 } 1500 1501 func TestGenerateModel_WithAllOf(t *testing.T) { 1502 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1503 if assert.NoError(t, err) { 1504 definitions := specDoc.Spec().Definitions 1505 schema := definitions["WithAllOf"] 1506 opts := opts() 1507 genModel, err := makeGenDefinition("WithAllOf", "models", schema, specDoc, opts) 1508 if assert.NoError(t, err) { 1509 assert.Len(t, genModel.AllOf, 7) 1510 assert.True(t, genModel.AllOf[1].HasAdditionalProperties) 1511 assert.True(t, genModel.IsComplexObject) 1512 assert.Equal(t, "WithAllOf", genModel.Name) 1513 assert.Equal(t, "WithAllOf", genModel.GoType) 1514 buf := bytes.NewBuffer(nil) 1515 err := templates.MustGet("model").Execute(buf, genModel) 1516 if assert.NoError(t, err) { 1517 ct, err := opts.LanguageOpts.FormatContent("all_of_schema.go", buf.Bytes()) 1518 if assert.NoError(t, err) { 1519 res := string(ct) 1520 assertInCode(t, "type WithAllOf struct {", res) 1521 assertInCode(t, "type WithAllOfAO2P2 struct {", res) 1522 assertInCode(t, "type WithAllOfAO3P3 struct {", res) 1523 assertInCode(t, "type WithAllOfParamsAnon struct {", res) 1524 assertInCode(t, "type WithAllOfAO4Tuple4 struct {", res) 1525 assertInCode(t, "type WithAllOfAO5Tuple5 struct {", res) 1526 assertInCode(t, "Notable", res) 1527 assertInCode(t, "Title string `json:\"title,omitempty\"`", res) 1528 assertInCode(t, "Body string `json:\"body,omitempty\"`", res) 1529 assertInCode(t, "Name string `json:\"name,omitempty\"`", res) 1530 assertInCode(t, "P0 *float32 `json:\"-\"`", res) 1531 assertInCode(t, "P0 *float64 `json:\"-\"`", res) 1532 assertInCode(t, "P1 *strfmt.DateTime `json:\"-\"`", res) 1533 assertInCode(t, "P1 *strfmt.Date `json:\"-\"`", res) 1534 assertInCode(t, "Opinion string `json:\"opinion,omitempty\"`", res) 1535 assertInCode(t, "WithAllOfAO5Tuple5Items []strfmt.Password `json:\"-\"`", res) 1536 assertInCode(t, "AO1 map[string]int32 `json:\"-\"`", res) 1537 assertInCode(t, "WithAllOfAO2P2 map[string]int64 `json:\"-\"`", res) 1538 } 1539 } 1540 } 1541 } 1542 } 1543 1544 func findProperty(properties []GenSchema, name string) *GenSchema { 1545 for _, p := range properties { 1546 if p.Name == name { 1547 return &p 1548 } 1549 } 1550 return nil 1551 } 1552 1553 func getDefinitionProperty(genModel *GenDefinition, name string) *GenSchema { 1554 return findProperty(genModel.Properties, name) 1555 } 1556 1557 func TestNumericKeys(t *testing.T) { 1558 specDoc, err := loads.Spec("../fixtures/bugs/162/swagger.yml") 1559 if assert.NoError(t, err) { 1560 definitions := specDoc.Spec().Definitions 1561 schema := definitions["AvatarUrls"] 1562 opts := opts() 1563 genModel, err := makeGenDefinition("AvatarUrls", "models", schema, specDoc, opts) 1564 if assert.NoError(t, err) { 1565 buf := bytes.NewBuffer(nil) 1566 err := templates.MustGet("model").Execute(buf, genModel) 1567 if assert.NoError(t, err) { 1568 ct, err := opts.LanguageOpts.FormatContent("all_of_schema.go", buf.Bytes()) 1569 if assert.NoError(t, err) { 1570 res := string(ct) 1571 assertInCode(t, "Nr16x16 string `json:\"16x16,omitempty\"`", res) 1572 } 1573 } 1574 } 1575 } 1576 } 1577 1578 func TestGenModel_Issue196(t *testing.T) { 1579 specDoc, err := loads.Spec("../fixtures/bugs/196/swagger.yml") 1580 if assert.NoError(t, err) { 1581 definitions := specDoc.Spec().Definitions 1582 schema := definitions["Event"] 1583 opts := opts() 1584 genModel, err := makeGenDefinition("Event", "models", schema, specDoc, opts) 1585 if assert.NoError(t, err) { 1586 buf := bytes.NewBuffer(nil) 1587 err := templates.MustGet("model").Execute(buf, genModel) 1588 if assert.NoError(t, err) { 1589 ct, err := opts.LanguageOpts.FormatContent("primitive_event.go", buf.Bytes()) 1590 if assert.NoError(t, err) { 1591 res := string(ct) 1592 assertInCode(t, "Event) Validate(formats strfmt.Registry) error", res) 1593 } 1594 } 1595 } 1596 } 1597 } 1598 1599 func TestGenModel_Issue222(t *testing.T) { 1600 specDoc, err := loads.Spec("../fixtures/codegen/tasklist.basic.yml") 1601 if assert.NoError(t, err) { 1602 definitions := specDoc.Spec().Definitions 1603 k := "Price" 1604 opts := opts() 1605 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1606 if assert.NoError(t, err) && assert.True(t, genModel.HasValidations) { 1607 buf := bytes.NewBuffer(nil) 1608 err := templates.MustGet("model").Execute(buf, genModel) 1609 if assert.NoError(t, err) { 1610 ct, err := opts.LanguageOpts.FormatContent("price.go", buf.Bytes()) 1611 if assert.NoError(t, err) { 1612 res := string(ct) 1613 assertInCode(t, "Price) Validate(formats strfmt.Registry) error", res) 1614 assertInCode(t, "Currency Currency `json:\"currency,omitempty\"`", res) 1615 assertInCode(t, "m.Currency.Validate(formats); err != nil", res) 1616 } 1617 } 1618 } 1619 } 1620 } 1621 1622 func TestGenModel_Issue243(t *testing.T) { 1623 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1624 if assert.NoError(t, err) { 1625 definitions := specDoc.Spec().Definitions 1626 k := "HasDynMeta" 1627 opts := opts() 1628 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1629 if assert.NoError(t, err) { 1630 buf := bytes.NewBuffer(nil) 1631 err := templates.MustGet("model").Execute(buf, genModel) 1632 if assert.NoError(t, err) { 1633 ct, err := opts.LanguageOpts.FormatContent("has_dyn_meta.go", buf.Bytes()) 1634 if assert.NoError(t, err) { 1635 res := string(ct) 1636 if !assertInCode(t, "Metadata DynamicMetaData `json:\"metadata,omitempty\"`", res) { 1637 fmt.Println(res) 1638 } 1639 } 1640 } 1641 } 1642 } 1643 } 1644 1645 func TestGenModel_Issue252(t *testing.T) { 1646 specDoc, err := loads.Spec("../fixtures/bugs/252/swagger.json") 1647 if assert.NoError(t, err) { 1648 definitions := specDoc.Spec().Definitions 1649 k := "SodaBrand" 1650 opts := opts() 1651 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1652 if assert.NoError(t, err) && assert.False(t, genModel.IsNullable) { 1653 buf := bytes.NewBuffer(nil) 1654 err := templates.MustGet("model").Execute(buf, genModel) 1655 if assert.NoError(t, err) { 1656 ct, err := opts.LanguageOpts.FormatContent("soda_brand.go", buf.Bytes()) 1657 if assert.NoError(t, err) { 1658 res := string(ct) 1659 b1 := assertInCode(t, "type "+k+" string", res) 1660 b2 := assertInCode(t, "(m "+k+") validateSodaBrand", res) 1661 b3 := assertInCode(t, "(m "+k+") Validate", res) 1662 if !(b1 && b2 && b3) { 1663 fmt.Println(res) 1664 } 1665 } 1666 } 1667 } 1668 } 1669 } 1670 1671 func TestGenModel_Issue251(t *testing.T) { 1672 specDoc, err := loads.Spec("../fixtures/bugs/251/swagger.yml") 1673 if assert.NoError(t, err) { 1674 definitions := specDoc.Spec().Definitions 1675 k := "example" 1676 opts := opts() 1677 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1678 if assert.NoError(t, err) { 1679 buf := bytes.NewBuffer(nil) 1680 err := templates.MustGet("model").Execute(buf, genModel) 1681 if assert.NoError(t, err) { 1682 ct, err := opts.LanguageOpts.FormatContent("example.go", buf.Bytes()) 1683 if assert.NoError(t, err) { 1684 res := string(ct) 1685 1686 b1 := assertInCode(t, "type "+swag.ToGoName(k)+" struct", res) 1687 b2 := assertInCode(t, "Begin *strfmt.DateTime `json:\"begin\"`", res) 1688 b3 := assertInCode(t, "End strfmt.DateTime `json:\"end,omitempty\"`", res) 1689 b4 := assertInCode(t, "Name string `json:\"name,omitempty\"`", res) 1690 b5 := assertInCode(t, "(m *"+swag.ToGoName(k)+") validateBegin", res) 1691 //b6 := assertInCode(t, "(m *"+swag.ToGoName(k)+") validateEnd", res) 1692 b7 := assertInCode(t, "(m *"+swag.ToGoName(k)+") Validate", res) 1693 if !(b1 && b2 && b3 && b4 && b5 && b7) { 1694 fmt.Println(res) 1695 } 1696 } 1697 } 1698 } 1699 } 1700 } 1701 1702 func TestGenModel_Issue257(t *testing.T) { 1703 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1704 if assert.NoError(t, err) { 1705 definitions := specDoc.Spec().Definitions 1706 k := "HasSpecialCharProp" 1707 opts := opts() 1708 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1709 if assert.NoError(t, err) { 1710 buf := bytes.NewBuffer(nil) 1711 err := templates.MustGet("model").Execute(buf, genModel) 1712 if assert.NoError(t, err) { 1713 ct, err := opts.LanguageOpts.FormatContent("example.go", buf.Bytes()) 1714 if assert.NoError(t, err) { 1715 res := string(ct) 1716 1717 b1 := assertInCode(t, "type "+swag.ToGoName(k)+" struct", res) 1718 b2 := assertInCode(t, "AtType string `json:\"@type,omitempty\"`", res) 1719 b3 := assertInCode(t, "Type string `json:\"type,omitempty\"`", res) 1720 if !(b1 && b2 && b3) { 1721 fmt.Println(res) 1722 } 1723 } 1724 } 1725 } 1726 } 1727 } 1728 1729 func TestGenModel_Issue340(t *testing.T) { 1730 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1731 if assert.NoError(t, err) { 1732 definitions := specDoc.Spec().Definitions 1733 k := "ImageTar" 1734 opts := opts() 1735 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1736 if assert.NoError(t, err) { 1737 buf := bytes.NewBuffer(nil) 1738 err := templates.MustGet("model").Execute(buf, genModel) 1739 if assert.NoError(t, err) { 1740 ct, err := opts.LanguageOpts.FormatContent("image_tar.go", buf.Bytes()) 1741 if assert.NoError(t, err) { 1742 res := string(ct) 1743 1744 b1 := assertInCode(t, "type "+swag.ToGoName(k)+" io.ReadCloser", res) 1745 b2 := assertNotInCode(t, "func (m ImageTar) Validate(formats strfmt.Registry) error", res) 1746 if !(b1 && b2) { 1747 fmt.Println(res) 1748 } 1749 } 1750 } 1751 } 1752 } 1753 } 1754 1755 func TestGenModel_Issue381(t *testing.T) { 1756 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1757 if assert.NoError(t, err) { 1758 definitions := specDoc.Spec().Definitions 1759 k := "flags_list" 1760 opts := opts() 1761 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1762 if assert.NoError(t, err) { 1763 buf := bytes.NewBuffer(nil) 1764 err := templates.MustGet("model").Execute(buf, genModel) 1765 if assert.NoError(t, err) { 1766 ct, err := opts.LanguageOpts.FormatContent("flags_list.go", buf.Bytes()) 1767 if assert.NoError(t, err) { 1768 res := string(ct) 1769 assertNotInCode(t, "m[i] != nil", res) 1770 } 1771 } 1772 } 1773 } 1774 } 1775 1776 func TestGenModel_Issue300(t *testing.T) { 1777 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1778 if assert.NoError(t, err) { 1779 definitions := specDoc.Spec().Definitions 1780 k := "ActionItem" 1781 opts := opts() 1782 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1783 if assert.NoError(t, err) { 1784 buf := bytes.NewBuffer(nil) 1785 err := templates.MustGet("model").Execute(buf, genModel) 1786 if assert.NoError(t, err) { 1787 ct, err := opts.LanguageOpts.FormatContent("action_item.go", buf.Bytes()) 1788 if assert.NoError(t, err) { 1789 res := string(ct) 1790 assertInCode(t, "Name ActionName `json:\"name\"`", res) 1791 } else { 1792 fmt.Println(buf.String()) 1793 } 1794 } 1795 } 1796 } 1797 } 1798 1799 func TestGenModel_Issue398(t *testing.T) { 1800 specDoc, err := loads.Spec("../fixtures/codegen/todolist.models.yml") 1801 if assert.NoError(t, err) { 1802 definitions := specDoc.Spec().Definitions 1803 k := "Property" 1804 opts := opts() 1805 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1806 if assert.NoError(t, err) { 1807 buf := bytes.NewBuffer(nil) 1808 err := templates.MustGet("model").Execute(buf, genModel) 1809 if assert.NoError(t, err) { 1810 ct, err := opts.LanguageOpts.FormatContent("action_item.go", buf.Bytes()) 1811 if assert.NoError(t, err) { 1812 res := string(ct) 1813 assertInCode(t, "Computed bool `json:\"computed,omitempty\"`", res) 1814 assertInCode(t, "Intval *int64 `json:\"intval\"`", res) 1815 assertInCode(t, "PropType *string `json:\"propType\"`", res) 1816 assertInCode(t, "Strval *string `json:\"strval\"`", res) 1817 } else { 1818 fmt.Println(buf.String()) 1819 } 1820 } 1821 } 1822 } 1823 } 1824 1825 func TestGenModel_Issue454(t *testing.T) { 1826 specDoc, err := loads.Spec("../fixtures/bugs/454/swagger.yml") 1827 if assert.NoError(t, err) { 1828 definitions := specDoc.Spec().Definitions 1829 schema := definitions["genericResource"] 1830 opts := opts() 1831 genModel, err := makeGenDefinition("genericResource", "models", schema, specDoc, opts) 1832 if assert.NoError(t, err) { 1833 buf := bytes.NewBuffer(nil) 1834 err := templates.MustGet("model").Execute(buf, genModel) 1835 if assert.NoError(t, err) { 1836 ct, err := opts.LanguageOpts.FormatContent("generic_resource.go", buf.Bytes()) 1837 if assert.NoError(t, err) { 1838 res := string(ct) 1839 assertInCode(t, "rcv.Meta = stage1.Meta", res) 1840 assertInCode(t, "json.Marshal(stage1)", res) 1841 assertInCode(t, "stage1.Meta = m.Meta", res) 1842 assertInCode(t, "json.Marshal(m.GenericResource)", res) 1843 } 1844 } 1845 } 1846 } 1847 } 1848 1849 func TestGenModel_Issue423(t *testing.T) { 1850 specDoc, err := loads.Spec("../fixtures/bugs/423/swagger.json") 1851 if assert.NoError(t, err) { 1852 definitions := specDoc.Spec().Definitions 1853 schema := definitions["SRN"] 1854 opts := opts() 1855 genModel, err := makeGenDefinition("SRN", "models", schema, specDoc, opts) 1856 if assert.NoError(t, err) { 1857 buf := bytes.NewBuffer(nil) 1858 err := templates.MustGet("model").Execute(buf, genModel) 1859 if assert.NoError(t, err) { 1860 ct, err := opts.LanguageOpts.FormatContent("SRN.go", buf.Bytes()) 1861 if assert.NoError(t, err) { 1862 res := string(ct) 1863 assertInCode(t, "propSite, err := UnmarshalSite(bytes.NewBuffer(data.Site), runtime.JSONConsumer())", res) 1864 assertInCode(t, "result.siteField = propSite", res) 1865 } 1866 } 1867 } 1868 } 1869 } 1870 1871 func TestGenModel_Issue453(t *testing.T) { 1872 specDoc, err := loads.Spec("../fixtures/bugs/453/swagger.yml") 1873 if assert.NoError(t, err) { 1874 definitions := specDoc.Spec().Definitions 1875 k := "out_obj" 1876 opts := opts() 1877 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1878 if assert.NoError(t, err) { 1879 buf := bytes.NewBuffer(nil) 1880 err := templates.MustGet("model").Execute(buf, genModel) 1881 if assert.NoError(t, err) { 1882 ct, err := opts.LanguageOpts.FormatContent("out_obj.go", buf.Bytes()) 1883 if assert.NoError(t, err) { 1884 res := string(ct) 1885 assertInCode(t, `func (m *OutObj) validateFld3(formats strfmt.Registry)`, res) 1886 } else { 1887 fmt.Println(buf.String()) 1888 } 1889 } 1890 } 1891 } 1892 } 1893 1894 func TestGenModel_Issue455(t *testing.T) { 1895 specDoc, err := loads.Spec("../fixtures/bugs/455/swagger.yml") 1896 if assert.NoError(t, err) { 1897 definitions := specDoc.Spec().Definitions 1898 k := "out_obj" 1899 opts := opts() 1900 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1901 if assert.NoError(t, err) { 1902 buf := bytes.NewBuffer(nil) 1903 err := templates.MustGet("model").Execute(buf, genModel) 1904 if assert.NoError(t, err) { 1905 ct, err := opts.LanguageOpts.FormatContent("out_obj.go", buf.Bytes()) 1906 if assert.NoError(t, err) { 1907 res := string(ct) 1908 assertInCode(t, `if err := validate.Required("fld2", "body", m.Fld2); err != nil {`, res) 1909 } else { 1910 fmt.Println(buf.String()) 1911 } 1912 } 1913 } 1914 } 1915 } 1916 1917 func TestGenModel_Issue763(t *testing.T) { 1918 specDoc, err := loads.Spec("../fixtures/bugs/763/swagger.yml") 1919 if assert.NoError(t, err) { 1920 definitions := specDoc.Spec().Definitions 1921 k := "test_list" 1922 opts := opts() 1923 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1924 if assert.NoError(t, err) { 1925 buf := bytes.NewBuffer(nil) 1926 err := templates.MustGet("model").Execute(buf, genModel) 1927 if assert.NoError(t, err) { 1928 ct, err := opts.LanguageOpts.FormatContent("test_list.go", buf.Bytes()) 1929 if assert.NoError(t, err) { 1930 res := string(ct) 1931 assertInCode(t, "TheArray []*int32 `json:\"the_array\"`", res) 1932 assertInCode(t, `validate.MinimumInt("the_array"+"."+strconv.Itoa(i), "body", int64(*m.TheArray[i]), 0, false)`, res) 1933 assertInCode(t, `validate.MaximumInt("the_array"+"."+strconv.Itoa(i), "body", int64(*m.TheArray[i]), 10, false)`, res) 1934 } else { 1935 fmt.Println(buf.String()) 1936 } 1937 } 1938 } 1939 } 1940 } 1941 1942 func TestGenModel_Issue811_NullType(t *testing.T) { 1943 specDoc, err := loads.Spec("../fixtures/bugs/811/swagger.json") 1944 if assert.NoError(t, err) { 1945 definitions := specDoc.Spec().Definitions 1946 k := "teamRepos" 1947 opts := opts() 1948 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1949 if assert.NoError(t, err) { 1950 buf := bytes.NewBuffer(nil) 1951 err := templates.MustGet("model").Execute(buf, genModel) 1952 if assert.NoError(t, err) { 1953 ct, err := opts.LanguageOpts.FormatContent("team_repos.go", buf.Bytes()) 1954 if assert.NoError(t, err) { 1955 res := string(ct) 1956 assertInCode(t, "Language interface{} `json:\"language,omitempty\"`", res) 1957 } else { 1958 fmt.Println(buf.String()) 1959 } 1960 } 1961 } 1962 } 1963 } 1964 1965 func TestGenModel_Issue811_Emojis(t *testing.T) { 1966 specDoc, err := loads.Spec("../fixtures/bugs/811/swagger.json") 1967 if assert.NoError(t, err) { 1968 definitions := specDoc.Spec().Definitions 1969 k := "emojis" 1970 opts := opts() 1971 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1972 if assert.NoError(t, err) { 1973 buf := bytes.NewBuffer(nil) 1974 err := templates.MustGet("model").Execute(buf, genModel) 1975 if assert.NoError(t, err) { 1976 ct, err := opts.LanguageOpts.FormatContent("team_repos.go", buf.Bytes()) 1977 if assert.NoError(t, err) { 1978 res := string(ct) 1979 assertInCode(t, "Plus1 string `json:\"+1,omitempty\"`", res) 1980 assertInCode(t, "Minus1 string `json:\"-1,omitempty\"`", res) 1981 } else { 1982 fmt.Println(buf.String()) 1983 } 1984 } 1985 } 1986 } 1987 } 1988 1989 func TestGenModel_Issue752_EOFErr(t *testing.T) { 1990 specDoc, err := loads.Spec("../fixtures/codegen/azure-text-analyis.json") 1991 if assert.NoError(t, err) { 1992 definitions := specDoc.Spec().Definitions 1993 k := "OperationResult" 1994 opts := opts() 1995 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 1996 if assert.NoError(t, err) { 1997 buf := bytes.NewBuffer(nil) 1998 err := templates.MustGet("model").Execute(buf, genModel) 1999 if assert.NoError(t, err) { 2000 ct, err := opts.LanguageOpts.FormatContent("out_obj.go", buf.Bytes()) 2001 if assert.NoError(t, err) { 2002 res := string(ct) 2003 assertInCode(t, `&& err != io.EOF`, res) 2004 } else { 2005 fmt.Println(buf.String()) 2006 } 2007 } 2008 } 2009 } 2010 } 2011 2012 func TestImports_ExistingModel(t *testing.T) { 2013 specDoc, err := loads.Spec("../fixtures/codegen/existing-model.yml") 2014 if assert.NoError(t, err) { 2015 definitions := specDoc.Spec().Definitions 2016 k := "JsonWebKeySet" 2017 opts := opts() 2018 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 2019 if assert.NoError(t, err) && 2020 assert.NotNil(t, genModel) && 2021 assert.NotNil(t, genModel.Imports) { 2022 assert.Equal(t, "github.com/user/package", genModel.Imports["jwk"]) 2023 } 2024 k = "JsonWebKey" 2025 genModel, err = makeGenDefinition(k, "models", definitions[k], specDoc, opts) 2026 if assert.NoError(t, err) { 2027 assert.NotNil(t, genModel) 2028 assert.NotNil(t, genModel.Imports) 2029 assert.Equal(t, "github.com/user/package", genModel.Imports["jwk"]) 2030 } 2031 } 2032 } 2033 2034 func TestGenModel_Issue786(t *testing.T) { 2035 specDoc, err := loads.Spec("../fixtures/bugs/786/swagger.yml") 2036 if assert.NoError(t, err) { 2037 definitions := specDoc.Spec().Definitions 2038 k := "MyFirstObject" 2039 opts := opts() 2040 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 2041 if assert.NoError(t, err) && assert.False(t, genModel.Properties[0].AdditionalProperties.IsNullable) { 2042 buf := bytes.NewBuffer(nil) 2043 err := templates.MustGet("model").Execute(buf, genModel) 2044 if assert.NoError(t, err) { 2045 ct, err := opts.LanguageOpts.FormatContent("MyFirstObject.go", buf.Bytes()) 2046 if assert.NoError(t, err) { 2047 res := string(ct) 2048 assertInCode(t, `m.validateEntreeChoiceValueEnum("entree_choice"+"."+k, "body", m.EntreeChoice[k])`, res) 2049 } else { 2050 fmt.Println(buf.String()) 2051 } 2052 } 2053 } 2054 } 2055 } 2056 2057 func TestGenModel_Issue822(t *testing.T) { 2058 specDoc, err := loads.Spec("../fixtures/bugs/822/swagger.yml") 2059 if assert.NoError(t, err) { 2060 definitions := specDoc.Spec().Definitions 2061 k := "Pet" 2062 opts := opts() 2063 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 2064 ap := genModel.AdditionalProperties 2065 if assert.NoError(t, err) && assert.True(t, genModel.HasAdditionalProperties) && assert.NotNil(t, ap) && assert.False(t, ap.IsNullable) { 2066 buf := bytes.NewBuffer(nil) 2067 err := templates.MustGet("model").Execute(buf, genModel) 2068 if assert.NoError(t, err) { 2069 ct, err := opts.LanguageOpts.FormatContent("pet.go", buf.Bytes()) 2070 if assert.NoError(t, err) { 2071 res := string(ct) 2072 assertInCode(t, `PetAdditionalProperties map[string]interface{}`, res) 2073 assertInCode(t, `m.PetAdditionalProperties = result`, res) 2074 assertInCode(t, `additional, err := json.Marshal(m.PetAdditionalProperties)`, res) 2075 } else { 2076 fmt.Println(buf.String()) 2077 } 2078 } 2079 } 2080 } 2081 } 2082 2083 func TestGenModel_Issue981(t *testing.T) { 2084 specDoc, err := loads.Spec("../fixtures/bugs/981/swagger.json") 2085 if assert.NoError(t, err) { 2086 definitions := specDoc.Spec().Definitions 2087 k := "User" 2088 opts := opts() 2089 genModel, err := makeGenDefinition(k, "models", definitions[k], specDoc, opts) 2090 if assert.NoError(t, err) { 2091 buf := bytes.NewBuffer(nil) 2092 err := templates.MustGet("model").Execute(buf, genModel) 2093 if assert.NoError(t, err) { 2094 ct, err := opts.LanguageOpts.FormatContent("user.go", buf.Bytes()) 2095 if assert.NoError(t, err) { 2096 res := string(ct) 2097 //fmt.Println(res) 2098 assertInCode(t, "FirstName string `json:\"first_name,omitempty\"`", res) 2099 assertInCode(t, "LastName string `json:\"last_name,omitempty\"`", res) 2100 assertInCode(t, "if swag.IsZero(m.Type)", res) 2101 assertInCode(t, `validate.MinimumInt("user_type", "body", int64(m.Type), 1, false)`, res) 2102 assertInCode(t, `validate.MaximumInt("user_type", "body", int64(m.Type), 5, false)`, res) 2103 } else { 2104 fmt.Println(buf.String()) 2105 } 2106 } 2107 } 2108 } 2109 2110 } 2111 2112 func TestGenModel_Issue1341(t *testing.T) { 2113 specDoc, err := loads.Spec("../fixtures/bugs/1341/swagger.yaml") 2114 if assert.NoError(t, err) { 2115 definitions := specDoc.Spec().Definitions 2116 k := "ExecutableValueString" 2117 schema := definitions[k] 2118 opts := opts() 2119 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2120 if assert.NoError(t, err) { 2121 buf := bytes.NewBuffer(nil) 2122 err := templates.MustGet("model").Execute(buf, genModel) 2123 if assert.NoError(t, err) { 2124 ff, err := opts.LanguageOpts.FormatContent("executable_value_string.go", buf.Bytes()) 2125 if assert.NoError(t, err) { 2126 res := string(ff) 2127 //fmt.Println(res) 2128 assertInCode(t, `return errors.New(422, "invalid ValueType value: %q", base.ValueType`, res) 2129 assertInCode(t, "result.testField = base.Test", res) 2130 assertInCode(t, "Test *string `json:\"Test\"`", res) 2131 assertInCode(t, "Test: m.Test(),", res) 2132 } else { 2133 fmt.Println(buf.String()) 2134 } 2135 } 2136 } 2137 } 2138 } 2139 2140 // This tests to check that format validation is performed on non required schema properties 2141 func TestGenModel_Issue1347(t *testing.T) { 2142 specDoc, err := loads.Spec("../fixtures/bugs/1347/fixture-1347.yaml") 2143 if assert.NoError(t, err) { 2144 definitions := specDoc.Spec().Definitions 2145 schema := definitions["ContainerConfig"] 2146 opts := opts() 2147 genModel, err := makeGenDefinition("ContainerConfig", "models", schema, specDoc, opts) 2148 if assert.NoError(t, err) { 2149 buf := bytes.NewBuffer(nil) 2150 err := templates.MustGet("model").Execute(buf, genModel) 2151 if assert.NoError(t, err) { 2152 ff, err := opts.LanguageOpts.FormatContent("Foo.go", buf.Bytes()) 2153 if assert.NoError(t, err) { 2154 res := string(ff) 2155 //log.Println("1347") 2156 //log.Println(res) 2157 // Just verify that the validation call is generated even though we add a non-required property 2158 assertInCode(t, `validate.FormatOf("config1", "body", "hostname", m.Config1.String(), formats)`, res) 2159 } else { 2160 fmt.Println(buf.String()) 2161 } 2162 } 2163 } 2164 } 2165 } 2166 2167 // This tests to check that format validation is performed on MAC format 2168 func TestGenModel_Issue1348(t *testing.T) { 2169 specDoc, err := loads.Spec("../fixtures/bugs/1348/fixture-1348.yaml") 2170 if assert.NoError(t, err) { 2171 definitions := specDoc.Spec().Definitions 2172 k := "ContainerConfig" 2173 schema := definitions[k] 2174 opts := opts() 2175 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2176 if assert.NoError(t, err) { 2177 buf := bytes.NewBuffer(nil) 2178 err := templates.MustGet("model").Execute(buf, genModel) 2179 if assert.NoError(t, err) { 2180 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2181 if assert.NoError(t, err) { 2182 res := string(ct) 2183 // Just verify that the validation call is generated with proper format 2184 assertInCode(t, `if err := validate.FormatOf("config1", "body", "mac", m.Config1.String(), formats)`, res) 2185 } else { 2186 fmt.Println(buf.String()) 2187 } 2188 } 2189 } 2190 } 2191 } 2192 2193 // This tests that additionalProperties with validation is generated properly. 2194 func TestGenModel_Issue1198(t *testing.T) { 2195 specDoc, err := loads.Spec("../fixtures/bugs/1198/fixture-1198.yaml") 2196 if assert.NoError(t, err) { 2197 definitions := specDoc.Spec().Definitions 2198 k := "pet" 2199 schema := definitions[k] 2200 opts := opts() 2201 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2202 if assert.NoError(t, err) { 2203 buf := bytes.NewBuffer(nil) 2204 err := templates.MustGet("model").Execute(buf, genModel) 2205 if assert.NoError(t, err) { 2206 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2207 if assert.NoError(t, err) { 2208 res := string(ct) 2209 //log.Println("1198") 2210 //log.Println(res) 2211 // Just verify that the validation call is generated with proper format 2212 assertInCode(t, `if err := m.validateDate(formats); err != nil {`, res) 2213 } else { 2214 fmt.Println(buf.String()) 2215 } 2216 } 2217 } 2218 } 2219 } 2220 2221 // This tests that additionalProperties with validation is generated properly. 2222 func TestGenModel_Issue1397a(t *testing.T) { 2223 specDoc, err := loads.Spec("../fixtures/bugs/1397/fixture-1397a.yaml") 2224 if assert.NoError(t, err) { 2225 definitions := specDoc.Spec().Definitions 2226 k := "ContainerConfig" 2227 schema := definitions[k] 2228 opts := opts() 2229 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2230 if assert.NoError(t, err) { 2231 buf := bytes.NewBuffer(nil) 2232 err := templates.MustGet("model").Execute(buf, genModel) 2233 if assert.NoError(t, err) { 2234 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2235 if assert.NoError(t, err) { 2236 res := string(ct) 2237 //log.Println("1397a") 2238 //log.Println(res) 2239 // Just verify that the validation call is generated with proper format 2240 assertInCode(t, `if swag.IsZero(m[k]) { // not required`, res) 2241 } else { 2242 fmt.Println(buf.String()) 2243 } 2244 } 2245 } 2246 } 2247 } 2248 2249 // This tests that an enum of object values validates properly. 2250 func TestGenModel_Issue1397b(t *testing.T) { 2251 specDoc, err := loads.Spec("../fixtures/bugs/1397/fixture-1397b.yaml") 2252 if assert.NoError(t, err) { 2253 definitions := specDoc.Spec().Definitions 2254 k := "ContainerConfig" 2255 schema := definitions[k] 2256 opts := opts() 2257 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2258 if assert.NoError(t, err) { 2259 buf := bytes.NewBuffer(nil) 2260 err := templates.MustGet("model").Execute(buf, genModel) 2261 if assert.NoError(t, err) { 2262 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2263 if assert.NoError(t, err) { 2264 res := string(ct) 2265 //log.Println("1397b") 2266 //log.Println(res) 2267 // Just verify that the validation call is generated with proper format 2268 assertInCode(t, `if err := m.validateContainerConfigEnum("", "body", m); err != nil {`, res) 2269 } else { 2270 fmt.Println(buf.String()) 2271 } 2272 } 2273 } 2274 } 2275 } 2276 2277 // This tests that additionalProperties with an array of polymorphic objects is generated properly. 2278 func TestGenModel_Issue1409(t *testing.T) { 2279 specDoc, err := loads.Spec("../fixtures/bugs/1409/fixture-1409.yaml") 2280 if assert.NoError(t, err) { 2281 definitions := specDoc.Spec().Definitions 2282 k := "Graph" 2283 schema := definitions[k] 2284 opts := opts() 2285 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2286 if assert.NoError(t, err) { 2287 buf := bytes.NewBuffer(nil) 2288 err := templates.MustGet("model").Execute(buf, genModel) 2289 if assert.NoError(t, err) { 2290 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2291 if assert.NoError(t, err) { 2292 res := string(ct) 2293 //log.Println("1409") 2294 //log.Println(res) 2295 // Just verify that the validation call is generated with proper format 2296 assertInCode(t, `nodes, err := UnmarshalNodeSlice(bytes.NewBuffer(data.Nodes), runtime.JSONConsumer())`, res) 2297 assertInCode(t, `if err := json.Unmarshal(raw, &rawProps); err != nil {`, res) 2298 assertInCode(t, `m.GraphAdditionalProperties[k] = toadd`, res) 2299 assertInCode(t, `b3, err = json.Marshal(m.GraphAdditionalProperties)`, res) 2300 } else { 2301 fmt.Println(buf.String()) 2302 } 2303 } 2304 } 2305 } 2306 } 2307 2308 // This tests makes sure model definitions from inline schema in response are properly flattened and get validation 2309 func TestGenModel_Issue866(t *testing.T) { 2310 log.SetOutput(ioutil.Discard) 2311 defer log.SetOutput(os.Stdout) 2312 2313 specDoc, err := loads.Spec("../fixtures/bugs/866/fixture-866.yaml") 2314 if assert.NoError(t, err) { 2315 p, ok := specDoc.Spec().Paths.Paths["/"] 2316 if assert.True(t, ok) { 2317 op := p.Get 2318 responses := op.Responses.StatusCodeResponses 2319 for k, r := range responses { 2320 t.Logf("Response: %d", k) 2321 schema := *r.Schema 2322 opts := opts() 2323 genModel, err := makeGenDefinition("GetOKBody", "models", schema, specDoc, opts) 2324 if assert.NoError(t, err) { 2325 buf := bytes.NewBuffer(nil) 2326 err := templates.MustGet("model").Execute(buf, genModel) 2327 if assert.NoError(t, err) { 2328 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2329 if assert.NoError(t, err) { 2330 res := string(ct) 2331 assertInCode(t, `if err := validate.Required(`, res) 2332 assertInCode(t, `if err := validate.MaxLength(`, res) 2333 assertInCode(t, `if err := m.validateAccessToken(formats); err != nil {`, res) 2334 assertInCode(t, `if err := m.validateAccountID(formats); err != nil {`, res) 2335 } else { 2336 fmt.Println(buf.String()) 2337 } 2338 } 2339 } 2340 } 2341 } 2342 } 2343 } 2344 2345 // This tests makes sure marshalling and validation is generated in aliased formatted definitions 2346 func TestGenModel_Issue946(t *testing.T) { 2347 specDoc, err := loads.Spec("../fixtures/bugs/946/fixture-946.yaml") 2348 if assert.NoError(t, err) { 2349 definitions := specDoc.Spec().Definitions 2350 k := "mydate" 2351 schema := definitions[k] 2352 opts := opts() 2353 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2354 if assert.NoError(t, err) { 2355 buf := bytes.NewBuffer(nil) 2356 err := templates.MustGet("model").Execute(buf, genModel) 2357 if assert.NoError(t, err) { 2358 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2359 if assert.NoError(t, err) { 2360 res := string(ct) 2361 assertInCode(t, `type Mydate strfmt.Date`, res) 2362 assertInCode(t, `func (m *Mydate) UnmarshalJSON(b []byte) error {`, res) 2363 assertInCode(t, `return ((*strfmt.Date)(m)).UnmarshalJSON(b)`, res) 2364 assertInCode(t, `func (m Mydate) MarshalJSON() ([]byte, error) {`, res) 2365 assertInCode(t, `return (strfmt.Date(m)).MarshalJSON()`, res) 2366 assertInCode(t, `if err := validate.FormatOf("", "body", "date", strfmt.Date(m).String(), formats); err != nil {`, res) 2367 } else { 2368 fmt.Println(buf.String()) 2369 } 2370 } 2371 } 2372 } 2373 } 2374 2375 // This tests makes sure that docstring in inline schema in response properly reflect the Required property 2376 func TestGenModel_Issue910(t *testing.T) { 2377 specDoc, err := loads.Spec("../fixtures/bugs/910/fixture-910.yaml") 2378 if assert.NoError(t, err) { 2379 p, ok := specDoc.Spec().Paths.Paths["/mytest"] 2380 if assert.True(t, ok) { 2381 op := p.Get 2382 responses := op.Responses.StatusCodeResponses 2383 for k, r := range responses { 2384 t.Logf("Response: %d", k) 2385 schema := *r.Schema 2386 opts := opts() 2387 genModel, err := makeGenDefinition("GetMyTestOKBody", "models", schema, specDoc, opts) 2388 if assert.NoError(t, err) { 2389 buf := bytes.NewBuffer(nil) 2390 err := templates.MustGet("model").Execute(buf, genModel) 2391 if assert.NoError(t, err) { 2392 ct, err := opts.LanguageOpts.FormatContent("foo.go", buf.Bytes()) 2393 if assert.NoError(t, err) { 2394 res := string(ct) 2395 assertInCode(t, "// bar\n // Required: true\n Bar *int64 `json:\"bar\"`", res) 2396 assertInCode(t, "// foo\n // Required: true\n Foo interface{} `json:\"foo\"`", res) 2397 assertInCode(t, "// baz\n Baz int64 `json:\"baz,omitempty\"`", res) 2398 assertInCode(t, "// quux\n Quux []string `json:\"quux\"`", res) 2399 assertInCode(t, `if err := validate.Required("bar", "body", m.Bar); err != nil {`, res) 2400 assertInCode(t, `if err := validate.Required("foo", "body", m.Foo); err != nil {`, res) 2401 assertNotInCode(t, `if err := validate.Required("baz", "body", m.Baz); err != nil {`, res) 2402 assertNotInCode(t, `if err := validate.Required("quux", "body", m.Quux); err != nil {`, res) 2403 // NOTE(fredbi); fixed Required in slices. This property has actually no validation 2404 assertNotInCode(t, `if swag.IsZero(m.Quux) { // not required`, res) 2405 } else { 2406 fmt.Println(buf.String()) 2407 } 2408 } 2409 } 2410 } 2411 } 2412 } 2413 } 2414 2415 func TestGenerateModel_Xorder(t *testing.T) { 2416 specDoc, err := loads.Spec("../fixtures/codegen/x-order.yml") 2417 if assert.NoError(t, err) { 2418 definitions := specDoc.Spec().Definitions 2419 k := "sessionData" 2420 schema := definitions[k] 2421 opts := opts() 2422 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2423 if assert.NoError(t, err) { 2424 buf := bytes.NewBuffer(nil) 2425 err := templates.MustGet("model").Execute(buf, genModel) 2426 if assert.NoError(t, err) { 2427 ff, err := opts.LanguageOpts.FormatContent("x-order.go", buf.Bytes()) 2428 if assert.NoError(t, err) { 2429 res := string(ff) 2430 // if no x-order then alphabetical order, like DeviceID, SessionID, UMain. 2431 // There is x-order 2432 // sessionId 2433 // x-order: 0 2434 // deviceId: 2435 // x-order: 1 2436 // uMain: 2437 // x-order: 2 2438 // This is need for msgpack-array. 2439 foundDeviceID := strings.Index(res, "DeviceID") 2440 foundSessionID := strings.Index(res, "SessionID") 2441 foundUMain := strings.Index(res, "UMain") 2442 foundAaa := strings.Index(res, "Aaa") 2443 foundBbb := strings.Index(res, "Bbb") 2444 foundZzz := strings.Index(res, "Zzz") 2445 assert.True(t, foundSessionID < foundDeviceID) 2446 assert.True(t, foundSessionID < foundUMain) 2447 assert.True(t, foundUMain < foundAaa) 2448 assert.True(t, foundAaa < foundBbb) 2449 assert.True(t, foundBbb < foundZzz) 2450 } 2451 } 2452 } 2453 } 2454 } 2455 2456 func TestGenModel_Issue1623(t *testing.T) { 2457 specDoc, err := loads.Spec("../fixtures/enhancements/1623/swagger.yml") 2458 if !assert.NoError(t, err) { 2459 return 2460 } 2461 2462 definitions := specDoc.Spec().Definitions 2463 k := "Foo" 2464 schema := definitions[k] 2465 opts := opts() 2466 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2467 if !assert.NoError(t, err) { 2468 return 2469 } 2470 2471 buf := bytes.NewBuffer(nil) 2472 err = templates.MustGet("model").Execute(buf, genModel) 2473 if !assert.NoError(t, err) { 2474 fmt.Println(buf.String()) 2475 return 2476 } 2477 2478 ff, err := opts.LanguageOpts.FormatContent("Foo.go", buf.Bytes()) 2479 if !assert.NoError(t, err) { 2480 return 2481 } 2482 2483 res := string(ff) 2484 assertInCode(t, "ArrayHasOmitEmptyFalse []string `json:\"arrayHasOmitEmptyFalse\"`", res) 2485 assertInCode(t, "ArrayHasOmitEmptyTrue []string `json:\"arrayHasOmitEmptyTrue,omitempty\"`", res) 2486 assertInCode(t, "ArrayNoOmitEmpty []string `json:\"arrayNoOmitEmpty\"`", res) 2487 assertInCode(t, "GeneralHasOmitEmptyFalse string `json:\"generalHasOmitEmptyFalse\"`", res) 2488 assertInCode(t, "GeneralHasOmitEmptyTrue string `json:\"generalHasOmitEmptyTrue,omitempty\"`", res) 2489 assertInCode(t, "GeneralNoOmitEmpty string `json:\"generalNoOmitEmpty,omitempty\"`", res) 2490 assertInCode(t, "RefHasOmitEmptyFalse Bar `json:\"refHasOmitEmptyFalse\"`", res) 2491 assertInCode(t, "RefHasOmitEmptyTrue Bar `json:\"refHasOmitEmptyTrue,omitempty\"`", res) 2492 assertInCode(t, "RefNoOmitEmpty Bar `json:\"refNoOmitEmpty,omitempty\"`", res) 2493 } 2494 2495 func TestGenModel_KeepSpecPropertiesOrder(t *testing.T) { 2496 ymlFile := "../fixtures/codegen/keep-spec-order.yml" 2497 opts := opts() 2498 abcType := "abctype" 2499 2500 specDoc, err := loads.Spec(ymlFile) 2501 assert.NoError(t, err) 2502 orderedSpecDoc, err := loads.Spec(WithAutoXOrder(ymlFile)) 2503 assert.NoError(t, err) 2504 2505 definitions := specDoc.Spec().Definitions 2506 orderedDefinitions := orderedSpecDoc.Spec().Definitions 2507 2508 genModel, err := makeGenDefinition(abcType, "models", definitions[abcType], specDoc, opts) 2509 assert.NoError(t, err) 2510 orderGenModel, err := makeGenDefinition(abcType, "models", orderedDefinitions[abcType], orderedSpecDoc, opts) 2511 assert.NoError(t, err) 2512 2513 buf := bytes.NewBuffer(nil) 2514 assert.NoError(t, templates.MustGet("model").Execute(buf, genModel)) 2515 orderBuf := bytes.NewBuffer(nil) 2516 assert.NoError(t, templates.MustGet("model").Execute(orderBuf, orderGenModel)) 2517 2518 ff, err := opts.LanguageOpts.FormatContent("keepSpecOrder.go", buf.Bytes()) 2519 assert.NoError(t, err) 2520 modelCode := string(ff) 2521 ff, err = opts.LanguageOpts.FormatContent("keepSpecOrder-ordered.go", orderBuf.Bytes()) 2522 assert.NoError(t, err) 2523 orderModelCode := string(ff) 2524 2525 //without auto order , properties sorted by alphanumeric 2526 foundA := strings.Index(modelCode, "Aaa") 2527 foundB := strings.Index(modelCode, "Bbb") 2528 foundC := strings.Index(modelCode, "Ccc") 2529 assert.True(t, foundA < foundB) 2530 assert.True(t, foundB < foundC) 2531 2532 foundOrderA := strings.Index(orderModelCode, "Aaa") 2533 foundOrderB := strings.Index(orderModelCode, "Bbb") 2534 foundOrderC := strings.Index(orderModelCode, "Ccc") 2535 2536 assert.True(t, foundOrderC < foundOrderB) 2537 assert.True(t, foundOrderB < foundOrderA) 2538 2539 foundInnerA := strings.Index(modelCode, "InnerAaa") 2540 foundInnerB := strings.Index(modelCode, "InnerBbb") 2541 foundInnerC := strings.Index(modelCode, "InnerCcc") 2542 assert.True(t, foundInnerA < foundInnerB) 2543 assert.True(t, foundInnerB < foundInnerC) 2544 2545 foundOrderInnerA := strings.Index(orderModelCode, "InnerAaa") 2546 foundOrderInnerB := strings.Index(orderModelCode, "InnerBbb") 2547 foundOrderInnerC := strings.Index(orderModelCode, "InnerCcc") 2548 2549 assert.True(t, foundOrderInnerC < foundOrderInnerB) 2550 assert.True(t, foundOrderInnerB < foundOrderInnerA) 2551 } 2552 2553 func TestGenModel_StrictAdditionalProperties(t *testing.T) { 2554 specDoc, err := loads.Spec("../fixtures/codegen/strict-additional-properties.yml") 2555 if assert.NoError(t, err) { 2556 definitions := specDoc.Spec().Definitions 2557 k := "Body" 2558 schema := definitions[k] 2559 opts := opts() 2560 2561 opts.StrictAdditionalProperties = true 2562 2563 genModel, err := makeGenDefinition(k, "models", schema, specDoc, opts) 2564 if assert.NoError(t, err) { 2565 buf := bytes.NewBuffer(nil) 2566 err = templates.MustGet("model").Execute(buf, genModel) 2567 if assert.NoError(t, err) { 2568 ff, err := opts.LanguageOpts.FormatContent("strictAdditionalProperties.go", buf.Bytes()) 2569 if assert.NoError(t, err) { 2570 res := string(ff) 2571 for _, tt := range []struct { 2572 name string 2573 assertion func(testing.TB, string, string) bool 2574 }{ 2575 {k, assertInCode}, 2576 {k + "Explicit", assertInCode}, 2577 {k + "Implicit", assertInCode}, 2578 {k + "Disabled", assertNotInCode}, 2579 } { 2580 fn := funcBody(res, "*"+tt.name+") UnmarshalJSON(data []byte) error") 2581 if assert.NotEmpty(t, fn, "Method UnmarshalJSON should be defined for type *"+tt.name) { 2582 tt.assertion(t, "dec.DisallowUnknownFields()", fn) 2583 } 2584 } 2585 } else { 2586 fmt.Println(buf.String()) 2587 } 2588 } 2589 } 2590 } 2591 }