◇ Competitor Intelligence Monitor Python · Playwright · Claude · Postgres · Slack Project Blueprint
Competitive Intelligence

Know what your competitors did before standup.

Every morning at eight, an agent walks your competitors' pricing pages, changelogs, blogs, and job boards, compares them to yesterday, and posts what actually changed to Slack. When nothing moved, it stays quiet.

Below, the daily run, what it watches, and how it's built.
01

The Daily Run

Five steps and a fork. Everything runs unattended, and the only thing that ever reaches a person is a digest worth reading.

01 Trigger 08:00 daily 🌐 02 Scrape four page types 🔍 03 Detect diff vs yesterday 🔖 04 Classify what kind of move 📝 05 Write the digest changes found Slack digest Nothing sent nothing notable next morning, 08:00
you configure once runs unattended silence is a valid outcome
01
Trigger
A scheduled job fires at 8am.
🌐
02
Scrape
Pricing, blog, changelog, careers.
🔍
03
Detect
Diff against yesterday, drop the noise.
🔖
04
Classify
Pricing, feature, positioning, hiring.
📝
05
Write
A short brief with sources attached.
changes found → Slack digest
nothing notable → logged, no message
runs again tomorrow, 08:00
02

Inside Each Step

01 Scheduled trigger

A scheduled job fires every morning before anyone opens Slack. The time is configurable, and so is the competitor list — add or drop a name and the next run picks it up. That list is the entire human involvement in the system.

cron · configurable competitor list
🌐

02 Scrape

Each competitor's pricing page, blog, changelog, and careers page gets visited. Playwright handles sites that only render through JavaScript; static pages take a lighter path; and where an RSS or Atom feed exists it's parsed directly, which produces far cleaner diffs than HTML ever will. Hiring signals come from the company's own careers page — no LinkedIn dependency, nothing in grey territory.

Playwright · requests + BeautifulSoup · feedparser
🔍

03 Detect changes

Fresh content is compared against yesterday's stored snapshot. Most of what changes on a marketing page overnight is noise — rotated testimonials, timestamps, reshuffled boilerplate — and that gets filtered out before anything moves forward. Every snapshot is kept, so the archive doubles as a trend record.

PostgreSQL snapshots · noise filter
🔖

04 Classify

Each surviving change gets a type: a price or packaging change, a feature launch, a shift in positioning, a hiring surge in one department. The type is what makes a digest scannable in fifteen seconds, and what makes patterns visible when you look back across weeks.

Claude API · change classification
📝

05 Write the digest

The classified changes are synthesised into one short brief. Every item says what changed, why it might matter, and links straight to the source, so anyone reading can verify a claim in a single click rather than taking the summary on faith.

Claude API · what changed / why it matters / source
📩

06 Route or stay silent

If nothing notable happened, the run is logged and no message is sent. That restraint is the feature. A digest that arrives every single day gets muted inside a week; one that only arrives when something actually moved gets read every time.

Slack webhook · silent log
The design decision that matters

Most days, it says nothing.

Every filtering choice in the pipeline — the noise gate on the diff, the classification step, the send-or-skip fork — exists to protect the same thing: the team's willingness to read the message when it does arrive.

03

What It Watches

Five signal types. Each one is a leading indicator of something a competitor hasn't announced yet.

PRICING
Plans, prices, packaging

Tier changes, listed prices, usage limits, what moved behind an enterprise call. You know the same day it happens rather than the week a prospect mentions it on a call.

PRODUCT
Changelogs and releases

Release notes, new feature pages, changelog entries. What shipped tells you what they prioritised, and how often it ships tells you how fast they can.

POSITIONING
Homepage and messaging

A rewritten headline is rarely cosmetic. It usually means a new target segment, a new category claim, or a story that stopped working.

HIRING
Roles by department

Six engineers on a team that didn't exist last quarter is a roadmap. Hiring surfaces direction three to six months before anything is announced publicly.

SENTIMENT
Review trends

A dip in review sentiment usually means a product problem in progress — which is a problem your sales team can speak to while it's still live.

04

Architecture

One scheduled job, three ways of fetching a page, and a filter that decides whether a human hears about it.

Scheduler

cron · configurable time and competitor list

One job, one time of day, no manual action. The only surface anyone touches after setup.

Dynamic pages

Playwright

headless browser

For pricing pages and apps that only assemble themselves once JavaScript has run.

Static pages

requests + BeautifulSoup

plain fetch and parse

Lighter and faster for pages that ship their content in the HTML. Used wherever a browser isn't needed.

Feeds

feedparser

RSS · Atom

Where a feed exists it's read directly. Structured entries diff far more cleanly than rendered markup.

Change engine

PostgreSQL · daily snapshots · diff → filter → classify

Reads yesterday's snapshot, writes today's, and decides what counts as a change. Everything that survives the noise filter gets a type before it moves on. The snapshot history stays for trend analysis.

Digest and delivery

Claude API · Slack webhook

Synthesises the day's changes into a brief and posts it to the designated channel — or, on a quiet day, records the run and sends nothing at all.

05

How It's Built

Six modular blocks. Competitors, page types, and delivery channel swap per client; the shape of the run doesn't.

01

Scheduler

trigger

Starts the run once a day, unattended.

02

Scraper pool

collection

Three fetch strategies, chosen per page type.

03

Snapshot store

memory

Yesterday's copy of every page, kept for trends.

04

Diff & filter

noise gate

Separates real movement from page churn.

05

Classifier

labelling

Sorts each change into a signal type.

06

Digest & delivery

output

Writes the brief, or decides not to send one.

06

Stack

Python Playwright BeautifulSoup feedparser Claude API PostgreSQL Slack cron