← All projects
Accountancy

A practice management platform for a UK accountancy practice

Accountancy practices run on software that is nearly right. The deadlines are close but not quite yours, the workflows are someone else’s, the data sits on a vendor’s servers and the monthly bill grows with headcount. Past a certain point the workarounds cost more than the software. This is what the replacement looks like, built and in daily use.

Sector
UK accountancy practice
Built
From scratch, still in development
Status
Live, in daily use
Scope
Architecture, build, hosting, maintenance
~90feature modules, one per area of the practice
2,730automated tests kept green on every change
192screens built for the practice to work from
12external systems integrated, from Companies House to the accounting ledger

What it does

Built to replace the off-the-shelf practice software a UK accountancy practice had outgrown: client register, statutory deadlines, Companies House filing tools, anti-money-laundering checks, e-signatures, client portal and an outgoing comms queue, in one owned system.

Client register and CRM

The system of record for every client the practice acts for, built to hold what an accountancy firm actually needs rather than what a generic CRM offers.

  • A client schema with over 400 fields covering statutory, contact, service and compliance data
  • Custom fields the firm can add without a developer
  • Merge and de-duplication tooling for the mess that arrives with any data migration
  • Archiving that keeps former clients visible as history without letting them back into live deadline chasing

Statutory deadlines and automated task generation

The engine at the centre of the platform. Deadlines drive work, and work is generated rather than remembered.

  • Cadence rules are configuration, not code, so the firm changes them itself
  • Each deadline generates a workflow checklist built from a reusable template
  • Generation runs as a dry run first, so a rule change is previewed across every client before anything is written
  • Tasks are de-duplicated on client, task and deadline, so a re-run is always safe

Companies House monitoring and filing tools

Two separate rails: one that reads the public register continuously, and one built to submit filings.

  • Continuous read of officers, PSCs, filing history and due dates from the Companies House data API
  • Confirmation statement (CS01) submission built against the Companies House XML Gateway
  • Officer, registered-office, PSC and accounts filings built and tested against the gateway test environment
  • Live filing is disabled by default and gated behind separate production credentials

HMRC obligations

Read-only by design, and built against the sandbox: production access is applied for, not granted. Nothing here submits anything on a client’s behalf.

  • OAuth-authenticated Making Tax Digital client built to read VAT and Income Tax obligation status, tested against the sandbox
  • Read-only scopes only: the software has no permission to file
  • HMRC fraud prevention headers implemented as required for API access
  • A separate legacy rail for agent authorisation

Anti-money-laundering and identity verification

AML is a legal obligation with a paper trail attached. It belongs on the client record, not in a separate portal someone forgets to check.

  • Identity and AML screening handled through dedicated verification platforms, with results attached to the client
  • Sanctions, PEP and adverse-media match review sits alongside the client’s own data so a match can actually be judged
  • Identity document data passes through a single allowlisting module: a deliberate firewall giving raw ID data one entry point
  • Subject access export and retention rules built in for GDPR requests

E-signatures and the client portal

Engagement letters and authorisations signed in the same system that tracks them, with a second identity check at the point of signing.

  • Envelope-based e-signature engine with two-factor identity verification at signing
  • Signing tokens stored as hashes and deliberately excluded from database backups, so a leaked backup cannot reconstruct a live signing link
  • Passwordless client portal login by emailed code, so there are no client passwords to leak or reset
  • Clients see their own documents, requests and deadlines without a staff member sending anything

Communications hub

Every outbound client message passes a human before it sends. The automation drafts; a person dispatches.

  • Read-only inbox sync so client replies land against the right client record
  • An outgoing queue where drafted emails and messages wait for staff review
  • AI-drafted replies and chase messages built from approved templates, never sent automatically
  • Email, SMS and WhatsApp channels with reply tracking, so a chase stops when the client answers

Payments, payroll and documents

The surrounding systems mirrored in, read-only, so the practice has one place to look.

  • Stripe and GoCardless payment mirrors with webhook updates
  • Xero read-only mirror of invoices, contacts and VAT settings
  • Payroll filing documents matched automatically to the right client folder
  • Scanned correspondence indexed through a document management integration, and PDFs signed and stamped in-platform

What it connects to

Most of the value in a system like this comes from the systems it talks to, and most of the risk does too. Each connection is scoped to the access it needs for the job.

Government and regulatory

  • Companies House data APIContinuous read of company, officer, PSC and filing data
  • Companies House XML GatewayConfirmation statement submission built to the gateway specification, with further forms built and gateway-tested
  • HMRC Making Tax DigitalRead-only VAT and Income Tax obligation status. Built and sandbox-tested; production access applied for, not granted
  • HMRC agent authorisationLegacy government gateway rail for agent authorisation

