Automation for the flows that move money
Automated regression across billing and the wider practice-management suite, replacing a substantial part of the manual pass on every release
- Client
- RXNT
A bug in a billing platform does not announce itself. Nobody sees a stack trace — a claim goes out slightly wrong, a payment posts to the wrong place, and the cost surfaces weeks later in a reconciliation. That is the category of defect Toobler automated against on RXNT’s Practice Management applications, across two deliberately different tracks.
Customer and context
RXNT builds practice-management and revenue-cycle software for US healthcare providers. Its billing workflows carry the kind of risk where correctness is not a quality preference: encounters become claims, claims become payer responses, payer responses become payments that have to post and distribute accurately.
Every release previously leaned on manual regression testing — a human working through test cases, at whatever depth the schedule allowed that week. Toobler’s QA engineering replaced a substantial part of that with automation, and built it so the coverage could keep expanding rather than calcifying.
The challenge
The difficulty was not deciding what to test. The test cases already existed. It was making automated checks reliable enough that a failure meant something.
- The interface fights the automation. Loading overlays, notification toasts, modal backdrops and iframe-scoped content all sit between a test and the element it needs, and all of them intercept clicks that a user would have landed.
- The markup is generated. A UI component library invents its own class names and element ids, so selectors written against today’s DOM are a liability by the next release.
- The backend finishes after the screen does. Claim submission, payer processing and payment distribution complete well after the interface stops indicating activity. A test that asserts immediately is testing the spinner.
- The data is the scenario. Different patients, providers, procedure codes, charge amounts and payment outcomes are not variations on one test — they are the test.
- Breadth and depth pull against each other. Hand-writing code for every screen in a practice-management suite is a maintenance bill nobody pays twice; recording everything produces coverage that shatters on the next redesign.
The solution
A click that survives the application. Every page object inherits a shared click pipeline:
- Wait for any notification toast to clear.
- Hide blocking overlays and modal backdrops.
- Wait for the target to be genuinely visible.
- Click — falling back to a forced click when an element is not natively actionable. One pattern, applied everywhere, removes an entire class of failure that would otherwise have been diagnosed one flaky test at a time.
Locators that declare several routes at once. An element is defined by test id, accessible role and name, visible text, class, xpath, and the frame it lives in — chained so whichever currently matches the DOM wins. Generated markup stops being able to break the suite by itself. Selector definitions live in their own configuration files rather than inline in specs, and the genuinely fragile ones — positional navigation tabs, generated column ids — are flagged where they are defined, so the next engineer knows what is load-bearing before they touch it.
A failure bar above the assertions. Tests fail automatically on an unexpected browser console error, an uncaught page error, or any HTTP response of 400 or worse, with a narrow allowlist for known-broken static assets. Applied through a shared fixture that every spec imports, so the standard is uniform rather than remembered. A screen that technically passed while throwing errors is not a screen that works.
Waits that match the backend, not the screen. Long-running workflows get explicit synchronization and polling, so a test asserting on a posted payment waits for the payment rather than for the animation.
Data as data. Scenarios are driven from spreadsheets rather than hard-coded into specs, so adding a payment outcome or a procedure code is a row.
Two tracks, scoped deliberately. This is the part most worth copying, and it is why the engagement sits alongside our wider product engineering work rather than beside it. Code-based Playwright automation covers the billing core — encounter creation and claim submission, insurance payment posting and distribution end to end, and the billing dashboard — where a silent regression is most expensive and justifies the maintenance cost of hand-written code. An AI-driven recorded track covers the breadth of the practice-management application: patient dashboard and patient creation, encounters, patient payments including ledger and funds, statements, remittance advice, reporting and utilities. The two are scoped against each other so the same workflow is not covered twice.
A suite that reads as documentation. Each automated case has a plain-English description of the same steps kept alongside it, and spec files are named after the test-management case they implement. Every logical action is wrapped and named, so a failure report says which step failed in words rather than pointing into a page object.
Results
Automated regression now covers RXNT’s most business-critical practice-management workflows — the billing core in code, the wider application through the recorded track — replacing a substantial portion of the manual regression previously required on every release.
Two things follow beyond the coverage itself. The checks are repeatable on demand, so they run the same way every time instead of depending on who is available and what they remember. And because every automated case carries its plain-English twin, the suite is the only documentation of these workflows that cannot quietly go out of date — it fails when it stops being true.
Where it stands, precisely. The code-based suite runs on demand today. It is not yet wired into the build pipeline, and a recurring schedule has been scaffolded rather than built. That sequencing is deliberate: a suite earns automation of its own trigger by being trustworthy first, because wiring an unreliable suite into CI teaches a team to ignore it. The patterns above are what buys that trust, and the next step is to make the runs continuous.
The approach behind this engagement is described in more detail on our test automation page, and sits among our other engineering case studies.
Related work and capabilities
A suite your team still trusts
Regression automation whose failures mean something — resilient locators, a click pipeline that survives loading overlays, and a bar above the assertions.
Proof, engineered
Case studies from Toobler — real platforms engineered across event technology, construction and digital twins. The work behind the claims.
SaaS Product Engineering
SaaS products outgrow the architecture that launched them. Toobler designs, builds, scales and re-platforms software products for SaaS companies, ISVs and funded startups.