Skip to main content
This page is also available in Ukrainian.

Overview

This release adds two major groups of endpoints:
  1. Google Ads Management CRUD — create, update, and delete ad groups, ads (RSAs), keywords, ad schedule, and location targeting directly via the API
  2. Live Campaign Editing — read and update settings on already-published Google Ads campaigns
There are also a few changes to existing GET endpoints worth noting.

Changes to existing endpoints

login_customer_id parameter no longer needed

The login_customer_id query parameter is no longer used by any Google Ads endpoint. The backend now resolves it automatically from the database based on customer_id. If you’re currently passing login_customer_id, nothing will break — it’s simply ignored. However, we recommend removing it from your API calls to keep things clean, since it no longer has any effect.

New campaign_id filter on /ads endpoint

The GET /ads endpoint now accepts an optional campaign_id query parameter to filter ads by campaign. This is in addition to the existing ad_group_id filter.

Status filters relaxed

Data table endpoints that previously returned only ENABLED resources now also return PAUSED resources. This affects campaigns, ad groups, ads, and keywords. The frontend should be prepared to display both statuses.

Server-side search (?search=)

All data table GET endpoints now support a search query parameter. See the dedicated Table Search guide for the full API spec (searchable fields per table, parameter rules, etc.). This section focuses on how to implement search on the frontend, based on how admin.cattix.com already does it. The admin panel implements search at two levels:
  1. Per-table search bar — a text input above each data table that filters that specific table via ?search=<term>
  2. Global search dialog (Cmd+K) — fires the same ?search= query against all 7 tables in parallel, showing results grouped by category
You can implement either or both.

1. Debounce the input (300ms)

Don’t fire an API call on every keystroke. The admin uses a 300ms debounce:

2. Prevent stale results (race condition guard)

If the user types “sho” then quickly changes to “brand”, the “sho” response may arrive after “brand”. Use a search-ID ref to discard stale responses:

3. For global search — fire parallel requests

The admin fires all 7 category requests independently (not with Promise.all), so results appear progressively as each category resolves:
This gives the UI a nice progressive-loading feel with a progress indicator (“Searching… 3/7 loaded”).

4. UI states to handle

5. Navigate from global search to table

When a user selects a result in the global dialog, navigate to the data table with the search pre-filled:
On the data page, read search from URL params and auto-fetch on mount.

Reference implementation

The full working implementation lives in admin.cattix.com:
All management endpoints are under the /api/v1/google-ads/ prefix and require a customer_id query parameter. Base URL pattern:
All endpoints require Authorization: Bearer <token>.

Ad Groups

Create ad group (Swagger)

integer
required
Campaign ID to create the ad group in.
string
required
Ad group name (1-256 characters).
string
default:"SEARCH_STANDARD"
One of: SEARCH_STANDARD, DISPLAY_STANDARD, SHOPPING_PRODUCT_ADS.
string
default:"ENABLED"
Initial status: ENABLED or PAUSED.
integer
Default CPC bid in micros (1,000,000 = $1.00). Must be > 0.
Response: AdGroupMutationResult

Update ad group status (Swagger)

string
required
New status: ENABLED or PAUSED.

Delete ad group (Swagger)


Ads (Responsive Search Ads)

Create RSA (Swagger)

integer
required
Ad group to create the RSA in.
string
required
Landing page URL.
RSAAssetInput[]
required
3-15 headlines. Each has text (required) and optional pinned_field (HEADLINE_1, HEADLINE_2, etc.).
RSAAssetInput[]
required
2-4 descriptions. Same structure as headlines.
string
Max 15 characters.
string
Max 15 characters.
string
Optional mobile-specific landing page.
string
Optional tracking template.
Response: AdMutationResult

Update RSA (Swagger)

All fields optional — only provided fields are updated. When headlines or descriptions are provided, they replace all existing assets.

Delete ad (Swagger)

Note: both ad_group_id and ad_id are required in the path.

Keywords

Create keywords (Swagger)

integer
required
Ad group to add keywords to.
KeywordInput[]
required
Array of keywords. Each has:
  • text (string, required) — keyword text
  • match_type (string, default "PHRASE") — EXACT, PHRASE, or BROAD
Response: BatchKeywordOperationResponseSchema (same as existing batch keyword response).

