On month change, run.py redirected the write to the previous month's
GACampaignMes record but built the JSON from the new month's near-empty
record, overwriting the previous month's full daily history with just
the redirected day. Now it merges with the previous month's real
MetricasDiarias (via get_metricas_diarias_prev_month) before writing.
Also add get_metrics_for_date() and get_daily_metrics_for_month() to
GoogleAdsClient for reconstructing historical daily cost/conversions,
needed by the backfill scripts.
- Add get_monthly_metrics_all() bulk method to GoogleAdsClient
- Use bulk fetch in first pass instead of N individual API calls
- Pre-compute leadform conversions per course number
- For PMX campaigns with leadform companion, leads_grupo = PMX conv + leadform conv
- fco_pmx_60 now correctly shows 334 leads at 61% margin (was negative)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add get_daily_conversions_for_month() to GoogleAdsClient
- Add backfill_leads_google_mayo.py: populates 'leads' (Google conv) for all May days
- 147 day-entries updated across 49 GACampaignMes records
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Each optimizer run writes yesterday's cost, revenue (conversions x PPL)
and margin per campaign as a JSON entry keyed by day number into the
MetricasDiarias field. Yesterday is used because Google Ads data for
the current day is not yet available.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Fix GoogleCampaignID matching with comma delimiters (exact word boundary)
- Remove attr_utm_medium filter (campaign ID filter is specific enough)
- Fix get_campaign_metrics: accumulate all daily rows for monthly totals
- Fix SPRINT urgency: only trigger when capping > 0
- Add Log field to GACampaignMes with Airtable vs Google Ads discrepancy info
- batch_update_gacampaignmes_advice now also updates Log field
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add get_monthly_metrics_all() in GoogleAdsClient: fetches
conversions and cost for all campaigns in one query
- sync_campaigns_from_google_ads() now accepts monthly_metrics
and updates ConvMes and CosteMes fields in Airtable
- run.py fetches monthly metrics before sync and passes them
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Before each run, fetch all non-removed campaigns from Google Ads
and upsert them into the Airtable campaigns table: new campaigns
are created (Activa=False, pending manual PPL/Cap/CPA setup) and
existing ones get their name updated if it changed.
https://claude.ai/code/session_01WEcdWPxGWZKk8FGwBRLGR2