curl --request POST \
--url https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"domains": [
"<string>"
],
"group_label": "<string>"
}
'import requests
url = "https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights"
payload = {
"domains": ["<string>"],
"group_label": "<string>"
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({domains: ['<string>'], group_label: '<string>'})
};
fetch('https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'domains' => [
'<string>'
],
'group_label' => '<string>'
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights"
payload := strings.NewReader("{\n \"domains\": [\n \"<string>\"\n ],\n \"group_label\": \"<string>\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"domains\": [\n \"<string>\"\n ],\n \"group_label\": \"<string>\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"domains\": [\n \"<string>\"\n ],\n \"group_label\": \"<string>\"\n}"
response = http.request(request)
puts response.read_body{
"brand_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"generated_at": "2023-11-07T05:31:56Z",
"group_key": "<string>",
"module": "google-ads",
"group_label": "<string>",
"brand_domain": "<string>",
"domains": [
"<string>"
],
"cohort_domains": [
"<string>"
],
"coverage": {
"targets_total": 0,
"measured": 0,
"missing": [
"<string>"
],
"fetch_failed": [
"<string>"
],
"persist_failed": [
"<string>"
],
"skipped_cost": [
"<string>"
],
"last_run_at": "2023-11-07T05:31:56Z",
"brand_measured": false,
"brand_domain": "<string>",
"brand_not_measured_reason": "<string>",
"near_duplicate_pairs": [
{
"domain_a": "<string>",
"domain_b": "<string>",
"edit_distance": 123
}
],
"near_duplicate_scan_truncated": false,
"near_duplicate_scanned_count": 0
},
"totals": {
"measured_count": 0,
"est_group_monthly_spend_usd": 123,
"spend_measured_count": 0,
"est_group_paid_traffic": 123,
"traffic_measured_count": 0,
"median_cpc_usd": 123,
"cpc_measured_count": 0,
"data_from": "2023-11-07T05:31:56Z",
"data_to": "2023-11-07T05:31:56Z",
"estimate_notice": "Estimated — modelled from competitor paid keywords (DataForSEO). Not actual competitor spend.",
"sample_notice": "Keyword counts are the stored tracked sample (up to 200 per brand), not the full paid-keyword population."
},
"members": [
{
"domain": "<string>",
"est_monthly_spend_usd": 123,
"spend_share_pct": 123,
"est_paid_traffic": 123,
"paid_keyword_count": 123,
"avg_cpc_usd": 123,
"paid_vs_organic_ratio": 123,
"overlap_keyword_count": 123,
"gap_keyword_count": 123,
"captured_at": "2023-11-07T05:31:56Z"
}
],
"brand_reference": {
"domain": "<string>",
"est_monthly_spend_usd": 123,
"spend_share_pct": 123,
"est_paid_traffic": 123,
"paid_keyword_count": 123,
"avg_cpc_usd": 123,
"paid_vs_organic_ratio": 123,
"overlap_keyword_count": 123,
"gap_keyword_count": 123,
"captured_at": "2023-11-07T05:31:56Z"
},
"momentum": {
"window_days": 90,
"series": [
{
"domain": "<string>",
"points": [
{
"captured_at": "2023-11-07T05:31:56Z",
"est_monthly_spend_usd": 123,
"paid_keyword_count": 123
}
]
}
],
"risers": [
{
"domain": "<string>",
"delta_usd": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"faders": [
{
"domain": "<string>",
"delta_usd": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"keyword_risers": [
{
"domain": "<string>",
"delta_keywords": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"keyword_faders": [
{
"domain": "<string>",
"delta_keywords": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"insufficient_history": [
"<string>"
],
"measured": false,
"comparison_basis": {
"measured": false,
"domains_with_captures": 0,
"domains_with_prior_capture": 0,
"has_prior_snapshot": false,
"domains_with_in_window_prior_capture": 0
},
"estimate_notice": "Estimated — modelled from competitor paid keywords (DataForSEO). Not actual competitor spend."
},
"gap_consensus": {
"keywords": [
{
"keyword": "<string>",
"member_domains": 0,
"example_domains": [
"<string>"
],
"search_volume": 123,
"cpc": 123,
"best_position": 123
}
],
"measured_domains": 0,
"union_count": 123,
"consensus_count": 0,
"total_search_volume": 123,
"measured": false,
"promoted_keyword": "<string>",
"displaced_keyword": "<string>",
"basis_notice": "Keyword counts are the stored tracked sample (up to 200 per brand), not the full paid-keyword population."
},
"overlap_pressure": {
"rows": [
{
"domain": "<string>",
"shared_count": 123,
"comparable_count": 0,
"outranked_count": 123,
"outranked_share_pct": 123,
"top_contested": [
{
"keyword": "<string>",
"search_volume": 123,
"cpc": 123,
"brand_position": 123,
"competitor_position": 123
}
]
}
],
"measured_domains": 0,
"measured": false,
"position_basis": "SERP position proxy from stored paid-intersection rows — not Google Auction Insights."
},
"ad_copy": {
"members": [
{
"domain": "<string>",
"text_count": 0,
"image_count": 0,
"video_count": 0,
"creatives": [
{
"media_kind": "text",
"headline": "<string>",
"body": "<string>",
"cta": "<string>",
"surface": "<string>",
"snapshot_url": "<string>",
"image_url": "<string>",
"started_at": "2023-11-07T05:31:56Z",
"scraped_at": "2023-11-07T05:31:56Z",
"observed_running_days": 123,
"video_url": "<string>",
"landing_page_url": "<string>",
"verified": true,
"position": 123
}
]
}
],
"measured_domains": 0,
"total_creatives": 123,
"text_count": 0,
"image_count": 0,
"video_count": 0,
"top_ctas": [
{
"cta": "<string>",
"count": 0,
"member_domains": 0
}
],
"longest_running": [
{
"domain": "<string>",
"headline": "<string>",
"observed_running_days": 0,
"started_at": "2023-11-07T05:31:56Z"
}
],
"changes": {
"measured": false,
"new_count": 0,
"retired_count": 0,
"compared_domains": 0,
"previous_captured_at": "2023-11-07T05:31:56Z",
"latest_captured_at": "2023-11-07T05:31:56Z",
"basis_notice": "Compared against each brand's previous capture, over creatives the provider gave a stable id. Unkeyed creatives cannot be matched across captures and are counted as neither new nor retired."
},
"measured": false,
"capture_notice": "Captured sample from the Google Ads Transparency Center — not a census of the group's ads."
},
"findings": [
{
"rule_id": "<string>",
"module": "seo",
"panel": "<string>",
"title": "<string>",
"detail": "<string>",
"severity": "info",
"evidence_refs": [
"<string>"
]
}
],
"estimate_notice": "Estimated — modelled from competitor paid keywords (DataForSEO). Not actual competitor spend."
}{
"detail": [
{
"loc": [
"<string>"
],
"msg": "<string>",
"type": "<string>",
"input": "<unknown>",
"ctx": {}
}
]
}Get Brand Intelligence Google Ads Group Insights Route
Cohort paid-search analysis for one competitor Brand Group (INSIGHTS tab).
POST because the cohort is a client-curated domain set, mirroring the SEO
route. An empty domains list means “the whole tracked set”. Reads only
already-persisted DataForSEO captures — no new provider spend.
curl --request POST \
--url https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"domains": [
"<string>"
],
"group_label": "<string>"
}
'import requests
url = "https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights"
payload = {
"domains": ["<string>"],
"group_label": "<string>"
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({domains: ['<string>'], group_label: '<string>'})
};
fetch('https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'domains' => [
'<string>'
],
'group_label' => '<string>'
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights"
payload := strings.NewReader("{\n \"domains\": [\n \"<string>\"\n ],\n \"group_label\": \"<string>\"\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"domains\": [\n \"<string>\"\n ],\n \"group_label\": \"<string>\"\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.example.com/api/v1/brands/{brand_id}/brand-intelligence/google-ads-group-insights")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"domains\": [\n \"<string>\"\n ],\n \"group_label\": \"<string>\"\n}"
response = http.request(request)
puts response.read_body{
"brand_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"generated_at": "2023-11-07T05:31:56Z",
"group_key": "<string>",
"module": "google-ads",
"group_label": "<string>",
"brand_domain": "<string>",
"domains": [
"<string>"
],
"cohort_domains": [
"<string>"
],
"coverage": {
"targets_total": 0,
"measured": 0,
"missing": [
"<string>"
],
"fetch_failed": [
"<string>"
],
"persist_failed": [
"<string>"
],
"skipped_cost": [
"<string>"
],
"last_run_at": "2023-11-07T05:31:56Z",
"brand_measured": false,
"brand_domain": "<string>",
"brand_not_measured_reason": "<string>",
"near_duplicate_pairs": [
{
"domain_a": "<string>",
"domain_b": "<string>",
"edit_distance": 123
}
],
"near_duplicate_scan_truncated": false,
"near_duplicate_scanned_count": 0
},
"totals": {
"measured_count": 0,
"est_group_monthly_spend_usd": 123,
"spend_measured_count": 0,
"est_group_paid_traffic": 123,
"traffic_measured_count": 0,
"median_cpc_usd": 123,
"cpc_measured_count": 0,
"data_from": "2023-11-07T05:31:56Z",
"data_to": "2023-11-07T05:31:56Z",
"estimate_notice": "Estimated — modelled from competitor paid keywords (DataForSEO). Not actual competitor spend.",
"sample_notice": "Keyword counts are the stored tracked sample (up to 200 per brand), not the full paid-keyword population."
},
"members": [
{
"domain": "<string>",
"est_monthly_spend_usd": 123,
"spend_share_pct": 123,
"est_paid_traffic": 123,
"paid_keyword_count": 123,
"avg_cpc_usd": 123,
"paid_vs_organic_ratio": 123,
"overlap_keyword_count": 123,
"gap_keyword_count": 123,
"captured_at": "2023-11-07T05:31:56Z"
}
],
"brand_reference": {
"domain": "<string>",
"est_monthly_spend_usd": 123,
"spend_share_pct": 123,
"est_paid_traffic": 123,
"paid_keyword_count": 123,
"avg_cpc_usd": 123,
"paid_vs_organic_ratio": 123,
"overlap_keyword_count": 123,
"gap_keyword_count": 123,
"captured_at": "2023-11-07T05:31:56Z"
},
"momentum": {
"window_days": 90,
"series": [
{
"domain": "<string>",
"points": [
{
"captured_at": "2023-11-07T05:31:56Z",
"est_monthly_spend_usd": 123,
"paid_keyword_count": 123
}
]
}
],
"risers": [
{
"domain": "<string>",
"delta_usd": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"faders": [
{
"domain": "<string>",
"delta_usd": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"keyword_risers": [
{
"domain": "<string>",
"delta_keywords": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"keyword_faders": [
{
"domain": "<string>",
"delta_keywords": 123,
"from_captured_at": "2023-11-07T05:31:56Z",
"to_captured_at": "2023-11-07T05:31:56Z",
"delta_pct": 123
}
],
"insufficient_history": [
"<string>"
],
"measured": false,
"comparison_basis": {
"measured": false,
"domains_with_captures": 0,
"domains_with_prior_capture": 0,
"has_prior_snapshot": false,
"domains_with_in_window_prior_capture": 0
},
"estimate_notice": "Estimated — modelled from competitor paid keywords (DataForSEO). Not actual competitor spend."
},
"gap_consensus": {
"keywords": [
{
"keyword": "<string>",
"member_domains": 0,
"example_domains": [
"<string>"
],
"search_volume": 123,
"cpc": 123,
"best_position": 123
}
],
"measured_domains": 0,
"union_count": 123,
"consensus_count": 0,
"total_search_volume": 123,
"measured": false,
"promoted_keyword": "<string>",
"displaced_keyword": "<string>",
"basis_notice": "Keyword counts are the stored tracked sample (up to 200 per brand), not the full paid-keyword population."
},
"overlap_pressure": {
"rows": [
{
"domain": "<string>",
"shared_count": 123,
"comparable_count": 0,
"outranked_count": 123,
"outranked_share_pct": 123,
"top_contested": [
{
"keyword": "<string>",
"search_volume": 123,
"cpc": 123,
"brand_position": 123,
"competitor_position": 123
}
]
}
],
"measured_domains": 0,
"measured": false,
"position_basis": "SERP position proxy from stored paid-intersection rows — not Google Auction Insights."
},
"ad_copy": {
"members": [
{
"domain": "<string>",
"text_count": 0,
"image_count": 0,
"video_count": 0,
"creatives": [
{
"media_kind": "text",
"headline": "<string>",
"body": "<string>",
"cta": "<string>",
"surface": "<string>",
"snapshot_url": "<string>",
"image_url": "<string>",
"started_at": "2023-11-07T05:31:56Z",
"scraped_at": "2023-11-07T05:31:56Z",
"observed_running_days": 123,
"video_url": "<string>",
"landing_page_url": "<string>",
"verified": true,
"position": 123
}
]
}
],
"measured_domains": 0,
"total_creatives": 123,
"text_count": 0,
"image_count": 0,
"video_count": 0,
"top_ctas": [
{
"cta": "<string>",
"count": 0,
"member_domains": 0
}
],
"longest_running": [
{
"domain": "<string>",
"headline": "<string>",
"observed_running_days": 0,
"started_at": "2023-11-07T05:31:56Z"
}
],
"changes": {
"measured": false,
"new_count": 0,
"retired_count": 0,
"compared_domains": 0,
"previous_captured_at": "2023-11-07T05:31:56Z",
"latest_captured_at": "2023-11-07T05:31:56Z",
"basis_notice": "Compared against each brand's previous capture, over creatives the provider gave a stable id. Unkeyed creatives cannot be matched across captures and are counted as neither new nor retired."
},
"measured": false,
"capture_notice": "Captured sample from the Google Ads Transparency Center — not a census of the group's ads."
},
"findings": [
{
"rule_id": "<string>",
"module": "seo",
"panel": "<string>",
"title": "<string>",
"detail": "<string>",
"severity": "info",
"evidence_refs": [
"<string>"
]
}
],
"estimate_notice": "Estimated — modelled from competitor paid keywords (DataForSEO). Not actual competitor spend."
}{
"detail": [
{
"loc": [
"<string>"
],
"msg": "<string>",
"type": "<string>",
"input": "<unknown>",
"ctx": {}
}
]
}Authorizations
Bearer authentication header of the form Bearer <token>, where <token> is your auth token.
Path Parameters
Body
Response
Successful Response
"google-ads"N-of-M acquisition coverage for one module's cohort (the ★S0/★C0 strip).
measured counts cohort domains that produced a stored metric row.
missing are targets that never did — their fetch or persist failed, or
they have not been acquired yet. For Content, fetch_failed is a typed
subset of missing, not an additional shortfall, so clients must
de-duplicate rather than sum those lengths. A competitor with a failed
acquisition must render as a failure chip, never as a measured zero.
Show child attributes
Show child attributes
Header-tile aggregates over MEASURED members only.
Every dollar/traffic/CPC figure is a DataForSEO MODEL — the D3 estimate notice ships with the payload so no renderer can forget it. Each metric carries its own measured-member count: a sum over 4 of 10 members must say so.
Show child attributes
Show child attributes
Show child attributes
Show child attributes
One measured member — feeds the leaderboard, positioning map and CPC/paid-dependence ladder from a single fetch.
Show child attributes
Show child attributes
Windowed spend movement. History is event-driven (bootstrap + manual
refresh), so sparse series are the EXPECTED state — members with fewer
than two in-window measured points land in insufficient_history,
never as a zero-change mover.
Show child attributes
Show child attributes
Keywords to steal — the cross-member union of stored gap lists.
union_count is a LOWER BOUND (each member's list is a <=200-row
sample); consensus_count counts keywords >=2 members bid on, over the
FULL union, never the rendered slice. promoted_keyword /
displaced_keyword disclose the last-row substitution; both None means
the rendered slice is exactly the top-ranked rows.
Show child attributes
Show child attributes
Show child attributes
Show child attributes
What the group says in its ads — captured creatives per member, exact CTA frequency (deterministic, no LLM in the measured layer), and the observed-run-time hint for creatives that carried both dates.
Show child attributes
Show child attributes
Show child attributes
Show child attributes
Was this page helpful?