Skip to main content
Thirdwatchthirdwatch
Other

Build a Trend Monitoring Dashboard with Google Trends Data

Automate Google Trends data collection into a monitoring dashboard. Scheduled runs, slope-based alerts, and rising-query detection with a Python pipeline.

May 26, 2026 · 6 min read · 1,353 words
See the scraper →

Thirdwatch's Google Trends Scraper powers automated trend monitoring dashboards by returning structured JSON for any keyword list -- interest timeseries, directional slope, peak dates, and rising related queries. Schedule daily or weekly runs and pipe the output into a dashboard, spreadsheet, or alerting system. Built for growth teams, product managers, and analysts who want to track market signals continuously without manual Google Trends visits.

Why build a trend monitoring dashboard with Google Trends

Manual trend watching does not scale. According to Think with Google, search interest is one of the strongest leading indicators of consumer demand, often shifting weeks before sales data reflects the change. Brands that track these signals continuously can react to emerging demand faster than those relying on quarterly market reports.

The core problem is operational. A product manager tracking 30 category keywords visits trends.google.com daily, compares charts by memory, and flags changes in a Slack channel when something looks different. This process breaks at scale, misses gradual shifts, and relies on subjective visual interpretation. Research from Google's Keyword Planner documentation confirms that search volume signals correlate with downstream purchase intent across most verticals. A structured dashboard fed by scheduled scraper runs replaces manual monitoring with quantified slope values, automated spike detection, and historical baselines. The actor returns avgInterest, slope, peakDate, and timeline arrays that map directly to dashboard components -- no parsing, no chart screenshots, no manual data entry.

How does this compare to the alternatives?

Three approaches to continuous trend monitoring:

Approach Cost Reliability Setup time Maintenance
Manual Google Trends checks Free, high labor cost Inconsistent, depends on analyst 0 minutes Daily manual effort
DIY cron job with pytrends Free compute, fragile sessions Breaks on Google rate limits 4-8 hours You fix session/IP issues
Thirdwatch Google Trends Scraper + Apify schedule Pay per result Managed, rate-limit handling built in 15 minutes Thirdwatch maintains

The manual approach works for five keywords checked weekly. It fails at 50 keywords checked daily. The pytrends cron job is the classic engineering solution, but maintaining session rotation and handling Google's throttling is ongoing work that has nothing to do with your actual trend analysis. The Google Trends Scraper handles the collection layer so your engineering time goes into the dashboard and alerting logic.

How to build a trend monitoring dashboard in 4 steps

Step 1: How do I set up scheduled trend data collection?

Create an Apify schedule that runs the Google Trends Scraper daily. This ensures fresh data arrives automatically without manual triggers.

export APIFY_TOKEN="apify_api_xxxxxxxxxxxxxxxx"

curl -X POST "https://api.apify.com/v2/schedules?token=$APIFY_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "trends-dashboard-daily",
    "cronExpression": "0 8 * * *",
    "timezone": "America/New_York",
    "isEnabled": true,
    "actions": [{
      "type": "RUN_ACTOR",
      "actorId": "thirdwatch~google-trends-scraper",
      "runInput": {
        "keywords": [
          "ai coding assistant", "copilot alternative", "cursor ide",
          "windsurf editor", "claude code", "devin ai"
        ],
        "geo": "US",
        "timeRange": "today 3-m",
        "includeRelated": true
      }
    }]
  }'

This runs every morning at 8 AM Eastern. The three-month window provides enough historical context to calculate meaningful week-over-week delta while keeping the timeseries manageable.

Step 2: How do I fetch results and compute week-over-week changes?

After each scheduled run completes, fetch the dataset and compare the latest interest values against the prior week.

import os, requests, pandas as pd
from datetime import datetime, timedelta

TOKEN = os.environ["APIFY_TOKEN"]
ACTOR = "thirdwatch~google-trends-scraper"

# Fetch the latest run's dataset
runs = requests.get(
    f"https://api.apify.com/v2/acts/{ACTOR}/runs",
    params={"token": TOKEN, "limit": 1, "desc": True},
).json()
dataset_id = runs["data"]["items"][0]["defaultDatasetId"]

items = requests.get(
    f"https://api.apify.com/v2/datasets/{dataset_id}/items",
    params={"token": TOKEN},
).json()

for item in items:
    tl = item.get("timeline", [])
    if len(tl) < 2:
        continue
    latest = tl[-1]["value"]
    week_ago = tl[-2]["value"] if len(tl) >= 2 else latest
    delta = latest - week_ago
    direction = "up" if delta > 0 else "down" if delta < 0 else "flat"
    print(f"{item['keyword']:30s}  now={latest:3d}  "
          f"delta={delta:+3d} ({direction})  slope={item['slope']:+.2f}")

The slope field gives you the overall direction across the full window, while the week-over-week delta from the last two timeline points shows recent momentum. Both signals together distinguish between steady trends and sudden spikes.

Step 3: How do I set up spike alerts?

Define a threshold for what constitutes a meaningful spike and trigger a notification when crossed. A two-standard-deviation threshold catches genuine breakouts while filtering noise.

import numpy as np

SPIKE_THRESHOLD = 2.0  # standard deviations above mean

