Auto-rollback safety

Every change the agent makes captures a pre-execution snapshot before mutation. The agent then measures whether the change actually improved the campaign. If it made things worse, the change is automatically rolled back to the pre-execution state.

This works on Pro and Max: for changes you approve, and for changes Max hands-free applies by itself.

How it works

At execution time, the executor captures the relevant Google Ads state into pre_execution_state on the optimization session row. After mutation, measure-outcomes cron checks the campaign's metrics at fixed time windows relative to executed_at:

  • Surgical changes: T+24h and T+7d
  • Meaningful changes: T+24h, T+7d, and T+14d

Each window compares the post-change metrics against the pre-change baseline (the daily average over the 21 days before execution). Verdict is computed per window.

Measurement windows

The windows match Smart Bidding's settling curve. Bidding algorithms can produce noisy 24-hour data, so a bidding strategy change is never judged at T+24h. T+7d is where surgical changes settle. T+14d is where meaningful changes (bidding strategy switches, device bid modifiers) settle.

The user-level circuit breaker (3 auto-rollbacks in 30 days) only counts rollbacks from FINAL windows (T+7d for surgical, T+14d for meaningful). T+24h false positives never trip the breaker.

Verdicts

Three outcomes:

  • Improved. Metrics moved in the expected direction by more than the noise threshold. Recorded as a win in diagnostic_rule_outcomes.
  • Unchanged. Metrics moved within the noise band. Neither win nor loss. Recorded as neutral.
  • Worsened. Metrics dropped by more than the threshold. Auto-rollback fires.

Worsened thresholds vary by blast radius:

  • Surgical: 2-of-4 negative signals (cost up 25%, conversions down 20%, impressions down 40%, CPC up 35%). Small scale = more noise tolerance.
  • Meaningful: single strong negative signal (any of the 4 above). Larger scale = tighter threshold.

Rollback mechanics

When a worsened verdict triggers, measure-outcomes invokes agent-optimize with action="rollback". The rollback executor:

  1. Loads pre_execution_state from the session row.
  2. Constructs inverse operations (PAUSED → ENABLED, new bid → old bid, added negative → remove, etc.).
  3. Mutates Google Ads to restore the pre-change state.
  4. Marks the session rolled_back_at = NOW with a reason.
  5. Inserts a real-time notification: "Agent reverted [action] on [campaign] because metrics worsened in the [window]."
  6. Feeds the failure into diagnostic_rule_outcomes for fleet-wide rule learning.
Rollback is non-destructive on the Google Ads side. We never delete data that was not added by VibeAds. The original campaign state is what gets restored.

Manual undo

For changes that the agent thinks are fine but you disagree with, every executed session has an "Undo Changes" button in the Optimize tab. Available for 7 days (surgical), 14 days (meaningful) or 48 hours (larger changes) after execution. Same rollback machinery, triggered by you instead of the cron.

The weekly digest email links each change that can still be undone to that campaign's Optimize tab. The email itself never changes anything: undoing always happens on the page.

Feeding fleet-wide learning

Every verdict (improved, unchanged, worsened) writes a row to the PII-free diagnostic_rule_outcomes table. Nightly, agent-aggregate refreshes a materialized view diagnostic_rule_success_rates grouped by (rule_action × category × tier).

This view drives the meaningful gate for Max hands-free: a rule needs a cautious (Wilson 95% lower bound) success rate of 80% or more, from at least 8 decisive outcomes in your category, before Max hands-free can apply it at the meaningful blast radius. New rules start manual-only and graduate to auto as evidence accumulates.

Below 40% success in a category with 50+ samples, the rule is auto-downgraded fleet-wide to manual until it recovers.