Compliance and identity

  • AML and ID verification platformIdentity checks, sanctions and PEP screening, evidence stored against the client
  • Biometric identity verificationVerified identity attempts delivered by webhook and reconciled automatically

Finance

  • XeroRead-only mirror of invoices, contacts and VAT settings
  • StripePayment mirror with webhook reconciliation
  • GoCardlessDirect Debit mandate and payment mirror

Workplace

  • Google WorkspaceDomain-restricted staff sign-in, Drive mirror, Gmail drafts and labels
  • Document managementScanned post and correspondence indexed against clients
  • Task and note toolsOne-way task mirror and a migration importer from the previous stack

How it fits together

The path a piece of work takes through the system, start to finish.

Data comes in on its own

Companies House, the accounting system, the payment providers and the inbox are all read on a schedule. Nobody re-keys anything, and nothing depends on a staff member remembering to check a portal.

Changes are proposed, never applied

When an external source disagrees with the client record (a new officer, a changed address, a different VAT setting) the system does not overwrite. It raises the difference in an approval queue for a person to accept or reject. This pattern repeats across every integration in the platform.

Deadlines become work

The deadline engine turns statutory dates and service cadences into dated tasks with checklists, assigned to the right person. Rule changes are previewed as a dry run across the whole client book before a single task is created.

Clients are contacted through a queue

Chases, requests and reminders are drafted automatically from approved templates, then wait in a review queue. Staff read and send. Replies are tracked, so the chase stops the moment the client responds.

Filings and signatures leave a record

Confirmation statements are built to submit through the Companies House gateway; engagement letters and authorisations go out as two-factor e-signature envelopes. The e-signature rail leaves a full audit trail of who did what and when.

Everything is written down

Every state change lands in an audit log. The practice can answer "what did we do, when, and on whose instruction" for any client without reconstructing it from inboxes.

The hard parts

The problems that decided how this was built. They are the reason it works the way it does rather than the obvious way.

Changing a deadline rule without breaking the whole client book

The problem

Deadline rules change: a new service, a different chase cadence, an adjusted lead time. In a system that generates tasks automatically, a careless rule change means hundreds of wrong tasks landing in real people’s lists, and no clean way to undo it.

What we did

Rules are data rather than code, and generation always runs as a preview first: the system shows exactly what would be created across the entire client book before anything is written. Generation is de-duplicated on client, task and deadline, so re-running is a no-op rather than a duplicate.

The result

The practice tunes its own cadences, sees the blast radius before committing, and can re-run generation safely at any time.

Building against a government gateway that does not document its own edge cases

The problem

Companies House XML submissions are unforgiving, and the published schema is not the whole story. One rejection code covers several unrelated situations, and a schema-valid submission can still be refused.

What we did

Every form was built and exercised against the gateway test environment until the failure modes were understood, including a field that validates against the schema but is rejected on certain submissions, and a generic rejection code that conflates a harmless test-mode refusal with a genuine duplicate filing.

The result

Test-gateway submissions that pass validation and fail predictably rather than mysteriously, with live filing kept behind an explicit switch and separate production credentials.

Integrating a document store without ever being able to delete

The problem

A file store integration that can write can usually also delete. For a practice holding statutory records, an automation with delete permission is an unacceptable risk, and "we agreed not to call that endpoint" is not a control.

What we did

The integration carries no delete or trash call anywhere in its code path, write access is allowlisted to a single folder, and each of those properties has a test that fails the build if it is ever weakened. The credentials themselves still carry whatever permissions the provider grants, so this is a constraint on our code rather than a permission boundary.

The result

A property that survives future developers, including us, because removing it breaks the build. It is not a claim that deletion is impossible at the account level.

Letting AI draft client communications without letting it send them

The problem

AI drafting saves real time on chases and routine replies. Sending automatically to a client, under a regulated firm’s name, is a different risk entirely.

What we did

Drafting and dispatch are separate systems. AI writes into a queue built from approved templates; the queue shows each message in full alongside reasons it should not go, such as the client having already replied. Sending is a human action, every time.

The result

The time saving of automated drafting, without automated sending.

Built with

PythonDjangoPostgreSQLDockerCloudflare Tunnel and AccessWebAuthn passkeysTOTP two-factorpyHanko PDF signingClaude APIModel Context Protocol

We don’t publish screenshots, logos or client names for this work. Much of it runs inside a business and handles sensitive data, so we describe what was built rather than who it was built for. We’re happy to walk through the detail on a call.

Ask a question

Tell us what your version of this needs to do and we’ll come back within one business day with scope, approach and a price.

What is your question about? (required)

Need something like this?

Every build on this page started as a workflow that off-the-shelf software nearly handled. Tell us where the gap is and we’ll scope what it takes to close it.