alerts = []
for item in items:
    values = [p["value"] for p in item.get("timeline", [])]
    if len(values) < 4:
        continue
    mean = np.mean(values[:-1])
    std = np.std(values[:-1])
    latest = values[-1]
    if std > 0 and (latest - mean) / std > SPIKE_THRESHOLD:
        alerts.append({
            "keyword": item["keyword"],
            "current": latest,
            "avg": round(mean, 1),
            "std_devs": round((latest - mean) / std, 1),
            "slope": item["slope"],
        })

if alerts:
    print(f"\n{len(alerts)} spike alert(s):")
    for a in alerts:
        print(f"  {a['keyword']}: {a['current']} vs avg {a['avg']} "
              f"({a['std_devs']} sigma, slope {a['slope']:+.2f})")

Pipe the alerts list into your notification system -- Slack webhook, email, PagerDuty, or a dashboard red-flag indicator. The relatedRising field on spiking keywords often reveals the specific trigger behind the surge.

Step 4: How do I visualize the dashboard?

Export the accumulated trend data to a visualization layer. A simple approach uses pandas and a CSV that grows with each scheduled run.

import json
from pathlib import Path

HISTORY_FILE = Path("trends_history.jsonl")

# Append latest run to history
with HISTORY_FILE.open("a") as f:
    for item in items:
        record = {
            "keyword": item["keyword"],
            "avgInterest": item["avgInterest"],
            "slope": item["slope"],
            "peakInterest": item["peakInterest"],
            "peakDate": item["peakDate"],
            "latest_value": item["timeline"][-1]["value"] if item.get("timeline") else None,
            "fetched_at": datetime.now().isoformat(),
        }
        f.write(json.dumps(record) + "\n")

# Load full history for dashboard
history = pd.read_json(HISTORY_FILE, lines=True)
pivot = history.pivot_table(
    index="fetched_at", columns="keyword",
    values="latest_value", aggfunc="first"
)
print(pivot.tail(7))  # Last 7 days of trend data

For a production dashboard, push this data into Metabase, Grafana, or Google Sheets via API. The structured JSON output from the actor eliminates any parsing step -- each field maps directly to a dashboard metric.

Sample output

A single record from a scheduled monitoring run:

{
    "keyword": "cursor ide",
    "geo": "US",
    "timeRange": "today 3-m",
    "avgInterest": 54,
    "slope": 0.31,
    "peakInterest": 78,
    "peakDate": "2026-05-18",
    "timeline": [
        { "time": "2026-03-02", "value": 38 },
        { "time": "2026-03-09", "value": 41 },
        { "time": "2026-05-18", "value": 78 }
    ],
    "relatedTop": [
        { "query": "cursor ide pricing", "value": 100 },
        { "query": "cursor vs copilot", "value": 87 }
    ],
    "relatedRising": [
        { "query": "cursor agent mode", "value": "Breakout" },
        { "query": "cursor ide enterprise", "value": "+420%" }
    ]
}

slope at 0.31 confirms strong upward momentum over the three-month window. peakDate pinpoints when interest hit its maximum -- useful for correlating with product launches or press coverage. relatedRising surfaces the specific sub-topics driving the trend, which is actionable intelligence for content or product teams.

Common pitfalls

Three mistakes when building trend monitoring dashboards. Polling too frequently -- Google Trends data updates with a one-to-three-day lag. Running the scraper hourly for a 12-month window returns identical data and wastes budget. Match your schedule cadence to the time range: daily for today 3-m, weekly for today 12-m or today 5-y. Not normalizing across runs -- each run's 0-100 scale is self-contained. A keyword at 60 today and 60 next week does not mean identical absolute volume; it means the same relative position within each window. For cross-run comparison, track the raw timeline values and compute your own rolling averages. Ignoring the related queries -- the relatedRising field is often more actionable than the interest score itself. A "Breakout" related query tells you exactly what is driving a trend shift, which is more useful for content strategy than a bare number moving up.

Thirdwatch's actor handles the data collection and rate-limit management so your dashboard always has fresh data without session-management overhead.

Related use cases

Frequently asked questions

How often should I schedule Google Trends data collection?

For most use cases, daily or weekly is sufficient. Google Trends data updates with a one to three day lag, so running more frequently than daily yields duplicate values. Use the past-hour or past-day time ranges only for real-time event monitoring where sub-daily cadence matters.

Can I track hundreds of keywords in one scheduled run?

Yes. Pass up to several hundred keywords in the keywords array. The actor processes them sequentially and returns one dataset item per keyword. Larger batches take proportionally longer but work within a single run, keeping scheduling simple.

How do I detect a sudden spike in interest?

Compare the latest timeline value against the rolling average. If the most recent data point exceeds two standard deviations above the trailing mean, flag it as a spike. The slope field also helps -- a sharp positive slope over the past month window indicates recent acceleration.

What time range works best for a weekly dashboard?

Use today 3-m or today 12-m for weekly dashboards. These ranges give enough historical context to compute meaningful week-over-week changes while smoothing out daily noise. The past-seven-day range is too volatile for trend detection.

Can I send alerts to Slack when a keyword trends up?

Yes. Add a webhook on the Apify schedule that fires on run completion. The webhook payload includes the dataset URL. A lightweight serverless function can fetch the results, filter for keywords with positive slope above a threshold, and post a Slack message via the Slack API.

Related

Try it yourself

100 free credits, no credit card.

About 30 real searches. Add the MCP to Claude or Cursor in two minutes.