---
name: google-ads-wasted-search-terms
description: "Every Wednesday, the search terms that cost money over 30 days with zero conversions, a proposed negative keyword for each, and one question: add them?. Use when the user asks for this, or when it runs on a schedule."
---

# Google Ads wasted search terms

Every Wednesday, the search terms that cost money over 30 days with zero conversions, a proposed negative keyword for each, and one question: add them?

The search terms report is where broad and phrase match show their work, and where part of the budget goes to searches nobody would have bid on: job seekers, people who want it free, a competitor's login page. Reading it is tedious, which is why negative keyword lists go stale.

The agent reads it weekly, picks the terms that spent real money without converting, and proposes the narrowest negative that blocks each one. Nothing changes until you say so. Then it adds the approved negatives to your shared list and reports exactly what it did.

## Two ways to get the data

Use the API or MCP route when you have an MCP server, a CLI or an API token for the app. Otherwise, if you can drive a browser the user is signed in to (Claude in Chrome, a Playwright or Chrome DevTools MCP server), use the browser route. Say which one you used.

## Route A: API or MCP server

### What you need

- Standard (edit) access to the Google Ads account, since approved negatives are written to it; read access is enough until you approve.
- Google Ads API access through a Google Cloud project with at least Basic access and OAuth credentials (developer tokens were retired in September 2026). The official Google Ads MCP server is read-only, so the write step needs the API or a connector that can make changes.
- The name of the shared negative keyword list to add to, or the campaigns to use instead.

If something is missing, say what and stop; do not invent numbers.

### Steps

1. **Pull 30 days of search terms** (Google Ads): Run GAQL on `search_term_view` selecting `search_term_view.search_term`, `search_term_view.status`, `campaign.name`, `ad_group.name`, `metrics.cost_micros`, `metrics.clicks` and `metrics.conversions`, `WHERE segments.date DURING LAST_30_DAYS AND metrics.conversions = 0 AND metrics.cost_micros > 25000000`, ordered by cost.
2. **Skip what is already handled**: Drop terms whose `status` is already `EXCLUDED` or `ADDED_EXCLUDED`, terms with 5 clicks or fewer, and anything containing your brand name.
3. **Propose the narrowest negative**: Use an exact match negative for a one-off term, and a phrase match negative for a single word that rules out any search (`jobs`, `login`, `meaning`). Negatives do not match close variants, so add the plural or the misspelling when that shows up too.
4. **Ask before changing anything**: Post an action card with the terms, their cost and the proposed negatives, naming where they will go: a shared negative keyword list or specific campaigns.
5. **Add the approved negatives** (Google Ads): On approval, create `SharedCriterion` entries with `keyword.text` and `keyword.match_type` in the shared set through `SharedCriterionService.MutateSharedCriteria`, or campaign negatives through `CampaignCriterionService` with `negative: true`. Then report what was added.

## Route B: the browser

### What you need

- Signed in to Google Ads with Standard access if negatives will be added in the browser; Read-only access is enough to review the list.

If something is missing, say what and stop; do not invent numbers.

### Steps

Start at https://ads.google.com/aw/keywords/searchterms. The user is signed in already; never type passwords or codes, and ask if a sign-in page appears.

1. **Open the search terms report**: Open `https://ads.google.com/aw/keywords/searchterms` (Campaigns, then Insights and reports, then Search terms). Pick the client account if asked, and set the date range to `Last 30 days`.
2. **Filter to spend without conversions**: Add filters `Conversions = 0` and `Cost > 25`, then sort by Cost, highest first. Check that the `Clicks`, `Campaign`, `Ad group` and `Added/Excluded` columns are visible.
3. **Skip what is handled**: Ignore rows already marked Excluded in the Added/Excluded column, rows with 5 clicks or fewer, and anything containing the brand name.
4. **Propose a negative per term**: Exact match for a one-off term, phrase match for a single word that rules out any search (`jobs`, `login`, `meaning`). Negatives ignore close variants, so include a plural or misspelling when it appears too.
5. **Ask, then add the approved ones**: Show the list with cost and clicks and stop. After approval, tick the rows, click `Add as negative keyword`, choose the negative keyword list or campaign, set the match type and save; then report what was added.

