Overview
A Mutation is an explicit change directive that encodes:
- Category (repair | optimize | innovate)
- Risk level (low | medium | high)
- Trigger signals that caused it
- Expected effect and target
Mutations are first-class objects that make evolution decisions auditable and reversible.
Mutation Structure
// From src/gep/mutation.js:100
function buildMutation({ signals, selectedGene, driftEnabled, personalityState }) {
const ts = Date.now();
const category = mutationCategoryFromContext({ signals, driftEnabled });
const triggerSignals = uniqStrings(signals);
const base = {
type: 'Mutation',
id: `mut_${ts}`,
category,
trigger_signals: triggerSignals,
target: String(target || targetFromGene(selectedGene)),
expected_effect: String(expected_effect || expectedEffectFromCategory(category)),
risk_level: 'low',
};
// Risk assignment and safety constraints...
return base;
}
Fields
Unique identifier (e.g., mut_1709876543210)
Change intent: repair | optimize | innovate
Signals that triggered this mutation
What is being changed (e.g., gene:error_handling_robust)
Human-readable description of the intended outcome
Mutation Categories
The category is determined by analyzing the signal context:
// From src/gep/mutation.js:55
function mutationCategoryFromContext({ signals, driftEnabled }) {
if (hasErrorishSignal(signals)) return 'repair';
if (driftEnabled) return 'innovate';
if (hasOpportunitySignal(signals)) return 'innovate';
// Consult strategy preset
try {
var strategy = require('./strategy').resolveStrategy();
if (strategy && strategy.innovate >= 0.5) return 'innovate';
} catch (_) {}
return 'optimize';
}
Repair
Intent: Fix errors and increase stability
Triggered by:
log_error
errsig:...
recurring_error
Expected effect:
// From src/gep/mutation.js:71
if (category === 'repair')
return 'reduce runtime errors, increase stability, and lower failure rate';
After 3+ consecutive failed repairs, the system forces innovation to break the loop.
Optimize
Intent: Improve success rate and reduce operational cost
Triggered by:
stable_success_plateau
- No errors + no opportunity signals
Expected effect:
if (category === 'optimize')
return 'improve success rate and reduce repeated operational cost';
Innovate
Intent: Explore new strategy combinations to escape local optimum
Triggered by:
user_feature_request
capability_gap
perf_bottleneck
force_innovation_after_repair_loop
- Drift enabled
Expected effect:
if (category === 'innovate')
return 'explore new strategy combinations to escape local optimum';
Innovation is the only way to add new capabilities. Repair and optimize are conservative.
Risk Levels
Default Assignment
// From src/gep/mutation.js:123
const base = {
// ...
risk_level: 'low',
};
if (category === 'innovate') base.risk_level = 'medium';
High-Risk Escalation
High-risk mutations are rare and guarded by strict safety constraints:
// From src/gep/mutation.js:127
if (allowHighRisk && category === 'innovate') {
base.risk_level = 'high';
}
High-risk mutations are only allowed when allowHighRisk=true is explicitly passed.
Safety Constraints
Two hard safety rules prevent dangerous combinations:
Rule 1: No Innovate + High-Risk Personality
// From src/gep/mutation.js:134
const highRiskPersonality = isHighRiskPersonality(personalityState);
if (base.category === 'innovate' && highRiskPersonality) {
base.category = 'optimize';
base.expected_effect = 'safety downgrade: optimize under high-risk personality';
base.risk_level = 'low';
base.trigger_signals = [
...base.trigger_signals,
'safety:avoid_innovate_with_high_risk_personality'
];
}
High-risk personality is defined as:
// From src/gep/mutation.js:84
function isHighRiskPersonality(p) {
const rigor = p && Number.isFinite(p.rigor) ? p.rigor : null;
const riskTol = p && Number.isFinite(p.risk_tolerance) ? p.risk_tolerance : null;
if (rigor != null && rigor < 0.5) return true;
if (riskTol != null && riskTol > 0.6) return true;
return false;
}
Rule 2: High-Risk Requires Safe Personality
// From src/gep/mutation.js:142
if (base.risk_level === 'high' && !isHighRiskMutationAllowed(personalityState)) {
base.risk_level = 'medium';
base.trigger_signals = [...base.trigger_signals, 'safety:downgrade_high_risk'];
}
High-risk mutations require:
// From src/gep/mutation.js:91
function isHighRiskMutationAllowed(personalityState) {
const rigor = personalityState && personalityState.rigor || 0;
const riskTol = personalityState && personalityState.risk_tolerance || 1;
return rigor >= 0.6 && riskTol <= 0.5;
}
A personality with rigor < 0.6 or risk_tolerance > 0.5 cannot execute high-risk mutations.
Blast Radius Estimation
The blast radius measures the scope of change (files and lines modified).
This is calculated in solidify.js after the mutation is executed:
// From src/gep/solidify.js (referenced in evolve.js)
const blastRadius = {
files: modifiedFiles.length,
lines: totalLinesChanged,
insertions: totalInsertions,
deletions: totalDeletions,
};
Risk × Blast Radius Matrix
| Risk Level | Typical Blast Radius | Validation Strategy |
|---|
| Low | 1-3 files, less than 50 lines | Local tests only |
| Medium | 3-10 files, 50-200 lines | Full test suite |
| High | 10+ files, 200+ lines | Multi-stage validation + manual review |
If a “low-risk” mutation produces a large blast radius, it’s automatically flagged for review.
Mutation Strategies
The EVOLVE_STRATEGY env var controls intent balance:
EVOLVE_STRATEGY=balanced # Default: balanced mix
EVOLVE_STRATEGY=innovate # Maximize new features
EVOLVE_STRATEGY=harden # Focus on stability
EVOLVE_STRATEGY=repair-only # Emergency fix mode
Strategy Presets
// From src/gep/mutation.js:63
try {
var strategy = require('./strategy').resolveStrategy();
if (strategy && strategy.innovate >= 0.5) return 'innovate';
} catch (_) {}
See the Strategy Configuration guide for details.
Validation Flow
Every mutation goes through validation before being solidified:
Example Mutations
Repair Mutation
{
"type": "Mutation",
"id": "mut_1709876543210",
"category": "repair",
"trigger_signals": [
"log_error",
"errsig:TypeError: Cannot read property 'id' of undefined"
],
"target": "gene:error_handling_robust",
"expected_effect": "reduce runtime errors, increase stability, and lower failure rate",
"risk_level": "low"
}
Innovation Mutation
{
"type": "Mutation",
"id": "mut_1709876654321",
"category": "innovate",
"trigger_signals": [
"user_feature_request:add support for CSV export",
"capability_gap"
],
"target": "gene:feature_expansion",
"expected_effect": "explore new strategy combinations to escape local optimum",
"risk_level": "medium"
}
Safety-Downgraded Mutation
{
"type": "Mutation",
"id": "mut_1709876765432",
"category": "optimize",
"trigger_signals": [
"user_feature_request:refactor authentication",
"safety:avoid_innovate_with_high_risk_personality"
],
"target": "behavior:protocol",
"expected_effect": "safety downgrade: optimize under high-risk personality (avoid innovate+high-risk combo)",
"risk_level": "low"
}
Mutation Lifecycle
- Build:
buildMutation() constructs the object from signals
- Validate: Check
isValidMutation() for schema compliance
- Execute: Agent performs the change guided by the mutation
- Record: Outcome is stored in
events.jsonl with blast radius
- Learn: Memory graph updates causal paths
Next Steps
Personality
See how personality traits modulate mutation behavior
Evolution Cycle
Understand the full execution flow