What we sell · Colombia

Maintenance became archaeology. We do the digging.

Our reading of where Drupal estates actually hurt right now — and the three things we do about it.

Talk to us

Somewhere in your codebase is a custom module written for one requirement, by someone who left two years later. No tests. No README. Commit messages that say fix. It still runs, nobody knows quite why, so nobody touches it — and everything you want to build now has to route around it.

That is the condition we think the market is actually in. Not broken sites: abandoned bespoke code, and maintenance that has quietly turned into archaeology. You are no longer extending a system. You are excavating one — recovering intent from artefacts, left by people you cannot ask.

These three are our reading of where that hurts most right now. Each is something we do to our own estate first: five Drupal 11 properties on one stack, rebuilt from an empty database whenever we need to prove it still can be.

Technical debt

The site deploys, so long as one particular person does it. Config drifted out of sync with production years ago and nobody trusts an import any more. Staging stopped matching live the day someone changed a setting through the UI. There are four custom modules; two are load-bearing, one is dead, and no one can tell you which is which without reading all of them. The honest estimate for a two-hour job is two weeks, and most of that is reading.

We do the reading. Codebase, configuration, deploy path, dependency tree — then we rank what we find by what it costs you to keep, not by severity theatre. Every custom module gets a verdict: load-bearing, replaceable by contrib, or dead and safe to delete. That last category is usually larger than anyone expects, and deleting it is the cheapest win on the list.

What we look for is what has bitten us on our own sites: config drift, deploys that cannot be repeated, contrib pinned to versions with open advisories, content models changed in place instead of migrated, a cache papering over a query that should never have been written. We keep a written record of each one we have hit. The audit is that record, turned on your site.

Fixed price, time-boxed. You get the list, the order to do it in, and a price to have us do it. The output is yours whether or not we do the work that follows.

Roadmapping

Leadership wants a number and a date. Engineering cannot give one, because the answer depends on what is inside code nobody has read since it was written. So the roadmap becomes a wish list, the wish list becomes a budget, the budget is wrong by the first month — and everyone quietly learns not to ask again.

A plan built on unread code is fiction. So we read first, then sequence: what blocks what, what can run in parallel, what is safe to defer another year, and what is quietly accruing interest while you defer it. Each item names the change, the risk of making it, the risk of not making it, and how you will know it worked. It is written to be handed to whoever does the work — us or your own team.

No swimlanes, no phases, no invented certainty about month nine. Where something cannot be known yet, it says so, and says what would make it knowable.

Migrations

You are on a version that stopped getting security cover, or a host you are leaving, or a content model that outgrew its shape three years ago. Every quote you have been given assumes a rebuild — because a rebuild is far easier to price than an honest migration, and it conveniently discards the part that is genuinely yours: your content, and the decisions buried inside your bespoke code.

A rebuild throws away the archaeology instead of doing it. Sometimes that is the right call, and we will say so. Usually it means paying again for behaviour you already own and cannot now describe.

The work is the same in every case: make the site reproducible from code before you move it, then move it in one command — and be able to move it back. We have done the ugly ones. Changing a field's storage type in place, on a site where the revision table the API expects does not exist, so the delete throws and the config change completes anyway. Changing a site's default language after it has content, where a single wrong save writes an empty translation over live field values, and setting the language back does not restore them. Both cost us a database restore to learn. You get the version where we already know.

Quoted after the audit, not before. Pricing a migration before anyone has read the site is guesswork with an invoice attached.

Whether this is for you

We take few clients and we say no to work that does not fit: Drupal 11, reproducibility mandatory, bilingual by default. We are a small studio and we would rather tell you now than three weeks in.

If you recognised your own estate above, the cheapest next step is a conversation. Write to us through Contact, or ask the concierge on the front page — it answers questions about how any of this works, and puts you in touch if it fits.