mirror of
https://github.com/LukeHagar/libopenapi.git
synced 2025-12-06 04:20:11 +00:00
Large refactor and addedGetAllChanges to each change
tons of updates, so many things.
This commit is contained in:
601
document_examples_test.go
Normal file
601
document_examples_test.go
Normal file
@@ -0,0 +1,601 @@
|
||||
// Copyright 2023 Princess B33f Heavy Industries / Dave Shanley
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
package libopenapi
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/pb33f/libopenapi/datamodel"
|
||||
"io/ioutil"
|
||||
"net/url"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"github.com/pb33f/libopenapi/datamodel/high"
|
||||
low "github.com/pb33f/libopenapi/datamodel/low/base"
|
||||
v3 "github.com/pb33f/libopenapi/datamodel/low/v3"
|
||||
"github.com/pb33f/libopenapi/resolver"
|
||||
"github.com/pb33f/libopenapi/utils"
|
||||
"github.com/stretchr/testify/assert"
|
||||
)
|
||||
|
||||
func ExampleNewDocument_fromOpenAPI3Document() {
|
||||
|
||||
// How to read in an OpenAPI 3 Specification, into a Document.
|
||||
|
||||
// load an OpenAPI 3 specification from bytes
|
||||
petstore, _ := ioutil.ReadFile("test_specs/petstorev3.json")
|
||||
|
||||
// create a new document from specification bytes
|
||||
document, err := NewDocument(petstore)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// because we know this is a v3 spec, we can build a ready to go model from it.
|
||||
v3Model, errors := document.BuildV3Model()
|
||||
|
||||
// if anything went wrong when building the v3 model, a slice of errors will be returned
|
||||
if len(errors) > 0 {
|
||||
for i := range errors {
|
||||
fmt.Printf("error: %e\n", errors[i])
|
||||
}
|
||||
panic(fmt.Sprintf("cannot create v3 model from document: %d errors reported", len(errors)))
|
||||
}
|
||||
|
||||
// get a count of the number of paths and schemas.
|
||||
paths := len(v3Model.Model.Paths.PathItems)
|
||||
schemas := len(v3Model.Model.Components.Schemas)
|
||||
|
||||
// print the number of paths and schemas in the document
|
||||
fmt.Printf("There are %d paths and %d schemas in the document", paths, schemas)
|
||||
// Output: There are 13 paths and 8 schemas in the document
|
||||
}
|
||||
|
||||
func ExampleNewDocument_fromWithDocumentConfigurationFailure() {
|
||||
|
||||
// This example shows how to create a document that prevents the loading of external references/
|
||||
// from files or the network
|
||||
|
||||
// load in the Digital Ocean OpenAPI specification
|
||||
digitalOcean, _ := ioutil.ReadFile("test_specs/digitalocean.yaml")
|
||||
|
||||
// create a DocumentConfiguration that prevents loading file and remote references
|
||||
config := datamodel.DocumentConfiguration{
|
||||
AllowFileReferences: false,
|
||||
AllowRemoteReferences: false,
|
||||
}
|
||||
|
||||
// create a new document from specification bytes
|
||||
doc, err := NewDocumentWithConfiguration(digitalOcean, &config)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// only errors will be thrown, so just capture them and print the number of errors.
|
||||
_, errors := doc.BuildV3Model()
|
||||
|
||||
// if anything went wrong when building the v3 model, a slice of errors will be returned
|
||||
if len(errors) > 0 {
|
||||
fmt.Println("Error building Digital Ocean spec errors reported")
|
||||
}
|
||||
// Output: Error building Digital Ocean spec errors reported
|
||||
}
|
||||
|
||||
func ExampleNewDocument_fromWithDocumentConfigurationSuccess() {
|
||||
|
||||
// This example shows how to create a document that prevents the loading of external references/
|
||||
// from files or the network
|
||||
|
||||
// load in the Digital Ocean OpenAPI specification
|
||||
digitalOcean, _ := ioutil.ReadFile("test_specs/digitalocean.yaml")
|
||||
|
||||
// Digital Ocean needs a baseURL to be set, so we can resolve relative references.
|
||||
baseURL, _ := url.Parse("https://raw.githubusercontent.com/digitalocean/openapi/main/specification")
|
||||
|
||||
// create a DocumentConfiguration that allows loading file and remote references, and sets the baseURL
|
||||
// to somewhere that can resolve the relative references.
|
||||
config := datamodel.DocumentConfiguration{
|
||||
AllowFileReferences: true,
|
||||
AllowRemoteReferences: true,
|
||||
BaseURL: baseURL,
|
||||
}
|
||||
|
||||
// create a new document from specification bytes
|
||||
doc, err := NewDocumentWithConfiguration(digitalOcean, &config)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// only errors will be thrown, so just capture them and print the number of errors.
|
||||
_, errors := doc.BuildV3Model()
|
||||
|
||||
// if anything went wrong when building the v3 model, a slice of errors will be returned
|
||||
if len(errors) > 0 {
|
||||
fmt.Println("Error building Digital Ocean spec errors reported")
|
||||
} else {
|
||||
fmt.Println("Digital Ocean spec built successfully")
|
||||
}
|
||||
// Output: Digital Ocean spec built successfully
|
||||
}
|
||||
|
||||
func ExampleNewDocument_fromSwaggerDocument() {
|
||||
|
||||
// How to read in a Swagger / OpenAPI 2 Specification, into a Document.
|
||||
|
||||
// load a Swagger specification from bytes
|
||||
petstore, _ := ioutil.ReadFile("test_specs/petstorev2.json")
|
||||
|
||||
// create a new document from specification bytes
|
||||
document, err := NewDocument(petstore)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// because we know this is a v2 spec, we can build a ready to go model from it.
|
||||
v2Model, errors := document.BuildV2Model()
|
||||
|
||||
// if anything went wrong when building the v3 model, a slice of errors will be returned
|
||||
if len(errors) > 0 {
|
||||
for i := range errors {
|
||||
fmt.Printf("error: %e\n", errors[i])
|
||||
}
|
||||
panic(fmt.Sprintf("cannot create v3 model from document: %d errors reported", len(errors)))
|
||||
}
|
||||
|
||||
// get a count of the number of paths and schemas.
|
||||
paths := len(v2Model.Model.Paths.PathItems)
|
||||
schemas := len(v2Model.Model.Definitions.Definitions)
|
||||
|
||||
// print the number of paths and schemas in the document
|
||||
fmt.Printf("There are %d paths and %d schemas in the document", paths, schemas)
|
||||
// Output: There are 14 paths and 6 schemas in the document
|
||||
}
|
||||
|
||||
func ExampleNewDocument_fromUnknownVersion() {
|
||||
|
||||
// load an unknown version of an OpenAPI spec
|
||||
petstore, _ := ioutil.ReadFile("test_specs/burgershop.openapi.yaml")
|
||||
|
||||
// create a new document from specification bytes
|
||||
document, err := NewDocument(petstore)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
var paths, schemas int
|
||||
var errors []error
|
||||
|
||||
// We don't know which type of document this is, so we can use the spec info to inform us
|
||||
if document.GetSpecInfo().SpecType == utils.OpenApi3 {
|
||||
v3Model, errs := document.BuildV3Model()
|
||||
if len(errs) > 0 {
|
||||
errors = errs
|
||||
}
|
||||
if len(errors) <= 0 {
|
||||
paths = len(v3Model.Model.Paths.PathItems)
|
||||
schemas = len(v3Model.Model.Components.Schemas)
|
||||
}
|
||||
}
|
||||
if document.GetSpecInfo().SpecType == utils.OpenApi2 {
|
||||
v2Model, errs := document.BuildV2Model()
|
||||
if len(errs) > 0 {
|
||||
errors = errs
|
||||
}
|
||||
if len(errors) <= 0 {
|
||||
paths = len(v2Model.Model.Paths.PathItems)
|
||||
schemas = len(v2Model.Model.Definitions.Definitions)
|
||||
}
|
||||
}
|
||||
|
||||
// if anything went wrong when building the model, report errors.
|
||||
if len(errors) > 0 {
|
||||
for i := range errors {
|
||||
fmt.Printf("error: %e\n", errors[i])
|
||||
}
|
||||
panic(fmt.Sprintf("cannot create v3 model from document: %d errors reported", len(errors)))
|
||||
}
|
||||
|
||||
// print the number of paths and schemas in the document
|
||||
fmt.Printf("There are %d paths and %d schemas in the document", paths, schemas)
|
||||
// Output: There are 5 paths and 6 schemas in the document
|
||||
}
|
||||
|
||||
func ExampleNewDocument_mutateValuesAndSerialize() {
|
||||
|
||||
// How to mutate values in an OpenAPI Specification, without re-ordering original content.
|
||||
|
||||
// create very small, and useless spec that does nothing useful, except showcase this feature.
|
||||
spec := `
|
||||
openapi: 3.1.0
|
||||
info:
|
||||
title: This is a title
|
||||
contact:
|
||||
name: Some Person
|
||||
email: some@emailaddress.com
|
||||
license:
|
||||
url: http://some-place-on-the-internet.com/license
|
||||
`
|
||||
// create a new document from specification bytes
|
||||
document, err := NewDocument([]byte(spec))
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// because we know this is a v3 spec, we can build a ready to go model from it.
|
||||
v3Model, errors := document.BuildV3Model()
|
||||
|
||||
// if anything went wrong when building the v3 model, a slice of errors will be returned
|
||||
if len(errors) > 0 {
|
||||
for i := range errors {
|
||||
fmt.Printf("error: %e\n", errors[i])
|
||||
}
|
||||
panic(fmt.Sprintf("cannot create v3 model from document: %d errors reported", len(errors)))
|
||||
}
|
||||
|
||||
// mutate the title, to do this we currently need to drop down to the low-level API.
|
||||
v3Model.Model.GoLow().Info.Value.Title.Mutate("A new title for a useless spec")
|
||||
|
||||
// mutate the email address in the contact object.
|
||||
v3Model.Model.GoLow().Info.Value.Contact.Value.Email.Mutate("buckaroo@pb33f.io")
|
||||
|
||||
// mutate the name in the contact object.
|
||||
v3Model.Model.GoLow().Info.Value.Contact.Value.Name.Mutate("Buckaroo")
|
||||
|
||||
// mutate the URL for the license object.
|
||||
v3Model.Model.GoLow().Info.Value.License.Value.URL.Mutate("https://pb33f.io/license")
|
||||
|
||||
// serialize the document back into the original YAML or JSON
|
||||
mutatedSpec, serialError := document.Serialize()
|
||||
|
||||
// if something went wrong serializing
|
||||
if serialError != nil {
|
||||
panic(fmt.Sprintf("cannot serialize document: %e", serialError))
|
||||
}
|
||||
|
||||
// print our modified spec!
|
||||
fmt.Println(string(mutatedSpec))
|
||||
// Output: openapi: 3.1.0
|
||||
//info:
|
||||
// title: A new title for a useless spec
|
||||
// contact:
|
||||
// name: Buckaroo
|
||||
// email: buckaroo@pb33f.io
|
||||
// license:
|
||||
// url: https://pb33f.io/license
|
||||
}
|
||||
|
||||
func ExampleCompareDocuments_openAPI() {
|
||||
|
||||
// How to compare two different OpenAPI specifications.
|
||||
|
||||
// load an original OpenAPI 3 specification from bytes
|
||||
burgerShopOriginal, _ := ioutil.ReadFile("test_specs/burgershop.openapi.yaml")
|
||||
|
||||
// load an **updated** OpenAPI 3 specification from bytes
|
||||
burgerShopUpdated, _ := ioutil.ReadFile("test_specs/burgershop.openapi-modified.yaml")
|
||||
|
||||
// create a new document from original specification bytes
|
||||
originalDoc, err := NewDocument(burgerShopOriginal)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// create a new document from updated specification bytes
|
||||
updatedDoc, err := NewDocument(burgerShopUpdated)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// Compare documents for all changes made
|
||||
documentChanges, errs := CompareDocuments(originalDoc, updatedDoc)
|
||||
|
||||
// If anything went wrong when building models for documents.
|
||||
if len(errs) > 0 {
|
||||
for i := range errs {
|
||||
fmt.Printf("error: %e\n", errs[i])
|
||||
}
|
||||
panic(fmt.Sprintf("cannot compare documents: %d errors reported", len(errs)))
|
||||
}
|
||||
|
||||
// Extract SchemaChanges from components changes.
|
||||
schemaChanges := documentChanges.ComponentsChanges.SchemaChanges
|
||||
|
||||
// Print out some interesting stats about the OpenAPI document changes.
|
||||
fmt.Printf("There are %d changes, of which %d are breaking. %v schemas have changes.",
|
||||
documentChanges.TotalChanges(), documentChanges.TotalBreakingChanges(), len(schemaChanges))
|
||||
//Output: There are 72 changes, of which 17 are breaking. 5 schemas have changes.
|
||||
|
||||
}
|
||||
|
||||
func ExampleCompareDocuments_swagger() {
|
||||
|
||||
// How to compare two different Swagger specifications.
|
||||
|
||||
// load an original OpenAPI 3 specification from bytes
|
||||
petstoreOriginal, _ := ioutil.ReadFile("test_specs/petstorev2-complete.yaml")
|
||||
|
||||
// load an **updated** OpenAPI 3 specification from bytes
|
||||
petstoreUpdated, _ := ioutil.ReadFile("test_specs/petstorev2-complete-modified.yaml")
|
||||
|
||||
// create a new document from original specification bytes
|
||||
originalDoc, err := NewDocument(petstoreOriginal)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// create a new document from updated specification bytes
|
||||
updatedDoc, err := NewDocument(petstoreUpdated)
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// Compare documents for all changes made
|
||||
documentChanges, errs := CompareDocuments(originalDoc, updatedDoc)
|
||||
|
||||
// If anything went wrong when building models for documents.
|
||||
if len(errs) > 0 {
|
||||
for i := range errs {
|
||||
fmt.Printf("error: %e\n", errs[i])
|
||||
}
|
||||
panic(fmt.Sprintf("cannot compare documents: %d errors reported", len(errs)))
|
||||
}
|
||||
|
||||
// Extract SchemaChanges from components changes.
|
||||
schemaChanges := documentChanges.ComponentsChanges.SchemaChanges
|
||||
|
||||
// Print out some interesting stats about the Swagger document changes.
|
||||
fmt.Printf("There are %d changes, of which %d are breaking. %v schemas have changes.",
|
||||
documentChanges.TotalChanges(), documentChanges.TotalBreakingChanges(), len(schemaChanges))
|
||||
//Output: There are 52 changes, of which 27 are breaking. 5 schemas have changes.
|
||||
|
||||
}
|
||||
|
||||
func TestDocument_Paths_As_Array(t *testing.T) {
|
||||
|
||||
// paths can now be wrapped in an array.
|
||||
spec := `{
|
||||
"openapi": "3.1.0",
|
||||
"paths": [
|
||||
"/": {
|
||||
"get": {}
|
||||
}
|
||||
]
|
||||
}
|
||||
`
|
||||
// create a new document from specification bytes
|
||||
doc, err := NewDocument([]byte(spec))
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
v3Model, _ := doc.BuildV3Model()
|
||||
assert.NotNil(t, v3Model)
|
||||
}
|
||||
|
||||
// If you want to know more about circular references that have been found
|
||||
// during the parsing/indexing/building of a document, you can capture the
|
||||
// []errors thrown which are pointers to *resolver.ResolvingError
|
||||
func ExampleNewDocument_infinite_circular_references() {
|
||||
|
||||
// create a specification with an obvious and deliberate circular reference
|
||||
spec := `openapi: "3.1"
|
||||
components:
|
||||
schemas:
|
||||
One:
|
||||
description: "test one"
|
||||
properties:
|
||||
things:
|
||||
"$ref": "#/components/schemas/Two"
|
||||
required:
|
||||
- things
|
||||
Two:
|
||||
description: "test two"
|
||||
properties:
|
||||
testThing:
|
||||
"$ref": "#/components/schemas/One"
|
||||
required:
|
||||
- testThing
|
||||
`
|
||||
// create a new document from specification bytes
|
||||
doc, err := NewDocument([]byte(spec))
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
_, errs := doc.BuildV3Model()
|
||||
|
||||
// extract resolving error
|
||||
resolvingError := errs[0]
|
||||
|
||||
// resolving error is a pointer to *resolver.ResolvingError
|
||||
// which provides access to rich details about the error.
|
||||
circularReference := resolvingError.(*resolver.ResolvingError).CircularReference
|
||||
|
||||
// capture the journey with all details
|
||||
var buf strings.Builder
|
||||
for n := range circularReference.Journey {
|
||||
|
||||
// add the full definition name to the journey.
|
||||
buf.WriteString(circularReference.Journey[n].Definition)
|
||||
if n < len(circularReference.Journey)-1 {
|
||||
buf.WriteString(" -> ")
|
||||
}
|
||||
}
|
||||
|
||||
// print out the journey and the loop point.
|
||||
fmt.Printf("Journey: %s\n", buf.String())
|
||||
fmt.Printf("Loop Point: %s", circularReference.LoopPoint.Definition)
|
||||
// Output: Journey: #/components/schemas/Two -> #/components/schemas/One -> #/components/schemas/Two
|
||||
// Loop Point: #/components/schemas/Two
|
||||
}
|
||||
|
||||
// This tests checks that circular references which are _not_ marked as required pass correctly
|
||||
func TestNewDocument_terminable_circular_references(t *testing.T) {
|
||||
|
||||
// create a specification with an obvious and deliberate circular reference
|
||||
spec := `openapi: "3.1"
|
||||
components:
|
||||
schemas:
|
||||
One:
|
||||
description: "test one"
|
||||
properties:
|
||||
things:
|
||||
"$ref": "#/components/schemas/Two"
|
||||
Two:
|
||||
description: "test two"
|
||||
properties:
|
||||
testThing:
|
||||
"$ref": "#/components/schemas/One"
|
||||
`
|
||||
// create a new document from specification bytes
|
||||
doc, err := NewDocument([]byte(spec))
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
_, errs := doc.BuildV3Model()
|
||||
|
||||
assert.Len(t, errs, 0)
|
||||
}
|
||||
|
||||
// If you're using complex types with OpenAPI Extensions, it's simple to unpack extensions into complex
|
||||
// types using `high.UnpackExtensions()`. libopenapi retains the original raw data in the low model (not the high)
|
||||
// which means unpacking them can be a little complex.
|
||||
//
|
||||
// This example demonstrates how to use the `UnpackExtensions` with custom OpenAPI extensions.
|
||||
func ExampleNewDocument_unpacking_extensions() {
|
||||
|
||||
// define an example struct representing a cake
|
||||
type cake struct {
|
||||
Candles int `yaml:"candles"`
|
||||
Frosting string `yaml:"frosting"`
|
||||
Some_Strange_Var_Name string `yaml:"someStrangeVarName"`
|
||||
}
|
||||
|
||||
// define a struct that holds a map of cake pointers.
|
||||
type cakes struct {
|
||||
Description string
|
||||
Cakes map[string]*cake
|
||||
}
|
||||
|
||||
// define a struct representing a burger
|
||||
type burger struct {
|
||||
Sauce string
|
||||
Patty string
|
||||
}
|
||||
|
||||
// define a struct that holds a map of cake pointers
|
||||
type burgers struct {
|
||||
Description string
|
||||
Burgers map[string]*burger
|
||||
}
|
||||
|
||||
// create a specification with a schema and parameter that use complex custom cakes and burgers extensions.
|
||||
spec := `openapi: "3.1"
|
||||
components:
|
||||
schemas:
|
||||
SchemaOne:
|
||||
description: "Some schema with custom complex extensions"
|
||||
x-custom-cakes:
|
||||
description: some cakes
|
||||
cakes:
|
||||
someCake:
|
||||
candles: 10
|
||||
frosting: blue
|
||||
someStrangeVarName: something
|
||||
anotherCake:
|
||||
candles: 1
|
||||
frosting: green
|
||||
parameters:
|
||||
ParameterOne:
|
||||
description: "Some parameter also using complex extensions"
|
||||
x-custom-burgers:
|
||||
description: some burgers
|
||||
burgers:
|
||||
someBurger:
|
||||
sauce: ketchup
|
||||
patty: meat
|
||||
anotherBurger:
|
||||
sauce: mayo
|
||||
patty: lamb`
|
||||
// create a new document from specification bytes
|
||||
doc, err := NewDocument([]byte(spec))
|
||||
|
||||
// if anything went wrong, an error is thrown
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// build a v3 model.
|
||||
docModel, errs := doc.BuildV3Model()
|
||||
|
||||
// if anything went wrong building, indexing and resolving the model, an error is thrown
|
||||
if errs != nil {
|
||||
panic(fmt.Sprintf("cannot create new document: %e", err))
|
||||
}
|
||||
|
||||
// get a reference to SchemaOne and ParameterOne
|
||||
schemaOne := docModel.Model.Components.Schemas["SchemaOne"].Schema()
|
||||
parameterOne := docModel.Model.Components.Parameters["ParameterOne"]
|
||||
|
||||
// unpack schemaOne extensions into complex `cakes` type
|
||||
schemaOneExtensions, schemaUnpackErrors := high.UnpackExtensions[cakes, *low.Schema](schemaOne)
|
||||
if schemaUnpackErrors != nil {
|
||||
panic(fmt.Sprintf("cannot unpack schema extensions: %e", err))
|
||||
}
|
||||
|
||||
// unpack parameterOne into complex `burgers` type
|
||||
parameterOneExtensions, paramUnpackErrors := high.UnpackExtensions[burgers, *v3.Parameter](parameterOne)
|
||||
if paramUnpackErrors != nil {
|
||||
panic(fmt.Sprintf("cannot unpack parameter extensions: %e", err))
|
||||
}
|
||||
|
||||
// extract extension by name for schemaOne
|
||||
customCakes := schemaOneExtensions["x-custom-cakes"]
|
||||
|
||||
// extract extension by name for schemaOne
|
||||
customBurgers := parameterOneExtensions["x-custom-burgers"]
|
||||
|
||||
// print out schemaOne complex extension details.
|
||||
fmt.Printf("schemaOne 'x-custom-cakes' (%s) has %d cakes, 'someCake' has %d candles and %s frosting\n",
|
||||
customCakes.Description,
|
||||
len(customCakes.Cakes),
|
||||
customCakes.Cakes["someCake"].Candles,
|
||||
customCakes.Cakes["someCake"].Frosting,
|
||||
)
|
||||
|
||||
// print out parameterOne complex extension details.
|
||||
fmt.Printf("parameterOne 'x-custom-burgers' (%s) has %d burgers, 'anotherBurger' has %s sauce and a %s patty\n",
|
||||
customBurgers.Description,
|
||||
len(customBurgers.Burgers),
|
||||
customBurgers.Burgers["anotherBurger"].Sauce,
|
||||
customBurgers.Burgers["anotherBurger"].Patty,
|
||||
)
|
||||
|
||||
// Output: schemaOne 'x-custom-cakes' (some cakes) has 2 cakes, 'someCake' has 10 candles and blue frosting
|
||||
//parameterOne 'x-custom-burgers' (some burgers) has 2 burgers, 'anotherBurger' has mayo sauce and a lamb patty
|
||||
}
|
||||
Reference in New Issue
Block a user