Policy Testing
Policy testing is the difference between "the regex looks right" and "we know this control behaves correctly under real traffic."
For most teams, that means testing three separate things:
- the pattern itself
- the policy resource you created
- the end-to-end request behavior once the policy is active
If you skip any of those layers, it is easy to ship a policy that looks correct in a review but causes false positives, misses real violations, or behaves differently once it is part of the full request flow.
What You Should Test
Good policy validation usually covers:
- known-bad inputs you expect to catch
- known-good inputs that must not be blocked
- borderline inputs that often produce false positives
- realistic workload context from the actual applications using the platform
That mix matters more than having a large number of toy examples.
1. Pattern Testing In The SDK
The fastest first step is to validate a pattern before you create or update a policy.
TypeScript
import { AxonFlow } from '@axonflow/sdk';
const client = new AxonFlow({
endpoint: 'http://localhost:8080',
clientId: 'my-tenant',
});
const result = await client.testPattern(
'\\b(\\d{3})[- ]?(\\d{2})[- ]?(\\d{4})\\b',
[
'My SSN is 123-45-6789',
'No SSN here',
'Multiple: 111-22-3333 and 444-55-6666',
]
);
for (const match of result.matches) {
console.log(`${match.input} -> ${match.matched}`);
}
Python
from axonflow import AxonFlow
client = AxonFlow(
endpoint="http://localhost:8080",
client_id="my-tenant",
)
result = await client.test_pattern(
r"\b(\d{3})[- ]?(\d{2})[- ]?(\d{4})\b",
[
"My SSN is 123-45-6789",
"No SSN here",
"Multiple: 111-22-3333 and 444-55-6666",
],
)
for match in result.matches:
print(f"{match.input} -> {match.matched}")
These examples use the current SDK signatures:
- TypeScript:
testPattern(pattern, inputs) - Python:
test_pattern(pattern, inputs)
2. Pattern Testing Via REST API
The Agent exposes a dedicated pattern-test endpoint:
POST /api/v1/static-policies/test
curl -X POST http://localhost:8080/api/v1/static-policies/test \
-H "Content-Type: application/json" \
-H "Authorization: Basic $(echo -n 'CLIENT_ID:CLIENT_SECRET' | base64)" \
-d '{
"pattern": "\\b(\\d{3})[- ]?(\\d{2})[- ]?(\\d{4})\\b",
"inputs": [
"My SSN is 123-45-6789",
"No SSN here",
"Multiple: 111-22-3333 and 444-55-6666"
]
}'
That endpoint is useful when:
- you want language-neutral test fixtures
- you are wiring policy validation into CI or scripts
- you want to validate the backend behavior directly instead of only trusting an SDK wrapper
3. End-To-End Request Testing
Pattern tests are not enough by themselves. You also need to validate how the active policy behaves in the real request pipeline.
For proxy-mode request testing, use the current agent entry point:
POST /api/request
curl -X POST http://localhost:8080/api/request \
-H "Content-Type: application/json" \
-H "Authorization: Basic $(echo -n 'CLIENT_ID:CLIENT_SECRET' | base64)" \
-d '{
"query": "My SSN is 123-45-6789",
"request_type": "chat",
"user_token": "test-user",
"client_id": "my-tenant"
}'
When a request is blocked, the response shape typically includes:
blocked: trueblock_reasonpolicy_info
That is the level you actually care about in production, because it proves the policy is not just syntactically valid but functionally effective in the live request path.
4. Policy Simulation Before Rollout
If you have an Evaluation or Enterprise license, also use Policy Simulation & Impact Report before rollout. That is the best way to validate how a policy behaves against realistic inputs without affecting live traffic.
This is especially useful when:
- the rule is broad
- the application is shared across teams
- a false positive would break important workflows
Unit Testing Patterns In Code
If your team maintains critical custom patterns, keep them under test in source control.
Go Example
package policy_test
import (
"regexp"
"testing"
)
func TestSSNPattern(t *testing.T) {
pattern := regexp.MustCompile(`\b(\d{3})[- ]?(\d{2})[- ]?(\d{4})\b`)
tests := []struct {
name string
input string
matched bool
}{
{"SSN with dashes", "My SSN is 123-45-6789", true},
{"No SSN present", "No sensitive data here", false},
{"Invalid format", "12-345-6789", false},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
got := pattern.MatchString(tt.input)
if got != tt.matched {
t.Errorf("got %v, want %v", got, tt.matched)
}
})
}
}
This kind of unit test is still valuable even when you also use the platform APIs, because it catches accidental pattern regressions early in the development cycle.
A Practical Review Workflow
A strong policy review cycle usually looks like this:
- test the regex or pattern directly
- create or update the policy resource
- run end-to-end request validation through
/api/request - use simulation or impact analysis if the change is broad or risky
- only then roll the policy into a shared environment
That sequence gives product, platform, and security teams a much better chance of agreeing on the real effect of the rule before it reaches production users.
Related Documentation
- Policy Overview for authoring and lifecycle
- Policy Syntax for field semantics and structure
- Policy Examples for concrete patterns
- Policy Simulation & Impact Report for dry-run governance validation
