Skip to content

confit.draft

MetaDraft [source]

Bases: type

A metaclass for Draft that allows the user to create specify the type the Draft should become when instantiated.

In addition to allowing static typing, this metaclass also provides a way to validate the Draft object when used in combination with pydantic validation.

Examples

from confit import Draft


@validate_arguments
def make_hi(name, prefix) -> str:
    return prefix + " " + name


@validate_arguments
def print_hi(param: Draft[str]):
    val = param.instantiate(prefix="Hello")
    print(val)


print_hi(make_hi.draft(name="John"))
Source code in confit/draft.py
72
73
74
def __init__(cls, name, bases, dct):
    super().__init__(name, bases, dct)
    cls.type_ = Any

Draft [source]

Bases: Generic[R]

A Draft is a placeholder for a value that has not been instantiated yet, likely because it is missing an argument that will be provided later by the library.

Source code in confit/draft.py
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
def __init__(
    self,
    func: Callable[P, R],
    kwargs: Dict[str, Any],
    loc=(),
):
    self._func = func
    self._kwargs = kwargs
    self._loc = tuple(loc)
    return_type = inspect.signature(func).return_annotation
    if isinstance(return_type, str):
        raise RuntimeError(
            f"{func} has been annotated as a string return type, "
            f"and therefore cannot be used to validate the output : please "
            "type hint it using non string type hints."
        )

instantiate [source]

Finalize the Draft object into an instance of the expected type using the provided arguments. The new arguments are merged with the existing ones, with the old ones taking precedence. The rationale for this is that the user makes the Draft, and the library completes any missing arguments.

Source code in confit/draft.py
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
def instantiate(self, **kwargs) -> R:
    """
    Finalize the Draft object into an instance of the expected type
    using the provided arguments. The new arguments are merged with the
    existing ones, with the old ones taking precedence. The rationale
    for this is that the user makes the Draft, and the library
    completes any missing arguments.
    """
    if not isinstance(self, Draft):
        return self

    # Order matters: priority is given to the kwargs provided
    # by the user, so most likely when the Partial is instantiated
    try:
        res = self._func(**{**kwargs, **self._kwargs})
    except ConfitValidationError as e:
        raise e.with_path(self._loc).with_traceback(e.__traceback__)
    return res