Skip to content

For developers

Maintainers

Add a Run on Setup button, a Runs on Setup badge and a setup.json to your repository, and how Setup verifies your recipe.

On this page
  1. The Run on Setup link
  2. Badge and button snippets
  3. Check the slug
  4. What the badge shows
  5. Public, unlisted and private projects
  6. Add a setup.json to your repository
  7. Check setup.json in CI
  8. How verification works
  9. How verification is repeated

If you maintain an open-source project, you can let people try it without installing anything. A "Run on Setup" link opens Setup with your repository already pasted. Setup works out how to run it, and the visitor gets a running copy in a sandbox for about an hour.

The "Runs on Setup" badge shows whether that actually works. It turns green after a real runner started your project and all its checks passed, and goes grey again when the last successful run is more than 30 days old. If you commit a setup.json to your repository, Setup uses your recipe instead of guessing.

You don't need an account to add the link or the badge. The generator on the maintainers page writes both for you.

The link is /run?source=<url>:

https://setup.run/run?source=github.com/louislam/uptime-kuma

source takes anything the box on Home takes, usually a repository URL. A visitor who is signed in goes straight to the analysis. Everyone else signs in or creates an account first and lands on the same analysis afterwards. From there they read the recipe and start a trial.

Badge and button snippets

The generator on the maintainers page takes owner/repo or a GitHub URL and produces these two snippets. Both link the badge to the Run on Setup link.

Markdown:

