Feature Flags Age + AST-Grep Collector
Enforce Feature Flags Age using data collected by AST-Grep Collector. Automatically check testing and quality standards on every PR.
How AST-Grep Collector Powers This Guardrail
The AST-Grep Collector gathers metadata from your code analysis, security systems. This data flows into Lunar's Component JSON, where the Feature Flags Age guardrail evaluates it against your standards.
When enabled, this check runs automatically on every PR and in AI coding workflows, providing real-time enforcement with actionable feedback.
Quick Start Configuration
Add both the collector and policy to your lunar-config.yml to enable this guardrail.
# Step 1: Enable the AST-Grep Collector
collectors:
- uses: github://earthly/lunar-lib/collectors/ast-grep@v1.0.0
# with: ...
# Step 2: Enable the Feature Flags Guardrails
policies:
- uses: github://earthly/lunar-lib/policies/feature-flags@v1.0.0
include: [feature-flags-age]
# with: ...
What AST-Grep Collector Collects
This collector gathers the following data that the Feature Flags Age guardrail evaluates.
ast-grep
Runs user-defined ast-grep YAML rules against source code and collects pattern matches.
Supports full ast-grep rule syntax including relational rules (inside, has), composite
rules (all, any, not), and metavariables ($VAR, $$$ARGS). Groups results by rule ID
(format: category.subcategory) and writes structured matches with file, range, and code
snippet to .code_patterns.
Example Data Flow
Here's an example of the data that AST-Grep Collector writes to the Component JSON, which Feature Flags Age then evaluates.
{
"code_patterns": {
"source": {
"tool": "ast-grep",
"version": "0.40.5"
},
"security": {
"sql_concat": {
"count": 0,
"message": "SQL query built via string concatenation",
"severity": "error",
"matches": []
},
"eval": {
"count": 2,
"message": "Dangerous eval() usage",
"severity": "error",
"matches": [
{
"file": "utils/dynamic.py",
"range": { "start": { "line": 45, "column": 8 }, "end": { "line": 45, "column": 25 } },
"code": "eval(user_input)"
},
{
"file": "handlers/admin.py",
"range": { "start": { "line": 112, "column": 12 }, "end": { "line": 112, "column": 30 } },
"code": "exec(code_string)"
}
]
}
},
"logging": {
"printf": {
"count": 5,
"message": "Use structured logging instead of fmt.Printf",
"severity": "warning",
"matches": [
{
"file": "handler.go",
"range": { "start": { "line": 42, "column": 2 }, "end": { "line": 42, "column": 38 } },
"code": "fmt.Printf(\"User: %s\", user)"
}
]
}
}
}
}
Configuration Options
AST-Grep Collector Inputs
| Input | Required | Default | Description |
|---|---|---|---|
rules |
Required | — | Multi-line YAML string containing ast-grep rules. Use YAML multi-document syntax (---) to define multiple rules. Rule IDs should follow the format <category>.<subcategory> to map to Component JSON paths. Example: id: security.sql_concat -> .code_patterns.security.sql_concat |
exclude_paths |
Optional |
vendor,node_modules,.git,dist,build
|
Comma-separated paths to exclude from scanning |
max_matches_per_rule |
Optional |
100
|
Maximum matches to report per rule (prevents huge output) |
debug |
Optional |
false
|
Enable debug output (echoes rules and raw ast-grep output) |
Feature Flags Guardrails Inputs
| Input | Required | Default | Description |
|---|---|---|---|
max_days |
Optional |
90
|
Maximum number of days a feature flag should exist before failing the check |
Ready to Automate Your Standards?
See how Lunar can turn your engineering wiki, compliance docs, or postmortem action items into automated guardrails with our 100+ built-in guardrails.