Update keyword (Swagger)

string
ENABLED or PAUSED.
integer
New CPC bid in micros. Must be > 0.
Response: KeywordMutationResult

Remove keywords (batch) (Swagger)

Uses the same BatchKeywordOperationRequestSchema as the existing batch endpoint.

Ad Schedule

Add ad schedule entries (Swagger)

integer
required
Campaign to add schedule to.
AdScheduleEntryInput[]
required
Schedule entries. Each entry has:
  • day_of_week (string) — MONDAY, TUESDAY, … SUNDAY
  • start_hour (int, 0-23)
  • start_minute (int, default 0) — 0, 15, 30, or 45
  • end_hour (int, 0-24)
  • end_minute (int, default 0) — 0, 15, 30, or 45
Response: CriteriaMutationResult

Replace all ad schedule entries (Swagger)

Same body as POST. Replaces all existing schedule entries on the campaign.

Delete ad schedule entries (Swagger)

integer
required
Campaign owning the criteria.
string[]
required
Resource names of schedule criteria to remove.

Location Targeting

Add locations (Swagger)

integer
required
Campaign to add locations to.
LocationTargetingEntry[]
required
Array of locations. Each has:
  • geo_target_constant_id (integer) — Google Ads geo target constant ID
  • target_type (string, default "INCLUDE") — INCLUDE or EXCLUDE
Response: CriteriaMutationResult

Replace all locations (Swagger)

Same body as POST. Replaces all existing location targeting on the campaign.

Delete location targeting (Swagger)

Same body as ad schedule delete (campaign_id + resource_names).

Live Campaign Editing

These endpoints allow reading and updating settings on already-published (live) Google Ads campaigns, under the /api/v1/campaigns/live/ prefix.

Get campaign settings (Swagger)

Returns the full campaign settings for the edit UI:

Update campaign settings (Swagger)

Only provided fields are updated. All fields are optional.
string
New campaign name (1-256 characters).
string
ENABLED or PAUSED. Cannot set to REMOVED — use DELETE.
integer
New daily budget in micros.
BiddingStrategySchema
New bidding strategy configuration.
NetworkSettingsSchema
Search/display network settings.
integer[]
Replace-all — sets exactly these language IDs.
LocationTargetSchema[]
Replace-all — sets exactly these locations.
AdScheduleSchema
Replace-all — sets exactly this schedule.
string (YYYY-MM-DD)
Campaign start date.
string (YYYY-MM-DD)
Campaign end date.
ConversionGoalSchema[]
Replace-all — sets exactly these conversion goals.
Targeting fields (language_ids, location_targets, ad_schedule, conversion_goals) use replace-all semantics. When any of these fields is provided, the existing values are fully replaced. If you omit a field, it remains unchanged.
Response: UpdateCampaignResultSchema

Delete campaign (Swagger)

Returns 204 No Content on success. This is irreversible — the campaign and all child resources (ad groups, keywords, ads) will be removed.

Error handling

All mutation endpoints return consistent error shapes:

Single-resource mutations

AdGroupMutationResult, AdMutationResult, KeywordMutationResult:

Batch/criteria mutations

CriteriaMutationResult:

Common HTTP errors


Migration checklist

1

Implement server-side search

This is likely the biggest FE task. Add per-table search bars and optionally a global Cmd+K search dialog. See the implementation guide above for patterns (debounce, race-condition guard, progressive loading) and the admin.cattix.com reference code.
2

Handle PAUSED resources in data tables

Data tables now return both ENABLED and PAUSED campaigns, ad groups, and keywords. Add status badges or visual distinction for paused items.
3

Build CRUD UI for ad groups, ads, keywords

Use the new management endpoints to implement create/edit/delete actions in data tables.
4

Build campaign edit page

Use GET /campaigns/live/{cid}/{campaign_id} to populate the edit form and PATCH to save changes.
5

Add campaign_id filter to ads table

The /ads endpoint now supports ?campaign_id= for filtering. Use this when showing ads within a specific campaign.
6

Clean up login_customer_id from API calls (optional)

It’s no longer used and will be silently ignored, but removing it keeps your code clean.

TypeScript interfaces

For frontend type safety, here are the key interfaces: