Registry / web-framework / venusian

venusian

JSON →
library3.1.1pypypi✓ verified 26d ago

Venusian is a Python library that enables framework authors to defer actions typically performed by decorators at import time. Instead, these actions are executed during a separate 'scan' phase. This allows for more flexible configuration and improved testability of decorated code. The library is actively maintained, with the current version being 3.1.1, and supports CPython and PyPy versions 3.7 and above.

pip install venusian
INSTALL
IMPORT
SIG · VENUSIAN
V
venusian
web-frameworkpythonv3.1.1
Install
1.6s avg
Import
34ms
Disk
16MB
Pass rate
10/ 10
Env Coverage10 / 10
glibc
3.93.13
musl
3.93.13
Install & Compatibility
Where this runs
tested against v3.1.1 · pip install
no network on importno background threads
Install × environment matrix
Each cell = how many times install + import succeeded across repeated harness runs. Partial = flaky.
glibc = Debian/Ubuntu slim · musl = Alpine Linux
musl
py 3.103.95 runs
installs and imports cleanly · install 0.0s · import 0.034s · 17.8MB
glibc
py 3.103.95 runs
installs and imports cleanly · install 1.6s · import 0.034s · 18MB
16MB installed
● package 16MB
Code
Verified usage

Verified import paths — ran on the pinned version, not inferred.

Scanner
from venusian import Scanner
Used to initiate the deferred decorator action scan.
attach
venusian.attach(wrapped, callback)
Attaches a callback to a decorated object for later processing during a scan.

This example demonstrates how to create a custom decorator that uses `venusian.attach` to defer its actions. A `venusian.Scanner` is then used to explicitly trigger these deferred actions, collecting metadata about the decorated functions into a custom registry.

import venusian # Define a custom decorator that uses venusian.attach class mydecorator: def __init__(self, category='default'): self.category = category def __call__(self, wrapped): def callback(scanner, name, obj): # This function is called during the scan phase print(f"Scanning {obj.__name__} in category '{self.category}'") # You might register `obj` or `name` in a registry here scanner.registry.append((name, obj, self.category)) venusian.attach(wrapped, callback, category=self.category) return wrapped # Return the original object, untouched at import time # Define some functions to be decorated @mydecorator(category='views') def my_view(): return "Hello, Venusian!" @mydecorator(category='api') def my_api_endpoint(): return {"data": "from api"} # Create a scanner instance and a custom registry scanner = venusian.Scanner(registry=[]) # Scan the current module (or a specific package/module) # The callbacks attached via mydecorator will now be executed scanner.scan(__name__) # Access the collected information from the registry print("\n--- Collected Registry Data ---") for name, obj, category in scanner.registry: print(f"Name: {name}, Object: {obj.__name__}, Category: {category}") # Verify that original functions are callable print(f"\nDirect call to my_view: {my_view()}")
Debug
Known issues
breakingVersions 3.0.0 and 2.0.0 dropped support for Python 2.7, 3.3, and 3.4. Projects on these older Python versions must remain on `venusian < 2.0.0` or `venusian < 3.0.0` respectively (for Python 3.x).
fix
Upgrade to Python 3.5+ to use `venusian >= 3.0.0`.
affects: < 3.0.0
breakingVersion 3.1.0 removed support for Python 3.5 and 3.6. Users on these Python versions should use `venusian < 3.1.0` if they cannot upgrade their Python interpreter.
fix
Upgrade to Python 3.7+ to use `venusian >= 3.1.0`.
affects: < 3.1.0
gotchaBy default, `venusian.Scanner.scan()` will propagate `ImportError` exceptions encountered while trying to import modules. To suppress or handle these errors, provide an `onerror` callback function to the `scan()` method.
fix
Pass an `onerror` callable to `scanner.scan(..., onerror=my_error_handler_func)` to customize error handling.
affects: All versions (since 1.0)
gotchaVenusian decorators attached to a class are not implicitly inherited by subclasses. Each class declaration should have its own local set of callbacks; callbacks added via decorations are not inherited from a superclass.
fix
If decorator inheritance is desired, it must be explicitly handled within your custom decorator logic or scan phase, for example, by re-attaching or copying callbacks from the superclass during the scan.
affects: All versions (fixed in 0.4 / 1.0 but design decision)
Upgrade
Version history
3.1.1latest on PyPI · released Dec 2, 2024
Audit
Dependencies

No dependency data recorded yet.

Agent activity
15 hits · last 30 days
node
14
Resources
venusian — pip install venusian · libregistry