Skip to content

decorator ¤

Module containing the decorator provided to users.

Functions:

  • create_duty

    Register a duty in the collection.

  • duty

    Decorate a callable to transform it and register it as a duty.

create_duty ¤

create_duty(
    func: Callable,
    *,
    name: str | None = None,
    aliases: Iterable[str] | None = None,
    pre: DutyListType | None = None,
    post: DutyListType | None = None,
    skip_if: bool = False,
    skip_reason: str | None = None,
    **opts: Any
) -> Duty

Register a duty in the collection.

Parameters:

  • func (Callable) –

    The callable to register as a duty.

  • name (str | None, default: None ) –

    The duty name.

  • aliases (Iterable[str] | None, default: None ) –

    A set of aliases for this duty.

  • pre (DutyListType | None, default: None ) –

    Pre-duties.

  • post (DutyListType | None, default: None ) –

    Post-duties.

  • skip_if (bool, default: False ) –

    Skip running the duty if the given condition is met.

  • skip_reason (str | None, default: None ) –

    Custom message when skipping.

  • opts (Any, default: {} ) –

    Options passed to the context.

Returns:

  • Duty

    The registered duty.

Source code in src/duty/decorator.py
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
def create_duty(
    func: Callable,
    *,
    name: str | None = None,
    aliases: Iterable[str] | None = None,
    pre: DutyListType | None = None,
    post: DutyListType | None = None,
    skip_if: bool = False,
    skip_reason: str | None = None,
    **opts: Any,
) -> Duty:
    """Register a duty in the collection.

    Parameters:
        func: The callable to register as a duty.
        name: The duty name.
        aliases: A set of aliases for this duty.
        pre: Pre-duties.
        post: Post-duties.
        skip_if: Skip running the duty if the given condition is met.
        skip_reason: Custom message when skipping.
        opts: Options passed to the context.

    Returns:
        The registered duty.
    """
    aliases = set(aliases) if aliases else set()
    name = name or func.__name__
    dash_name = name.replace("_", "-")
    if name != dash_name:
        aliases.add(name)
        name = dash_name
    description = inspect.getdoc(func) or ""
    if skip_if:
        func = _skip(func, skip_reason or f"{dash_name}: skipped")
    duty = Duty(name, description, func, aliases=aliases, pre=pre, post=post, opts=opts)
    duty.__name__ = name  # type: ignore[attr-defined]
    duty.__doc__ = description
    duty.__wrapped__ = func  # type: ignore[attr-defined]
    return duty

duty ¤

duty(**kwargs: Any) -> Callable[[Callable], Duty]
duty(func: Callable) -> Duty
duty(*args: Any, **kwargs: Any) -> Callable | Duty

Decorate a callable to transform it and register it as a duty.

Parameters:

  • args (Any, default: () ) –

    One callable.

  • kwargs (Any, default: {} ) –

    Context options.

Raises:

Examples:

Decorate a function:

@duty
def clean(ctx):
    ctx.run("rm -rf build", silent=True)

Pass options to the context:

@duty(silent=True)
def clean(ctx):
    ctx.run("rm -rf build")  # silent=True is implied

Returns:

  • Callable | Duty

    A duty when used without parentheses, a decorator otherwise.

Source code in src/duty/decorator.py
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
def duty(*args: Any, **kwargs: Any) -> Callable | Duty:
    """Decorate a callable to transform it and register it as a duty.

    Parameters:
        args: One callable.
        kwargs: Context options.

    Raises:
        ValueError: When the decorator is misused.

    Examples:
        Decorate a function:

        ```python
        @duty
        def clean(ctx):
            ctx.run("rm -rf build", silent=True)
        ```

        Pass options to the context:

        ```python
        @duty(silent=True)
        def clean(ctx):
            ctx.run("rm -rf build")  # silent=True is implied
        ```

    Returns:
        A duty when used without parentheses, a decorator otherwise.
    """
    if args:
        if len(args) > 1:
            raise ValueError("The duty decorator accepts only one positional argument")
        return create_duty(args[0], **kwargs)

    def decorator(func: Callable) -> Duty:
        return create_duty(func, **kwargs)

    return decorator