aboutsummaryrefslogtreecommitdiffstats
path: root/vendor/github.com/go-openapi/spec
diff options
context:
space:
mode:
author6543 <6543@obermui.de>2021-01-28 17:56:38 +0100
committerGitHub <noreply@github.com>2021-01-28 17:56:38 +0100
commitd1353e1f7c9bf648cd72bd9731b4f843b0dc9a86 (patch)
treec41437643185d16ab257cf9856a3e1ae8a835112 /vendor/github.com/go-openapi/spec
parente45bf12a34d04b18f09663f179fb58aca9ffa192 (diff)
downloadgitea-d1353e1f7c9bf648cd72bd9731b4f843b0dc9a86.tar.gz
gitea-d1353e1f7c9bf648cd72bd9731b4f843b0dc9a86.zip
Vendor Update (#14496)
* update code.gitea.io/sdk/gitea v0.13.1 -> v0.13.2 * update github.com/go-swagger/go-swagger v0.25.0 -> v0.26.0 * update github.com/google/uuid v1.1.2 -> v1.2.0 * update github.com/klauspost/compress v1.11.3 -> v1.11.7 * update github.com/lib/pq 083382b7e6fc -> v1.9.0 * update github.com/markbates/goth v1.65.0 -> v1.66.1 * update github.com/mattn/go-sqlite3 v1.14.4 -> v1.14.6 * update github.com/mgechev/revive 246eac737dc7 -> v1.0.3 * update github.com/minio/minio-go/v7 v7.0.6 -> v7.0.7 * update github.com/niklasfasching/go-org v1.3.2 -> v1.4.0 * update github.com/olivere/elastic/v7 v7.0.21 -> v7.0.22 * update github.com/pquerna/otp v1.2.0 -> v1.3.0 * update github.com/xanzy/go-gitlab v0.39.0 -> v0.42.0 * update github.com/yuin/goldmark v1.2.1 -> v1.3.1
Diffstat (limited to 'vendor/github.com/go-openapi/spec')
-rw-r--r--vendor/github.com/go-openapi/spec/.golangci.yml11
-rw-r--r--vendor/github.com/go-openapi/spec/.travis.yml20
-rw-r--r--vendor/github.com/go-openapi/spec/README.md24
-rw-r--r--vendor/github.com/go-openapi/spec/appveyor.yml34
-rw-r--r--vendor/github.com/go-openapi/spec/bindata.go6
-rw-r--r--vendor/github.com/go-openapi/spec/cache.go54
-rw-r--r--vendor/github.com/go-openapi/spec/contact_info.go3
-rw-r--r--vendor/github.com/go-openapi/spec/errors.go18
-rw-r--r--vendor/github.com/go-openapi/spec/expander.go506
-rw-r--r--vendor/github.com/go-openapi/spec/go.mod13
-rw-r--r--vendor/github.com/go-openapi/spec/go.sum47
-rw-r--r--vendor/github.com/go-openapi/spec/header.go6
-rw-r--r--vendor/github.com/go-openapi/spec/items.go22
-rw-r--r--vendor/github.com/go-openapi/spec/license.go3
-rw-r--r--vendor/github.com/go-openapi/spec/normalizer.go41
-rw-r--r--vendor/github.com/go-openapi/spec/operation.go1
-rw-r--r--vendor/github.com/go-openapi/spec/parameter.go11
-rw-r--r--vendor/github.com/go-openapi/spec/properties.go91
-rw-r--r--vendor/github.com/go-openapi/spec/ref.go4
-rw-r--r--vendor/github.com/go-openapi/spec/resolver.go128
-rw-r--r--vendor/github.com/go-openapi/spec/response.go25
-rw-r--r--vendor/github.com/go-openapi/spec/schema.go120
-rw-r--r--vendor/github.com/go-openapi/spec/schema_loader.go170
-rw-r--r--vendor/github.com/go-openapi/spec/security_scheme.go44
-rw-r--r--vendor/github.com/go-openapi/spec/spec.go14
-rw-r--r--vendor/github.com/go-openapi/spec/validations.go215
26 files changed, 1166 insertions, 465 deletions
diff --git a/vendor/github.com/go-openapi/spec/.golangci.yml b/vendor/github.com/go-openapi/spec/.golangci.yml
index 4e17ed4979..a5e3239799 100644
--- a/vendor/github.com/go-openapi/spec/.golangci.yml
+++ b/vendor/github.com/go-openapi/spec/.golangci.yml
@@ -26,3 +26,14 @@ linters:
- gocognit
- whitespace
- wsl
+ - wrapcheck
+ - testpackage
+ - nlreturn
+ - gomnd
+ - exhaustivestruct
+ - goerr113
+ - errorlint
+ - nestif
+ - godot
+ - gofumpt
+ - paralleltest
diff --git a/vendor/github.com/go-openapi/spec/.travis.yml b/vendor/github.com/go-openapi/spec/.travis.yml
index f1a3f80b35..e8ceca446b 100644
--- a/vendor/github.com/go-openapi/spec/.travis.yml
+++ b/vendor/github.com/go-openapi/spec/.travis.yml
@@ -1,8 +1,26 @@
after_success:
- bash <(curl -s https://codecov.io/bash)
go:
-- 1.13.x
- 1.14.x
+- 1.x
+arch:
+ - amd64
+jobs:
+ include:
+ # only run fast tests on ppc64le
+ - go: 1.x
+ arch: ppc64le
+ script:
+ - gotestsum -f short-verbose -- ./...
+
+ # include linting job, but only for latest go version and amd64 arch
+ - go: 1.x
+ arch: amd64
+ install:
+ go get github.com/golangci/golangci-lint/cmd/golangci-lint
+ script:
+ - golangci-lint run --new-from-rev master
+
install:
- GO111MODULE=off go get -u gotest.tools/gotestsum
language: go
diff --git a/vendor/github.com/go-openapi/spec/README.md b/vendor/github.com/go-openapi/spec/README.md
index 6354742cbf..8d13b70242 100644
--- a/vendor/github.com/go-openapi/spec/README.md
+++ b/vendor/github.com/go-openapi/spec/README.md
@@ -2,9 +2,29 @@
[![license](http://img.shields.io/badge/license-Apache%20v2-orange.svg)](https://raw.githubusercontent.com/go-openapi/spec/master/LICENSE)
[![GoDoc](https://godoc.org/github.com/go-openapi/spec?status.svg)](http://godoc.org/github.com/go-openapi/spec)
-[![GolangCI](https://golangci.com/badges/github.com/go-openapi/spec.svg)](https://golangci.com)
[![Go Report Card](https://goreportcard.com/badge/github.com/go-openapi/spec)](https://goreportcard.com/report/github.com/go-openapi/spec)
The object model for OpenAPI specification documents.
-Currently supports Swagger 2.0.
+### FAQ
+
+* What does this do?
+
+> 1. This package knows how to marshal and unmarshal Swagger API specifications into a golang object model
+> 2. It knows how to resolve $ref and expand them to make a single root documment
+
+* How does it play with the rest of the go-openapi packages ?
+
+> 1. This package is at the core of the go-openapi suite of packages and [code generator](https://github.com/go-swagger/go-swagger)
+> 2. There is a [spec loading package](https://github.com/go-openapi/loads) to fetch specs as JSON or YAML from local or remote locations
+> 3. There is a [spec validation package](https://github.com/go-openapi/validate) built on top of it
+> 4. There is a [spec analysis package](https://github.com/go-openapi/analysis) built on top of it, to analyze, flatten, fix and merge spec documents
+
+* Does this library support OpenAPI 3?
+
+> No.
+> This package currently only supports OpenAPI 2.0 (aka Swagger 2.0).
+> There is no plan to make it evolve toward supporting OpenAPI 3.x.
+> This [discussion thread](https://github.com/go-openapi/spec/issues/21) relates the full story.
+>
+> An early attempt to support Swagger 3 may be found at: https://github.com/go-openapi/spec3
diff --git a/vendor/github.com/go-openapi/spec/appveyor.yml b/vendor/github.com/go-openapi/spec/appveyor.yml
new file mode 100644
index 0000000000..e5d28bd1e4
--- /dev/null
+++ b/vendor/github.com/go-openapi/spec/appveyor.yml
@@ -0,0 +1,34 @@
+version: "0.1.{build}"
+
+clone_folder: C:\go-openapi\spec
+shallow_clone: true # for startup speed
+pull_requests:
+ do_not_increment_build_number: true
+
+#skip_tags: true
+#skip_branch_with_pr: true
+
+# appveyor.yml
+build: off
+
+environment:
+ GOPATH: c:\gopath
+
+stack: go 1.12
+
+test_script:
+ - echo "test disabled for now"
+ #- go test -v -timeout 20m ./...
+#artifacts:
+# - path: '%GOPATH%\bin\*.exe'
+deploy: off
+
+notifications:
+ - provider: Slack
+ incoming_webhook: https://hooks.slack.com/services/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
+ auth_token:
+ secure: Sf7kZf7ZGbnwWUMpffHwMu5A0cHkLK2MYY32LNTPj4+/3qC3Ghl7+9v4TSLOqOlCwdRNjOGblAq7s+GDJed6/xgRQl1JtCi1klzZNrYX4q01pgTPvvGcwbBkIYgeMaPeIRcK9OZnud7sRXdttozgTOpytps2U6Js32ip7uj5mHSg2ub0FwoSJwlS6dbezZ8+eDhoha0F/guY99BEwx8Bd+zROrT2TFGsSGOFGN6wFc7moCqTHO/YkWib13a2QNXqOxCCVBy/lt76Wp+JkeFppjHlzs/2lP3EAk13RIUAaesdEUHvIHrzCyNJEd3/+KO2DzsWOYfpktd+KBCvgaYOsoo7ubdT3IROeAegZdCgo/6xgCEsmFc9ZcqCfN5yNx2A+BZ2Vwmpws+bQ1E1+B5HDzzaiLcYfG4X2O210QVGVDLWsv1jqD+uPYeHY2WRfh5ZsIUFvaqgUEnwHwrK44/8REAhQavt1QAj5uJpsRd7CkRVPWRNK+yIky+wgbVUFEchRNmS55E7QWf+W4+4QZkQi7vUTMc9nbTUu2Es9NfvfudOpM2wZbn98fjpb/qq/nRv6Bk+ca+7XD5/IgNLMbWp2ouDdzbiHLCOfDUiHiDJhLfFZx9Bwo7ZwfzeOlbrQX66bx7xRKYmOe4DLrXhNcpbsMa8qbfxlZRCmYbubB/Y8h4=
+ channel: bots
+ on_build_success: false
+ on_build_failure: true
+ on_build_status_changed: true
diff --git a/vendor/github.com/go-openapi/spec/bindata.go b/vendor/github.com/go-openapi/spec/bindata.go
index 66b1f32635..afc83850c2 100644
--- a/vendor/github.com/go-openapi/spec/bindata.go
+++ b/vendor/github.com/go-openapi/spec/bindata.go
@@ -247,9 +247,9 @@ type bintree struct {
}
var _bintree = &bintree{nil, map[string]*bintree{
- "jsonschema-draft-04.json": &bintree{jsonschemaDraft04Json, map[string]*bintree{}},
- "v2": &bintree{nil, map[string]*bintree{
- "schema.json": &bintree{v2SchemaJson, map[string]*bintree{}},
+ "jsonschema-draft-04.json": {jsonschemaDraft04Json, map[string]*bintree{}},
+ "v2": {nil, map[string]*bintree{
+ "schema.json": {v2SchemaJson, map[string]*bintree{}},
}},
}}
diff --git a/vendor/github.com/go-openapi/spec/cache.go b/vendor/github.com/go-openapi/spec/cache.go
index 3fada0daef..122993b44b 100644
--- a/vendor/github.com/go-openapi/spec/cache.go
+++ b/vendor/github.com/go-openapi/spec/cache.go
@@ -14,7 +14,9 @@
package spec
-import "sync"
+import (
+ "sync"
+)
// ResolutionCache a cache for resolving urls
type ResolutionCache interface {
@@ -27,12 +29,23 @@ type simpleCache struct {
store map[string]interface{}
}
+func (s *simpleCache) ShallowClone() ResolutionCache {
+ store := make(map[string]interface{}, len(s.store))
+ s.lock.RLock()
+ for k, v := range s.store {
+ store[k] = v
+ }
+ s.lock.RUnlock()
+
+ return &simpleCache{
+ store: store,
+ }
+}
+
// Get retrieves a cached URI
func (s *simpleCache) Get(uri string) (interface{}, bool) {
- debugLog("getting %q from resolution cache", uri)
s.lock.RLock()
v, ok := s.store[uri]
- debugLog("got %q from resolution cache: %t", uri, ok)
s.lock.RUnlock()
return v, ok
@@ -45,16 +58,41 @@ func (s *simpleCache) Set(uri string, data interface{}) {
s.lock.Unlock()
}
-var resCache ResolutionCache
+var (
+ // resCache is a package level cache for $ref resolution and expansion.
+ // It is initialized lazily by methods that have the need for it: no
+ // memory is allocated unless some expander methods are called.
+ //
+ // It is initialized with JSON schema and swagger schema,
+ // which do not mutate during normal operations.
+ //
+ // All subsequent utilizations of this cache are produced from a shallow
+ // clone of this initial version.
+ resCache *simpleCache
+ onceCache sync.Once
-func init() {
- resCache = initResolutionCache()
+ _ ResolutionCache = &simpleCache{}
+)
+
+// initResolutionCache initializes the URI resolution cache. To be wrapped in a sync.Once.Do call.
+func initResolutionCache() {
+ resCache = defaultResolutionCache()
}
-// initResolutionCache initializes the URI resolution cache
-func initResolutionCache() ResolutionCache {
+func defaultResolutionCache() *simpleCache {
return &simpleCache{store: map[string]interface{}{
"http://swagger.io/v2/schema.json": MustLoadSwagger20Schema(),
"http://json-schema.org/draft-04/schema": MustLoadJSONSchemaDraft04(),
}}
}
+
+func cacheOrDefault(cache ResolutionCache) ResolutionCache {
+ onceCache.Do(initResolutionCache)
+
+ if cache != nil {
+ return cache
+ }
+
+ // get a shallow clone of the base cache with swagger and json schema
+ return resCache.ShallowClone()
+}
diff --git a/vendor/github.com/go-openapi/spec/contact_info.go b/vendor/github.com/go-openapi/spec/contact_info.go
index f9bf42e8dd..2f7bb219b5 100644
--- a/vendor/github.com/go-openapi/spec/contact_info.go
+++ b/vendor/github.com/go-openapi/spec/contact_info.go
@@ -28,12 +28,14 @@ type ContactInfo struct {
VendorExtensible
}
+// ContactInfoProps hold the properties of a ContactInfo object
type ContactInfoProps struct {
Name string `json:"name,omitempty"`
URL string `json:"url,omitempty"`
Email string `json:"email,omitempty"`
}
+// UnmarshalJSON hydrates ContactInfo from json
func (c *ContactInfo) UnmarshalJSON(data []byte) error {
if err := json.Unmarshal(data, &c.ContactInfoProps); err != nil {
return err
@@ -41,6 +43,7 @@ func (c *ContactInfo) UnmarshalJSON(data []byte) error {
return json.Unmarshal(data, &c.VendorExtensible)
}
+// MarshalJSON produces ContactInfo as json
func (c ContactInfo) MarshalJSON() ([]byte, error) {
b1, err := json.Marshal(c.ContactInfoProps)
if err != nil {
diff --git a/vendor/github.com/go-openapi/spec/errors.go b/vendor/github.com/go-openapi/spec/errors.go
new file mode 100644
index 0000000000..10a693a5da
--- /dev/null
+++ b/vendor/github.com/go-openapi/spec/errors.go
@@ -0,0 +1,18 @@
+package spec
+
+import "errors"
+
+var (
+ // ErrUnknownTypeForReference indicates that a resolved reference was found in an unsupported container type
+ ErrUnknownTypeForReference = errors.New("unknown type for the resolved reference")
+
+ // ErrResolveRefNeedsAPointer indicates that a $ref target must be a valid JSON pointer
+ ErrResolveRefNeedsAPointer = errors.New("resolve ref: target needs to be a pointer")
+
+ // ErrDerefUnsupportedType indicates that a resolved reference was found in an unsupported container type.
+ // At the moment, $ref are supported only inside: schemas, parameters, responses, path items
+ ErrDerefUnsupportedType = errors.New("deref: unsupported type")
+
+ // ErrExpandUnsupportedType indicates that $ref expansion is attempted on some invalid type
+ ErrExpandUnsupportedType = errors.New("expand: unsupported type. Input should be of type *Parameter or *Response")
+)
diff --git a/vendor/github.com/go-openapi/spec/expander.go b/vendor/github.com/go-openapi/spec/expander.go
index 1f30e7f8b1..8a80e2bb81 100644
--- a/vendor/github.com/go-openapi/spec/expander.go
+++ b/vendor/github.com/go-openapi/spec/expander.go
@@ -17,140 +17,21 @@ package spec
import (
"encoding/json"
"fmt"
- "strings"
)
-// ExpandOptions provides options for spec expand
+// ExpandOptions provides options for the spec expander.
type ExpandOptions struct {
- RelativeBase string
- SkipSchemas bool
- ContinueOnError bool
- AbsoluteCircularRef bool
-}
+ RelativeBase string
+ SkipSchemas bool
+ ContinueOnError bool
+ PathLoader func(string) (json.RawMessage, error) `json:"-"`
-// ResolveRefWithBase resolves a reference against a context root with preservation of base path
-func ResolveRefWithBase(root interface{}, ref *Ref, opts *ExpandOptions) (*Schema, error) {
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return nil, err
- }
- specBasePath := ""
- if opts != nil && opts.RelativeBase != "" {
- specBasePath, _ = absPath(opts.RelativeBase)
- }
-
- result := new(Schema)
- if err := resolver.Resolve(ref, result, specBasePath); err != nil {
- return nil, err
- }
- return result, nil
-}
-
-// ResolveRef resolves a reference against a context root
-// ref is guaranteed to be in root (no need to go to external files)
-// ResolveRef is ONLY called from the code generation module
-func ResolveRef(root interface{}, ref *Ref) (*Schema, error) {
- res, _, err := ref.GetPointer().Get(root)
- if err != nil {
- panic(err)
- }
- switch sch := res.(type) {
- case Schema:
- return &sch, nil
- case *Schema:
- return sch, nil
- case map[string]interface{}:
- b, _ := json.Marshal(sch)
- newSch := new(Schema)
- _ = json.Unmarshal(b, newSch)
- return newSch, nil
- default:
- return nil, fmt.Errorf("unknown type for the resolved reference")
- }
-}
-
-// ResolveParameter resolves a parameter reference against a context root
-func ResolveParameter(root interface{}, ref Ref) (*Parameter, error) {
- return ResolveParameterWithBase(root, ref, nil)
-}
-
-// ResolveParameterWithBase resolves a parameter reference against a context root and base path
-func ResolveParameterWithBase(root interface{}, ref Ref, opts *ExpandOptions) (*Parameter, error) {
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return nil, err
- }
-
- result := new(Parameter)
- if err := resolver.Resolve(&ref, result, ""); err != nil {
- return nil, err
- }
- return result, nil
-}
-
-// ResolveResponse resolves response a reference against a context root
-func ResolveResponse(root interface{}, ref Ref) (*Response, error) {
- return ResolveResponseWithBase(root, ref, nil)
-}
-
-// ResolveResponseWithBase resolves response a reference against a context root and base path
-func ResolveResponseWithBase(root interface{}, ref Ref, opts *ExpandOptions) (*Response, error) {
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return nil, err
- }
-
- result := new(Response)
- if err := resolver.Resolve(&ref, result, ""); err != nil {
- return nil, err
- }
- return result, nil
-}
-
-// ResolveItems resolves parameter items reference against a context root and base path.
-//
-// NOTE: stricly speaking, this construct is not supported by Swagger 2.0.
-// Similarly, $ref are forbidden in response headers.
-func ResolveItems(root interface{}, ref Ref, opts *ExpandOptions) (*Items, error) {
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return nil, err
- }
- basePath := ""
- if opts.RelativeBase != "" {
- basePath = opts.RelativeBase
- }
- result := new(Items)
- if err := resolver.Resolve(&ref, result, basePath); err != nil {
- return nil, err
- }
- return result, nil
-}
-
-// ResolvePathItem resolves response a path item against a context root and base path
-func ResolvePathItem(root interface{}, ref Ref, opts *ExpandOptions) (*PathItem, error) {
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return nil, err
- }
- basePath := ""
- if opts.RelativeBase != "" {
- basePath = opts.RelativeBase
- }
- result := new(PathItem)
- if err := resolver.Resolve(&ref, result, basePath); err != nil {
- return nil, err
- }
- return result, nil
+ AbsoluteCircularRef bool
}
// ExpandSpec expands the references in a swagger spec
func ExpandSpec(spec *Swagger, options *ExpandOptions) error {
- resolver, err := defaultSchemaLoader(spec, options, nil, nil)
- // Just in case this ever returns an error.
- if resolver.shouldStopOnError(err) {
- return err
- }
+ resolver := defaultSchemaLoader(spec, options, nil, nil)
// getting the base path of the spec to adjust all subsequent reference resolutions
specBasePath := ""
@@ -160,9 +41,10 @@ func ExpandSpec(spec *Swagger, options *ExpandOptions) error {
if options == nil || !options.SkipSchemas {
for key, definition := range spec.Definitions {
- var def *Schema
- var err error
- if def, err = expandSchema(definition, []string{fmt.Sprintf("#/definitions/%s", key)}, resolver, specBasePath); resolver.shouldStopOnError(err) {
+ parentRefs := make([]string, 0, 10)
+ parentRefs = append(parentRefs, fmt.Sprintf("#/definitions/%s", key))
+ def, err := expandSchema(definition, parentRefs, resolver, specBasePath)
+ if resolver.shouldStopOnError(err) {
return err
}
if def != nil {
@@ -189,157 +71,140 @@ func ExpandSpec(spec *Swagger, options *ExpandOptions) error {
if spec.Paths != nil {
for key := range spec.Paths.Paths {
- path := spec.Paths.Paths[key]
- if err := expandPathItem(&path, resolver, specBasePath); resolver.shouldStopOnError(err) {
+ pth := spec.Paths.Paths[key]
+ if err := expandPathItem(&pth, resolver, specBasePath); resolver.shouldStopOnError(err) {
return err
}
- spec.Paths.Paths[key] = path
+ spec.Paths.Paths[key] = pth
}
}
return nil
}
-const rootBase = "root"
-// baseForRoot loads in the cache the root document and produces a fake "root" base path entry
+const rootBase = ".root"
+
+// baseForRoot loads in the cache the root document and produces a fake ".root" base path entry
// for further $ref resolution
+//
+// Setting the cache is optional and this parameter may safely be left to nil.
func baseForRoot(root interface{}, cache ResolutionCache) string {
- // cache the root document to resolve $ref's
- if root != nil {
- base, _ := absPath(rootBase)
- normalizedBase := normalizeAbsPath(base)
- debugLog("setting root doc in cache at: %s", normalizedBase)
- if cache == nil {
- cache = resCache
- }
- cache.Set(normalizedBase, root)
- return rootBase
+ if root == nil {
+ return ""
}
- return ""
+
+ // cache the root document to resolve $ref's
+ base, _ := absPath(rootBase)
+ normalizedBase := normalizeAbsPath(base)
+ cache.Set(normalizedBase, root)
+
+ return normalizedBase
}
-// ExpandSchema expands the refs in the schema object with reference to the root object
-// go-openapi/validate uses this function
-// notice that it is impossible to reference a json schema in a different file other than root
+// ExpandSchema expands the refs in the schema object with reference to the root object.
+//
+// go-openapi/validate uses this function.
+//
+// Notice that it is impossible to reference a json schema in a different document other than root
+// (use ExpandSchemaWithBasePath to resolve external references).
+//
+// Setting the cache is optional and this parameter may safely be left to nil.
func ExpandSchema(schema *Schema, root interface{}, cache ResolutionCache) error {
+ cache = cacheOrDefault(cache)
+ if root == nil {
+ root = schema
+ }
+
opts := &ExpandOptions{
// when a root is specified, cache the root as an in-memory document for $ref retrieval
RelativeBase: baseForRoot(root, cache),
SkipSchemas: false,
ContinueOnError: false,
- // when no base path is specified, remaining $ref (circular) are rendered with an absolute path
- AbsoluteCircularRef: true,
}
+
return ExpandSchemaWithBasePath(schema, cache, opts)
}
-// ExpandSchemaWithBasePath expands the refs in the schema object, base path configured through expand options
+// ExpandSchemaWithBasePath expands the refs in the schema object, base path configured through expand options.
+//
+// Setting the cache is optional and this parameter may safely be left to nil.
func ExpandSchemaWithBasePath(schema *Schema, cache ResolutionCache, opts *ExpandOptions) error {
if schema == nil {
return nil
}
+ cache = cacheOrDefault(cache)
+
var basePath string
if opts.RelativeBase != "" {
basePath, _ = absPath(opts.RelativeBase)
}
- resolver, err := defaultSchemaLoader(nil, opts, cache, nil)
+ resolver := defaultSchemaLoader(nil, opts, cache, nil)
+
+ parentRefs := make([]string, 0, 10)
+ s, err := expandSchema(*schema, parentRefs, resolver, basePath)
if err != nil {
return err
}
-
- refs := []string{""}
- var s *Schema
- if s, err = expandSchema(*schema, refs, resolver, basePath); err != nil {
- return err
+ if s != nil {
+ // guard for when continuing on error
+ *schema = *s
}
- *schema = *s
+
return nil
}
func expandItems(target Schema, parentRefs []string, resolver *schemaLoader, basePath string) (*Schema, error) {
- if target.Items != nil {
- if target.Items.Schema != nil {
- t, err := expandSchema(*target.Items.Schema, parentRefs, resolver, basePath)
- if err != nil {
- return nil, err
- }
- *target.Items.Schema = *t
+ if target.Items == nil {
+ return &target, nil
+ }
+
+ // array
+ if target.Items.Schema != nil {
+ t, err := expandSchema(*target.Items.Schema, parentRefs, resolver, basePath)
+ if err != nil {
+ return nil, err
}
- for i := range target.Items.Schemas {
- t, err := expandSchema(target.Items.Schemas[i], parentRefs, resolver, basePath)
- if err != nil {
- return nil, err
- }
- target.Items.Schemas[i] = *t
+ *target.Items.Schema = *t
+ }
+
+ // tuple
+ for i := range target.Items.Schemas {
+ t, err := expandSchema(target.Items.Schemas[i], parentRefs, resolver, basePath)
+ if err != nil {
+ return nil, err
}
+ target.Items.Schemas[i] = *t
}
+
return &target, nil
}
func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, basePath string) (*Schema, error) {
if target.Ref.String() == "" && target.Ref.IsRoot() {
- // normalizing is important
newRef := normalizeFileRef(&target.Ref, basePath)
target.Ref = *newRef
return &target, nil
-
}
// change the base path of resolution when an ID is encountered
// otherwise the basePath should inherit the parent's
- // important: ID can be relative path
if target.ID != "" {
- debugLog("schema has ID: %s", target.ID)
- // handling the case when id is a folder
- // remember that basePath has to be a file
- refPath := target.ID
- if strings.HasSuffix(target.ID, "/") {
- // path.Clean here would not work correctly if basepath is http
- refPath = fmt.Sprintf("%s%s", refPath, "placeholder.json")
- }
- basePath = normalizePaths(refPath, basePath)
+ basePath, _ = resolver.setSchemaID(target, target.ID, basePath)
}
- var t *Schema
- // if Ref is found, everything else doesn't matter
- // Ref also changes the resolution scope of children expandSchema
if target.Ref.String() != "" {
- // here the resolution scope is changed because a $ref was encountered
- normalizedRef := normalizeFileRef(&target.Ref, basePath)
- normalizedBasePath := normalizedRef.RemoteURI()
-
- if resolver.isCircular(normalizedRef, basePath, parentRefs...) {
- // this means there is a cycle in the recursion tree: return the Ref
- // - circular refs cannot be expanded. We leave them as ref.
- // - denormalization means that a new local file ref is set relative to the original basePath
- debugLog("shortcut circular ref: basePath: %s, normalizedPath: %s, normalized ref: %s",
- basePath, normalizedBasePath, normalizedRef.String())
- if !resolver.options.AbsoluteCircularRef {
- target.Ref = *denormalizeFileRef(normalizedRef, normalizedBasePath, resolver.context.basePath)
- } else {
- target.Ref = *normalizedRef
- }
- return &target, nil
- }
+ return expandSchemaRef(target, parentRefs, resolver, basePath)
+ }
- debugLog("basePath: %s: calling Resolve with target: %#v", basePath, target)
- if err := resolver.Resolve(&target.Ref, &t, basePath); resolver.shouldStopOnError(err) {
- return nil, err
+ for k := range target.Definitions {
+ tt, err := expandSchema(target.Definitions[k], parentRefs, resolver, basePath)
+ if resolver.shouldStopOnError(err) {
+ return &target, err
}
-
- if t != nil {
- parentRefs = append(parentRefs, normalizedRef.String())
- var err error
- transitiveResolver, err := resolver.transitiveResolver(basePath, target.Ref)
- if transitiveResolver.shouldStopOnError(err) {
- return nil, err
- }
-
- basePath = resolver.updateBasePath(transitiveResolver, normalizedBasePath)
-
- return expandSchema(*t, parentRefs, transitiveResolver, basePath)
+ if tt != nil {
+ target.Definitions[k] = *tt
}
}
@@ -356,15 +221,21 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
if resolver.shouldStopOnError(err) {
return &target, err
}
- target.AllOf[i] = *t
+ if t != nil {
+ target.AllOf[i] = *t
+ }
}
+
for i := range target.AnyOf {
t, err := expandSchema(target.AnyOf[i], parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
return &target, err
}
- target.AnyOf[i] = *t
+ if t != nil {
+ target.AnyOf[i] = *t
+ }
}
+
for i := range target.OneOf {
t, err := expandSchema(target.OneOf[i], parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
@@ -374,6 +245,7 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
target.OneOf[i] = *t
}
}
+
if target.Not != nil {
t, err := expandSchema(*target.Not, parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
@@ -383,6 +255,7 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
*target.Not = *t
}
}
+
for k := range target.Properties {
t, err := expandSchema(target.Properties[k], parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
@@ -392,6 +265,7 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
target.Properties[k] = *t
}
}
+
if target.AdditionalProperties != nil && target.AdditionalProperties.Schema != nil {
t, err := expandSchema(*target.AdditionalProperties.Schema, parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
@@ -401,6 +275,7 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
*target.AdditionalProperties.Schema = *t
}
}
+
for k := range target.PatternProperties {
t, err := expandSchema(target.PatternProperties[k], parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
@@ -410,6 +285,7 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
target.PatternProperties[k] = *t
}
}
+
for k := range target.Dependencies {
if target.Dependencies[k].Schema != nil {
t, err := expandSchema(*target.Dependencies[k].Schema, parentRefs, resolver, basePath)
@@ -421,6 +297,7 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
}
}
}
+
if target.AdditionalItems != nil && target.AdditionalItems.Schema != nil {
t, err := expandSchema(*target.AdditionalItems.Schema, parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
@@ -430,16 +307,48 @@ func expandSchema(target Schema, parentRefs []string, resolver *schemaLoader, ba
*target.AdditionalItems.Schema = *t
}
}
- for k := range target.Definitions {
- t, err := expandSchema(target.Definitions[k], parentRefs, resolver, basePath)
- if resolver.shouldStopOnError(err) {
- return &target, err
- }
- if t != nil {
- target.Definitions[k] = *t
+ return &target, nil
+}
+
+func expandSchemaRef(target Schema, parentRefs []string, resolver *schemaLoader, basePath string) (*Schema, error) {
+ // if a Ref is found, all sibling fields are skipped
+ // Ref also changes the resolution scope of children expandSchema
+
+ // here the resolution scope is changed because a $ref was encountered
+ normalizedRef := normalizeFileRef(&target.Ref, basePath)
+ normalizedBasePath := normalizedRef.RemoteURI()
+
+ if resolver.isCircular(normalizedRef, basePath, parentRefs...) {
+ // this means there is a cycle in the recursion tree: return the Ref
+ // - circular refs cannot be expanded. We leave them as ref.
+ // - denormalization means that a new local file ref is set relative to the original basePath
+ debugLog("short circuit circular ref: basePath: %s, normalizedPath: %s, normalized ref: %s",
+ basePath, normalizedBasePath, normalizedRef.String())
+ if !resolver.options.AbsoluteCircularRef {
+ target.Ref = *denormalizeFileRef(normalizedRef, normalizedBasePath, resolver.context.basePath)
+ } else {
+ target.Ref = *normalizedRef
}
+ return &target, nil
}
- return &target, nil
+
+ var t *Schema
+ err := resolver.Resolve(&target.Ref, &t, basePath)
+ if resolver.shouldStopOnError(err) {
+ return nil, err
+ }
+
+ if t == nil {
+ // guard for when continuing on error
+ return &target, nil
+ }
+
+ parentRefs = append(parentRefs, normalizedRef.String())
+ transitiveResolver := resolver.transitiveResolver(basePath, target.Ref)
+
+ basePath = resolver.updateBasePath(transitiveResolver, normalizedBasePath)
+
+ return expandSchema(*t, parentRefs, transitiveResolver, basePath)
}
func expandPathItem(pathItem *PathItem, resolver *schemaLoader, basePath string) error {
@@ -447,25 +356,24 @@ func expandPathItem(pathItem *PathItem, resolver *schemaLoader, basePath string)
return nil
}
- parentRefs := []string{}
+ parentRefs := make([]string, 0, 10)
if err := resolver.deref(pathItem, parentRefs, basePath); resolver.shouldStopOnError(err) {
return err
}
+
if pathItem.Ref.String() != "" {
- transitiveResolver, err := resolver.transitiveResolver(basePath, pathItem.Ref)
- if transitiveResolver.shouldStopOnError(err) {
- return err
- }
+ transitiveResolver := resolver.transitiveResolver(basePath, pathItem.Ref)
basePath = transitiveResolver.updateBasePath(resolver, basePath)
resolver = transitiveResolver
}
- pathItem.Ref = Ref{}
- for idx := range pathItem.Parameters {
- if err := expandParameterOrResponse(&(pathItem.Parameters[idx]), resolver, basePath); resolver.shouldStopOnError(err) {
+ pathItem.Ref = Ref{}
+ for i := range pathItem.Parameters {
+ if err := expandParameterOrResponse(&(pathItem.Parameters[i]), resolver, basePath); resolver.shouldStopOnError(err) {
return err
}
}
+
ops := []*Operation{
pathItem.Get,
pathItem.Head,
@@ -480,6 +388,7 @@ func expandPathItem(pathItem *PathItem, resolver *schemaLoader, basePath string)
return err
}
}
+
return nil
}
@@ -496,42 +405,47 @@ func expandOperation(op *Operation, resolver *schemaLoader, basePath string) err
op.Parameters[i] = param
}
- if op.Responses != nil {
- responses := op.Responses
- if err := expandParameterOrResponse(responses.Default, resolver, basePath); resolver.shouldStopOnError(err) {
+ if op.Responses == nil {
+ return nil
+ }
+
+ responses := op.Responses
+ if err := expandParameterOrResponse(responses.Default, resolver, basePath); resolver.shouldStopOnError(err) {
+ return err
+ }
+
+ for code := range responses.StatusCodeResponses {
+ response := responses.StatusCodeResponses[code]
+ if err := expandParameterOrResponse(&response, resolver, basePath); resolver.shouldStopOnError(err) {
return err
}
- for code := range responses.StatusCodeResponses {
- response := responses.StatusCodeResponses[code]
- if err := expandParameterOrResponse(&response, resolver, basePath); resolver.shouldStopOnError(err) {
- return err
- }
- responses.StatusCodeResponses[code] = response
- }
+ responses.StatusCodeResponses[code] = response
}
+
return nil
}
// ExpandResponseWithRoot expands a response based on a root document, not a fetchable document
+//
+// Notice that it is impossible to reference a json schema in a different document other than root
+// (use ExpandResponse to resolve external references).
+//
+// Setting the cache is optional and this parameter may safely be left to nil.
func ExpandResponseWithRoot(response *Response, root interface{}, cache ResolutionCache) error {
+ cache = cacheOrDefault(cache)
opts := &ExpandOptions{
RelativeBase: baseForRoot(root, cache),
SkipSchemas: false,
ContinueOnError: false,
- // when no base path is specified, remaining $ref (circular) are rendered with an absolute path
- AbsoluteCircularRef: true,
- }
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return err
}
+ resolver := defaultSchemaLoader(root, opts, cache, nil)
return expandParameterOrResponse(response, resolver, opts.RelativeBase)
}
// ExpandResponse expands a response based on a basepath
-// This is the exported version of expandResponse
-// all refs inside response will be resolved relative to basePath
+//
+// All refs inside response will be resolved relative to basePath
func ExpandResponse(response *Response, basePath string) error {
var specBasePath string
if basePath != "" {
@@ -540,27 +454,23 @@ func ExpandResponse(response *Response, basePath string) error {
opts := &ExpandOptions{
RelativeBase: specBasePath,
}
- resolver, err := defaultSchemaLoader(nil, opts, nil, nil)
- if err != nil {
- return err
- }
+ resolver := defaultSchemaLoader(nil, opts, nil, nil)
return expandParameterOrResponse(response, resolver, opts.RelativeBase)
}
-// ExpandParameterWithRoot expands a parameter based on a root document, not a fetchable document
+// ExpandParameterWithRoot expands a parameter based on a root document, not a fetchable document.
+//
+// Notice that it is impossible to reference a json schema in a different document other than root
+// (use ExpandParameter to resolve external references).
func ExpandParameterWithRoot(parameter *Parameter, root interface{}, cache ResolutionCache) error {
+ cache = cacheOrDefault(cache)
opts := &ExpandOptions{
RelativeBase: baseForRoot(root, cache),
SkipSchemas: false,
ContinueOnError: false,
- // when no base path is specified, remaining $ref (circular) are rendered with an absolute path
- AbsoluteCircularRef: true,
- }
- resolver, err := defaultSchemaLoader(root, opts, nil, nil)
- if err != nil {
- return err
}
+ resolver := defaultSchemaLoader(root, opts, cache, nil)
return expandParameterOrResponse(parameter, resolver, opts.RelativeBase)
}
@@ -576,17 +486,17 @@ func ExpandParameter(parameter *Parameter, basePath string) error {
opts := &ExpandOptions{
RelativeBase: specBasePath,
}
- resolver, err := defaultSchemaLoader(nil, opts, nil, nil)
- if err != nil {
- return err
- }
+ resolver := defaultSchemaLoader(nil, opts, nil, nil)
return expandParameterOrResponse(parameter, resolver, opts.RelativeBase)
}
func getRefAndSchema(input interface{}) (*Ref, *Schema, error) {
- var ref *Ref
- var sch *Schema
+ var (
+ ref *Ref
+ sch *Schema
+ )
+
switch refable := input.(type) {
case *Parameter:
if refable == nil {
@@ -601,8 +511,9 @@ func getRefAndSchema(input interface{}) (*Ref, *Schema, error) {
ref = &refable.Ref
sch = refable.Schema
default:
- return nil, nil, fmt.Errorf("expand: unsupported type %T. Input should be of type *Parameter or *Response", input)
+ return nil, nil, fmt.Errorf("unsupported type: %T: %w", input, ErrExpandUnsupportedType)
}
+
return ref, sch, nil
}
@@ -611,41 +522,70 @@ func expandParameterOrResponse(input interface{}, resolver *schemaLoader, basePa
if err != nil {
return err
}
+
if ref == nil {
return nil
}
- parentRefs := []string{}
- if err := resolver.deref(input, parentRefs, basePath); resolver.shouldStopOnError(err) {
+
+ parentRefs := make([]string, 0, 10)
+ if err = resolver.deref(input, parentRefs, basePath); resolver.shouldStopOnError(err) {
return err
}
+
ref, sch, _ := getRefAndSchema(input)
if ref.String() != "" {
- transitiveResolver, err := resolver.transitiveResolver(basePath, *ref)
- if transitiveResolver.shouldStopOnError(err) {
- return err
- }
+ transitiveResolver := resolver.transitiveResolver(basePath, *ref)
basePath = resolver.updateBasePath(transitiveResolver, basePath)
resolver = transitiveResolver
}
- if sch != nil && sch.Ref.String() != "" {
- // schema expanded to a $ref in another root
- var ern error
- sch.Ref, ern = NewRef(normalizePaths(sch.Ref.String(), ref.RemoteURI()))
+ if sch == nil {
+ // nothing to be expanded
+ if ref != nil {
+ *ref = Ref{}
+ }
+ return nil
+ }
+
+ if sch.Ref.String() != "" {
+ rebasedRef, ern := NewRef(normalizePaths(sch.Ref.String(), basePath))
if ern != nil {
return ern
}
+
+ switch {
+ case resolver.isCircular(&rebasedRef, basePath, parentRefs...):
+ // this is a circular $ref: stop expansion
+ if !resolver.options.AbsoluteCircularRef {
+ sch.Ref = *denormalizeFileRef(&rebasedRef, basePath, resolver.context.basePath)
+ } else {
+ sch.Ref = rebasedRef
+ }
+ case !resolver.options.SkipSchemas:
+ // schema expanded to a $ref in another root
+ sch.Ref = rebasedRef
+ default:
+ // skip schema expansion but rebase $ref to schema
+ sch.Ref = *denormalizeFileRef(&rebasedRef, basePath, resolver.context.basePath)
+ }
}
+
if ref != nil {
*ref = Ref{}
}
- if !resolver.options.SkipSchemas && sch != nil {
+ // expand schema
+ if !resolver.options.SkipSchemas {
s, err := expandSchema(*sch, parentRefs, resolver, basePath)
if resolver.shouldStopOnError(err) {
return err
}
+ if s == nil {
+ // guard for when continuing on error
+ return nil
+ }
*sch = *s
}
+
return nil
}
diff --git a/vendor/github.com/go-openapi/spec/go.mod b/vendor/github.com/go-openapi/spec/go.mod
index 14e5f2dac3..1717d0836c 100644
--- a/vendor/github.com/go-openapi/spec/go.mod
+++ b/vendor/github.com/go-openapi/spec/go.mod
@@ -1,12 +1,13 @@
module github.com/go-openapi/spec
require (
- github.com/go-openapi/jsonpointer v0.19.3
- github.com/go-openapi/jsonreference v0.19.2
- github.com/go-openapi/swag v0.19.5
- github.com/stretchr/testify v1.3.0
- golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297 // indirect
- gopkg.in/yaml.v2 v2.2.4
+ github.com/go-openapi/jsonpointer v0.19.5
+ github.com/go-openapi/jsonreference v0.19.5
+ github.com/go-openapi/swag v0.19.12
+ github.com/stretchr/testify v1.6.1
+ golang.org/x/net v0.0.0-20201224014010-6772e930b67b // indirect
+ golang.org/x/text v0.3.4 // indirect
+ gopkg.in/yaml.v2 v2.4.0
)
go 1.13
diff --git a/vendor/github.com/go-openapi/spec/go.sum b/vendor/github.com/go-openapi/spec/go.sum
index c209ff9712..730dddba7e 100644
--- a/vendor/github.com/go-openapi/spec/go.sum
+++ b/vendor/github.com/go-openapi/spec/go.sum
@@ -2,48 +2,71 @@ github.com/PuerkitoBio/purell v1.1.1 h1:WEQqlqaGbrPkxLJWfBwQmfEAE1Z7ONdDLqrN38tN
github.com/PuerkitoBio/purell v1.1.1/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbtSwDGJws/X0=
github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 h1:d+Bc7a5rLufV/sSk/8dngufqelfh6jnri85riMAaF/M=
github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE=
+github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
-github.com/go-openapi/jsonpointer v0.19.2 h1:A9+F4Dc/MCNB5jibxf6rRvOvR/iFgQdyNx9eIhnGqq0=
-github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg=
github.com/go-openapi/jsonpointer v0.19.3 h1:gihV7YNZK1iK6Tgwwsxo2rJbD1GTbdm72325Bq8FI3w=
github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
-github.com/go-openapi/jsonreference v0.19.2 h1:o20suLFB4Ri0tuzpWtyHlh7E7HnkqTNLq6aR6WVNS1w=
-github.com/go-openapi/jsonreference v0.19.2/go.mod h1:jMjeRr2HHw6nAVajTXJ4eiUwohSTlpa0o73RUL1owJc=
-github.com/go-openapi/swag v0.19.2 h1:jvO6bCMBEilGwMfHhrd61zIID4oIFdwb76V17SM88dE=
-github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
+github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY=
+github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
+github.com/go-openapi/jsonreference v0.19.5 h1:1WJP/wi4OjB4iV8KVbH73rQaoialJrqv8gitZLxGLtM=
+github.com/go-openapi/jsonreference v0.19.5/go.mod h1:RdybgQwPxbL4UEjuAruzK1x3nE69AqPYEJeo/TWfEeg=
github.com/go-openapi/swag v0.19.5 h1:lTz6Ys4CmqqCQmZPBlbQENR1/GucA2bzYTE12Pw4tFY=
github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
+github.com/go-openapi/swag v0.19.12 h1:Bc0bnY2c3AoF7Gc+IMIAQQsD8fLHjHpc19wXvYuayQI=
+github.com/go-openapi/swag v0.19.12/go.mod h1:eFdyEBkTdoAf/9RXBvj4cr1nH7GD8Kzo5HTt47gr72M=
+github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY=
+github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y=
github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI=
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
+github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
+github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63 h1:nTT4s92Dgz2HlrB2NaMgvlfqHH39OgMhA7z3PK7PGD4=
github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e h1:hB2xlXdHp/pmPZq0y3QnmWAArdw9PqbmotexnWx/FU8=
github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
+github.com/mailru/easyjson v0.7.6 h1:8yTIVnZgCoiM1TgqoeTl+LfU5Jg6/xL3QhGQnimLYnA=
+github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc=
+github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e h1:fD57ERR4JtEqsWbfPhv4DMiApHyliiK5xCTNVSPiaAs=
+github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.3.0 h1:TivCn/peBQ7UY8ooIcPgZFpTNSz0Q2U6UrFlUfqbe0Q=
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
+github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0=
+github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
-golang.org/x/net v0.0.0-20190613194153-d28f0bde5980 h1:dfGZHvZk057jK2MCeWus/TowKpJ8y4AmooUzdBSR9GU=
-golang.org/x/net v0.0.0-20190613194153-d28f0bde5980/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297 h1:k7pJ2yAPLPgbskkFdhRCsA77k2fySZ1zf2zCjvQCiIM=
golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
+golang.org/x/net v0.0.0-20201224014010-6772e930b67b h1:iFwSg7t5GZmB/Q5TjiEAsdoLDrdJRC1RiF2WhuV29Qw=
+golang.org/x/net v0.0.0-20201224014010-6772e930b67b/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
+golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
+golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg=
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
-golang.org/x/text v0.3.2 h1:tW2bmiBqwgJj/UpqtC8EpXEZVYOwU0yG4iWbprSVAcs=
-golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
+golang.org/x/text v0.3.3 h1:cokOdA+Jmi5PJGXLlLllQSgYigAEfHXJAERHVMaCc2k=
+golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
+golang.org/x/text v0.3.4 h1:0YWbFKbhXG/wIiuHDSKpS0Iy7FSA+u45VtBMfQcFTTc=
+golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f h1:BLraFXnmrev5lT+xlilqcH8XK9/i0At2xKjWk4p6zsU=
+gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
-gopkg.in/yaml.v2 v2.2.4 h1:/eiJrUcujPVeJ3xlSWaiNi3uSVmDGBK1pDHUHAnao1I=
-gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
+gopkg.in/yaml.v2 v2.3.0 h1:clyUAQHOM3G0M3f5vQj7LuJrETvjVot3Z5el9nffUtU=
+gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
+gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
+gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
+gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo=
+gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
+gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776 h1:tQIYjPdBoyREyB9XMu+nnTclpTYkz2zFM+lzLJFO4gQ=
+gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
diff --git a/vendor/github.com/go-openapi/spec/header.go b/vendor/github.com/go-openapi/spec/header.go
index 39efe452bb..9dfd17b185 100644
--- a/vendor/github.com/go-openapi/spec/header.go
+++ b/vendor/github.com/go-openapi/spec/header.go
@@ -141,6 +141,12 @@ func (h *Header) AllowDuplicates() *Header {
return h
}
+// WithValidations is a fluent method to set header validations
+func (h *Header) WithValidations(val CommonValidations) *Header {
+ h.SetValidations(SchemaValidations{CommonValidations: val})
+ return h
+}
+
// MarshalJSON marshal this to JSON
func (h Header) MarshalJSON() ([]byte, error) {
b1, err := json.Marshal(h.CommonValidations)
diff --git a/vendor/github.com/go-openapi/spec/items.go b/vendor/github.com/go-openapi/spec/items.go
index 365d163158..e2afb2133b 100644
--- a/vendor/github.com/go-openapi/spec/items.go
+++ b/vendor/github.com/go-openapi/spec/items.go
@@ -53,22 +53,6 @@ func (s *SimpleSchema) ItemsTypeName() string {
return s.Items.TypeName()
}
-// CommonValidations describe common JSON-schema validations
-type CommonValidations struct {
- Maximum *float64 `json:"maximum,omitempty"`
- ExclusiveMaximum bool `json:"exclusiveMaximum,omitempty"`
- Minimum *float64 `json:"minimum,omitempty"`
- ExclusiveMinimum bool `json:"exclusiveMinimum,omitempty"`
- MaxLength *int64 `json:"maxLength,omitempty"`
- MinLength *int64 `json:"minLength,omitempty"`
- Pattern string `json:"pattern,omitempty"`
- MaxItems *int64 `json:"maxItems,omitempty"`
- MinItems *int64 `json:"minItems,omitempty"`
- UniqueItems bool `json:"uniqueItems,omitempty"`
- MultipleOf *float64 `json:"multipleOf,omitempty"`
- Enum []interface{} `json:"enum,omitempty"`
-}
-
// Items a limited subset of JSON-Schema's items object.
// It is used by parameter definitions that are not located in "body".
//
@@ -180,6 +164,12 @@ func (i *Items) AllowDuplicates() *Items {
return i
}
+// WithValidations is a fluent method to set Items validations
+func (i *Items) WithValidations(val CommonValidations) *Items {
+ i.SetValidations(SchemaValidations{CommonValidations: val})
+ return i
+}
+
// UnmarshalJSON hydrates this items instance with the data from JSON
func (i *Items) UnmarshalJSON(data []byte) error {
var validations CommonValidations
diff --git a/vendor/github.com/go-openapi/spec/license.go b/vendor/github.com/go-openapi/spec/license.go
index e1529b401c..b42f80368e 100644
--- a/vendor/github.com/go-openapi/spec/license.go
+++ b/vendor/github.com/go-openapi/spec/license.go
@@ -28,11 +28,13 @@ type License struct {
VendorExtensible
}
+// LicenseProps holds the properties of a License object
type LicenseProps struct {
Name string `json:"name,omitempty"`
URL string `json:"url,omitempty"`
}
+// UnmarshalJSON hydrates License from json
func (l *License) UnmarshalJSON(data []byte) error {
if err := json.Unmarshal(data, &l.LicenseProps); err != nil {
return err
@@ -40,6 +42,7 @@ func (l *License) UnmarshalJSON(data []byte) error {
return json.Unmarshal(data, &l.VendorExtensible)
}
+// MarshalJSON produces License as json
func (l License) MarshalJSON() ([]byte, error) {
b1, err := json.Marshal(l.LicenseProps)
if err != nil {
diff --git a/vendor/github.com/go-openapi/spec/normalizer.go b/vendor/github.com/go-openapi/spec/normalizer.go
index b8957e7c0c..e9010a7d03 100644
--- a/vendor/github.com/go-openapi/spec/normalizer.go
+++ b/vendor/github.com/go-openapi/spec/normalizer.go
@@ -20,9 +20,12 @@ import (
"os"
"path"
"path/filepath"
+ "runtime"
"strings"
)
+const windowsOS = "windows"
+
// normalize absolute path for cache.
// on Windows, drive letters should be converted to lower as scheme in net/url.URL
func normalizeAbsPath(path string) string {
@@ -71,27 +74,51 @@ func normalizePaths(refPath, base string) string {
return baseURL.String()
}
+// isRoot is a temporary hack to discern windows file ref for ref.IsRoot().
+// TODO: a more thorough change is needed to handle windows file refs.
+func isRoot(ref *Ref) bool {
+ if runtime.GOOS != windowsOS {
+ return ref.IsRoot()
+ }
+ return !filepath.IsAbs(ref.String())
+}
+
+// isAbs is a temporary hack to discern windows file ref for url IsAbs().
+// TODO: a more thorough change is needed to handle windows file refs.
+func isAbs(u *url.URL) bool {
+ if runtime.GOOS != windowsOS {
+ return u.IsAbs()
+ }
+ if len(u.Scheme) <= 1 {
+ // drive letter got caught as URI scheme
+ return false
+ }
+ return u.IsAbs()
+}
+
// denormalizePaths returns to simplest notation on file $ref,
// i.e. strips the absolute path and sets a path relative to the base path.
//
// This is currently used when we rewrite ref after a circular ref has been detected
func denormalizeFileRef(ref *Ref, relativeBase, originalRelativeBase string) *Ref {
- debugLog("denormalizeFileRef for: %s", ref.String())
+ debugLog("denormalizeFileRef for: %s (relative: %s, original: %s)", ref.String(),
+ relativeBase, originalRelativeBase)
- if ref.String() == "" || ref.IsRoot() || ref.HasFragmentOnly {
+ // log.Printf("denormalize: %s, IsRoot: %t,HasFragmentOnly: %t, HasFullURL: %t", ref.String(), ref.IsRoot(), ref.HasFragmentOnly, ref.HasFullURL)
+ if ref.String() == "" || isRoot(ref) || ref.HasFragmentOnly {
return ref
}
// strip relativeBase from URI
relativeBaseURL, _ := url.Parse(relativeBase)
relativeBaseURL.Fragment = ""
- if relativeBaseURL.IsAbs() && strings.HasPrefix(ref.String(), relativeBase) {
+ if isAbs(relativeBaseURL) && strings.HasPrefix(ref.String(), relativeBase) {
// this should work for absolute URI (e.g. http://...): we have an exact match, just trim prefix
r, _ := NewRef(strings.TrimPrefix(ref.String(), relativeBase))
return &r
}
- if relativeBaseURL.IsAbs() {
+ if isAbs(relativeBaseURL) {
// other absolute URL get unchanged (i.e. with a non-empty scheme)
return ref
}
@@ -111,7 +138,7 @@ func denormalizeFileRef(ref *Ref, relativeBase, originalRelativeBase string) *Re
// my normalized ref points to: /mypath/item.json#/target
// expected result: item.json#/target
parts := strings.Split(ref.String(), "#")
- relativePath, err := filepath.Rel(path.Dir(originalRelativeBaseURL.String()), parts[0])
+ relativePath, err := filepath.Rel(filepath.Dir(originalRelativeBaseURL.String()), parts[0])
if err != nil {
// there is no common ancestor (e.g. different drives on windows)
// leaves the ref unchanged
@@ -132,8 +159,6 @@ func normalizeFileRef(ref *Ref, relativeBase string) *Ref {
return &r
}
- debugLog("normalizing %s against %s", ref.String(), relativeBase)
-
s := normalizePaths(ref.String(), relativeBase)
r, _ := NewRef(s)
return &r
@@ -148,5 +173,5 @@ func absPath(fname string) (string, error) {
return fname, nil
}
wd, err := os.Getwd()
- return filepath.Join(wd, fname), err
+ return normalizeAbsPath(filepath.Join(wd, fname)), err
}
diff --git a/vendor/github.com/go-openapi/spec/operation.go b/vendor/github.com/go-openapi/spec/operation.go
index b1ebd59945..995ce6acb1 100644
--- a/vendor/github.com/go-openapi/spec/operation.go
+++ b/vendor/github.com/go-openapi/spec/operation.go
@@ -25,7 +25,6 @@ import (
)
func init() {
- //gob.Register(map[string][]interface{}{})
gob.Register(map[string]interface{}{})
gob.Register([]interface{}{})
}
diff --git a/vendor/github.com/go-openapi/spec/parameter.go b/vendor/github.com/go-openapi/spec/parameter.go
index cecdff5456..2b2b89b67b 100644
--- a/vendor/github.com/go-openapi/spec/parameter.go
+++ b/vendor/github.com/go-openapi/spec/parameter.go
@@ -39,8 +39,7 @@ func PathParam(name string) *Parameter {
// BodyParam creates a body parameter
func BodyParam(name string, schema *Schema) *Parameter {
- return &Parameter{ParamProps: ParamProps{Name: name, In: "body", Schema: schema},
- SimpleSchema: SimpleSchema{Type: "object"}}
+ return &Parameter{ParamProps: ParamProps{Name: name, In: "body", Schema: schema}}
}
// FormDataParam creates a body parameter
@@ -58,7 +57,7 @@ func FileParam(name string) *Parameter {
func SimpleArrayParam(name, tpe, fmt string) *Parameter {
return &Parameter{ParamProps: ParamProps{Name: name},
SimpleSchema: SimpleSchema{Type: jsonArray, CollectionFormat: "csv",
- Items: &Items{SimpleSchema: SimpleSchema{Type: "string", Format: fmt}}}}
+ Items: &Items{SimpleSchema: SimpleSchema{Type: tpe, Format: fmt}}}}
}
// ParamRef creates a parameter that's a json reference
@@ -278,6 +277,12 @@ func (p *Parameter) AllowDuplicates() *Parameter {
return p
}
+// WithValidations is a fluent method to set parameter validations
+func (p *Parameter) WithValidations(val CommonValidations) *Parameter {
+ p.SetValidations(SchemaValidations{CommonValidations: val})
+ return p
+}
+
// UnmarshalJSON hydrates this items instance with the data from JSON
func (p *Parameter) UnmarshalJSON(data []byte) error {
if err := json.Unmarshal(data, &p.CommonValidations); err != nil {
diff --git a/vendor/github.com/go-openapi/spec/properties.go b/vendor/github.com/go-openapi/spec/properties.go
new file mode 100644
index 0000000000..2af13787ab
--- /dev/null
+++ b/vendor/github.com/go-openapi/spec/properties.go
@@ -0,0 +1,91 @@
+package spec
+
+import (
+ "bytes"
+ "encoding/json"
+ "reflect"
+ "sort"
+)
+
+// OrderSchemaItem holds a named schema (e.g. from a property of an object)
+type OrderSchemaItem struct {
+ Name string
+ Schema
+}
+
+// OrderSchemaItems is a sortable slice of named schemas.
+// The ordering is defined by the x-order schema extension.
+type OrderSchemaItems []OrderSchemaItem
+
+// MarshalJSON produces a json object with keys defined by the name schemas
+// of the OrderSchemaItems slice, keeping the original order of the slice.
+func (items OrderSchemaItems) MarshalJSON() ([]byte, error) {
+ buf := bytes.NewBuffer(nil)
+ buf.WriteString("{")
+ for i := range items {
+ if i > 0 {
+ buf.WriteString(",")
+ }
+ buf.WriteString("\"")
+ buf.WriteString(items[i].Name)
+ buf.WriteString("\":")
+ bs, err := json.Marshal(&items[i].Schema)
+ if err != nil {
+ return nil, err
+ }
+ buf.Write(bs)
+ }
+ buf.WriteString("}")
+ return buf.Bytes(), nil
+}
+
+func (items OrderSchemaItems) Len() int { return len(items) }
+func (items OrderSchemaItems) Swap(i, j int) { items[i], items[j] = items[j], items[i] }
+func (items OrderSchemaItems) Less(i, j int) (ret bool) {
+ ii, oki := items[i].Extensions.GetString("x-order")
+ ij, okj := items[j].Extensions.GetString("x-order")
+ if oki {
+ if okj {
+ defer func() {
+ if err := recover(); err != nil {
+ defer func() {
+ if err = recover(); err != nil {
+ ret = items[i].Name < items[j].Name
+ }
+ }()
+ ret = reflect.ValueOf(ii).String() < reflect.ValueOf(ij).String()
+ }
+ }()
+ return reflect.ValueOf(ii).Int() < reflect.ValueOf(ij).Int()
+ }
+ return true
+ } else if okj {
+ return false
+ }
+ return items[i].Name < items[j].Name
+}
+
+// SchemaProperties is a map representing the properties of a Schema object.
+// It knows how to transform its keys into an ordered slice.
+type SchemaProperties map[string]Schema
+
+// ToOrderedSchemaItems transforms the map of properties into a sortable slice
+func (properties SchemaProperties) ToOrderedSchemaItems() OrderSchemaItems {
+ items := make(OrderSchemaItems, 0, len(properties))
+ for k, v := range properties {
+ items = append(items, OrderSchemaItem{
+ Name: k,
+ Schema: v,
+ })
+ }
+ sort.Sort(items)
+ return items
+}
+
+// MarshalJSON produces properties as json, keeping their order.
+func (properties SchemaProperties) MarshalJSON() ([]byte, error) {
+ if properties == nil {
+ return []byte("null"), nil
+ }
+ return json.Marshal(properties.ToOrderedSchemaItems())
+}
diff --git a/vendor/github.com/go-openapi/spec/ref.go b/vendor/github.com/go-openapi/spec/ref.go
index 1f31a9ead0..b0ef9bd9c9 100644
--- a/vendor/github.com/go-openapi/spec/ref.go
+++ b/vendor/github.com/go-openapi/spec/ref.go
@@ -48,7 +48,7 @@ type Ref struct {
// RemoteURI gets the remote uri part of the ref
func (r *Ref) RemoteURI() string {
if r.String() == "" {
- return r.String()
+ return ""
}
u := *r.GetURL()
@@ -68,7 +68,7 @@ func (r *Ref) IsValidURI(basepaths ...string) bool {
}
if r.HasFullURL {
- //#nosec
+ //nolint:noctx,gosec
rr, err := http.Get(v)
if err != nil {
return false
diff --git a/vendor/github.com/go-openapi/spec/resolver.go b/vendor/github.com/go-openapi/spec/resolver.go
new file mode 100644
index 0000000000..177292ad23
--- /dev/null
+++ b/vendor/github.com/go-openapi/spec/resolver.go
@@ -0,0 +1,128 @@
+package spec
+
+import (
+ "github.com/go-openapi/swag"
+)
+
+func resolveAnyWithBase(root interface{}, ref *Ref, result interface{}, options *ExpandOptions) error {
+ resolver := defaultSchemaLoader(root, options, nil, nil)
+
+ basePath := ""
+ if options != nil && options.RelativeBase != "" {
+ basePath, _ = absPath(options.RelativeBase)
+ }
+
+ if err := resolver.Resolve(ref, result, basePath); err != nil {
+ return err
+ }
+
+ return nil
+}
+
+// ResolveRefWithBase resolves a reference against a context root with preservation of base path
+func ResolveRefWithBase(root interface{}, ref *Ref, options *ExpandOptions) (*Schema, error) {
+ result := new(Schema)
+ err := resolveAnyWithBase(root, ref, result, options)
+ if err != nil {
+ return nil, err
+ }
+
+ return result, nil
+}
+
+// ResolveRef resolves a reference for a schema against a context root
+// ref is guaranteed to be in root (no need to go to external files)
+//
+// ResolveRef is ONLY called from the code generation module
+func ResolveRef(root interface{}, ref *Ref) (*Schema, error) {
+ res, _, err := ref.GetPointer().Get(root)
+ if err != nil {
+ return nil, err
+ }
+
+ switch sch := res.(type) {
+ case Schema:
+ return &sch, nil
+ case *Schema:
+ return sch, nil
+ case map[string]interface{}:
+ newSch := new(Schema)
+ if err = swag.DynamicJSONToStruct(sch, newSch); err != nil {
+ return nil, err
+ }
+ return newSch, nil
+ default:
+ return nil, ErrUnknownTypeForReference
+ }
+}
+
+// ResolveParameterWithBase resolves a parameter reference against a context root and base path
+func ResolveParameterWithBase(root interface{}, ref Ref, options *ExpandOptions) (*Parameter, error) {
+ result := new(Parameter)
+ err := resolveAnyWithBase(root, &ref, result, options)
+ if err != nil {
+ return nil, err
+ }
+
+ return result, nil
+}
+
+// ResolveParameter resolves a parameter reference against a context root
+func ResolveParameter(root interface{}, ref Ref) (*Parameter, error) {
+ return ResolveParameterWithBase(root, ref, nil)
+}
+
+// ResolveResponseWithBase resolves response a reference against a context root and base path
+func ResolveResponseWithBase(root interface{}, ref Ref, options *ExpandOptions) (*Response, error) {
+ result := new(Response)
+ err := resolveAnyWithBase(root, &ref, result, options)
+ if err != nil {
+ return nil, err
+ }
+
+ return result, nil
+}
+
+// ResolveResponse resolves response a reference against a context root
+func ResolveResponse(root interface{}, ref Ref) (*Response, error) {
+ return ResolveResponseWithBase(root, ref, nil)
+}
+
+// ResolvePathItemWithBase resolves response a path item against a context root and base path
+func ResolvePathItemWithBase(root interface{}, ref Ref, options *ExpandOptions) (*PathItem, error) {
+ result := new(PathItem)
+ err := resolveAnyWithBase(root, &ref, result, options)
+ if err != nil {
+ return nil, err
+ }
+
+ return result, nil
+}
+
+// ResolvePathItem resolves response a path item against a context root and base path
+//
+// Deprecated: use ResolvePathItemWithBase instead
+func ResolvePathItem(root interface{}, ref Ref, options *ExpandOptions) (*PathItem, error) {
+ return ResolvePathItemWithBase(root, ref, options)
+}
+
+// ResolveItemsWithBase resolves parameter items reference against a context root and base path.
+//
+// NOTE: stricly speaking, this construct is not supported by Swagger 2.0.
+// Similarly, $ref are forbidden in response headers.
+func ResolveItemsWithBase(root interface{}, ref Ref, options *ExpandOptions) (*Items, error) {
+ result := new(Items)
+ err := resolveAnyWithBase(root, &ref, result, options)
+ if err != nil {
+ return nil, err
+ }
+
+ return result, nil
+}
+
+// ResolveItems resolves parameter items reference against a context root and base path.
+//
+// Deprecated: use ResolveItemsWithBase instead
+func ResolveItems(root interface{}, ref Ref, options *ExpandOptions) (*Items, error) {
+ return ResolveItemsWithBase(root, ref, options)
+}
diff --git a/vendor/github.com/go-openapi/spec/response.go b/vendor/github.com/go-openapi/spec/response.go
index 27729c1d93..0340b60d84 100644
--- a/vendor/github.com/go-openapi/spec/response.go
+++ b/vendor/github.com/go-openapi/spec/response.go
@@ -23,7 +23,7 @@ import (
// ResponseProps properties specific to a response
type ResponseProps struct {
- Description string `json:"description,omitempty"`
+ Description string `json:"description"`
Schema *Schema `json:"schema,omitempty"`
Headers map[string]Header `json:"headers,omitempty"`
Examples map[string]interface{} `json:"examples,omitempty"`
@@ -63,10 +63,31 @@ func (r *Response) UnmarshalJSON(data []byte) error {
// MarshalJSON converts this items object to JSON
func (r Response) MarshalJSON() ([]byte, error) {
- b1, err := json.Marshal(r.ResponseProps)
+ var (
+ b1 []byte
+ err error
+ )
+
+ if r.Ref.String() == "" {
+ // when there is no $ref, empty description is rendered as an empty string
+ b1, err = json.Marshal(r.ResponseProps)
+ } else {
+ // when there is $ref inside the schema, description should be omitempty-ied
+ b1, err = json.Marshal(struct {
+ Description string `json:"description,omitempty"`
+ Schema *Schema `json:"schema,omitempty"`
+ Headers map[string]Header `json:"headers,omitempty"`
+ Examples map[string]interface{} `json:"examples,omitempty"`
+ }{
+ Description: r.ResponseProps.Description,
+ Schema: r.ResponseProps.Schema,
+ Examples: r.ResponseProps.Examples,
+ })
+ }
if err != nil {
return nil, err
}
+
b2, err := json.Marshal(r.Refable)
if err != nil {
return nil, err
diff --git a/vendor/github.com/go-openapi/spec/schema.go b/vendor/github.com/go-openapi/spec/schema.go
index 37858ece90..a8d0f737a7 100644
--- a/vendor/github.com/go-openapi/spec/schema.go
+++ b/vendor/github.com/go-openapi/spec/schema.go
@@ -158,41 +158,41 @@ func (r *SchemaURL) fromMap(v map[string]interface{}) error {
// SchemaProps describes a JSON schema (draft 4)
type SchemaProps struct {
- ID string `json:"id,omitempty"`
- Ref Ref `json:"-"`
- Schema SchemaURL `json:"-"`
- Description string `json:"description,omitempty"`
- Type StringOrArray `json:"type,omitempty"`
- Nullable bool `json:"nullable,omitempty"`
- Format string `json:"format,omitempty"`
- Title string `json:"title,omitempty"`
- Default interface{} `json:"default,omitempty"`
- Maximum *float64 `json:"maximum,omitempty"`
- ExclusiveMaximum bool `json:"exclusiveMaximum,omitempty"`
- Minimum *float64 `json:"minimum,omitempty"`
- ExclusiveMinimum bool `json:"exclusiveMinimum,omitempty"`
- MaxLength *int64 `json:"maxLength,omitempty"`
- MinLength *int64 `json:"minLength,omitempty"`
- Pattern string `json:"pattern,omitempty"`
- MaxItems *int64 `json:"maxItems,omitempty"`
- MinItems *int64 `json:"minItems,omitempty"`
- UniqueItems bool `json:"uniqueItems,omitempty"`
- MultipleOf *float64 `json:"multipleOf,omitempty"`
- Enum []interface{} `json:"enum,omitempty"`
- MaxProperties *int64 `json:"maxProperties,omitempty"`
- MinProperties *int64 `json:"minProperties,omitempty"`
- Required []string `json:"required,omitempty"`
- Items *SchemaOrArray `json:"items,omitempty"`
- AllOf []Schema `json:"allOf,omitempty"`
- OneOf []Schema `json:"oneOf,omitempty"`
- AnyOf []Schema `json:"anyOf,omitempty"`
- Not *Schema `json:"not,omitempty"`
- Properties map[string]Schema `json:"properties,omitempty"`
- AdditionalProperties *SchemaOrBool `json:"additionalProperties,omitempty"`
- PatternProperties map[string]Schema `json:"patternProperties,omitempty"`
- Dependencies Dependencies `json:"dependencies,omitempty"`
- AdditionalItems *SchemaOrBool `json:"additionalItems,omitempty"`
- Definitions Definitions `json:"definitions,omitempty"`
+ ID string `json:"id,omitempty"`
+ Ref Ref `json:"-"`
+ Schema SchemaURL `json:"-"`
+ Description string `json:"description,omitempty"`
+ Type StringOrArray `json:"type,omitempty"`
+ Nullable bool `json:"nullable,omitempty"`
+ Format string `json:"format,omitempty"`
+ Title string `json:"title,omitempty"`
+ Default interface{} `json:"default,omitempty"`
+ Maximum *float64 `json:"maximum,omitempty"`
+ ExclusiveMaximum bool `json:"exclusiveMaximum,omitempty"`
+ Minimum *float64 `json:"minimum,omitempty"`
+ ExclusiveMinimum bool `json:"exclusiveMinimum,omitempty"`
+ MaxLength *int64 `json:"maxLength,omitempty"`
+ MinLength *int64 `json:"minLength,omitempty"`
+ Pattern string `json:"pattern,omitempty"`
+ MaxItems *int64 `json:"maxItems,omitempty"`
+ MinItems *int64 `json:"minItems,omitempty"`
+ UniqueItems bool `json:"uniqueItems,omitempty"`
+ MultipleOf *float64 `json:"multipleOf,omitempty"`
+ Enum []interface{} `json:"enum,omitempty"`
+ MaxProperties *int64 `json:"maxProperties,omitempty"`
+ MinProperties *int64 `json:"minProperties,omitempty"`
+ Required []string `json:"required,omitempty"`
+ Items *SchemaOrArray `json:"items,omitempty"`
+ AllOf []Schema `json:"allOf,omitempty"`
+ OneOf []Schema `json:"oneOf,omitempty"`
+ AnyOf []Schema `json:"anyOf,omitempty"`
+ Not *Schema `json:"not,omitempty"`
+ Properties SchemaProperties `json:"properties,omitempty"`
+ AdditionalProperties *SchemaOrBool `json:"additionalProperties,omitempty"`
+ PatternProperties SchemaProperties `json:"patternProperties,omitempty"`
+ Dependencies Dependencies `json:"dependencies,omitempty"`
+ AdditionalItems *SchemaOrBool `json:"additionalItems,omitempty"`
+ Definitions Definitions `json:"definitions,omitempty"`
}
// SwaggerSchemaProps are additional properties supported by swagger schemas, but not JSON-schema (draft 4)
@@ -513,6 +513,56 @@ func (s *Schema) AsUnwrappedXML() *Schema {
return s
}
+// SetValidations defines all schema validations.
+//
+// NOTE: Required, ReadOnly, AllOf, AnyOf, OneOf and Not are not considered.
+func (s *Schema) SetValidations(val SchemaValidations) {
+ s.Maximum = val.Maximum
+ s.ExclusiveMaximum = val.ExclusiveMaximum
+ s.Minimum = val.Minimum
+ s.ExclusiveMinimum = val.ExclusiveMinimum
+ s.MaxLength = val.MaxLength
+ s.MinLength = val.MinLength
+ s.Pattern = val.Pattern
+ s.MaxItems = val.MaxItems
+ s.MinItems = val.MinItems
+ s.UniqueItems = val.UniqueItems
+ s.MultipleOf = val.MultipleOf
+ s.Enum = val.Enum
+ s.MinProperties = val.MinProperties
+ s.MaxProperties = val.MaxProperties
+ s.PatternProperties = val.PatternProperties
+}
+
+// WithValidations is a fluent method to set schema validations
+func (s *Schema) WithValidations(val SchemaValidations) *Schema {
+ s.SetValidations(val)
+ return s
+}
+
+// Validations returns a clone of the validations for this schema
+func (s Schema) Validations() SchemaValidations {
+ return SchemaValidations{
+ CommonValidations: CommonValidations{
+ Maximum: s.Maximum,
+ ExclusiveMaximum: s.ExclusiveMaximum,
+ Minimum: s.Minimum,
+ ExclusiveMinimum: s.ExclusiveMinimum,
+ MaxLength: s.MaxLength,
+ MinLength: s.MinLength,
+ Pattern: s.Pattern,
+ MaxItems: s.MaxItems,
+ MinItems: s.MinItems,
+ UniqueItems: s.UniqueItems,
+ MultipleOf: s.MultipleOf,
+ Enum: s.Enum,
+ },
+ MinProperties: s.MinProperties,
+ MaxProperties: s.MaxProperties,
+ PatternProperties: s.PatternProperties,
+ }
+}
+
// MarshalJSON marshal this to JSON
func (s Schema) MarshalJSON() ([]byte, error) {
b1, err := json.Marshal(s.SchemaProps)
diff --git a/vendor/github.com/go-openapi/spec/schema_loader.go b/vendor/github.com/go-openapi/spec/schema_loader.go
index 02d9966c1a..9ea78b5d52 100644
--- a/vendor/github.com/go-openapi/spec/schema_loader.go
+++ b/vendor/github.com/go-openapi/spec/schema_loader.go
@@ -25,7 +25,14 @@ import (
"github.com/go-openapi/swag"
)
-// PathLoader function to use when loading remote refs
+// PathLoader is a function to use when loading remote refs.
+//
+// This is a package level default. It may be overridden or bypassed by
+// specifying the loader in ExpandOptions.
+//
+// NOTE: if you are using the go-openapi/loads package, it will override
+// this value with its own default (a loader to retrieve YAML documents as
+// well as JSON ones).
var PathLoader func(string) (json.RawMessage, error)
func init() {
@@ -41,19 +48,30 @@ func init() {
// resolverContext allows to share a context during spec processing.
// At the moment, it just holds the index of circular references found.
type resolverContext struct {
- // circulars holds all visited circular references, which allows shortcuts.
- // NOTE: this is not just a performance improvement: it is required to figure out
- // circular references which participate several cycles.
+ // circulars holds all visited circular references, to shortcircuit $ref resolution.
+ //
// This structure is privately instantiated and needs not be locked against
// concurrent access, unless we chose to implement a parallel spec walking.
circulars map[string]bool
basePath string
+ loadDoc func(string) (json.RawMessage, error)
}
-func newResolverContext(originalBasePath string) *resolverContext {
+func newResolverContext(expandOptions *ExpandOptions) *resolverContext {
+ absBase, _ := absPath(expandOptions.RelativeBase)
+
+ // path loader may be overridden from option
+ var loader func(string) (json.RawMessage, error)
+ if expandOptions.PathLoader == nil {
+ loader = PathLoader
+ } else {
+ loader = expandOptions.PathLoader
+ }
+
return &resolverContext{
circulars: make(map[string]bool),
- basePath: originalBasePath, // keep the root base path in context
+ basePath: absBase, // keep the root base path in context
+ loadDoc: loader,
}
}
@@ -62,21 +80,20 @@ type schemaLoader struct {
options *ExpandOptions
cache ResolutionCache
context *resolverContext
- loadDoc func(string) (json.RawMessage, error)
}
-func (r *schemaLoader) transitiveResolver(basePath string, ref Ref) (*schemaLoader, error) {
+func (r *schemaLoader) transitiveResolver(basePath string, ref Ref) *schemaLoader {
if ref.IsRoot() || ref.HasFragmentOnly {
- return r, nil
+ return r
}
- baseRef, _ := NewRef(basePath)
+ baseRef := MustCreateRef(basePath)
currentRef := normalizeFileRef(&ref, basePath)
if strings.HasPrefix(currentRef.String(), baseRef.String()) {
- return r, nil
+ return r
}
- // Set a new root to resolve against
+ // set a new root against which to resolve
rootURL := currentRef.GetURL()
rootURL.Fragment = ""
root, _ := r.cache.Get(rootURL.String())
@@ -85,16 +102,13 @@ func (r *schemaLoader) transitiveResolver(basePath string, ref Ref) (*schemaLoad
// traversing multiple documents
newOptions := r.options
newOptions.RelativeBase = rootURL.String()
- debugLog("setting new root: %s", newOptions.RelativeBase)
return defaultSchemaLoader(root, newOptions, r.cache, r.context)
}
func (r *schemaLoader) updateBasePath(transitive *schemaLoader, basePath string) string {
if transitive != r {
- debugLog("got a new resolver")
if transitive.options != nil && transitive.options.RelativeBase != "" {
basePath, _ = absPath(transitive.options.RelativeBase)
- debugLog("new basePath = %s", basePath)
}
}
return basePath
@@ -103,17 +117,19 @@ func (r *schemaLoader) updateBasePath(transitive *schemaLoader, basePath string)
func (r *schemaLoader) resolveRef(ref *Ref, target interface{}, basePath string) error {
tgt := reflect.ValueOf(target)
if tgt.Kind() != reflect.Ptr {
- return fmt.Errorf("resolve ref: target needs to be a pointer")
+ return ErrResolveRefNeedsAPointer
}
- refURL := ref.GetURL()
- if refURL == nil {
+ if ref.GetURL() == nil {
return nil
}
- var res interface{}
- var data interface{}
- var err error
+ var (
+ res interface{}
+ data interface{}
+ err error
+ )
+
// Resolve against the root if it isn't nil, and if ref is pointing at the root, or has a fragment only which means
// it is pointing somewhere in the root.
root := r.root
@@ -122,12 +138,11 @@ func (r *schemaLoader) resolveRef(ref *Ref, target interface{}, basePath string)
root, _, _, _ = r.load(baseRef.GetURL())
}
}
+
if (ref.IsRoot() || ref.HasFragmentOnly) && root != nil {
data = root
} else {
baseRef := normalizeFileRef(ref, basePath)
- debugLog("current ref is: %s", ref.String())
- debugLog("current ref normalized file: %s", baseRef.String())
data, _, _, err = r.load(baseRef.GetURL())
if err != nil {
return err
@@ -150,27 +165,29 @@ func (r *schemaLoader) load(refURL *url.URL) (interface{}, url.URL, bool, error)
toFetch.Fragment = ""
var err error
- path := toFetch.String()
- if path == rootBase {
- path, err = absPath(rootBase)
+ pth := toFetch.String()
+ if pth == rootBase {
+ pth, err = absPath(rootBase)
if err != nil {
return nil, url.URL{}, false, err
}
}
- normalized := normalizeAbsPath(path)
+ normalized := normalizeAbsPath(pth)
data, fromCache := r.cache.Get(normalized)
if !fromCache {
- b, err := r.loadDoc(normalized)
+ b, err := r.context.loadDoc(normalized)
if err != nil {
- debugLog("unable to load the document: %v", err)
- return nil, url.URL{}, false, err
+ return nil, url.URL{}, false, fmt.Errorf("%s [%s]: %w", pth, normalized, err)
}
- if err := json.Unmarshal(b, &data); err != nil {
+ var doc interface{}
+ if err := json.Unmarshal(b, &doc); err != nil {
return nil, url.URL{}, false, err
}
- r.cache.Set(normalized, data)
+ r.cache.Set(normalized, doc)
+
+ return doc, toFetch, fromCache, nil
}
return data, toFetch, fromCache, nil
@@ -185,17 +202,20 @@ func (r *schemaLoader) isCircular(ref *Ref, basePath string, parentRefs ...strin
foundCycle = true
return
}
- foundCycle = swag.ContainsStringsCI(parentRefs, normalizedRef)
+ foundCycle = swag.ContainsStringsCI(parentRefs, normalizedRef) // TODO(fred): normalize windows url and remove CI equality
if foundCycle {
r.context.circulars[normalizedRef] = true
}
return
}
-// Resolve resolves a reference against basePath and stores the result in target
-// Resolve is not in charge of following references, it only resolves ref by following its URL
-// if the schema that ref is referring to has more refs in it. Resolve doesn't resolve them
-// if basePath is an empty string, ref is resolved against the root schema stored in the schemaLoader struct
+// Resolve resolves a reference against basePath and stores the result in target.
+//
+// Resolve is not in charge of following references: it only resolves ref by following its URL.
+//
+// If the schema the ref is referring to holds nested refs, Resolve doesn't resolve them.
+//
+// If basePath is an empty string, ref is resolved against the root schema stored in the schemaLoader struct
func (r *schemaLoader) Resolve(ref *Ref, target interface{}, basePath string) error {
return r.resolveRef(ref, target, basePath)
}
@@ -212,30 +232,32 @@ func (r *schemaLoader) deref(input interface{}, parentRefs []string, basePath st
case *PathItem:
ref = &refable.Ref
default:
- return fmt.Errorf("deref: unsupported type %T", input)
+ return fmt.Errorf("unsupported type: %T: %w", input, ErrDerefUnsupportedType)
}
curRef := ref.String()
- if curRef != "" {
- normalizedRef := normalizeFileRef(ref, basePath)
- normalizedBasePath := normalizedRef.RemoteURI()
+ if curRef == "" {
+ return nil
+ }
- if r.isCircular(normalizedRef, basePath, parentRefs...) {
- return nil
- }
+ normalizedRef := normalizeFileRef(ref, basePath)
+ normalizedBasePath := normalizedRef.RemoteURI()
- if err := r.resolveRef(ref, input, basePath); r.shouldStopOnError(err) {
- return err
- }
+ if r.isCircular(normalizedRef, basePath, parentRefs...) {
+ return nil
+ }
- // NOTE(fredbi): removed basePath check => needs more testing
- if ref.String() != "" && ref.String() != curRef {
- parentRefs = append(parentRefs, normalizedRef.String())
- return r.deref(input, parentRefs, normalizedBasePath)
- }
+ if err := r.resolveRef(ref, input, basePath); r.shouldStopOnError(err) {
+ return err
+ }
+
+ if ref.String() == "" || ref.String() == curRef {
+ // done with rereferencing
+ return nil
}
- return nil
+ parentRefs = append(parentRefs, normalizedRef.String())
+ return r.deref(input, parentRefs, normalizedBasePath)
}
func (r *schemaLoader) shouldStopOnError(err error) bool {
@@ -250,30 +272,48 @@ func (r *schemaLoader) shouldStopOnError(err error) bool {
return false
}
+func (r *schemaLoader) setSchemaID(target interface{}, id, basePath string) (string, string) {
+ debugLog("schema has ID: %s", id)
+
+ // handling the case when id is a folder
+ // remember that basePath has to point to a file
+ var refPath string
+ if strings.HasSuffix(id, "/") {
+ // path.Clean here would not work correctly if there is a scheme (e.g. https://...)
+ refPath = fmt.Sprintf("%s%s", id, "placeholder.json")
+ } else {
+ refPath = id
+ }
+
+ // updates the current base path
+ // * important: ID can be a relative path
+ // * registers target to be fetchable from the new base proposed by this id
+ newBasePath := normalizePaths(refPath, basePath)
+
+ // store found IDs for possible future reuse in $ref
+ r.cache.Set(newBasePath, target)
+
+ return newBasePath, refPath
+}
+
func defaultSchemaLoader(
root interface{},
expandOptions *ExpandOptions,
cache ResolutionCache,
- context *resolverContext) (*schemaLoader, error) {
+ context *resolverContext) *schemaLoader {
- if cache == nil {
- cache = resCache
- }
if expandOptions == nil {
expandOptions = &ExpandOptions{}
}
- absBase, _ := absPath(expandOptions.RelativeBase)
+
if context == nil {
- context = newResolverContext(absBase)
+ context = newResolverContext(expandOptions)
}
+
return &schemaLoader{
root: root,
options: expandOptions,
- cache: cache,
+ cache: cacheOrDefault(cache),
context: context,
- loadDoc: func(path string) (json.RawMessage, error) {
- debugLog("fetching document at %q", path)
- return PathLoader(path)
- },
- }, nil
+ }
}
diff --git a/vendor/github.com/go-openapi/spec/security_scheme.go b/vendor/github.com/go-openapi/spec/security_scheme.go
index fe353842a6..f7176ef6ae 100644
--- a/vendor/github.com/go-openapi/spec/security_scheme.go
+++ b/vendor/github.com/go-openapi/spec/security_scheme.go
@@ -82,12 +82,12 @@ func OAuth2AccessToken(authorizationURL, tokenURL string) *SecurityScheme {
type SecuritySchemeProps struct {
Description string `json:"description,omitempty"`
Type string `json:"type"`
- Name string `json:"name,omitempty"` // api key
- In string `json:"in,omitempty"` // api key
- Flow string `json:"flow,omitempty"` // oauth2
- AuthorizationURL string `json:"authorizationUrl,omitempty"` // oauth2
- TokenURL string `json:"tokenUrl,omitempty"` // oauth2
- Scopes map[string]string `json:"scopes,omitempty"` // oauth2
+ Name string `json:"name,omitempty"` // api key
+ In string `json:"in,omitempty"` // api key
+ Flow string `json:"flow,omitempty"` // oauth2
+ AuthorizationURL string `json:"authorizationUrl"` // oauth2
+ TokenURL string `json:"tokenUrl,omitempty"` // oauth2
+ Scopes map[string]string `json:"scopes,omitempty"` // oauth2
}
// AddScope adds a scope to this security scheme
@@ -120,10 +120,40 @@ func (s SecurityScheme) JSONLookup(token string) (interface{}, error) {
// MarshalJSON marshal this to JSON
func (s SecurityScheme) MarshalJSON() ([]byte, error) {
- b1, err := json.Marshal(s.SecuritySchemeProps)
+ var (
+ b1 []byte
+ err error
+ )
+
+ if s.Type == oauth2 {
+ // when oauth2, empty AuthorizationURL is added as empty string
+ b1, err = json.Marshal(s.SecuritySchemeProps)
+ } else {
+ // when not oauth2, empty AuthorizationURL should be omitted
+ b1, err = json.Marshal(struct {
+ Description string `json:"description,omitempty"`
+ Type string `json:"type"`
+ Name string `json:"name,omitempty"` // api key
+ In string `json:"in,omitempty"` // api key
+ Flow string `json:"flow,omitempty"` // oauth2
+ AuthorizationURL string `json:"authorizationUrl,omitempty"` // oauth2
+ TokenURL string `json:"tokenUrl,omitempty"` // oauth2
+ Scopes map[string]string `json:"scopes,omitempty"` // oauth2
+ }{
+ Description: s.Description,
+ Type: s.Type,
+ Name: s.Name,
+ In: s.In,
+ Flow: s.Flow,
+ AuthorizationURL: s.AuthorizationURL,
+ TokenURL: s.TokenURL,
+ Scopes: s.Scopes,
+ })
+ }
if err != nil {
return nil, err
}
+
b2, err := json.Marshal(s.VendorExtensible)
if err != nil {
return nil, err
diff --git a/vendor/github.com/go-openapi/spec/spec.go b/vendor/github.com/go-openapi/spec/spec.go
index 0bb045bc06..7d38b6e625 100644
--- a/vendor/github.com/go-openapi/spec/spec.go
+++ b/vendor/github.com/go-openapi/spec/spec.go
@@ -14,7 +14,9 @@
package spec
-import "encoding/json"
+import (
+ "encoding/json"
+)
//go:generate curl -L --progress -o ./schemas/v2/schema.json http://swagger.io/v2/schema.json
//go:generate curl -L --progress -o ./schemas/jsonschema-draft-04.json http://json-schema.org/draft-04/schema
@@ -28,16 +30,6 @@ const (
JSONSchemaURL = "http://json-schema.org/draft-04/schema#"
)
-var (
- jsonSchema *Schema
- swaggerSchema *Schema
-)
-
-func init() {
- jsonSchema = MustLoadJSONSchemaDraft04()
- swaggerSchema = MustLoadSwagger20Schema()
-}
-
// MustLoadJSONSchemaDraft04 panics when Swagger20Schema returns an error
func MustLoadJSONSchemaDraft04() *Schema {
d, e := JSONSchemaDraft04()
diff --git a/vendor/github.com/go-openapi/spec/validations.go b/vendor/github.com/go-openapi/spec/validations.go
new file mode 100644
index 0000000000..6360a8ea77
--- /dev/null
+++ b/vendor/github.com/go-openapi/spec/validations.go
@@ -0,0 +1,215 @@
+package spec
+
+// CommonValidations describe common JSON-schema validations
+type CommonValidations struct {
+ Maximum *float64 `json:"maximum,omitempty"`
+ ExclusiveMaximum bool `json:"exclusiveMaximum,omitempty"`
+ Minimum *float64 `json:"minimum,omitempty"`
+ ExclusiveMinimum bool `json:"exclusiveMinimum,omitempty"`
+ MaxLength *int64 `json:"maxLength,omitempty"`
+ MinLength *int64 `json:"minLength,omitempty"`
+ Pattern string `json:"pattern,omitempty"`
+ MaxItems *int64 `json:"maxItems,omitempty"`
+ MinItems *int64 `json:"minItems,omitempty"`
+ UniqueItems bool `json:"uniqueItems,omitempty"`
+ MultipleOf *float64 `json:"multipleOf,omitempty"`
+ Enum []interface{} `json:"enum,omitempty"`
+}
+
+// SetValidations defines all validations for a simple schema.
+//
+// NOTE: the input is the larger set of validations available for schemas.
+// For simple schemas, MinProperties and MaxProperties are ignored.
+func (v *CommonValidations) SetValidations(val SchemaValidations) {
+ v.Maximum = val.Maximum
+ v.ExclusiveMaximum = val.ExclusiveMaximum
+ v.Minimum = val.Minimum
+ v.ExclusiveMinimum = val.ExclusiveMinimum
+ v.MaxLength = val.MaxLength
+ v.MinLength = val.MinLength
+ v.Pattern = val.Pattern
+ v.MaxItems = val.MaxItems
+ v.MinItems = val.MinItems
+ v.UniqueItems = val.UniqueItems
+ v.MultipleOf = val.MultipleOf
+ v.Enum = val.Enum
+}
+
+type clearedValidation struct {
+ Validation string
+ Value interface{}
+}
+
+type clearedValidations []clearedValidation
+
+func (c clearedValidations) apply(cbs []func(string, interface{})) {
+ for _, cb := range cbs {
+ for _, cleared := range c {
+ cb(cleared.Validation, cleared.Value)
+ }
+ }
+}
+
+// ClearNumberValidations clears all number validations.
+//
+// Some callbacks may be set by the caller to capture changed values.
+func (v *CommonValidations) ClearNumberValidations(cbs ...func(string, interface{})) {
+ done := make(clearedValidations, 0, 5)
+ defer func() {
+ done.apply(cbs)
+ }()
+
+ if v.Minimum != nil {
+ done = append(done, clearedValidation{Validation: "minimum", Value: v.Minimum})
+ v.Minimum = nil
+ }
+ if v.Maximum != nil {
+ done = append(done, clearedValidation{Validation: "maximum", Value: v.Maximum})
+ v.Maximum = nil
+ }
+ if v.ExclusiveMaximum {
+ done = append(done, clearedValidation{Validation: "exclusiveMaximum", Value: v.ExclusiveMaximum})
+ v.ExclusiveMaximum = false
+ }
+ if v.ExclusiveMinimum {
+ done = append(done, clearedValidation{Validation: "exclusiveMinimum", Value: v.ExclusiveMinimum})
+ v.ExclusiveMinimum = false
+ }
+ if v.MultipleOf != nil {
+ done = append(done, clearedValidation{Validation: "multipleOf", Value: v.MultipleOf})
+ v.MultipleOf = nil
+ }
+}
+
+// ClearStringValidations clears all string validations.
+//
+// Some callbacks may be set by the caller to capture changed values.
+func (v *CommonValidations) ClearStringValidations(cbs ...func(string, interface{})) {
+ done := make(clearedValidations, 0, 3)
+ defer func() {
+ done.apply(cbs)
+ }()
+
+ if v.Pattern != "" {
+ done = append(done, clearedValidation{Validation: "pattern", Value: v.Pattern})
+ v.Pattern = ""
+ }
+ if v.MinLength != nil {
+ done = append(done, clearedValidation{Validation: "minLength", Value: v.MinLength})
+ v.MinLength = nil
+ }
+ if v.MaxLength != nil {
+ done = append(done, clearedValidation{Validation: "maxLength", Value: v.MaxLength})
+ v.MaxLength = nil
+ }
+}
+
+// ClearArrayValidations clears all array validations.
+//
+// Some callbacks may be set by the caller to capture changed values.
+func (v *CommonValidations) ClearArrayValidations(cbs ...func(string, interface{})) {
+ done := make(clearedValidations, 0, 3)
+ defer func() {
+ done.apply(cbs)
+ }()
+
+ if v.MaxItems != nil {
+ done = append(done, clearedValidation{Validation: "maxItems", Value: v.MaxItems})
+ v.MaxItems = nil
+ }
+ if v.MinItems != nil {
+ done = append(done, clearedValidation{Validation: "minItems", Value: v.MinItems})
+ v.MinItems = nil
+ }
+ if v.UniqueItems {
+ done = append(done, clearedValidation{Validation: "uniqueItems", Value: v.UniqueItems})
+ v.UniqueItems = false
+ }
+}
+
+// Validations returns a clone of the validations for a simple schema.
+//
+// NOTE: in the context of simple schema objects, MinProperties, MaxProperties
+// and PatternProperties remain unset.
+func (v CommonValidations) Validations() SchemaValidations {
+ return SchemaValidations{
+ CommonValidations: v,
+ }
+}
+
+// HasNumberValidations indicates if the validations are for numbers or integers
+func (v CommonValidations) HasNumberValidations() bool {
+ return v.Maximum != nil || v.Minimum != nil || v.MultipleOf != nil
+}
+
+// HasStringValidations indicates if the validations are for strings
+func (v CommonValidations) HasStringValidations() bool {
+ return v.MaxLength != nil || v.MinLength != nil || v.Pattern != ""
+}
+
+// HasArrayValidations indicates if the validations are for arrays
+func (v CommonValidations) HasArrayValidations() bool {
+ return v.MaxItems != nil || v.MinItems != nil || v.UniqueItems
+}
+
+// HasEnum indicates if the validation includes some enum constraint
+func (v CommonValidations) HasEnum() bool {
+ return len(v.Enum) > 0
+}
+
+// SchemaValidations describes the validation properties of a schema
+//
+// NOTE: at this moment, this is not embedded in SchemaProps because this would induce a breaking change
+// in the exported members: all initializers using litterals would fail.
+type SchemaValidations struct {
+ CommonValidations
+
+ PatternProperties SchemaProperties `json:"patternProperties,omitempty"`
+ MaxProperties *int64 `json:"maxProperties,omitempty"`
+ MinProperties *int64 `json:"minProperties,omitempty"`
+}
+
+// HasObjectValidations indicates if the validations are for objects
+func (v SchemaValidations) HasObjectValidations() bool {
+ return v.MaxProperties != nil || v.MinProperties != nil || v.PatternProperties != nil
+}
+
+// SetValidations for schema validations
+func (v *SchemaValidations) SetValidations(val SchemaValidations) {
+ v.CommonValidations.SetValidations(val)
+ v.PatternProperties = val.PatternProperties
+ v.MaxProperties = val.MaxProperties
+ v.MinProperties = val.MinProperties
+}
+
+// Validations for a schema
+func (v SchemaValidations) Validations() SchemaValidations {
+ val := v.CommonValidations.Validations()
+ val.PatternProperties = v.PatternProperties
+ val.MinProperties = v.MinProperties
+ val.MaxProperties = v.MaxProperties
+ return val
+}
+
+// ClearObjectValidations returns a clone of the validations with all object validations cleared.
+//
+// Some callbacks may be set by the caller to capture changed values.
+func (v *SchemaValidations) ClearObjectValidations(cbs ...func(string, interface{})) {
+ done := make(clearedValidations, 0, 3)
+ defer func() {
+ done.apply(cbs)
+ }()
+
+ if v.MaxProperties != nil {
+ done = append(done, clearedValidation{Validation: "maxProperties", Value: v.MaxProperties})
+ v.MaxProperties = nil
+ }
+ if v.MinProperties != nil {
+ done = append(done, clearedValidation{Validation: "minProperties", Value: v.MinProperties})
+ v.MinProperties = nil
+ }
+ if v.PatternProperties != nil {
+ done = append(done, clearedValidation{Validation: "patternProperties", Value: v.PatternProperties})
+ v.PatternProperties = nil
+ }
+}