Toprank ads
Manage Google Ads — performance, keywords, bids, budgets, negatives, campaigns, ads, search terms, QS, location targeting, bulk operations. Use for any mention of Google Ads, CPA, ROAS, ad spend, or campaign settings.
git clone https://github.com/nowork-studio/toprank
T=$(mktemp -d) && git clone --depth=1 https://github.com/nowork-studio/toprank "$T" && mkdir -p ~/.claude/skills && cp -r "$T/google-ads/ads" ~/.claude/skills/nowork-studio-toprank-ads && rm -rf "$T"
google-ads/ads/SKILL.mdSetup
Read and follow
../shared/preamble.md — it handles MCP detection, token, and account selection. If config is already cached, this is instant.
Interaction Modes
This skill handles two very different request types. Recognizing which one you're in avoids unnecessary work.
Direct action (fast path):
User: "pause the keyword 'dog grooming' in the Seattle campaign"
- Confirm: "I'll pause 'dog grooming' in Pet Daycare - Seattle. Go ahead?"
- On approval: call
, log perpauseKeywordreferences/change-tracking.md- Done. No session checks, no performance analysis.
Change impact review:
User: "check my changes" / "did my changes work?" / "review my changes"
- Read
and run the change review checksreferences/session-checks.md- If no pending changes: tell the user no recent changes are logged
- If changes exist but review window hasn't passed: show maturation message (see
)references/session-checks.md- If ready for review: pull before/after metrics, compute deltas, show results
Analysis request:
User: "how are my ads doing?"
- Read
and run those checks (pending reviews, anomalies)references/session-checks.md- Pull data following the Performance Summary playbook in
references/workflow-playbooks.md- Read
for thresholdsreferences/analysis-heuristics.md- Deliver report using the template in
references/workflow-playbooks.md
Rules
- Confirm before writing. Show what you plan to change, the current value, and the new value. Users need to see the impact before approving — a blind "done" erodes trust.
- Start with reads. When the user asks about ads, begin with
andgetAccountInfo
to orient yourself.listCampaigns - Show numbers clearly. Format cost as dollars, CTR as percentages, include date ranges. Vague metrics are useless.
- Recommend before acting. When you spot waste, present the finding and wait for approval.
- Guardrails are server-side. Bid changes >25% and budget changes >50% will be rejected by the API.
- Log every write per
.references/change-tracking.md - moveKeywords defaults to PHRASE match and does NOT inherit from the source keyword. Always specify matchType explicitly — otherwise exact match keywords silently become phrase match.
Reference Routing
For simple operations (pause, rename, single bid change), you typically don't need reference files. For analysis, pick the right one:
| Situation | Read |
|---|---|
| Performance analysis, keyword evaluation, waste calculation | (start here — routes to deeper files) |
| Step-by-step playbooks, report template | |
| QS diagnostics, component-level fixes | |
| Bid strategy selection, migration, Smart Bidding | |
| Industry CPA/CTR/CPC benchmarks, seasonal adjustments | |
| Search term scoring, n-gram analysis, negative strategy | |
| Campaign/ad group structure, naming, restructuring | |
| GAQL query patterns, adaptive fetching by account size | |
Available Tools
Read (safe, no side effects)
- getAccountInfo — Account name, currency, timezone, test status
- listCampaigns — All campaigns with impressions, clicks, cost, conversions
- getCampaignPerformance — Daily metrics over a date range
- getKeywords — Top keywords with quality scores
- getSearchTermReport — Actual search queries triggering ads
- runGaqlQuery — Custom read-only GAQL SELECT query (max 50 rows; see
)../shared/gaql-cookbook.md - getChanges — Recent AdsAgent changes with
s for undochangeId - listConnectedAccounts — All connected Google Ads accounts
- getTrackingTemplate — Current tracking template at any level
- listAdGroups — Ad groups in a campaign with metrics
- listAds — Ads in a campaign/ad group with copy, URLs, status, metrics
- getImpressionShare — Search/top/abs-top IS and budget/rank-lost IS (max 90 days)
- getConversionActions — Conversion actions and settings
- getAccountSettings — Auto-tagging, tracking template, conversion tracking IDs
- getCampaignSettings — Bidding, network, locations, schedule
- getNegativeKeywords — Negative keywords for a campaign (check before adding to avoid duplicates)
- getRecommendations — Google optimization recommendations
- getKeywordIdeas — Keyword research suggestions based on seed keywords or URL
- getPmaxAssetGroups — Performance Max asset groups with metrics
- getPmaxAssets — Assets within a PMax asset group
- searchGeoTargets — Find geo target constant IDs for location targeting
Write (mutates the account — confirm with user first)
All write tools return a
changeId for undo within 7 days.
- pauseKeyword / enableKeyword — Stop or re-enable a keyword
- addKeyword — Add a new keyword to an ad group
- updateBid — Change CPC bid (manual/enhanced CPC only, max 25% change)
- addNegativeKeyword — Block irrelevant terms at campaign level (BROAD, PHRASE, or EXACT; default: PHRASE)
- removeNegativeKeyword — Remove a negative keyword
- updateCampaignBudget — Change daily budget (max 50% change, min $1/day)
- updateCampaignBidding — Change bid strategy (e.g., switch to Target CPA, Maximize Conversions). This is how you implement recommendations from
references/bid-strategy-decision-tree.md - updateCampaignGoals — Change campaign conversion goals
- createCampaign — Create a full paused search campaign. Headlines (3-15, max 30 chars), descriptions (2-4, max 90 chars), finalUrl required. Default: MAXIMIZE_CONVERSIONS
- pauseCampaign / enableCampaign — Pause or re-enable a campaign
- removeCampaign — PERMANENTLY delete (cannot undo — prefer pauseCampaign)
- setTrackingTemplate — Set/clear tracking template
- createAdGroup — Create a new ad group
- createAd — Create RSA. Headlines (3-15, max 30 chars), descriptions (2-4, max 90 chars), finalUrl required
- pauseAd / enableAd — Pause or re-enable an ad
- removeAd — Permanently delete an ad
- updateAdFinalUrl — Change an ad's landing page URL
- updateAdAssets — Replace RSA headlines/descriptions (complete replacement — provide every asset)
- bulkUpdateBids — Update up to 50 keyword bids (each capped at 25% change)
- bulkPauseKeywords — Pause up to 100 keywords (partial success possible — report what succeeded and what failed)
- bulkAddKeywords — Add up to 100 keywords to an ad group (partial success possible)
- moveKeywords — Move keywords between ad groups in same campaign. Max 100. See Rule 7 about match type.
- renameCampaign / renameAdGroup — Rename a campaign or ad group
- updateCampaignSettings — Update network and/or location targeting (geo target constant IDs, e.g. '2840' for US). Supports negative locations.
- pausePmaxAssetGroup / enablePmaxAssetGroup — Pause or enable a Performance Max asset group
- undoChange — Reverse a previous write by
changeId
Account Baseline
Maintain
{data_dir}/account-baseline.json for anomaly detection. Update at the END of any session where you pulled campaign data — no extra API calls needed.
{ "accountId": "<from config>", "lastUpdated": "<ISO 8601>", "campaigns": { "<campaignId>": { "name": "<campaign name>", "rolling30d": { "avgDailySpend": 0, "totalConversions": 0, "avgCpa": 0, "avgCtr": 0, "avgConvRate": 0, "totalSpend": 0 }, "recent7d": { "spend": 0, "conversions": 0, "cpa": 0, "ctr": 0, "clicks": 0, "impressions": 0 }, "snapshotDate": "<ISO 8601>" } } }
Update formula:
rolling30d = (0.7 x previous_rolling30d) + (0.3 x recent_7d x (30/7)). The (30/7) factor projects 7-day values to 30-day equivalents. New campaigns: initialize rolling30d from recent7d directly. Cap at 50 campaigns (spend > $0 in last 30 days only).
Conditional Handoffs
After analysis, proactively offer relevant skills:
- Ad copy problems (CTR issues in 2+ ad groups): suggest
/ads-copy - Missing business context (no
or >90 days old): suggestbusiness-context.json
first/ads-audit - Keyword gaps (3+ converting search terms not yet keywords): offer to add them
- Landing page misalignment (CTR above industry benchmark but conversion rate below on multiple ad groups): suggest
/ads-landing - Competitive intelligence (impression share declining or new competitor patterns): suggest
/ads-compete