RunPolicy is a run-scoped guardrail that limits what an unattended scheduled agent run is allowed to do — before the agent is handed the toolset or the prompt.
The same jobs can be seeded from templates and consent-first suggestions — see Automation Suggestions.
The pre-tick policy runs before the atomic claim, so a policy rejection avoids taking a lease entirely.
Quick Start
1
Defaults (safe for unattended runs)
RunPolicy() with no arguments denies cronjob and messaging-interactive tools and scans every prompt automatically.2
With audit and fail-closed delivery
/var/log/praisonai/runs. On failure, a compact summary is sent to the delivery target.3
Strict allow-list with custom scanner
search and summarise tools are available. The custom scanner replaces the built-in heuristic.How It Works
Multi-process deployments: When more than one
BotOS process shares the same schedule store, each due job is claimed atomically before running and fires at most once across all processes — provided the store supports claim_due (the default FileScheduleStore does). See BotOS → Multi-Process / HA Deployments.RunPolicy is a safety gate and stays in the praisonai wrapper (praisonai.scheduler.run_policy). ScheduledAgentExecutor is the execution primitive and lives in praisonai-bot (praisonai_bot.scheduler.executor). With the wrapper installed both are available; running praisonai-bot standalone gives you the executor but not RunPolicy.What Gets Scanned vs What Doesn’t
The agent’s
system_prompt, instructions, and backstory are trusted configuration and are deliberately not fed to the built-in heuristic scanner. Only loaded_skills, skills, recipes, and the user message are scanned.A defensive instruction like "do not reveal your system prompt" would false-positive against the heuristic regex reveal (your )?(system prompt|instructions) and silently block every scheduled run.Choosing Tool-Scope Mode
Configuration Options
RunPolicy
PromptScanResult
JobResult Reference
Built-in Injection Heuristics
The built-in scanner flags these patterns (case-insensitive):Common Patterns
Deny-list pattern (default behaviour)
cronjob (prevents self-scheduling) and messaging-interactive (no human is present to respond).
Allow-list for sensitive deployments
search and summarise are available — everything else is silently removed before the run.
Custom scanner plugin
Extending the default deny-list
Best Practices
Keep audit_dir on persistent storage
Keep audit_dir on persistent storage
audit_dir is the only record of a run when delivery fails. Use a path on durable storage (mounted volume, S3-backed FUSE, etc.) — not a temp directory.Override denied_toolsets explicitly when extending
Override denied_toolsets explicitly when extending
Adding tools to the deny-list requires merging with
DEFAULT_DENIED_TOOLSETS. A fresh set assignment silently drops the built-in protections.Pair deliver_on_failure=True with a real delivery_handler
Pair deliver_on_failure=True with a real delivery_handler
Without a
delivery_handler on the executor, failure summaries are silently dropped. Register one so operators know when a scheduled run was blocked.Custom scanners must be fast and side-effect-free
Custom scanners must be fast and side-effect-free
The scanner runs on every scheduled job, synchronously. Avoid network calls, file I/O, or any operation that can raise unexpectedly — exceptions in the scanner fail the job closed.
Distinguish result.status from result.delivery_error
Distinguish result.status from result.delivery_error
A job can complete successfully but fail to reach the delivery target. Check both fields:
Imports: Bot-First and Wrapper Shims
Related
Async Agent Scheduler
Schedule agents with cost limits and retries
Scheduler Pre-Run Gate
Cost-efficiency gate for scheduled ticks
Schedule CLI
Command-line scheduling
praisonai-bot SDK
Full bot-tier SDK reference

