# Spend Pacing Watch

Read live ad spend from the ad platform's API, compare it against the campaign's pacing targets, and alert a human when spend is running over or under budget.

## When to use

- On a recurring schedule (daily or intraday) to check active ad campaigns against their pacing targets.
- When a stakeholder asks whether a campaign is on track to hit budget by period end.
- After a budget or target change, to confirm the new pace is being tracked correctly.
- When prior alerts flagged an anomaly and a follow-up check is needed.

## Tools

- `http-get` — call the ad platform's REST API to read current spend, budget, and date-range data for each campaign.
- `shell-execute` — run a small script to compute expected pace, actual pace, and the variance percentage from the fetched figures.
- `send-message` — notify a human or another agent when a campaign is over-pacing, under-pacing, or when access is blocked.
- `schedule-task`: register this watch on a recurring cron cadence so it reruns automatically without a human re-enqueuing it.

## Cadence

Monitoring must repeat, not run once. On first setup, use `schedule-task` to register a recurring run of this check on an appropriate cron cadence (for example `0 * * * *` hourly or `0 9 * * *` daily), passing the same monitoring instruction as the schedule prompt. The platform then reruns it automatically at each due time — you never depend on a human to re-enqueue it. Create the schedule only once; if this check is already scheduled, skip re-creating it.

## Playbook

1. Identify the campaign(s) and reporting window in scope for this check.
2. Call the ad platform's REST API with `http-get` (e.g. GET https://api.adplatform.com/v1/campaigns/{id}/insights). Authentication is injected by the org's Integration row for this host — never ask for, echo, or hardcode credentials. If the call returns 401/403 or no Integration row exists, stop and message a human via `send-message` asking them to create the Integration, naming the service and required scopes.
3. Confirm the response includes spend-to-date, total budget, and campaign start/end dates. If any field is missing or the result set is empty, treat this as a data problem, not a pacing problem, and note it for troubleshooting.
4. Use `shell-execute` to run a short script that computes: days elapsed / total days in period, expected spend at this point (budget * elapsed fraction), actual spend, and variance percentage (actual vs expected).
5. Compare variance against the pacing thresholds (for example, more than 15% over or under expected pace counts as out-of-pace).
6. If every campaign checked is within threshold, log the check as clean and stop — no alert is needed.
7. If one or more campaigns are out-of-pace, use `shell-execute` to format a concise summary: campaign name, expected vs actual spend, variance percentage, and direction (over/under).
8. Send that summary to the relevant human or channel via `send-message`, flagging whether action is likely needed (for example, pause an over-pacing campaign or raise budget for an under-pacing one). Note that adjusting budgets or pausing campaigns requires a write operation (PATCH/PUT) this skill cannot perform — hand that decision and any resulting change to a human via `send-message`.
9. Repeat the check for each campaign in scope, aggregating all out-of-pace findings into a single message rather than sending one alert per campaign.

## Failure modes

- 401/403 response -> missing Integration for the ad platform; stop and escalate via `send-message` naming the service and required scopes.
- Empty or missing spend/budget fields in the response -> verify the endpoint and campaign ID/date-range parameters before re-running.
- Rate limited by the ad platform -> back off and retry later; note the rate limit in memory so future runs space out calls.
- Pacing math looks implausible (e.g. negative variance, spend exceeding total budget) -> do not alert on faulty numbers; flag the data anomaly to a human instead of a pacing alert.

## Done when

- Each in-scope campaign has a computed pace variance for the current period.
- Any campaign outside the pacing threshold has been summarized and sent to a human via `send-message`.
- Campaigns within threshold are confirmed clean with no unnecessary alert sent.