def _correct_schemas(self, schemas): models = { model.__name__: model for model in JsonSchemaMixin.__subclasses__() } needed_props = { "maximum", "exclusiveMaximum", "minimum", "exclusiveMinimum", "maxLength", "minLength" } for schema in schemas.keys(): if hasattr(models[schema], "__x_schema__"): schemas[schema].update({ f"x-{key}": value for key, value in models[schema].__x_schema__.items() }) schemas[schema][f"x-features"] = [ feat.__name__ for feat in getmro(models[schema]) ] for field in fields(models[schema]): if hasattr(field, "metadata") and field.metadata: for prop in needed_props & set(field.metadata.keys()): schemas[schema]["properties"][ field.name][prop] = field.metadata[prop] if "model" in field.metadata: schemas[schema]["properties"][ field.name]["x-model"] = field.metadata["model"] return schemas
def v3(self): result = {"openapi": "3.0.1"} c_keys = list(self.config.keys()) if "OA_INFO" in c_keys: result["info"] = self.config["OA_INFO"] if "OA_SERVER_DESCRIPTION" in c_keys: result["servers"] = [{ "url": self.config["SERVER_NAME"], "description": self.config["OA_SERVER_DESCRIPTION"] }] result["paths"] = self._paths() schemas = self._correct_schemas( JsonSchemaMixin.all_json_schemas(schema_type=SchemaType.OPENAPI_3)) result["components"] = { "x-root": self._root_model.__name__, "schemas": schemas } if hasattr(self, "_params"): result["components"]["parameters"] = self._params return result
return b64encode(value).decode("utf-8") def to_python(self, value: str) -> bytes: return b64decode(value) @property def json_schema(self) -> JsonDict: return { "type": "string", "pattern": r"^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=)?$", } JsonSchemaMixin.register_field_encoders({Binary: BinaryField()}) class DateTimeField(FieldEncoder): """Wrapper around Python datetime.datetime object""" def to_wire(self, value: DateTime) -> float: if isinstance(value, float): return value return value.timestamp() def to_python(self, value: float) -> DateTime: return DateTime(datetime.fromtimestamp(value)) @property def json_schema(self) -> JsonDict: return {"type": "number"}
class ParameterKeyField(FieldEncoder): @property def json_schema(self): return { "type": "string", "pattern": r"[a-zA-Z0-9]*^$", "Description": "CloudFormation parameter name, can contain letters and " "numbers only", } JsonSchemaMixin.register_field_encoders({ParameterKey: ParameterKeyField()}) class RegionField(FieldEncoder): @property def json_schema(self): return { "type": "string", "pattern": r"^(ap|eu|us|sa|ca|cn|af|me|us-gov)-(central|south|north|east|" r"west|southeast|southwest|northeast|northwest)-[0-9]$", "description": "AWS Region name eg.: 'us-east-1'", }
from enum import Enum from datetime import datetime from uuid import UUID from dataclasses_jsonschema import JsonSchemaMixin, FieldEncoder Postcode = NewType('Postcode', str) class PostcodeField(FieldEncoder): @property def json_schema(self): return {'type': 'string', 'minLength': 5, 'maxLength': 8} JsonSchemaMixin.register_field_encoders({Postcode: PostcodeField()}) class SubSchemas(JsonSchemaMixin): pass class Weekday(Enum): MON = 'Monday' TUE = 'Tuesday' WED = 'Wednesday' THU = 'Thursday' FRI = 'Friday' @dataclass(eq=True)
return {"type": "string"} class DecimalField(FieldEncoder): def to_wire(self, value): return value.to_decimal() def to_python(self, value): return Decimal128(str(value)) @property def json_schema(self): return {"type": "number"} JsonSchemaMixin.register_field_encoders({ObjectId: ObjectIdField()}) JsonSchemaMixin.register_field_encoders({Decimal128: DecimalField()}) class MongoJSONEncoder(JSONEncoder): def default(self, obj): if isinstance(obj, ObjectId): return str(obj) elif isinstance(obj, Decimal): return float(obj) elif isinstance(obj, Decimal128): return float(obj.to_decimal()) else: return JSONEncoder.default(self, obj)
from dataclasses_jsonschema.field_types import DateTimeFieldEncoder from slugify import slugify from yrest.utils import get_url Email = NewType("Email", str) class EmailField(FieldEncoder): @property def json_schema(self): return {"type": "string", "format": "email"} JsonSchemaMixin.register_field_encoders({Email: EmailField()}) Phone = NewType("Phone", str) class PhoneField(FieldEncoder): @property def json_schema(self): return {"type": "string", "format": "phone"} JsonSchemaMixin.register_field_encoders({Phone: PhoneField()}) Password = NewType("Password", str)
def test_embeddable_json_schema(): expected = {'Point': POINT_SCHEMA, 'Foo': FOO_SCHEMA} assert expected == Foo.json_schema(embeddable=True) assert expected == JsonSchemaMixin.json_schema()
def test_embeddable_json_schema(): expected = {'Point': POINT_SCHEMA, 'Foo': FOO_SCHEMA} assert expected == Foo.json_schema(embeddable=True) expected = {'Point': POINT_SCHEMA, 'Foo': FOO_SCHEMA, 'Recursive': RECURSIVE_SCHEMA, 'OpaqueData': OPAQUE_DATA_SCHEMA} assert expected == JsonSchemaMixin.json_schema()