A reusable workflow for deployments to vercel from Forgejo.
Find a file
2026-05-01 19:45:30 -05:00
.forgejo/workflows update docs 2026-05-01 19:45:30 -05:00
README.md update docs 2026-05-01 19:45:30 -05:00

Vercel Deploy Workflow @ v1

A reusable Forgejo workflow for deploying projects to Vercel. Routes pushes to a production branch to the live site and pushes to a preview branch to a preview environment.

Features

  • Separate production and preview deployments based on branch
  • Builds run on your Forgejo runner (build logs stay in Forgejo, not Vercel)
  • Bun and Node.js both available in the build environment
  • Configurable runtime versions, branch names, and runner label

Prerequisites

  • Forgejo v7 or later (reusable workflow support)
  • A registered Forgejo runner with the ubuntu-latest label (or override via the runs_on input)
  • A Vercel project that is not connected to any Git integration
  • Vercel API token, org ID, and project ID

Disconnecting Vercel from Git

If your project was previously deployed via Vercel's GitHub integration, disconnect it first to avoid duplicate deploys:

Vercel dashboard → Project → Settings → Git → Disconnect.

The project and its environment variables stay; only the auto-deploy hook is removed.

Obtaining credentials

Token: Vercel dashboard → Account Settings → Tokens → Create. Scope it to the team that owns the project.

Org ID and Project ID: Run npx vercel link once locally inside the repo. It creates .vercel/project.json containing both IDs. Copy the values, then delete the folder or verify it's in .gitignore.

Vercel's "team ID" and "org ID" refer to the same value — use whichever name your tooling expects.

Configuring a preview domain (optional)

Vercel's per-branch domain assignment requires their Git integration, which only supports GitHub/GitLab/BitBucket — so it doesn't work for Forgejo-driven deploys. Instead, this workflow aliases each preview deployment itself.

Add the subdomain in Vercel project Settings → Domains (without attaching it to a branch), then pass it to the workflow via the preview_domain input. After every preview deploy, the workflow runs vercel alias set to point the domain at the new deployment.

Usage

Add .forgejo/workflows/deploy.yml to your repo:

name: Deploy

on:
  push:
    branches: [main, preview]

jobs:
  deploy:
    uses: you/vercel-deploy-workflow/.forgejo/workflows/deploy.yml@v1
    secrets: inherit

Replace you/vercel-deploy-workflow with the actual path to this repo on your Forgejo instance. Add the three secrets via repo Settings → Actions → Secrets, or at the organization level if multiple repos will use this workflow.

secrets: inherit is required rather than per-secret declarations because Forgejo's runner does not yet implement the workflow_call.secrets key (tracked in forgejo#6069). On the upside, this means adding a fourth secret to the workflow later won't require updating any consumers.

With custom branch names

jobs:
  deploy:
    uses: you/vercel-deploy-workflow/.forgejo/workflows/deploy.yml@v1
    with:
      production_branch: production
      preview_branch: staging
    secrets: inherit

Make sure the on: push: branches: list in the caller matches the branches you've configured.

With a preview domain alias

jobs:
  deploy:
    uses: you/vercel-deploy-workflow/.forgejo/workflows/deploy.yml@v1
    with:
      preview_domain: preview.example.com
    secrets: inherit

Inputs

Input Type Default Description
production_branch string main Branch that triggers production deploys
preview_branch string preview Branch that triggers preview deploys
preview_domain string "" Custom domain to alias to each preview deploy. Leave empty to skip aliasing.
node_version string "24" Node.js version
bun_version string latest Bun version
runs_on string ubuntu-latest Runner label

Secrets

These must be defined at the repo or org level on your Forgejo instance. The reusable workflow doesn't pre-declare them (see the note in Usage), so missing secrets surface as auth errors at the first vercel command rather than as workflow validation errors.

Secret Required Description
VERCEL_TOKEN yes Vercel API token
VERCEL_ORG_ID yes Vercel team/org ID
VERCEL_PROJECT_ID yes Vercel project ID

Notes

GITHUB_API_URL override

The Pull and Build steps explicitly set GITHUB_API_URL and GITHUB_SERVER_URL to GitHub's real URLs. Forgejo runners default these to the Forgejo instance, and Bun reads GITHUB_API_URL to fetch tarballs for any github.com dependency. Without the override, bun install routes through the Forgejo API and 404s on every GitHub-hosted dependency.

Pinned action SHAs

Actions are pinned to commit SHAs from code.forgejo.org, the Forgejo mirror. If your runner is configured to resolve actions from a different source (e.g. github.com directly), you'll need to use SHAs from that source instead. setup-bun is referenced via its full GitHub URL because it isn't mirrored on code.forgejo.org.

To refresh a pin:

git ls-remote https://code.forgejo.org/actions/checkout refs/tags/v4
git ls-remote https://code.forgejo.org/actions/setup-node refs/tags/v4
git ls-remote https://github.com/oven-sh/setup-bun refs/tags/v2

Versioning this workflow

Consumers pin to a ref via @v1, @v1.2.0, or a full commit SHA. The recommended convention:

  • Cut tags v1.0.0, v1.1.0, etc. for releases
  • Maintain a floating v1 tag pointing at the latest 1.x release for consumers who want minor updates automatically
  • Bump the major version (v2) for any breaking change to inputs or behavior

This mirrors how actions/checkout and similar first-party actions handle versioning.