Note: The report omits low-volume search terms for privacy, in the UI as well as the API, and Performance Max terms are not in it (look under the campaign's Insights tab). Download the table when the account has more than a few hundred qualifying rows.

## The report

- **Wasted spend**: the total over 30 days on terms with no conversions.
- **Terms**: each with campaign, cost, clicks and the proposed negative with its match type.
- **The ask**: add all, add some, or skip this week.
- After approval, a short log of what was added and where.

## Post it to Briefkin

When `BRIEFKIN_TOKEN` is set, or `~/.config/briefkin/env` exists (the installer from https://briefkin.dev/docs writes it), also send the result to the user's Briefkin board as one card. Keep the `item_key` the same on every run so the card updates in place, use a new `event_id` per run, and put today's real numbers in place of the example ones. If the request fails, say so once and carry on.

```bash
[ -n "${BRIEFKIN_TOKEN:-}" ] || . ~/.config/briefkin/env
curl -sS -X POST "${BRIEFKIN_URL:-https://briefkin.dev}/v1/events" \
  -H "authorization: Bearer $BRIEFKIN_TOKEN" \
  -H "content-type: application/json" \
  -d @- <<'JSON'
{
  "v": 1,
  "event_id": "google-ads-wasted-search-terms/<date of this run, e.g. 2026-10-16>",
  "item_key": "google-ads-wasted-search-terms",
  "project": "Acme",
  "source": "Google Ads wasted search terms skill",
  "kind": "action",
  "title": "7 search terms spent $707 with no conversions",
  "summary": "Over the last 30 days these 7 search terms cost **$707** and brought 0 conversions. Four proposed negatives are phrase match on a single word that rules the search out; three are exact.",
  "action": {
    "request": "Add these 7 negatives to the shared list \"Account negatives\", which covers all Search campaigns?",
    "options": [
      "Add all 7",
      "Add the 4 phrase ones",
      "Add the 3 exact ones",
      "Not this week"
    ]
  },
  "widget": {
    "type": "Table",
    "props": {
      "columns": [
        "Search term",
        "Campaign",
        "Cost",
        "Clicks",
        "Negative"
      ],
      "align": [
        "left",
        "left",
        "right",
        "right",
        "left"
      ],
      "rows": [
        [
          "free invoice template",
          "Non-brand Search",
          "$184",
          61,
          "[free invoice template]"
        ],
        [
          "quickbooks login",
          "Competitors",
          "$142",
          52,
          "\"login\""
        ],
        [
          "invoice factoring companies",
          "Non-brand Search",
          "$112",
          34,
          "\"factoring\""
        ],
        [
          "invoice clerk jobs",
          "Non-brand Search",
          "$96",
          38,
          "\"jobs\""
        ],
        [
          "how to write an invoice by hand",
          "Non-brand Search",
          "$71",
          29,
          "[how to write an invoice by hand]"
        ],
        [
          "xero invoice template download",
          "Competitors",
          "$64",
          19,
          "[xero invoice template download]"
        ],
        [
          "invoice meaning in hindi",
          "Non-brand Search",
          "$38",
          21,
          "\"meaning\""
        ]
      ]
    }
  }
}
JSON
```

Widgets come from the Briefkin catalog (https://briefkin.dev/v1/catalog). Without a token, just give the user the report.

## Run it on a schedule

Suggested: Wednesdays at 10:00 (`0 10 * * 3`). From cron, with the agent signed in on that machine:

```bash
0 10 * * 3 claude -p "Run the google-ads-wasted-search-terms skill"
# Codex: codex exec, Gemini CLI: gemini -p, Copilot CLI: copilot -p, OpenCode: opencode run
```

Or use the agent's own scheduler (Claude Code routines, Codex automations, Claude or ChatGPT scheduled tasks): https://briefkin.dev/skills/google-ads-wasted-search-terms#schedule

Source: https://briefkin.dev/skills/google-ads-wasted-search-terms
