Case study · Healthcare

Patient balance collections platform for a US medical billing company

A secure web platform that takes a medical practice's overdue patient balances, puts them in priority order, prepares a three-letter collection sequence with live figures, and lets a member of staff approve every letter before it is sent by post or email.

The system decides what is due. A person decides what is sent.

ClientA US medical billing company serving independent practices
Our roleFull-stack design, build, deployment, and handover
DeploymentThe client's own cloud account, on their own domain
StatusDelivered and deployed. In final setup with its first practice.

Client and product are not named. All screens and data referenced are from a demonstration environment.

The client

A US medical billing company that manages patient receivables for independent practices. Its first practice on the platform is a cardiology practice in Texas. The engagement covered the complete product: requirements, architecture, design system, build, testing, deployment into the client's own cloud, and handover.

The problem

After insurance pays its share, the remainder of a medical bill falls to the patient: deductibles, co-insurance, and self-pay balances. Practices chase these balances by hand. Someone keeps a spreadsheet of who owes what, works out which patients are due a reminder, types letters, posts them, and tries to remember what was sent and when.

Three things go wrong. Letters go out with stale figures, so a patient who paid last week is asked for money the practice already has. Nobody can prove afterward what was sent or by whom, which matters because collection notices are legal documents. And the highest-value, oldest balances are not necessarily the ones being worked first.

What we built

A private web application the practice's billing staff sign into. It does the deciding and the paperwork; a person does the approving.

Bring the accounts in. Staff upload the practice's spreadsheet. The platform reads the file, recognizes the columns by their headers and, where a header is unclear, by the shape of the values in them, and shows the operator exactly how every column will be used before a single row is written. Choices are remembered per practice, so the next month's upload is pre-mapped. Messy real-world cells are handled: dates of service typed in a dozen formats, several visits in one cell, blank or dash balances, broken spreadsheet formulas, free-text call logs that become dated timeline entries. Re-importing the same file updates accounts in place instead of duplicating them, and it never overwrites work the team has done inside the platform with month-old figures from the sheet.

Put them in the right order. Every account is scored by how old the balance is and how large it is, with weights the practice can adjust. The worklist shows what to work on next, with filters by insurer, aging band, and "needs review", so the accounts the import could not settle on its own are one click away.

Work the queue. Each account has a single page: balances, itemized charges by date of service, insurance details, contact details, documents on file, payments recorded, calls logged, letters sent, and the full timeline. Staff can start a phone call from the page, log the outcome, record a payment, and book a call with the patient.

Attach the insurance paperwork. Explanation of benefits documents are uploaded to the account and read automatically into itemized charges, which staff review and apply to the balance. The document travels with every letter.

Read the actual letter. The three letters (friendly reminder, firmer notice, final notice) are generated from the live record: patient name and account number, insurer and member ID, the kind of balance, a table of every charge with a plain-English description of each procedure, the total outstanding, payments already received, a card payment link, and on the final notice the legally required warnings, which no one can edit or remove.

Approve and send. A named member of staff reads the full letter, chooses post, email, or both, and approves it. Only the letter that is actually due can be sent, timing windows are enforced on the server, and two clicks on approve cannot post two copies. Every send is recorded permanently.

See whether it is working. A dashboard shows outstanding balances by aging band, letters sent by stage, payments recorded, and the accounts flagged for review or agency referral.

Run more than one practice. The platform is multi-tenant. Each practice has its own settings, team, letter wording, cadence, integration keys, and data. One practice can never see another's patients.

The screens

Sign in and password resetWorklistPatient accountReview and send letterAdd accountEdit accountDashboardScheduleSettings: practice detailsSettings: letter cadenceSettings: letter contentSettings: service codesSettings: prioritizationSettings: teamSettings: integrationsSettings: data import and retentionAdd a practice

Built for a regulated environment

How it is built to hold in production

For technical readers Architecture and safeguards
  • Multi-tenant data model with row-level security enforced in the database; the application connects as a role that cannot bypass it.
  • Import pipeline with a preview step, header alias matching, fuzzy matching for typos, value-shape inference for unlabeled columns, and per-practice memory of confirmed mappings.
  • Merge rules for monthly re-imports: charges come from the sheet, payments from whichever side can prove more of them, workflow state from the application. A stale export can never reset worked accounts.
  • Letter sends serialized per account with a lock around the read-decide-write section, so a double submit cannot mail a patient twice. Cadence is re-checked on the server on every send.
  • Idempotency keys on every outbound provider call, so a retry cannot double-send.
  • Every timestamp shown or printed is rendered in the practice's own time zone, because the legal response window is counted from the date on the page.
  • Integrations resolved per practice from stored keys, with in-memory fakes when a key is absent, so the demo environment can never reach a real provider.
  • Build-aware clients: an open tab that predates a deployment reloads itself instead of posting stale actions.
  • Session signing, password reset by email, rate limiting, role-based access (agent, manager, admin), and a security review on every milestone.
  • Deployed behind TLS into the client's cloud, with rollback-safe deploys and infrastructure described as code.

How we delivered it

  1. Discovery and specification. The letter wording came from the practice's own lawyers and was reproduced faithfully. The cadence, aging bands, and scoring rules were agreed with the client before any code.
  2. Architecture and design. Security model, tenant model, and a design system carried through every screen and later matched to the client's marketing identity.
  3. Phased build with demos to the founders at each milestone.
  4. Testing. Unit, integration, and browser tests, including tests that boot a real database to prove the tenant isolation, plus a security review before each release.
  5. Deployment into the client's own cloud account, with the client's own domain and certificates.
  6. Handover. Full source code and IP transferred. Documentation for operators, a client handbook, an integration setup guide, and a recorded walkthrough.

Status

Delivered and deployed

In final setup with its first practice.

Everything the platform does

Accounts

  • Spreadsheet import with column preview, automatic column matching, and manual override
  • Remembered column choices per practice
  • Handling of messy cells: multi-visit date fields, blank and dash balances, broken formulas, free-text call logs
  • Re-import that updates in place and protects work done in the platform
  • Manual add, edit, delete, assign to a team member
  • Review flags on anything the import could not settle, with a one-click filter

Prioritization

  • Scoring by balance age and size, with practice-adjustable weights
  • Aging bands, configurable
  • Worklist filters by insurer, aging band, status, and review state, with sort options

Letters

  • Three-stage sequence: reminder, firmer notice, final notice
  • Practice-configurable response windows between stages
  • Live figures on every letter, including payments already received
  • Itemized charges with plain-English procedure descriptions from a practice glossary
  • Final-notice legal warnings that cannot be edited or removed
  • Full-letter preview before approval
  • Post, email, or both, chosen per send
  • Server-enforced timing and protection against double sends
  • Permanent record of every send

Documents and payments

  • Explanation of benefits upload, automatic reading into charges, staff review and apply
  • Documents attached to outgoing letters
  • Card payment link on every letter, payments recorded against the balance

Calls and scheduling

  • Click-to-call from the account page, with outcome logging
  • Patient self-booking link on every letter
  • Read-only sync of booked calls into the schedule, linked to accounts

Management

  • Dashboard: outstanding by aging band, letters by stage, payments, accounts needing review
  • Recovery reporting
  • Team with three roles and per-user access
  • Multi-practice support with complete separation

Compliance and data

  • Audit trail on every action, with user and time
  • Retention period per practice, with purge of resolved accounts only
  • Tenant isolation enforced in the database
  • Data held in the client's own cloud account

Have a process like this running on a spreadsheet?

Describe it and we will outline how we would approach it: what the system should decide, where a person should approve, and what it would take to deliver.

Talk to the team →