105 lines
2.8 KiB
Python
105 lines
2.8 KiB
Python
import re
|
|
from dataclasses import dataclass
|
|
from typing import Any, Callable, Optional, Pattern, TYPE_CHECKING, Tuple, Union
|
|
|
|
from apischema.metadata.keys import (
|
|
CONVERSION_METADATA,
|
|
DEFAULT_AS_SET_METADATA,
|
|
FALL_BACK_ON_DEFAULT_METADATA,
|
|
FLATTEN_METADATA,
|
|
INIT_VAR_METADATA,
|
|
NONE_AS_UNDEFINED_METADATA,
|
|
POST_INIT_METADATA,
|
|
PROPERTIES_METADATA,
|
|
REQUIRED_METADATA,
|
|
SKIP_METADATA,
|
|
VALIDATORS_METADATA,
|
|
)
|
|
from apischema.types import AnyType, Metadata, MetadataImplem, MetadataMixin
|
|
|
|
if TYPE_CHECKING:
|
|
from apischema.conversions.conversions import AnyConversion
|
|
from apischema.validation.validators import Validator
|
|
|
|
|
|
def simple_metadata(key: str) -> Metadata:
|
|
return MetadataImplem({key: ...})
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class ConversionMetadata(MetadataMixin):
|
|
key = CONVERSION_METADATA
|
|
deserialization: Optional["AnyConversion"] = None
|
|
serialization: Optional["AnyConversion"] = None
|
|
|
|
|
|
conversion = ConversionMetadata
|
|
|
|
default_as_set = simple_metadata(DEFAULT_AS_SET_METADATA)
|
|
|
|
fall_back_on_default = simple_metadata(FALL_BACK_ON_DEFAULT_METADATA)
|
|
|
|
flatten = simple_metadata(FLATTEN_METADATA)
|
|
flattened = flatten
|
|
merged = flatten
|
|
|
|
|
|
def init_var(tp: AnyType) -> Metadata:
|
|
return MetadataImplem({INIT_VAR_METADATA: tp})
|
|
|
|
|
|
none_as_undefined = simple_metadata(NONE_AS_UNDEFINED_METADATA)
|
|
|
|
post_init = simple_metadata(POST_INIT_METADATA)
|
|
|
|
|
|
class PropertiesMetadata(dict, Metadata): # type: ignore
|
|
def __init__(self):
|
|
super().__init__({PROPERTIES_METADATA: None})
|
|
|
|
def __call__(
|
|
self, pattern: Union[str, Pattern, "ellipsis"] # noqa: F821
|
|
) -> Metadata:
|
|
if pattern is not ...:
|
|
pattern = re.compile(pattern)
|
|
return MetadataImplem({PROPERTIES_METADATA: pattern})
|
|
|
|
|
|
properties = PropertiesMetadata()
|
|
|
|
required = simple_metadata(REQUIRED_METADATA)
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class SkipMetadata(MetadataMixin):
|
|
key = SKIP_METADATA
|
|
deserialization: bool = False
|
|
serialization: bool = False
|
|
serialization_default: bool = False
|
|
serialization_if: Optional[Callable[[Any], Any]] = None
|
|
|
|
def __call__(
|
|
self,
|
|
deserialization: bool = False,
|
|
serialization: bool = False,
|
|
serialization_default: bool = False,
|
|
serialization_if: Optional[Callable[[Any], Any]] = None,
|
|
) -> "SkipMetadata":
|
|
return SkipMetadata(
|
|
deserialization, serialization, serialization_default, serialization_if
|
|
)
|
|
|
|
|
|
skip = SkipMetadata(deserialization=True, serialization=True)
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class ValidatorsMetadata(MetadataMixin):
|
|
key = VALIDATORS_METADATA
|
|
validators: Tuple["Validator", ...]
|
|
|
|
|
|
def validators(*validator: Callable) -> ValidatorsMetadata:
|
|
from apischema.validation.validators import Validator
|
|
|
|
return ValidatorsMetadata(tuple(map(Validator, validator)))
|