Documentation
ReferenceArchitecture

Quickstart: deploy from a git push

This is the simplest way to get an app running on Tabbify. You write a few small files, push them to GitHub, and Tabbify does the rest: it clones your repo, builds it on its own machines, and runs it. Every later git push ships a new version with no downtime.

You do not need Docker on your laptop, a server, or any registry login.

What you need:

  • A GitHub account (free — github.com/signup).
  • A Tabbify API token. This comes with your Tabbify account. Keep it handy — you'll paste it into GitHub once, in step 3.

The whole thing takes about five minutes. There's a working copy of everything below at github.com/tabbify-io/quickstart — you can fork that instead of typing the files out.

Step 1 — Create the four files

Make a new folder on your computer and put these four files in it. Copy them exactly; you can change the words inside index.html to anything you like.

index.html — the page your app serves:

<!doctype html>
<html>
  <body style="font-family: system-ui; text-align: center; margin-top: 4rem">
    <h1>Hello from Tabbify 👋</h1>
    <p>Deployed straight from a git push.</p>
  </body>
</html>

Dockerfile — how your app is packaged. (You don't run this yourself — Tabbify does. The ENTRYPOINT line must use this exact bracket form.)

FROM busybox:1.36
COPY index.html /www/index.html
EXPOSE 8080
ENTRYPOINT ["busybox", "httpd", "-f", "-v", "-p", "8080", "-h", "/www"]

This listens on 8080, which is the default Tabbify probes — so nothing extra to set. If your app listens on a different port, add port = <n> under [runtime] (below), otherwise the readiness check hits the wrong port and the app crash-loops.

tabbify.toml — what to build and how to run it. Tabbify reads this to decide everything; you don't pick a server, and you don't pick an address — Tabbify gives your app a permanent URL automatically and prints it when you deploy (you'll see it in Step 4). Nothing to fill in:

[app]
name = "quickstart"

[build]
kind = "docker"          # build the Dockerfile into an image

[runtime]
type             = "firecracker"   # run the app in its own tiny VM
lifecycle        = "on_request"    # start on the first visit, sleep when idle
idle_timeout_sec = 300
memory_mb        = 256
vcpus            = 1

[routes]
dynamic_prefixes = ["/"]           # send every web address to your app

.github/workflows/deploy.yml — the part that deploys on every push. Copy it as-is:

name: Deploy to Tabbify
on:
  push:
    branches: [main]
jobs:
  deploy:
    runs-on: ubuntu-latest
    permissions:
      contents: read
    steps:
      - uses: actions/checkout@v4
      - uses: tabbify-io/deploy@v1
        with:
          token: ${{ secrets.TABBIFY_TOKEN }}

That last file lives in a folder called .github/workflows/ — create those two folders, with the leading dot, and put deploy.yml inside.

Step 2 — Put it on GitHub

  1. Go to github.com/new and create a repository. Give it any name (for example, my-first-tabbify-app). Leave everything else at its default and click Create repository.

  2. GitHub shows you a page of commands. The simplest path: on your computer, in your app folder, run the commands GitHub lists under "…or push an existing repository from the command line." They look like this:

    git init
    git add .
    git commit -m "my first app"
    git branch -M main
    git remote add origin https://github.com/YOUR-NAME/my-first-tabbify-app.git
    git push -u origin main
    

Don't worry if that first push kicks off a deploy that fails — you haven't added your token yet. That's step 3, and then you'll push once more.

Step 3 — Mint your deploy token and add it to GitHub

First, mint a deploy token in the Tabbify console. A deploy token is scoped to one of your networks (your private deploy target) and is what lets the CLI ship to it.

  1. Open Deploy tokens (the Deploy tokens tab in the console sidebar).
  2. You need a network to deploy into. If you don't have one yet, open Networks, create one, then come back.
  3. On your network, click Manage tokens, then Mint deploy token.
  4. The token appears once in a Deploy token field — click Copy. ⚠️ It is shown only once, so copy it now. It is valid for a year and you can Revoke it any time from the same list.

Now store it on GitHub. Your token is a password, so it goes into GitHub's encrypted Secrets, never into your code. Here's exactly where to click:

  1. Open your repository on GitHub.
  2. Click Settings (top-right of the repo menu bar).
  3. In the left sidebar, click Secrets and variables, then Actions.
  4. Click the green New repository secret button.
  5. For Name, type exactly: TABBIFY_TOKEN
  6. For Secret, paste the deploy token you just copied.
  7. Click Add secret.

That's it — the workflow you copied in step 1 reads this secret automatically.

Step 4 — Push and watch it deploy

Make any small change (edit a word in index.html), then push:

git add .
git commit -m "deploy"
git push

Now open the Actions tab at the top of your repository on GitHub. You'll see a run called "Deploy to Tabbify". Click it to watch the steps. When it turns green, the Deploy step prints your app's address — a line like:

app URL: https://app.tabbify.io/app/2f8c1a9e-…/

Open that link in your browser — you should see your page. That address is permanent: it stays the same for every future deploy.

Want a fixed, memorable id instead of the generated one? Add id = "…" under [app] in tabbify.toml (any UUID — run uuidgen). Optional; skip it and Tabbify picks one for you.

First visit is slow, then instant. With lifecycle = "on_request" your app sleeps when nobody's using it and wakes on the next visit. The very first request after a deploy (or after a long idle) takes a moment while the VM boots; everything after that is fast.

Step 5 — Ship a new version

There's nothing new to learn. Edit your files, commit, and push:

git add .
git commit -m "new version"
git push

Tabbify builds the new version, checks it's healthy, switches traffic over, and only then retires the old one — so visitors never see an error or a blank page. Same address, new version, zero downtime.

What just happened

When you pushed, GitHub Actions ran one step — the tabbify-io/deploy action — which handed your repo's address and commit to Tabbify. Tabbify then:

  1. Cloned your repo (using a short-lived, repo-scoped GitHub token — no GitHub App to install, nothing extra to authorize).
  2. Built your Dockerfile into an image on its own build machine.
  3. Ran that image as a Firecracker microVM and gave it an address on the private mesh.
  4. Routed app.tabbify.io/app/<your-id>/ to it.

Your laptop never built or pushed anything — it only did a git push.

Where to go next

  • tabbify.toml — every field of the app manifest, including environment variables and how to run more than one copy.
  • Runtimes — Firecracker, WASM, and Docker, and when to use each.
  • The deploy pipeline — what happens between git push and a running app, in depth.
  • CLI reference — deploy from your own terminal with tcli instead of GitHub Actions.