Dashboards mudam, janelas de atribuição mudam e decisões são tomadas ao longo do tempo. Um histórico simples em planilha não substitui a fonte oficial, mas ajuda a reconstruir o que a conta mostrava em cada execução e cria uma camada adicional para auditoria.

O que será registrado

Script completo

/**
 * HISTÓRICO DIÁRIO DO GOOGLE ADS NO GOOGLE SHEETS
 * Somente leitura: registra uma linha por execução.
 */
const CONFIG = {
  SPREADSHEET_URL: 'COLE_A_URL_DA_PLANILHA_AQUI',
  SHEET_NAME: 'Historico Google Ads'
};

function main() {
  const account = AdsApp.currentAccount();
  const query = `
    SELECT
      customer.id,
      metrics.impressions,
      metrics.clicks,
      metrics.cost_micros,
      metrics.conversions,
      metrics.conversions_value
    FROM customer
    WHERE segments.date DURING YESTERDAY
  `;

  const rows = AdsApp.search(query);
  if (!rows.hasNext()) {
    Logger.log('Sem dados para ontem.');
    return;
  }

  const row = rows.next();
  const sheet = getSheet();
  ensureHeader(sheet);

  const values = [[
    Utilities.formatDate(new Date(), account.getTimeZone(), 'yyyy-MM-dd HH:mm:ss'),
    account.getName(),
    account.getCustomerId(),
    Number(row.metrics.impressions || 0),
    Number(row.metrics.clicks || 0),
    Number(row.metrics.costMicros || 0) / 1e6,
    Number(row.metrics.conversions || 0),
    Number(row.metrics.conversionsValue || 0)
  ]];

  const nextRow = sheet.getLastRow() + 1;
  sheet.getRange(nextRow, 1, values.length, values[0].length).setValues(values);
  Logger.log(`Linha ${nextRow} registrada em ${CONFIG.SHEET_NAME}.`);
}

function getSheet() {
  if (!/^https:\/\/docs\.google\.com\/spreadsheets\//.test(CONFIG.SPREADSHEET_URL)) {
    throw new Error('Configure SPREADSHEET_URL com a URL completa da planilha.');
  }
  const ss = SpreadsheetApp.openByUrl(CONFIG.SPREADSHEET_URL);
  return ss.getSheetByName(CONFIG.SHEET_NAME) || ss.insertSheet(CONFIG.SHEET_NAME);
}

function ensureHeader(sheet) {
  if (sheet.getLastRow() > 0) return;
  sheet.getRange(1, 1, 1, 8).setValues([[
    'executado_em','conta','customer_id','impressoes','cliques','custo','conversoes','valor_conversoes'
  ]]);
  sheet.setFrozenRows(1);
}

Como preparar a planilha

  1. Crie uma planilha no Google Sheets.
  2. Copie a URL completa.
  3. Cole em SPREADSHEET_URL.
  4. Defina o nome da aba em SHEET_NAME.
  5. Autorize as permissões e rode em Visualizar.
  6. Depois de conferir a linha, programe uma execução diária.
Por que usar setValues()?Operações em lote são mais eficientes do que atualizar célula por célula. A própria documentação de boas práticas do Google recomenda reduzir chamadas repetitivas.

O que esse histórico não resolve

A planilha guarda um snapshot. Ela não corrige atribuição, deduplicação, consentimento ou diferença entre lead e venda. Para análise de negócio, conecte a leitura a CRM, receita confirmada e definição correta das conversões.

Como evoluir o script

Fontes oficiais