some random stuff. caelestia incoming

This commit is contained in:
voidarclabs
2025-08-21 17:40:48 +01:00
parent 12df9a0b6e
commit 1cc414a96a
1308 changed files with 217219 additions and 8 deletions

View File

@@ -0,0 +1,212 @@
import datetime
import ipaddress
from collections.abc import Sequence
from dataclasses import MISSING, dataclass, field
from enum import Enum
from typing import Any, Dict, List, Optional, Union
from typing_extensions import TYPE_CHECKING, Self, TypeAlias
from mashumaro.config import BaseConfig
from mashumaro.core.meta.helpers import iter_all_subclasses
from mashumaro.helper import pass_through
from mashumaro.jsonschema.dialects import DRAFT_2020_12, JSONSchemaDialect
if TYPE_CHECKING: # pragma: no cover
from mashumaro.jsonschema.plugins import BasePlugin
else:
BasePlugin = Any
try:
from mashumaro.mixins.orjson import (
DataClassORJSONMixin as DataClassJSONMixin,
)
except ImportError: # pragma: no cover
from mashumaro.mixins.json import DataClassJSONMixin # type: ignore
# https://github.com/python/mypy/issues/3186
Number: TypeAlias = Union[int, float]
Null = object()
class JSONSchemaInstanceType(Enum):
NULL = "null"
BOOLEAN = "boolean"
OBJECT = "object"
ARRAY = "array"
NUMBER = "number"
STRING = "string"
INTEGER = "integer"
class JSONSchemaInstanceFormat(Enum):
pass
class JSONSchemaStringFormat(JSONSchemaInstanceFormat):
DATETIME = "date-time"
DATE = "date"
TIME = "time"
DURATION = "duration"
EMAIL = "email"
IDN_EMAIL = "idn-email"
HOSTNAME = "hostname"
IDN_HOSTNAME = "idn-hostname"
IPV4ADDRESS = "ipv4"
IPV6ADDRESS = "ipv6"
URI = "uri"
URI_REFERENCE = "uri-reference"
IRI = "iri"
IRI_REFERENCE = "iri-reference"
UUID = "uuid"
URI_TEMPLATE = "uri-template"
JSON_POINTER = "json-pointer"
RELATIVE_JSON_POINTER = "relative-json-pointer"
REGEX = "regex"
class JSONSchemaInstanceFormatExtension(JSONSchemaInstanceFormat):
TIMEDELTA = "time-delta"
TIME_ZONE = "time-zone"
IPV4NETWORK = "ipv4network"
IPV6NETWORK = "ipv6network"
IPV4INTERFACE = "ipv4interface"
IPV6INTERFACE = "ipv6interface"
DECIMAL = "decimal"
FRACTION = "fraction"
BASE64 = "base64"
PATH = "path"
DATETIME_FORMATS = {
datetime.datetime: JSONSchemaStringFormat.DATETIME,
datetime.date: JSONSchemaStringFormat.DATE,
datetime.time: JSONSchemaStringFormat.TIME,
}
IPADDRESS_FORMATS = {
ipaddress.IPv4Address: JSONSchemaStringFormat.IPV4ADDRESS,
ipaddress.IPv6Address: JSONSchemaStringFormat.IPV6ADDRESS,
ipaddress.IPv4Network: JSONSchemaInstanceFormatExtension.IPV4NETWORK,
ipaddress.IPv6Network: JSONSchemaInstanceFormatExtension.IPV6NETWORK,
ipaddress.IPv4Interface: JSONSchemaInstanceFormatExtension.IPV4INTERFACE,
ipaddress.IPv6Interface: JSONSchemaInstanceFormatExtension.IPV6INTERFACE,
}
def _deserialize_json_schema_instance_format(
value: Any,
) -> JSONSchemaInstanceFormat:
for cls in iter_all_subclasses(JSONSchemaInstanceFormat):
try:
return cls(value)
except (ValueError, TypeError):
pass
raise ValueError(value)
@dataclass(unsafe_hash=True)
class JSONSchema(DataClassJSONMixin):
# Common keywords
schema: Optional[str] = None
type: Optional[JSONSchemaInstanceType] = None
enum: Optional[list[Any]] = None
const: Optional[Any] = field(default_factory=lambda: MISSING)
format: Optional[JSONSchemaInstanceFormat] = None
title: Optional[str] = None
description: Optional[str] = None
anyOf: Optional[List["JSONSchema"]] = None
reference: Optional[str] = None
definitions: Optional[Dict[str, "JSONSchema"]] = None
default: Optional[Any] = field(default_factory=lambda: MISSING)
deprecated: Optional[bool] = None
examples: Optional[list[Any]] = None
# Keywords for Objects
properties: Optional[Dict[str, "JSONSchema"]] = None
patternProperties: Optional[Dict[str, "JSONSchema"]] = None
additionalProperties: Union["JSONSchema", bool, None] = None
propertyNames: Optional["JSONSchema"] = None
# Keywords for Arrays
prefixItems: Optional[List["JSONSchema"]] = None
items: Optional["JSONSchema"] = None
contains: Optional["JSONSchema"] = None
# Validation keywords for numeric instances
multipleOf: Optional[Number] = None
maximum: Optional[Number] = None
exclusiveMaximum: Optional[Number] = None
minimum: Optional[Number] = None
exclusiveMinimum: Optional[Number] = None
# Validation keywords for Strings
maxLength: Optional[int] = None
minLength: Optional[int] = None
pattern: Optional[str] = None
# Validation keywords for Arrays
maxItems: Optional[int] = None
minItems: Optional[int] = None
uniqueItems: Optional[bool] = None
maxContains: Optional[int] = None
minContains: Optional[int] = None
# Validation keywords for Objects
maxProperties: Optional[int] = None
minProperties: Optional[int] = None
required: Optional[list[str]] = None
dependentRequired: Optional[dict[str, set[str]]] = None
class Config(BaseConfig):
omit_none = True
serialize_by_alias = True
aliases = {
"schema": "$schema",
"reference": "$ref",
"definitions": "$defs",
}
serialization_strategy = {
int: pass_through,
float: pass_through,
Null: pass_through,
JSONSchemaInstanceFormat: {
"deserialize": _deserialize_json_schema_instance_format,
},
}
def __pre_serialize__(self) -> Self:
if self.const is None:
self.const = Null
if self.default is None:
self.default = Null
return self
def __post_serialize__(self, d: dict[Any, Any]) -> dict[Any, Any]:
const = d.get("const")
if const is MISSING:
d.pop("const")
elif const is Null:
d["const"] = None
default = d.get("default")
if default is MISSING:
d.pop("default")
elif default is Null:
d["default"] = None
return d
@dataclass
class JSONObjectSchema(JSONSchema):
type: Optional[JSONSchemaInstanceType] = JSONSchemaInstanceType.OBJECT
@dataclass
class JSONArraySchema(JSONSchema):
type: Optional[JSONSchemaInstanceType] = JSONSchemaInstanceType.ARRAY
@dataclass
class Context:
dialect: JSONSchemaDialect = DRAFT_2020_12
definitions: dict[str, JSONSchema] = field(default_factory=dict)
all_refs: Optional[bool] = None
ref_prefix: Optional[str] = None
plugins: Sequence[BasePlugin] = ()