Skip to main content
Dispatches

Fibe Blog

Updates, guides, and engineering notes from the workshop.

Configuring a Genie: agents, skills, and memory

· 9 min read

A coding agent out of the box is generic. Claude Code, Codex, Cursor, Gemini — they all boot up knowing nothing about you, your repos, your conventions, or yesterday's conversation. On Fibe we call the running instance a Genie, and the platform's whole job is to make that generic Genie yours before a single token is generated.

"Yours" isn't one thing: a provider choice, credentials we have to protect, skill files, files you dragged in, and — the part people underestimate — memory of what happened last time. None of that lives in the container; it lives in an Agent, a small, boring, persistent config record the Genie reads from. This post walks through that record, down to how it reaches the container.

Cascades and the edges that deliberately do not exist

· 10 min read

Most of the time, the dangerous question in a distributed system isn't "what does this delete cascade to?" It's "what does it not cascade to — and are you sure?"

We spend a lot of energy reasoning about the edges that do fire: delete a Marquee, and a chain of consequences unfolds. But the bugs that wake you at 3am are usually the opposite shape. Someone toggles an innocuous setting — disables a Prop, edits a Secret, demotes a teammate — and a long-running environment they didn't mean to touch quietly falls over. The edge that surprised them is one nobody designed; it emerged because some well-meaning "keep things in sync on every save" hook reached one relationship too far.

Idempotency everywhere: payments, wallet posts, and claim-once webhooks

· 10 min read

There's a moment every billing engineer eventually has. A customer emails: "I was charged twice." You open the logs, and the request looks fine — one checkout, one order. Then you find the second event. Same payment, redelivered by the provider three minutes later because our 200 got lost on the wire. We processed it twice, minted the currency twice. The math was, briefly, generous to exactly the wrong person.

The lesson isn't "be more careful" — careful doesn't scale. It's that at-least-once delivery is the only honest contract a distributed system can offer, and once you accept that, exactly-once effects become something you build, on purpose, at every layer that touches money. Here's how we do it at Fibe — across wallet posts, the Mana-to-Sparks conversion, daily funding, provider webhooks, and the keys our SDK ships.

Provisioning a Marquee: from checkout to wildcard TLS in under two minutes

· 21 min read

A Player clicks "buy" on a tutorial bundle. A minute or two later they have a real Docker host on the public internet, reachable at a domain that already serves a valid HTTPS certificate for every subdomain it will ever use. No certificate warnings, no "give it five minutes for DNS to propagate," no SSH keys to paste. It just works.

That last clause is doing a lot of work. Between the checkout and the green light, a payment becomes an event, an event becomes a database row, a row dispatches a GitHub Actions workflow, Terraform conjures a VM and a fistful of DNS records, a series of webhooks walk the row through six discrete steps, and finally a background job coaxes Traefik into talking ACME with ZeroSSL until a wildcard cert exists and a real HTTPS client can verify it. If any of those steps stalls, the row doesn't sit in limbo forever — it has a clock on it. This is the story of that path, and of the small pile of state we keep so that "it just works" stays true even when a cloud API has a bad day.

Template variables that do not bite: required, random, secret, validated

· 14 min read

A template that only ever runs one way is just a Compose file with extra ceremony. The whole point of publishing to the Bazaar — or even sharing a template across two Marquees — is that the next person fills in their own subdomain, their own image tag, their own database password, and gets a working environment without editing your YAML. That is what template variables are for.

The catch is that variables in Fibe are not Compose's ${VAR} interpolation. They are a separate compile-time layer with its own declaration block, its own substitution rules, and its own ways to fail. Get the mental model right and they are boring and reliable. Get it wrong and you ship a template that compiles to an empty string in production, or hard-fails on launch with a cryptic error. This guide is the version we wish someone had handed us: how to declare variables, where the values can land, and which mistakes actually bite.

Reachability and the two healthchecks: ignore the blip, redeploy the outage

· 9 min read

Every monitoring system hits the same fork: a check just failed — act, or wait? Act too eagerly and you turn a 400ms hiccup into a full redeploy, with a user staring at a "deploying…" spinner for nothing. Wait too long and a genuinely dead environment sits there, unreachable, getting the benefit of the doubt.

On Fibe, the watched things are AgentChats — the "Genie" coding agents that run as Docker sidecars on a Player's Marquee. They're long-lived, they sit behind Traefik with wildcard TLS, and people are actively typing into them, so a false redeploy is a visible interruption. We don't have one healthcheck; we have two, and most of the effort went not into detecting failure but into deciding which failures are worth reacting to.

Wildcard TLS without the tears: ZeroSSL EAB and acme-dns

· 9 min read

A tutorial Marquee is a single Docker host that serves a small zoo of subdomains: one per Playground, one per service inside a Playground, one for each AgentChat sidecar, plus a few for routing and error pages. They appear and disappear as you work — you can't enumerate them up front, so you can't mint a cert per name. You need one wildcard cert, *.domain, the moment the box comes online — no humans in the loop.

That sounds like a one-liner in a Traefik config. It is not. A publicly trusted wildcard cert means proving you control the whole DNS zone, on a brand-new VM, before a single browser has connected — then not lying to yourself about whether it worked. This is the story of that chain: ZeroSSL with External Account Binding, acme-dns for DNS-01, a cert-warmup router, and a readiness probe that refuses to declare victory on faith.

Running AI coding agents as sidecars: the AgentChat deploy pipeline

· 21 min read

A user clicks "Start" on a Genie. Forty seconds later there's a Claude Code agent running in a container on their Marquee, reachable over TLS at a stable subdomain, talking to their repo through MCP, with their skills and main prompt already staged on disk. If the container later falls over, something notices within a minute and quietly puts it back.

That whole arc — from a config row in Postgres to a self-healing sidecar — is one job, one Redis lock, six steps, and a surprising amount of opinion about what counts as a failure. This post is a walk through the AgentChat deploy pipeline: what we build, in what order, which steps are allowed to fail and retry, and the one design decision that quietly shaped everything else — that a missed health check is not a reason to kill anything.

Where do secrets go? Launch variables vs Secret Vault vs Job ENV

· 13 min read

A Fibe Template is a Docker Compose file plus a handful of fibe.gg/* labels. It is meant to be shared — pushed to a Prop, published to the Bazaar, copied by a teammate. Which means the single worst place you can put a database password is the one place it feels most natural to type it: straight into the YAML, next to the service that needs it.

The good news is that you almost never have to. Fibe gives you three distinct homes for sensitive values, and each one exists precisely so that the secret stays out of the Template text. The trick is knowing which home a given value belongs in. This guide walks through all three, the decision that picks between them, and the random / secret / sensitive mechanics that let you author a credential-using Template without ever holding a real credential in your hand.

Routing with Traefik: wildcard TLS, maintenance pages, and a priority-one-million trick

· 10 min read

Every Fibe environment is a little pile of Docker containers on someone's machine, and the platform's job is to make that pile feel like a website: app.your-env.your-marquee.dev should resolve, terminate TLS, and land on the right container. When the environment is mid-rebuild with nothing healthy to land on, the URL should show a 503 that says "this is coming back," not a browser's "can't connect" screen.

That last part is where the interesting engineering lives. The happy path is solved; the hard question is the unhappy path: how do you serve a maintenance page from a router that has to beat the one that would otherwise serve the broken app, without playing whack-a-mole tearing routers down and back up? Our answer is a maintenance router with priority: 1_000_000 — blunt, exactly right, and the subject of this post.