An integration layer with no owner and no version
The most expensive architecture mistake I see in SMBs is a shared database nobody decided to share. By the time you notice, your integration layer is a schema with no owner and no version.
It happens the same way every time. App A needs a number that lives in App B’s tables, someone grants a read, and six months later four systems read and two write into one schema nobody owns. A manufacturing client ran an ERP, a shipping tool, and a homegrown reporting app, all writing to the same tables. A single column rename turned into a three-week job. The full cost of that rename is worth a look on its own, because it is what a boundary you backed into charges you on every change, forever, until someone pays to fix it.
The blocker is not technical
Here is the part most posts skip. The blocker is not technical. Deciding which system owns each piece of data is a governance fight, not a schema change. It is two managers arguing whose definition of a customer is canonical, and that argument is where modernisation stalls. If you cannot get that decision signed, no architecture saves you. This is why untangling a shared database is really a systems-integration problem with a governance core, not a database-refactoring problem with a political footnote.
The sequence that works on a live system
You rarely get to stop the system while you fix this, so the sequence has to work on something that cannot pause.
-
Name the owner for each piece of data, in a room, with the people who will fight about it. Get it in writing and signed. This is the step that stalls, and no amount of engineering skips it.
-
Collapse to one writer per table. This is the hard part and I will not pretend otherwise. On an ERP you do not control, moving a second writer onto the owner’s API means dual-writing while both paths run, parity tests you have to build from scratch because none exist, and a rollback plan for when the legacy writer does something inside its own transaction you cannot see. That is months, not a sprint, and it is where projects actually die.
-
Only once one writer remains do you put a view or small API in front of the readers.
The order is the whole point. Read coupling is annoying. Write coupling is the liability. If you invert the sequence and start by wrapping the readers, you have decorated the problem without touching it. The two writers are still quietly disagreeing underneath.
You do not need a service mesh
You do not need event sourcing or a service mesh to fix this. You need a decision about who owns what and the patience to migrate one writer at a time. The decision is what stalls; the migration is just hard, not mysterious. Teams reach for exotic architecture here precisely because it is easier to buy a pattern than to get two managers to agree whose customer record is canonical, and the pattern does not resolve the argument, it just hides it behind more moving parts.
A cleaner target is a composable architecture where each capability owns its own data and exposes it through a contract, so the next integration is a deliberate decision rather than another quiet grant of read access. But you only get there through the ownership decision, not around it.
So where did your last ownership cleanup stall: the live-writer migration, or the two people who both thought they owned the customer record? If you have a schema four systems write to and nobody owns, that is not a technical debt you can refactor your way out of quietly. Talk to TrueForge and we will help you get the ownership decision signed before we touch a table.