Deploying
A "deploy" takes your project source, builds it into a container image on the platform, and rolls that image out to a slot. You never build locally and you never write a Dockerfile. There are three ways to start a deploy: the CLI, a connected GitHub repo, and the dashboard upload.
Via the CLI
velixir deploy
This:
- Packages the current directory's source into
.velixir/source.tar.gz. Packing happens in-process, so notarbinary and no build tools are needed on your machine. - Detects your language (informational) and asks the platform for a presigned upload URL, then PUTs the archive straight to object storage.
- Creates a release and finalises it.
- The platform builds the image, enqueues a deployment, and the CLI polls until it lands or fails.
The server-side build is where your dependencies are resolved and your image is assembled, so the first deploy of a project takes a little longer than the ones after it. If the build fails, the failure reason streams back to your terminal.
Deploy to a named slot with velixir deploy --slot staging, or package a different directory with velixir deploy --source-dir ./service.
Via the dashboard
From an app's Overview tab, click Upload source. Pick a .tar.gz or .zip of your project source: your code plus its manifest, for example package.json, requirements.txt, go.mod, pom.xml, or a .csproj. We sign a one-time URL pointing at object storage; your browser uploads directly to that URL (no proxy hop, no Cloudflare body-size cap), and the build starts as soon as the upload lands.
Via GitHub (push-to-deploy)
Connect a GitHub repo and add the Velixir Action to your workflow. On every push, the Action runs velixir deploy from your checked-out repo: it packages your source and hands it to Velixir to build and roll out. There is no build step in your workflow and no artifact for Velixir to pull. Your CI simply triggers the same source upload the CLI does.
- One-click connect. A real GitHub App, no PATs and no webhook secrets to paste. You authorise the Velixir App on a single repo, GitHub redirects back, and you're done.
- Your CI stays simple. The Velixir Action is the only platform-specific step. Nothing in your workflow needs the .NET SDK, Node, or any other toolchain, because the build happens on the platform, not on the runner.
1. Add the deploy workflow to your repo
Drop this in .github/workflows/velixir.yml:
name: Deploy to Velixir
on:
push:
branches: [main] # change to your deploy branch
jobs:
deploy:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Deploy to Velixir
uses: velixir/velixir/actions/deploy@v1
env:
VELIXIR_API_KEY: ${{ secrets.VELIXIR_API_KEY }}
The Action runs velixir deploy for you. It reads the target app from the .velixir.json that velixir init wrote (commit that file; it holds only your app ID and slug, no secrets) and authenticates with a VELIXIR_API_KEY repo secret. That secret is the only thing you add. No setup-dotnet, no dotnet publish, no upload-artifact.
2. Connect GitHub from Velixir
On your app's Deploys tab in the dashboard, click Connect GitHub. We redirect you to GitHub's install page for the Velixir App; you pick which repo to grant access to (just the one this app deploys from, per-repo rather than "all repositories", to keep the blast radius tight).
GitHub redirects you back to Velixir with an installation ID. We persist it and verify the integration is reachable by listing what we can see, so you get a success toast that names the repo. Connecting links the repo to your app so deploys show up against it; the deploy itself is driven by the Action and your API key.
3. Push and watch the deploy
Push to the configured branch. GitHub Actions runs your workflow, the Velixir Action uploads your source, and the platform builds it and deploys it. Watch the Overview tab: a new release appears, then a deployment, then the live badge moves to it.
Disconnecting
- Soft disconnect (Velixir side only). On the Deploys tab, click Disconnect. We forget the installation and unlink the repo from the app. The Velixir App is still installed on GitHub but we won't call its API.
- Hard disconnect (full revoke). Go to GitHub → Settings → Integrations → Applications → Installed GitHub Apps → Velixir → Uninstall. GitHub revokes the installation immediately.
Use the soft path if you're just pausing the integration; use the hard path if you want our access entirely gone from the repo.
Common gotchas
- Missing API key. The Action needs a
VELIXIR_API_KEYrepo secret. Generate a Write-scoped key in the dashboard under API keys, then add it on GitHub under Settings → Secrets and variables → Actions. Without it the deploy step fails fast. - No app linked.
velixir deployneeds to know which app to target. Commit the.velixir.jsonthatvelixir initcreated, or pass--app <id>in the workflow step. - Branch mismatch. The workflow's
on: push: branches:filter decides which pushes deploy. Widen or narrow it to match your deploy branch. - Build failed. A failed build shows up on the app's Overview and in the workflow logs. Fix your source and push again.
Slots
Every app has at least one slot (production). You can deploy to a different slot to stage a release without touching live traffic:
velixir deploy --slot staging
From the dashboard's Slots tab you can then Promote that slot to live - a near-instant swap, the staged pods become production and the previously-live pods stay warm so you can flip back if anything's wrong.
Rollback
Every previous deploy is available from the Releases table on the Overview tab. Hit Redeploy on any earlier release to bring it back; we roll that release back out and the edge cuts traffic over once it's healthy.
After a deploy
- Set environment variables on the Environment tab - they're injected on the next deploy.
- The Logs tab tails container output live.
- The Metrics strip on the Overview tab updates every 10 seconds with replica count, CPU, memory, and HTTP traffic.