Skip to content

Add draft_ad_group tool for creating ad groups in existing campaigns - #6

Merged
kLOsk merged 4 commits into
kLOsk:mainfrom
alexrich700:feature/draft-ad-group
Mar 23, 2026
Merged

Add draft_ad_group tool for creating ad groups in existing campaigns#6
kLOsk merged 4 commits into
kLOsk:mainfrom
alexrich700:feature/draft-ad-group

Conversation

@alexrich700

Copy link
Copy Markdown

Adds a new draft_ad_group tool that creates ad groups within existing campaigns, following the same draft → preview → confirm_and_apply pattern as draft_campaign.

What it does:

  • Creates an ad group (ENABLED, SEARCH_STANDARD) in a specified campaign
  • Optionally attaches keywords in the same atomic operation
  • Supports optional ad-group-level CPC bid (for MANUAL_CPC campaigns)

Safety / preflight checks:

  • Validates campaign exists and is a SEARCH campaign (blocks non-SEARCH)
  • Warns on BROAD match keywords with non-Smart Bidding campaigns
  • Warns on duplicate ad group names within the same campaign
  • Warns if cpc_bid_micros is set on a Smart Bidding campaign (gets ignored)
  • Gracefully surfaces preflight failures as warnings rather than silent passes

Bug fix (existing code):

  • Fixed null match_type handling across _validate_campaign, _validate_keywords, and _check_broad_match_safetykw.get("match_type", "").upper() crashes when the value is explicitly None (common with MCP/JSON callers). Changed to (kw.get("match_type") or "").upper().

Files changed:

  • src/adloop/ads/write.py — new draft_ad_group, _validate_ad_group, _preflight_ad_group_checks, _apply_create_ad_group + null match_type fix
  • src/adloop/server.py — new MCP tool registration
  • .claude/rules/adloop.md / .cursor/rules/adloop.mdc — orchestration docs for the new tool
  • CLAUDE.md — updated tool count
  • tests/test_draft_ad_group.py — 25 tests covering validation, preflight checks, and plan creation

claude added 4 commits March 20, 2026 23:39
Adds the ability to create additional ad groups within existing campaigns,
closing the gap where only draft_campaign could create the initial ad group.
The new tool follows the same two-step draft/confirm pattern with BROAD match
safety checks, keyword validation, and atomic execution via GoogleAdsService.mutate().

https://claude.ai/code/session_01NNbaDSsxSFVeTEPgRWqVVM
…e, CPC bid

Three new safety checks before creating an ad group:
1. Reject non-SEARCH campaigns (DISPLAY/SHOPPING) since ad group type is SEARCH_STANDARD
2. Warn if an ad group with the same name already exists (duplicate name confusion)
3. Warn if cpc_bid_micros is set on a Smart Bidding campaign (bid will be ignored)

Also consolidates the broad match safety check into the same preflight function,
reducing API calls by combining campaign info into a single GAQL query.

https://claude.ai/code/session_01NNbaDSsxSFVeTEPgRWqVVM
- Renumber check comments sequentially (1, 2, 3, 4) and align docstring
- Fix CLAUDE.md tool count: actual @mcp.tool registrations is 29, not 27

https://claude.ai/code/session_01NNbaDSsxSFVeTEPgRWqVVM
- Use `(kw.get("match_type") or "").upper()` to handle null/None match_type
  from MCP/JSON callers instead of raising AttributeError
- Replace blanket `except Exception: pass` in preflight checks with a
  warning so users know validations were skipped
- Add tests for null and missing match_type keys

https://claude.ai/code/session_01NNbaDSsxSFVeTEPgRWqVVM
@kLOsk
kLOsk merged commit 2b065fe into kLOsk:main Mar 23, 2026
kLOsk added a commit that referenced this pull request Mar 23, 2026
…CPC-cap support

Rebased on main after merging PRs #2, #3, #6. Removed duplicate
draft_ad_group (kept PR #6's version with preflight checks). Adds:
- update_ad_group, draft_callouts, draft_structured_snippets, draft_image_assets
- Campaign expansion settings (search_partners, display_network, max_cpc)
- Structured error handling for developer token and OAuth issues
- Shared _apply_campaign_assets helper replacing duplicated sitelink logic

All 77 tests pass.
@alexrich700
alexrich700 deleted the feature/draft-ad-group branch March 27, 2026 17:49
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants