Skip to main content

Command Palette

Search for a command to run...

Deploy a Minimal FastAPI App to Leapcell

Published
4 min read
Deploy a Minimal FastAPI App to Leapcell

I’ll just dive right in. I’ve been looking at different ways to deploy a FastAPI-based application. I’ve used Fly.io and Leapcell recently.

Three quick contrasts with Fly.io, then the step‑by‑step.

References: the walkthrough I followed on YouTube is here → video, and my Fly.io deployment notes are here → Fly.io doc.

Leapcell vs Fly.io in three bullets

  1. Credit card: Leapcell’s free tier starts without a credit card, which reduces friction for students or university clubs that cannot attach a shared card. Fly.io often needs one early, even for simple prototypes.

  2. GitHub automation: Leapcell authorizes a single repo and auto‑builds on pushes without pasting personal access tokens. Fly.io can do CI, but you usually wire tokens or workflows yourself first.

  3. UX: Leapcell’s dashboard unifies deploys, logs, metrics, and managed add‑ons (PostgreSQL, S3‑style object storage, custom domains). If you prefer CLI‑first and VM‑style control, Fly.io is strong.


What you’ll deploy

A tiny FastAPI service with a root route (/) and a /health route. You will:

  • Initialize a project

  • Run locally

  • Push to GitHub

  • Connect Leapcell and deploy

  • Fix common pitfalls: uv vs pip, uvicorn target, and health checks

Prereqs

  • Git and a GitHub account

  • Python 3.12 recommended

  • Optionally uv. If you use uv locally, export a requirements.txt for Leapcell’s build.


1) Create the FastAPI app

You can use uv or plain pip. I followed the tutorial video which shows uv locally, then export requirements for Leapcell.

# new project folder
mkdir leapcell-deploy && cd leapcell-deploy

# optional: initialize uv project
uv init  # if the folder already has pyproject.toml, uv will warn

# add FastAPI and Uvicorn
uv add "fastapi[standard]"

Create main.py:

from fastapi import FastAPI

app = FastAPI()

@app.get("/")
def read_root():
    return {"message": "Hello Leapcell"}

@app.get("/health")
def health():
    return {"status": "ok"}

Run locally:

uv run uvicorn main:app --reload
# visit http://127.0.0.1:8000 and /health

2) Initialize Git and push to GitHub

git init
git add .
git commit -m "Initial FastAPI app"
git branch -M main
git remote add origin git@github.com:<your-username>/leapdeploy.git
git push -u origin main

Note: If you’re on a fresh setup, authenticate with the GitHub CLI:

gh auth login

3) Prepare for Leapcell builds

Leapcell’s Python preset installs dependencies with:

pip install -r requirements.txt

It does not include uv in the container by default, so a Start Command that uses uv run ... didn’t work for me.

Actually, I want to test this more. I got feedback on Reddit from Leapcell that in Build Script you could add pip install uv and then use uv sync and then uv run uvicorn main:app --host 0.0.0.0 --port 8080 I need to test this to verify, however.

Export a requirements.txt and use a plain uvicorn start command.

Export with uv:

uv export --no-hashes --format requirements.txt > requirements.txt
git add requirements.txt
git commit -m "Add requirements.txt for Leapcell"
git push

4) Connect Leapcell to your repo

  1. Sign up or sign in to Leapcell with GitHub. No credit card needed on the free plan.

  2. Create a new Service. Pick a region (US‑East/Virginia) and the Python 3.12 runtime.

  3. When prompted, install the Leapcell GitHub app for your single repository.

Build Command

pip install -r requirements.txt

Start Command

uvicorn main:app --host 0.0.0.0 --port 8080

Common mistakes to avoid:

  • Do not use uv run ... in Start Command.

  • Target the app correctly as main:app (module main.py, object app).

Click Deploy. Watch build logs, then open the generated .leapcell.dev domain once it’s live.


5) Verify and set a health route

Leapcell performs health checks. A trivial /health returning 200 OK is sufficient. If you skipped it earlier, add it now, commit, push, and let Leapcell redeploy.

@app.get("/health")
def health():
    return {"status": "ok"}
git add main.py
git commit -m "Add health route"
git push

Use the dashboard to confirm the deployment transitions to Active.


6) Common pitfalls and fixes

“uv: not found” in logs
Start Command uses uv run ... but uv is not installed in the container.
Fix: Keep pip install -r requirements.txt as Build Command and use uvicorn main:app --host 0.0.0.0 --port 8080 as Start Command.

Wrong app target
You wrote uvicorn main:FastAPI or main:App.
Fix: Ensure your file is main.py and the application object is named app, then use main:app.

Build succeeds, failing health
No /health route or the app crashes on import.
Fix: Add /health and check dashboard logs for import errors or typos.


Wrap‑up

For simple FastAPI prototypes, Leapcell’s no‑card start, repo‑level auto‑deploys, and integrated dashboard offer a quick path from local to public URL. If you prefer deep CLI workflows and VM‑style control, compare with the approach in my Fly.io doc. Start with the minimal uvicorn main:app service above, verify it, then layer in Postgres, object storage, and a custom domain as you iterate.

Also see the original walkthrough video for full context: https://youtu.be/xhOALd640tA?si=10AAuaIWhEbECPuW.

C
Craig Oda8mo ago

Great that Leapcell doesn't require a credit card at the free tier. I feel it is a significant behavior to creativity. I hope that their service does not get abused by people doing bad things and taking advantage of their generosity.

I would like to try and install uv into Leapcell with pip install uv and then use uv to manage the installation.

More from this blog

F

FastOpp

8 posts

FastOpp is a modern FastAPI starter package for AI web applications that ships with auth, admin, demo data, and a few practical examples for real projects.