Skip to content

Extensible schema models #211

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Mar 4, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions openapi_core/schema/components/factories.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from openapi_core.compat import lru_cache
from openapi_core.schema.components.models import Components
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.schemas.generators import SchemasGenerator
from openapi_core.schema.security_schemes.generators import (
SecuritySchemesGenerator,
Expand All @@ -21,6 +22,8 @@ def create(self, components_spec):
request_bodies_spec = components_deref.get('requestBodies', {})
security_schemes_spec = components_deref.get('securitySchemes', {})

extensions = self.extensions_generator.generate(components_deref)

schemas = self.schemas_generator.generate(schemas_spec)
responses = self._generate_response(responses_spec)
parameters = self._generate_parameters(parameters_spec)
Expand All @@ -30,13 +33,19 @@ def create(self, components_spec):
return Components(
schemas=list(schemas), responses=responses, parameters=parameters,
request_bodies=request_bodies, security_schemes=security_schemes,
extensions=extensions,
)

@property
@lru_cache()
def schemas_generator(self):
return SchemasGenerator(self.dereferencer, self.schemas_registry)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)

def _generate_response(self, responses_spec):
return responses_spec

Expand Down
4 changes: 3 additions & 1 deletion openapi_core/schema/components/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,13 @@ class Components(object):

def __init__(
self, schemas=None, responses=None, parameters=None,
request_bodies=None, security_schemes=None):
request_bodies=None, security_schemes=None, extensions=None):
self.schemas = schemas and dict(schemas) or {}
self.responses = responses and dict(responses) or {}
self.parameters = parameters and dict(parameters) or {}
self.request_bodies = request_bodies and dict(request_bodies) or {}
self.security_schemes = (
security_schemes and dict(security_schemes) or {}
)

self.extensions = extensions and dict(extensions) or {}
12 changes: 11 additions & 1 deletion openapi_core/schema/contacts/factories.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
"""OpenAPI core contacts factories module"""
from openapi_core.compat import lru_cache
from openapi_core.schema.contacts.models import Contact
from openapi_core.schema.extensions.generators import ExtensionsGenerator


class ContactFactory(object):
Expand All @@ -12,4 +14,12 @@ def create(self, contact_spec):
name = contact_deref.get('name')
url = contact_deref.get('url')
email = contact_deref.get('email')
return Contact(name=name, url=url, email=email)

extensions = self.extensions_generator.generate(contact_deref)

return Contact(name=name, url=url, email=email, extensions=extensions)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/contacts/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@

class Contact(object):

def __init__(self, name=None, url=None, email=None):
def __init__(self, name=None, url=None, email=None, extensions=None):
self.name = name
self.url = url
self.email = email

self.extensions = extensions and dict(extensions) or {}
14 changes: 13 additions & 1 deletion openapi_core/schema/external_docs/factories.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
"""OpenAPI core external docs factories module"""
from openapi_core.compat import lru_cache
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.external_docs.models import ExternalDocumentation


Expand All @@ -11,4 +13,14 @@ def create(self, external_doc_spec):
url = external_doc_spec['url']
description = external_doc_spec.get('description')

return ExternalDocumentation(url, description=description)
extensions = self.extensions_generator.generate(external_doc_spec)

return ExternalDocumentation(
url,
description=description, extensions=extensions,
)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/external_docs/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
class ExternalDocumentation(object):
"""Represents an OpenAPI External Documentation."""

def __init__(self, url, description=None):
def __init__(self, url, description=None, extensions=None):
self.url = url
self.description = description

self.extensions = extensions and dict(extensions) or {}
10 changes: 9 additions & 1 deletion openapi_core/schema/infos/factories.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
"""OpenAPI core infos factories module"""
from openapi_core.compat import lru_cache
from openapi_core.schema.contacts.factories import ContactFactory
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.infos.models import Info
from openapi_core.schema.licenses.factories import LicenseFactory

Expand All @@ -17,6 +18,8 @@ def create(self, info_spec):
description = info_deref.get('description')
terms_of_service = info_deref.get('termsOfService')

extensions = self.extensions_generator.generate(info_deref)

contact = None
if 'contact' in info_deref:
contact_spec = info_deref.get('contact')
Expand All @@ -30,7 +33,7 @@ def create(self, info_spec):
return Info(
title, version,
description=description, terms_of_service=terms_of_service,
contact=contact, license=license,
contact=contact, license=license, extensions=extensions,
)

@property
Expand All @@ -42,3 +45,8 @@ def contact_factory(self):
@lru_cache()
def license_factory(self):
return LicenseFactory(self.dereferencer)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/infos/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,13 @@ class Info(object):

def __init__(
self, title, version, description=None, terms_of_service=None,
contact=None, license=None,
contact=None, license=None, extensions=None,
):
self.title = title
self.version = version
self.description = description
self.terms_of_service = terms_of_service
self.contact = contact
self.license = license

self.extensions = extensions and dict(extensions) or {}
12 changes: 11 additions & 1 deletion openapi_core/schema/licenses/factories.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
"""OpenAPI core licenses factories module"""
from openapi_core.compat import lru_cache
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.licenses.models import License


Expand All @@ -11,4 +13,12 @@ def create(self, license_spec):
license_deref = self.dereferencer.dereference(license_spec)
name = license_deref['name']
url = license_deref.get('url')
return License(name, url=url)

extensions = self.extensions_generator.generate(license_deref)

return License(name, url=url, extensions=extensions)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/licenses/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@

class License(object):

def __init__(self, name, url=None):
def __init__(self, name, url=None, extensions=None):
self.name = name
self.url = url

