| name | paid-channel-recap |
| description | Generate a paid-channel performance recap as a shareable HTML dashboard for a client, partner, or internal stakeholder after (or during) a campaign window. Answers the standard 6 questions: which channel won, CAC by channel, top geos, creative winners, search terms to own, and the scaling sequence post-campaign. Pulls data from the Google Ads MCP, Meta Ads MCP, and an optional GA4 export. Use when asked to: "build a campaign recap", "performance report for [client]", "channel recap for [campaign]", or when a stakeholder is asking for post-campaign data to inform their own scaling.
|
| metadata | {"version":"1.0.0"} |
Paid Channel Performance Recap
This skill produces a shareable HTML dashboard that answers a predictable set of stakeholder questions about a paid-channel campaign's performance. The output is designed to be safe to forward (absolute spend stripped by default) and lands as a single self-contained HTML file you can host anywhere.
When to use
Triggers:
- "build a recap for [client/partner/campaign]"
- "paid channel recap for [campaign]"
- A stakeholder is asking for performance insights to inform their own scaling
Inputs required
Before starting, confirm with the user:
- Subject name (client, partner, product, or internal campaign label) for the header
- Campaign identifier — a slug, keyword, or campaign-name substring that filters Google Ads and Meta Ads to the relevant ads
- Window: start date and end date (inclusive). The campaign may still be live.
- (Optional) GA4 export — CSV with landing page + country + source/medium + session key event rate + sessions
- (Optional) Where to host the final HTML (GitHub Pages, Vercel, S3, or just hand back the file)
Data sources
The skill expects these MCP servers configured:
- Google Ads MCP —
execute_gaql for GAQL queries. Customer ID and login customer ID are inputs.
- Meta Ads MCP —
get_ads, get_ad_accounts, etc., for ad-level insights and creative URLs.
- GA4 — optional CSV export from the GA4 UI; the skill does not call GA4 directly.
If a source is missing, the skill degrades gracefully and notes the gap in the final deliverable.
Data collection workflow
Run these in parallel where possible.
1. Google Ads via MCP
Use execute_gaql against the customer ID the user provides. Run the queries in references/gaql-queries.md — 7 queries covering:
- Dedicated campaigns matching the campaign slug/name
- All search terms matching the slug (branded spelling variants)
- Adjacent / category terms the ads appeared for
- Geo breakdown (via
geographic_view)
- Device breakdown (via
segments.device)
- Ad creative performance (
ad_group_ad)
- Top campaigns overall (for context)
2. Meta Ads via MCP
Confirm account access via get_ad_accounts, then pull ad-level data filtered to the campaign window:
ads = mcp__meta-ads__get_ads(
date_preset=None,
time_range={"since": "<start_date>", "until": "<end_date>"},
fields=["name", "creative", "insights{spend,ctr,actions,action_values,impressions,clicks,cpm,cpc}"],
)
For each ad, extract:
- Ad name (use this as the authoritative identifier)
- Creative: video URL and/or image URL directly from the creative object
- Insights: spend, CTR, purchases (from
actions where action_type=purchase), purchase value, CPM, CPC, impressions
Compute per-ad: CAC, ROAS, Click→Purchase ratio. Identify UGC video vs static image from creative.video_id presence.
Roll up totals: total spend, total purchases, blended Meta CAC, blended Meta ROAS.
Because the MCP returns the real ad name alongside the creative's video/image URL, you can attach performance metrics directly to the correct creative without manual matching.
3. GA4 sessions by channel (if export provided)
Parse the GA4 CSV (landing page × country × source/medium × session key event rate × sessions).
Aggregate:
- By source/medium: total sessions + weighted CVR per channel
- By country: sessions + CVR (top 15 markets)
- Meta paid on-site CVR: filter to
meta / cpc source
- Google paid on-site CVR: filter to
google / cpc
These feed Section 1 (sessions by channel) and Section 3 (geography).
Output structure
The HTML has these sections, each mapping to a stakeholder question:
- At a glance — 4 stat cards: Gross revenue, Refund rate (if applicable), Blended Paid CAC, Paid Share of Sales
- Section 1 · Power channel — sessions by channel bar chart + purchases attributed by channel
- Section 2 · CAC by channel — table with Purchases, CAC, Role (no absolute-spend column by default)
- Section 3 · Audience & Geography — country CVR bars + interest/lookalike commentary
- Section 4 · Creative attribution — performance table + embedded video/image creative library
- Section 5 · Search terms to own — combined Google Ads table (branded + competitor + category), no spend column by default
- Recommended sequence — 5-step scaling playbook
The CSS skeleton lives in references/template.css (or inline in examples/example.html). Fill tokens with data from the collection steps.
Stakeholder-safe redaction (default mode)
When the recap will be forwarded to an external party (client, partner, etc.), the skill strips fields that would expose internal economics or strategy. See references/redaction-rules.md for the full list.
Default redact:
- Absolute paid spend ($ amounts)
- Margin / profit dollars
- Cash refund dollars (keep refund rate %)
- Internal campaign naming conventions — rename to human-readable role labels
- Account-level impression share
Default keep:
- Gross revenue and order/invoice count
- Refund rate %
- Purchase counts per channel
- CAC per channel (derived from spend but reasonable to share)
- CTR, CVR, Click→Purchase ratios
- Geography CVRs
- Creative media URLs and engagement metrics
- Search terms with clicks/conversions
The user can override redaction at the start ("internal mode — include spend") if the recap is for an internal audience.
Deployment
Three options the skill supports:
- Hand back the file — save to
./output/<slug>_recap.html and stop there.
- GitHub Pages — drop into a Pages-enabled repo path the user names, commit, push.
- Vercel / Netlify / S3 — emit a static file and a one-liner deploy command for the user's stack.
The HTML is self-contained (inline CSS, external creative media URLs only). No build step, no JS dependencies.
Final deliverable to user
Return:
- Live URL (if deployed) or local file path
- Summary of what's answered vs. any data gaps (e.g., "Google Ads data missing for last 3 days of window — re-run when fresh")
- Offer to draft a short forwarding message (Slack / email) the user can paste when sharing with the stakeholder
Related skills
| Skill | Relationship |
|---|
paid-ads-context | Reads section 4 (attribution), section 6 (redaction policy), section 1 (subject identity) |
google-ads-manager | Pulls the same GAQL data; this is the stakeholder-facing twin of its internal weekly review |
attribution-modeling | Provides the profit table that powers the "real CAC" and "real ROAS" columns |
weekly-ops-review | Sister skill — same data, different audience (internal operator vs external stakeholder) |
ad-creative | The recap surfaces creative winners; those feed back as input for the next round of creative iteration |
apple-grade-design | Optional: redesign the HTML template against your brand tokens before shipping the recap to a major partner |
References
references/gaql-queries.md — the 7 Google Ads GAQL queries
references/meta-ads-extraction.md — Meta Ads MCP extraction patterns
references/redaction-rules.md — stakeholder-safe redaction guidance
examples/example.html — synthetic example recap to use as a layout reference
Changelog
- v1.0.0 — initial public release