Skip to content

Docs / Start here

Publish a game

The full path from invite code to released game. Create a draft, prepare and upload a build (in the browser or from a terminal), add a cover, preview it and submit it to containment.

.md

Most steps happen in your browser, at /dev. Builds can also go up from a terminal or a coding agent, with an API token. The last step is a 48-hour vote by strangers.

Checklist

An agent connected to the MCP server can do steps 3 to 8: create the draft, prepare and deploy the build, upload a cover, fill in the description, and submit it when you say so. Without MCP, an agent can do steps 4 to 6 with an API token.

  1. Sign in with Discord or GitHub and claim a handle at /welcome. That's your badge.
  2. Redeem an invite code at /dev. Codes come from an admin.
  3. Create the game with New game on My games (/dev). The slug can't change later.
  4. Build for the web: index.html at the top, relative paths, allowed file types only. Run node check-build.mjs <folder-or-zip> until it is clean.
  5. Upload the zip or folder at /dev/<slug>, or deploy it from a terminal: node check-build.mjs deploy <folder> --game <slug>. Add patch notes if you want them.
  6. Add a cover on the same page.
  7. Make sure the game has a description. Click Preview and play the draft.
  8. Hold the Hold to submit button. A draft needs a live build, a cover and a description.
  9. Wait 48 hours. Released games are listed on /games. Buried games can come back after 7 days with a new build.

Get access

Developer access is invite-only.

  1. Sign in with Discord or GitHub.
  2. Claim a handle at /welcome. That's your badge. Your handle appears on your games and your profile.
  3. Open /dev. Without developer access the page shows an Invite code field.
  4. Enter the code. The format is XXXX-XXXX-XXXX. Case and dashes don't matter.

Every code has a use limit, and some expire. A code that is used up, expired or mistyped is refused. /dev then becomes My games, which is also in the menu under your avatar.

Create the game

Click New game on My games. /dev/new opens the same form.

FieldRules
TitleRequired. 1 to 60 characters. Editable later.
SlugPermanent. See below.
EngineThree.js, Unity, Godot or HTML5. A label on the game's card. It doesn't change how the build runs or what the uploader accepts.
OriginHandmade, AI-assisted or AI-generated. Shown on every card. Be straight about it.
What did AI make?Appears for AI-assisted and AI-generated. Pick at least one of Code, Art, Audio and Text.
DescriptionUp to 600 characters. Optional now, required before containment. A sentence or two: what it is and how it plays.

Slug

The slug is the game's own origin: https://<slug>.containment.cloud. That is where its saves live, so it can't be changed.

  • 1 to 47 characters.
  • Lowercase a-z, digits 0-9 and single dashes. No --.
  • Starts and ends with a letter or a digit.
  • Some names are reserved, for example www, api, admin, dev, docs, play and test. Anything starting with xn- is refused.

The form fills the slug from the title until you edit it, and checks availability as you type. The Create draft button stays disabled until the slug is free.

AI disclosure

Handmade means no AI flags. AI-assisted and AI-generated need at least one. The form and the server both refuse any other combination.

The new game is a draft. Only you and admins can see it. You can have ten drafts at once. Everything except the slug can be edited later under Details on the game's page.

Prepare a build

A build is the web export of your game. Before you upload:

  • index.html sits at the top of the build, or fradiation.json names another entry.
  • Every path is relative. assets/game.js works. /assets/game.js breaks.
  • Every file has an extension on the allowed list.
  • The game fills its window and handles resize.

fradiation.json at the top is optional. It sets entry, viewport and threads, and declares mutations and scoreboards. See fradiation.json. Games talk to the site through the SDK, which is also optional.

EngineGuide
UnityUnity
GodotGodot
Three.js, Vite, plain HTML5Web

Builds and uploads has every limit, path rule and file type. The machine-readable version is https://www.fradiation.games/docs/build-rules.json. Check a build before you open the browser:

bash
node check-build.mjs <folder-or-zip>

Download the script and see the other commands in Check a build first.

Upload the build

Open /dev/<slug> and find the Upload a build panel. To upload from a terminal instead, see From a terminal.

  1. Drop a .zip on the tray, or click browse. To upload a folder, click pick a folder. Dropping a folder doesn't work.
  2. The browser reads the build and checks it. Problems are listed, up to eight, and Upload build stays disabled until none remain.
  3. Set the Stage size. It appears only if fradiation.json has no viewport. Width is 160 to 4096 and height is 120 to 4096. The default is 1280 by 720, or the size of your current build. The site letterboxes the game to that aspect ratio.
  4. Write Patch notes if you want to. Up to 2,000 characters, shown in the game's update log.
  5. Choose what happens when the build is sealed. The choices depend on the game, as the table below shows.
  6. Click Upload build.

When it's sealed

