Welcome to decoguard
A lightweight validation layer for your decorators with clear, reliable error reporting
Overview
decoguard is a Python library designed for robust validation of decorated functions.
It provides a clean and structured way to ensure that functions using your decorators comply with specific conditions you have defined.
As of the time of writing, decoguard is the only library known to provide these features.
This library uses advanced Python concepts, applied in sophisticated ways. These include decorators, introspection, and type hints.
Before reading this documentation or using the library, make sure you are familiar with these concepts, as the documentation assumes prior knowledge.
The core idea is to use meta-decorators on your decorators to enforce and validate their correct usage.
Without decoguard, doing this manually in native Python often results in:
- Complex and error-prone introspection logic
- Repetitive validation code scattered across your decorators
- Poor error reporting caused by stack manipulation or decorator wrapping
decoguard solves these problems by offering a simple and expressive system for decorating your decorators.
It helps you enforce usage rules and provides clear, developer-friendly error messages when violations occur.
Features
-
Decorator and Decorator Factory Support
Works seamlessly with both regular decorators and decorator factories (decorators that accept arguments). -
Meta-Decorators for Validation
Use simple meta-decorators to wrap your decorators with validation logic. No need for messy introspection or boilerplate. -
Robust Function Validation
Enforce specific rules on how functions are decorated, such as checking argument types, presence of required attributes, or naming conventions. -
Centralized Validation Logic
Keep your validation rules clean and maintainable by moving them out of individual decorators into a centralized, reusable layer. -
Clear and Informative Errors
When validation fails,decoguardraises precise, developer-friendly exceptions, no more obscure tracebacks or silent failures. -
Drop-In Simplicity
Add validation to existing decorators with minimal changes to your codebase. Designed to integrate smoothly with existing Python code and decorator patterns.
Library architecture
decoguard is divided into 3 differents module:
-
decoguard.decoratorsThis module provides the meta-decorators required to enable validation logic on your custom decorators. Use these decorators to wrap your own, thereby integratingdecoguard's validation system seamlessly. -
decoguard.validatorsThis module provides a variety of validation functions, which are internally implemented as decorator factories. While they are technically decorators, they are not meant to be applied directly to your functions. Instead, these validators should be used as arguments inside a meta-decorator fromdecoguard.decorators. This allows you to specify which validation logic should be applied when decorating your functions. Use these to define fine-grained validation rules that are executed as part of the decorator pipeline. -
decoguard.assertsThis module includes various assertion utilities used internally bydecoguard. These functions are also exposed for general-purpose use, should you need standalone validation logic outside of the decorator context. Think of this as a utility module for reusable assertion checks.
Getting started
Require at least Python 3.8. Tested and working up to Python 3.13.
Install decoguard from PyPi using pip:
pip install decoguard
Once done, you can start by reviewing the following minimal examples to gain a quick understanding of the library's core capabilities. Additionally, feel free to explore other sections of the documentation to discover the full range of included features.
Guard your decorators
from decoguard.decorators import validate_decorated
from decoguard.validators import require_params
@validate_decorated(require_params("x", "y"))
def my_decorator(func): return func
@my_decorator
def correct_usage(x, y): pass
@my_decorator
def bad_usage(x): pass # Will raise an DecoratorUsageValidationError
Let’s break down what’s happening here. As mentioned earlier, you need both decoguard.decorators and decoguard.validators in order to set up the full validation pipeline.
In this case, we want to ensure that functions using @my_decorator are doing so correctly. To indicate that we want those validations, we decorate @my_decorator with @validate_decorated. Then, we specify that any function using @my_decorator must include at least x and y parameters in its signature by passing require_params("x", "y") to @validate_decorated.
Below, we have two examples of how @my_decorator is used. The first one, correct_usage(), respects the validation we applied to the decorator. The function includes all the required parameters (x and y), so it passes validation and simply executes whatever logic @my_decorator provides.
However, the second usage, bad_usage(), does not satisfy the conditions we defined earlier. As such, this incorrect usage will raise the following error:
Exception has occurred: DecoratorUsageValidationError
Function 'bad_usage()' is using '@my_decorator' decorator which requires the function to have the following missing parameters: y
And just like that, even without calling the function, anyone misusing your decorator will be prevented from doing so and will receive a clear explanation of what’s wrong and how to fix it.
Guard your decorator factories
decoguard works exactly the same for decorator factories, as you can see in the following snippet.
@validate_decorated(require_params("x", "y"))
def my_decorator_factory(param):
def inner(func):
return func
return inner
To guard the arguments sent to your decorator factories, you may use other Python libraries whose purpose is to perform validation directly on functions, as this is not the goal of this library. Indeed, the entire purpose here is to control the functions that use your decorator, not to validate the decorator itself.