BV
Browser Automation

Portal scrape → clean → load

Playwright signs into a legacy portal, extracts what the team used to copy by hand, normalises it, and loads it to the operational DB.

Industry · HealthcareClient · SMBTimeline · 6 weeksStatus · Live
PythonPlaywrightFastAPIPostgreSQLDocker
The challenge

What wasn't working

01

Legacy portal had no API and rate-limited screen-scraping aggressively.

02

Ops team copied 200+ records per day by hand, introducing typos into billing.

Objectives

What we needed to be true

Automate the full sign-in → extract → normalize → load loop.

Cut manual work to zero for the standard case, keep humans in the loop for exceptions.

The solution

How it was built

Step 01

Resilient sign-in

Playwright handles the multi-step login with a retry loop and a persistent session cache to avoid re-auth on every run.

01
Step 02

Extraction + validation

Structured extractors per record type, Pydantic validation, and a diff against the last snapshot to skip unchanged rows.

02
Step 03

Load + reconciliation

Records are upserted into Postgres inside a transaction; anomalies land in a review queue with the raw HTML for context.

03
System architecture

How the pieces connect

Node 01
Cron Trigger
Node 02
Playwright Worker
Node 03
Pydantic Validation
Node 04
Postgres Upsert
Node 05
Review Queue
Node 06
Slack Digest
Delivery

Implementation timeline

  1. Phase 01

    Reverse engineering

    Mapped every screen and form the ops team touched.

  2. Phase 02

    Worker + scheduler

    Containerized Playwright worker on a Docker host, cron-triggered every 15 minutes.

  3. Phase 03

    Observability

    Structured logs, per-run screenshots on failure, Slack digest of anomalies.

Technology

Stack

Python
Playwright
FastAPI
PostgreSQL
Docker
Features

What ships to the user

Session persistence

Sign-in only happens on cache expiry — every other run reuses cookies.

Business value
10× fewer logins

Anomaly review queue

Records that fail validation land in a queue with raw HTML + screenshot.

Business value
Zero silent failures
Impact

Before → after

Before

20+ hours/week copying by hand

After

0 hours in the standard case, ~1 hour/week reviewing exceptions

Results

Business impact

0+
hours/week saved
0.0%
extraction accuracy
0/7
coverage
Need something similar?

Let's map your workflow and see what's worth automating first.

Book a discovery call
Reflection

Lessons learned

Browser automation is only reliable when you build the observability first. Screenshots on failure are non-negotiable.

What's next

Future improvements

Add a lightweight web UI for the ops team to reprocess anomalies without engineering involvement.

FAQ

Common questions

Extractors are structured per record type with visual regression checks. When the portal changes, the pipeline surfaces the failure loudly instead of silently returning bad data.
Let's build yours

Have a workflow that looks like this?

Bring me one real bottleneck. I'll tell you whether it's worth automating, and what it would take.

Book 30 Minutes Call