DEV Community

Cover image for I'd rather not ask
Hideki Mori
Hideki Mori

Posted on

I'd rather not ask

From the outside, the translation layer I maintain has one interface. You hand it a set of segments. For each segment you get back one of two things: a translation, or an error code. That is the whole contract. It looks calm.

It is not calm. The calm is something I make.


None of them agree

Behind that interface is a row of engines, and no two of them agree on anything. One returns HTTP 200 for its own failures and hides the real status as an integer in the body. One answers in JSON until the input gets large and then switches to XML. One returns its results as two unordered lists you reconcile by id. One has a job state that runs backwards. One isn't on the network at all — it's a native library in my own process that, on a bad day, becomes a zombie in the process table and never returns.

Not one of them produces the shape my interface promises. The single result-or-error the caller sees does not exist out there. I assemble it.


The contract is something I make

So the contract isn't something I found by reading documentation. It's something I manufacture, at the boundary, one engine at a time. Every lie gets caught and rewritten into the one vocabulary the caller speaks. The 200 that means failure becomes an error code. The two lists become per-segment results, matched by id. The zombie becomes a clean "this didn't finish." The caller never learns any of it. They asked for translations; they get translations, or honest errors, in the order they expect. They stay naive because I decided they would.


The hard part is the half

The easy version of this is the engine that wholly succeeds or wholly fails. The real work is the middle: the batch that translated forty segments, errored on three, and then dropped the connection. The engine that returned results and a charge for work it never finished.

An honest interface has to be granular about that. This segment succeeded. This one carries an error. And — the part I care about most — you do not bill for what didn't come back. If a segment was skipped, it's skipped. If the engine billed me for work that never returned, I take it off. Absence is not billable. The tempting thing is to bill the request; it's simpler, and the number is right there. The discipline is to bill only the results. Partial failure is where most of the integrity lives, because it's the case nobody downstream can see — so it's the case only I can get wrong.


I'd rather not ask

After enough years of this I stopped pretending it was only an engineering decision. It's a personality. I am bad at asking people for things — bad enough that I'll route around a favor rather than ask for one. I have never been comfortable handing someone a problem I already understand. And I don't mind in the least being asked. Those two facts are most of how I work, and they're sitting right there in the code.

The interface is bad at asking, too. It never turns to the caller and says: handle this engine's lie for me, reconcile these lists for me, decide what to do about this zombie. It passes none of that outward. And it is endlessly available to be asked — hand it anything, it takes the request and returns a clean answer. I would rather absorb a mess than hand it to someone else. The contract is uniform not because the engines cooperate, but because I'd rather not ask the people downstream to deal with what I can deal with myself.


What it costs

This has an edge I've learned not to romanticize. A seam that absorbs everything is also the one place everything collects. The interface gets clean; the load doesn't vanish — it concentrates. Every quirk that doesn't reach the caller reaches me, and stays. The same instinct that keeps the people downstream naive makes the one upstream the place all of it lands. A clean interface isn't free. It's paid for, in a single spot, by whoever decided not to pass the bill along.


The same seam, from the inside

I wrote once, about the systems on the far side of the wire, that an integration is the one system you can never close, because the other side keeps reopening it. This is that same boundary, seen from the inside. I can't stop the chaos out there from changing. But I can decide where it stops — that it stops at me, and not one step further. The caller gets a translation, or an honest error. They never find out what it cost to make that true.

That's the part I'd rather not ask anyone else to do.


Built with Claude (Opus).

Top comments (0)