md
[![Runs on Setup](https://setup.run/api/badge/uptime-kuma)](https://setup.run/run?source=github.com/louislam/uptime-kuma)

HTML:

html
<a href="https://setup.run/run?source=github.com/louislam/uptime-kuma"
  ><img src="https://setup.run/api/badge/uptime-kuma" alt="Runs on Setup"
/></a>

Your project's catalog page at /catalog/<slug> has a For maintainers section with the same badge and a Run button, a dark "Run on Setup" button image served from /api/badge/<slug>/button:

md
[![Run on Setup](https://setup.run/api/badge/uptime-kuma/button)](https://setup.run/run?source=https%3A%2F%2Fgithub.com%2Flouislam%2Fuptime-kuma)

The snippets on your Setup show its own address. setup.run is used here as the example.

Check the slug

The badge URL ends in the project's slug. The generator guesses it from the repository name, so louislam/uptime-kuma becomes uptime-kuma. That matches projects in the curated catalog. A project that Setup created from an analysis usually has the owner in its slug, such as louislam-uptime-kuma, and gets a short random suffix if that name was taken.

The snippets in the For maintainers section of the catalog page always use the right slug. When in doubt, copy them from there.

What the badge shows

The badge reads setup on the left and the state on the right.

BadgeColorWhenHTTP status
setup verified v1.4.2greenA run on one of Setup's runners passed all its checks in the last 30 days.200
setup runsgreenThe same, when Setup doesn't know which release the recipe is for.200
setup ci passed v1.4.2blueOnly your own CI reported a pass in the last 30 days (see Check setup.json in CI).200
setup unverifiedgreyNo run has passed yet, or the last pass is older than 30 days.200
setup unknowngreyNo project has this slug, or the project is private.404

A run on Setup wins over a CI report. The response also carries the state (runs, ci, unverified or unknown) in an X-Setup-Badge header, which is handy for scripts. Badge images are cached for about five minutes, so a change can take a moment to show up.

Public, unlisted and private projects

Badges only answer for public and unlisted projects. Projects in the curated catalog are public. A project that Setup created from an analysis starts out private to the workspace that analyzed it first, and its badge reads unknown until it is public or unlisted. Unlisted projects can be opened by anyone with the link but don't appear in the catalog.

The dashboard has no switch for this yet. Members of the owning workspace can change it with an API key. GET /api/projects/<slug> returns the project with its id:

Terminal
curl -X PATCH https://setup.run/api/projects/<project-id> \
  -H "Authorization: Bearer $SETUP_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"visibility":"unlisted"}'

visibility is private, unlisted or public. If someone else's workspace analyzed your repository first and owns the project, write to us.

Add a setup.json to your repository

Put a setup.json in the root of your repository. If your link points to a subdirectory (/tree/<ref>/<dir>), put it in the root of that directory. The easiest way to get one is Download setup.json in the For maintainers section of your project's catalog page: it is the recipe Setup runs, with defaults left out. The format is described in Recipes. A small one looks like this:

json
{
  "version": 1,
  "slug": "uptime-kuma",
  "name": "Uptime Kuma",
  "category": "homelab",
  "source": {
    "kind": "github",
    "url": "https://github.com/louislam/uptime-kuma"
  },
  "services": {
    "app": {
      "image": "louislam/uptime-kuma:1.23.16",
      "ports": [{ "container": 3001 }],
      "volumes": [{ "name": "data", "path": "/app/data" }]
    }
  },
  "expose": { "service": "app", "port": 3001 },
  "checks": { "http": { "path": "/" } }
}

What Setup does with it:

  • It comes first. A valid setup.json wins over Setup's own detection. The analysis says "Recipe maintained in the repository (setup.json)".
  • The source is always yours. Setup builds the repository that was pasted, at the commit it analyzed. It replaces source in your file. If source.git.url points to another repository, Setup ignores it and shows a warning. A service that builds from another repository also gets a warning.
  • A broken file is skipped. Invalid JSON or a recipe that fails its checks is ignored with a warning, and Setup falls back to detecting how the project runs.
  • Changes become revisions. Each analysis reads the file at the analyzed commit. When the content changed, Setup stores it as a new recipe revision.

If your project is also in Setup's curated catalog, the catalog page keeps showing the curated recipe.

To try a recipe before you commit it, paste the file's contents into the box on Home and start a trial. You see the same checks a visitor would. With the runner installed, setup-runner validate setup.json checks the file offline with the same rules Setup uses and points at the line of each problem.

Check setup.json in CI

The Setup GitHub Action checks your setup.json on every pull request and reports release runs to Setup. The GitHub Action tab in the For maintainers section writes a workflow for your project. It looks like this:

yaml
on:
  pull_request:
    paths: [setup.json]
  push:
    tags: ["v*"]

jobs:
  verify:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: setup-run/verify-action@v1
        with:
          api-key: ${{ startsWith(github.ref, 'refs/tags/') && secrets.SETUP_API_KEY || '' }}

On each run the action validates the file and annotates problems in the pull request. It then starts your recipe in a throwaway sandbox on the GitHub runner's own Docker, runs its checks and removes the sandbox again. The report is uploaded as an artifact and summarized on the run.

To report runs, create a maintainer token under Maintainer tokens on your project's catalog page (only the project's owners see it) and store it in your repository as the SETUP_API_KEY secret. A maintainer token belongs to one project and can only report runs for it. It is shown once, you can give it an expiry, and you can revoke it at any time.

Runs your CI reports are labelled CI-reported. Setup didn't see them happen, so they never count as verified by Setup: they give the blue ci passed badge, while runs on Setup's own runners give the green one. Both kinds, passed and failed, appear in the Verification history on the catalog page with the tag or branch, the commit and a link to the CI run.

How verification works

A run verifies a recipe when the runner reports its checks and every one passes, for example images pulled, services started, health checks healthy and the HTTP check answered through the app's public address. Your recipe decides what the health and HTTP checks look at (see Recipes).

Two kinds of runs count:

  • Runs by people. Every trial or kept app that someone starts or updates from your project and that passes its checks adds a verification. A failed run by a visitor is not recorded against your recipe.
  • Verification runs. Setup also runs dedicated verification jobs, for example for every catalog entry. These record passes and failures.

For each verification Setup stores the recipe revision, the source commit, the runner's isolation and architecture, the individual checks and how long the run took. The catalog page shows the latest one under Verification and every run, including the ones your CI reported, under Verification history.

How verification is repeated

There is no fixed schedule per project. The badge follows the last passing run:

  • It stays green for 30 days after a passing run, then reads unverified until the next one.
  • When someone keeps an app from a Git repository, Setup checks your repository at most once a day for a new release, or a new commit if there are no releases. If it moved, Setup analyzes it again and adds a revision when the recipe changed. Kept apps with automatic updates move to that revision, and a passing update counts as a verification.
  • Every Run on Setup click analyzes your repository again, so new trials use your latest setup.json.

Note. A GitHub App that opens a pull request with a verified setup.json and checks it again on Setup's own runners on every release is planned. It does not exist yet; the GitHub Action above checks releases on your CI.