AdsApp.search() vs AdsApp.report(): which should you use?
The two ways to run a GAQL query in a Google Ads script, how their results differ and when each fits.
Google Ads scripts offer two functions for querying data with GAQL. They accept the same query and return it in different shapes.
AdsApp.search()
Returns an iterator of rows. Each row is a nested object that follows the structure of the query.
var rows = AdsApp.search(
"SELECT campaign.name, metrics.clicks FROM campaign " +
"WHERE segments.date DURING LAST_7_DAYS"
);
while (rows.hasNext()) {
var row = rows.next();
Logger.log(row.campaign.name + " " + row.metrics.clicks);
}Field names in the result are camelCase: metrics.cost_micros becomes row.metrics.costMicros.
AdsApp.report()
Returns a report object: flat rows keyed by the field name exactly as written in the query, plus a one-line export to a spreadsheet.
var report = AdsApp.report(
"SELECT campaign.name, metrics.clicks FROM campaign " +
"WHERE segments.date DURING LAST_7_DAYS"
);
report.exportToSheet(SpreadsheetApp.openByUrl(SHEET_URL).getActiveSheet());
var rows = report.rows();
while (rows.hasNext()) {
var row = rows.next();
Logger.log(row["campaign.name"] + " " + row["metrics.clicks"]);
}Which to use
- Writing straight to a sheet β
report(), forexportToSheet. - Making decisions in code β
search(). The nested objects are easier to work with. - Large result sets β both handle far more rows than entity iterators, which stop at 50,000.
Things to watch
- Values may come back as strings in report rows; convert before doing arithmetic.
- Money is in micros in both.
- Resource names and IDs are available in both and are the reliable way to refer back to an entity.
Getting a ready-made snippet
Write and test the query in GAQL Lab, then click AdsApp.search() to copy a script snippet that runs the same query.