self.extensions = extensions and dict(extensions) or {}
14 changes: 13 additions & 1 deletion openapi_core/schema/media_types/generators.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
"""OpenAPI core media types generators module"""
from six import iteritems

from openapi_core.compat import lru_cache
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.media_types.models import MediaType


Expand All @@ -21,8 +23,18 @@ def generate(self, content):
else:
example = example_spec

extensions = self.extensions_generator.generate(media_type)

schema = None
if schema_spec:
schema, _ = self.schemas_registry.get_or_create(schema_spec)

yield mimetype, MediaType(mimetype, schema=schema, example=example)
yield mimetype, MediaType(
mimetype,
schema=schema, example=example, extensions=extensions,
)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/media_types/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@
class MediaType(object):
"""Represents an OpenAPI MediaType."""

def __init__(self, mimetype, schema=None, example=None):
def __init__(self, mimetype, schema=None, example=None, extensions=None):
self.mimetype = mimetype
self.schema = schema
self.example = example

self.extensions = extensions and dict(extensions) or {}
9 changes: 8 additions & 1 deletion openapi_core/schema/operations/generators.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
from openapi_spec_validator.validators import PathItemValidator

from openapi_core.compat import lru_cache
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.external_docs.factories import (
ExternalDocumentationFactory,
)
Expand Down Expand Up @@ -47,6 +48,7 @@ def generate(self, path_name, path):
servers = self.servers_generator.generate(servers_spec)
security = self.security_requirements_generator.generate(
security_spec)
extensions = self.extensions_generator.generate(operation_deref)

external_docs = None
if 'externalDocs' in operation_deref:
Expand All @@ -68,7 +70,7 @@ def generate(self, path_name, path):
external_docs=external_docs, security=list(security),
request_body=request_body, deprecated=deprecated,
operation_id=operation_id, tags=list(tags_list),
servers=list(servers),
servers=list(servers), extensions=extensions,
),
)

Expand Down Expand Up @@ -101,3 +103,8 @@ def security_requirements_generator(self):
@lru_cache()
def servers_generator(self):
return ServersGenerator(self.dereferencer)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/operations/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ def __init__(
self, http_method, path_name, responses, parameters,
summary=None, description=None, external_docs=None, security=None,
request_body=None, deprecated=False, operation_id=None, tags=None,
servers=None):
servers=None, extensions=None):
self.http_method = http_method
self.path_name = path_name
self.responses = dict(responses)
Expand All @@ -25,6 +25,8 @@ def __init__(
self.tags = tags
self.servers = servers

self.extensions = extensions and dict(extensions) or {}

def __getitem__(self, name):
return self.parameters[name]

Expand Down
10 changes: 9 additions & 1 deletion openapi_core/schema/paths/generators.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
from six import iteritems

from openapi_core.compat import lru_cache
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.operations.generators import OperationsGenerator
from openapi_core.schema.parameters.generators import ParametersGenerator
from openapi_core.schema.paths.models import Path
Expand Down Expand Up @@ -29,12 +30,14 @@ def generate(self, paths):
servers = self.servers_generator.generate(servers_spec)
parameters = self.parameters_generator.generate_from_list(
parameters_list)
extensions = self.extensions_generator.generate(path_deref)

yield (
path_name,
Path(
path_name, list(operations), parameters=list(parameters),
summary=summary, description=description,
servers=list(servers),
servers=list(servers), extensions=extensions,
),
)

Expand All @@ -52,3 +55,8 @@ def servers_generator(self):
@lru_cache()
def parameters_generator(self):
return ParametersGenerator(self.dereferencer, self.schemas_registry)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
3 changes: 3 additions & 0 deletions openapi_core/schema/paths/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ class Path(object):
def __init__(
self, name, operations,
summary=None, description=None, parameters=None, servers=None,
extensions=None,
):
self.name = name
self.operations = dict(operations)
Expand All @@ -15,5 +16,7 @@ def __init__(
self.servers = servers
self.parameters = dict(parameters) if parameters else {}

self.extensions = extensions and dict(extensions) or {}

def __getitem__(self, http_method):
return self.operations[http_method]
14 changes: 13 additions & 1 deletion openapi_core/schema/request_bodies/factories.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
"""OpenAPI core request bodies factories module"""
from openapi_core.compat import lru_cache
from openapi_core.schema.extensions.generators import ExtensionsGenerator
from openapi_core.schema.media_types.generators import MediaTypeGenerator
from openapi_core.schema.request_bodies.models import RequestBody

Expand All @@ -16,9 +17,20 @@ def create(self, request_body_spec):
content = request_body_deref['content']
media_types = self.media_types_generator.generate(content)
required = request_body_deref.get('required', False)
return RequestBody(media_types, required=required)

extensions = self.extensions_generator.generate(request_body_deref)

return RequestBody(
media_types,
required=required, extensions=extensions,
)

@property
@lru_cache()
def media_types_generator(self):
return MediaTypeGenerator(self.dereferencer, self.schemas_registry)

@property
@lru_cache()
def extensions_generator(self):
return ExtensionsGenerator(self.dereferencer)
4 changes: 3 additions & 1 deletion openapi_core/schema/request_bodies/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,12 @@
class RequestBody(object):
"""Represents an OpenAPI RequestBody."""

def __init__(self, content, required=False):
def __init__(self, content, required=False, extensions=None):
self.content = Content(content)
self.required = required

self.extensions = extensions and dict(extensions) or {}

def __getitem__(self, mimetype):
try:
return self.content[mimetype]
Expand Down
Loading