Game statusChoiceResult
Draft or buriednoneThe upload becomes the live build. A draft always runs its newest build.
In containment or releasedGo live now (default) or Upload onlyGo live now makes it the live build. Upload only seals it and leaves the live build alone.
Any game with a playtestSend to testers (default) or Keep their buildTesters get the new build on their next load, with your patch notes, or keep the one they have.

What the uploader checks

Before it sends anything:

  • The entry file is at the top.
  • At most 1,000 files, 500 MB in total and 200 MB per file.
  • Every path follows the path rules and every file type is allowed.
  • fradiation.json, if present, is valid JSON.

The site then checks fradiation.json against its schema and confirms the entry file is in the file list. After the upload it checks that every file arrived at its full size. Then it seals the build. A sealed build never changes.

Progress

The bar moves through Checking files, Requesting a grant, Uploading and Verifying and sealing. Stay on the page. Leaving mid-upload asks you to confirm. If an upload fails or you cancel, start it again. The site cleans up what it left behind.

Only files the game doesn't already have are sent. An update that changes one file uploads one file. Each build in the Builds list shows how much it sent, for example (1.6 KB new) or (nothing new).

From a terminal

check-build.mjs uploads the same way the browser uploader does, with an API token instead of your browser session.

  1. Under Agents & tokens (/dev/agents), create a token in the API tokens panel, for all your games or one. Copy it: it's shown once.
  2. Set it as FRADIATION_TOKEN in your shell or your CI secrets.
  3. Deploy the build folder or zip:
bash
node check-build.mjs deploy Builds/Fradiation --game <slug> --notes "What changed"

It checks the build first, uploads only what the game doesn't have, and seals it. --live makes it live and --playtest sends it to testers, with the same rules as the choices above. node check-build.mjs live <buildId> ships or rolls back later. See Deploy from the command line for every option and the API behind it.

Limits

  • 20 uploads per rolling 24 hours, across all your games, from the browser and from tokens together. Failed and cancelled uploads count.
  • Files over 64 MB upload in parts. This is automatic.
  • Storage has a soft limit of 2 GB per developer. See Retention and storage.

Add a cover

Use the Cover panel on the game's page.

  1. Drop an image on it, or click to browse. PNG, JPEG, WebP or AVIF.
  2. The browser crops it to 4:3 from the center and re-encodes it as an 800 by 600 JPEG. The upload limit is 2 MB.
  3. It uploads at once. There is no separate save.

A draft needs a cover before it can be submitted. You can replace the cover at any time.

From a terminal or an agent: node check-build.mjs cover cover.png --game <slug> with an API token, or the MCP server's upload_cover (a presigned URL the agent PUTs the image to). The site does the same crop, from images up to 15 MB. See How covers work.

Preview the draft

Once the draft has a build, click Preview at the top of /dev/<slug>. That opens /games/<slug>, the real game page. A Draft notice says only you and admins can see it. Click Start to run the build inside the cabinet.

  • SDK calls run in test mode. ready() reports the mode preview. Calls are checked, and nothing is kept.
  • A mutation key the build doesn't declare, a negative score and a score above the board's max are rejected.
  • A toast marks each call: Test unlock: <name> or Test score: <value>.
  • Your own plays of your own draft don't count as plays.
  • Open on a build in the Builds list loads it directly on https://<slug>.containment.cloud/<buildId>/, outside the cabinet. There is no SDK connection there.

Other players can't see a draft. To get feedback before you submit, start a private playtest. See Playtests.

Submit to containment

A draft can be submitted when the status panel shows all three checks:

  • A live build.
  • A cover.
  • A description.

Hold the Hold to submit button for about a second. The game moves to In containment and is listed on /containment. For the next 48 hours, players who have played it vote to release it or bury it. You can't vote on your own game, and the tally is hidden until judgment closes. You can keep uploading builds while it's in there.

Send people the link to your game's page. Votes come only from players who have played it.

When judgment closes, the game is released or buried. Containment has the exact rules, the payouts and the way back from a burial.

After release

A released game has the same page at /dev/<slug>. New builds go live when you say so.

Updates

Upload a new build. Choose Go live now and players get it on their next load. Choose Upload only and the build is sealed but not live. Make it live later from the Builds list. From a terminal, deploy without --live is Upload only, and deploy --live is Go live now.

Patch notes show in the game's update log. Saves survive updates, because the game's origin doesn't change.

Rollbacks

Every sealed build that still has its files can be made live. Open the Builds list, find the build and click Make live, or run node check-build.mjs live <buildId> --game <slug>. That is how you ship and how you roll back. Builds whose files were deleted can't be made live. Upload them again. Pin a build to keep its files. See The builds list.

Playtests

A playtest is a private link that serves any sealed build you choose, independent of the live one. Use it to try your next update on testers before players get it. With a playtest open, an upload offers Send to testers or Keep their build. See Playtests.

If it was buried

A buried game keeps its page, and its developer can send it back for another round after 7 days with a new build. See Coming back.