Your First Custom Policy
This tutorial walks you through creating a policy from scratch, testing it in the sandbox, and seeing it enforce decisions on real agent actions.
Time: ~5 minutes
Prerequisites: A running TameFlare instance with at least one registered agent.
Step 1: Understand the goal
We'll create a policy that:
- Denies any attempt to delete a GitHub repository
- Requires approval for merging pull requests to the
mainbranch - Allows everything else
This is a common starting point — protect destructive actions, gate risky ones, and let safe actions through.
Step 2: Write the YAML
Go to Policies in the dashboard sidebar and click Create policy. Paste this YAML:
name: github-branch-protection
description: Protect main branch and prevent repo deletion
scope:
action_types:
- "github.*"
rules:
- name: block-repo-deletion
conditions:
all:
- field: action_spec.type
operator: equals
value: "github.repo.delete"
decision: deny
reason: "Repository deletion is not allowed through agents"
risk_score: 95
- name: require-approval-for-main-merge
conditions:
all:
- field: action_spec.type
operator: equals
value: "github.pr.merge"
- field: action_spec.parameters.branch_name
operator: equals
value: "main"
decision: requires_approval
reason: "Merging to main requires human approval"
risk_score: 70
approval:
timeout_seconds: 3600
approver_roles:
- admin
- owner
- name: allow-other-github-actions
conditions:
all:
- field: action_spec.type
operator: starts_with
value: "github."
decision: allow
reason: "Other GitHub actions are permitted"
risk_score: 20Click Create. The live validator will confirm the YAML is valid before you save.
Step 3: Test with the sandbox
Go back to Overview and open the Sandbox. Switch to the Custom tab and paste this action spec:
{
"type": "github.repo.delete",
"resource": {
"provider": "github",
"organization": "my-org",
"repository": "important-repo"
},
"parameters": {},
"risk_hints": {
"is_destructive": true
}
}Click Evaluate. You should see:
- Decision: Denied
- Reason: "Repository deletion is not allowed through agents"
- Risk score: 95
Now test the merge scenario:
{
"type": "github.pr.merge",
"resource": {
"provider": "github",
"organization": "my-org",
"repository": "important-repo"
},
"parameters": {
"branch_name": "main",
"pr_number": 42
},
"risk_hints": {
"affects_production": true
}
}Expected result: Requires approval, risk score 70.
And a safe action:
{
"type": "github.issue.create",
"resource": {
"provider": "github",
"organization": "my-org",
"repository": "important-repo"
},
"parameters": {
"title": "Bug report"
},
"risk_hints": {}
}Expected result: Allowed (no matching deny or approval rule, and the scope matches github.*).
Step 4: Understand rule evaluation
TameFlare evaluates rules in this order:
- Scope check — if the action type doesn't match the policy's
scope.action_types, the entire policy is skipped - Deny wins — if any rule returns
deny, the action is denied regardless of other rules - Approval next — if no deny but any rule returns
requires_approval, the action is held for approval - Allow last — if no deny or approval rules match, the action is allowed
- Priority — lower number = higher priority (priority 1 evaluates before priority 100), but deny always wins regardless of priority
This means you don't need to worry about rule ordering within a policy — the deny-wins logic handles conflicts automatically.
Step 5: Refine and iterate
Common next steps:
- Add environment scoping: Only enforce in production by adding
scope.environments: ["production"] - Add agent scoping: Only apply to specific agents by adding
scope.agents: ["deploy-bot"] - Adjust risk scores: Higher scores (0-100) appear more prominently in the dashboard
- Use the demo sandbox: The demo auto-seeds a "GitHub Safe Defaults" policy pack on first run to give you a working baseline
Full policy reference
For the complete schema including all 14 condition operators, nested any/all combinators, and more examples, see Writing Policies.