generates_rules
generates_rules(fn: Callable[_P, _T]) -> Callable[_P, _T]Mark a function or method that deliberately creates many rules.
PyRel emits a "Rules created in a loop" warning when many rules originate
from one call site, since that usually means an accidental Python loop that
should be a single data-driven rule. A transpiler, code generator, or
config-driven builder legitimately emits many rules and would trip that
heuristic. Decorating its entry point tells PyRel to count the whole call as
one rule-creating operation, so a single call no longer looks like a loop:
from relationalai.semantics import define, generates_rules
@generates_rulesdef build_rules(spec): for item in spec: # many define()/require() calls define(...)Calling a decorated function many times from one call site (e.g. build_rules
in a loop of its own) still warns and names the function — that is a genuine
rule explosion, not a false positive. Nested decorated calls share the
outermost one’s scope, so a decorated entry point that calls other decorated
helpers still counts as one operation.
Only plain functions and methods are supported.
Parameters
(fncallable) - The rule-generating function or method to wrap.
Returns
callable-fnwrapped to run inside a single rule-emission scope, so the rules it creates count as one operation for loop detection. The wrapper has the same signature and return value asfn.
Raises
TypeError- Iffnis a generator, async generator, or coroutine function. Such a function returns before its body runs, so the scope would close before any rules are emitted and the count would never cover them.