Self-hosting

Base is a Django API with Celery workers and a Next.js web app. Running it on your own machine takes seven processes, two Python environments and a few settings; training on Modal also needs Base to be reachable from the internet.

The repository's README.md has the complete list of settings; this page covers what a local Base needs.

Processes

Each runs in its own terminal, from backend/ unless noted:

ProcessCommandWhat breaks without it
Redisbrew services start redisEverything: the Celery broker and the WebSocket layer
APIpython manage.py runserver 8000Everything
Default workercelery -A config worker -l info --concurrency 2 -n default@%hDataset ops and deployment builds stay queued
Interactive workercelery -A config worker -Q interactive -l info --concurrency 2 -n interactive@%hReview sessions
Train workercelery -A config worker -Q train -l info --concurrency 2 -n train@%hTraining jobs stay queued
Beatcelery -A config beat -l infoJob states never update; stale runs and sessions are never reaped
Web appnpm run dev, from frontend/The GUI

runserver serves HTTP and WebSockets: Daphne is installed, so it runs the ASGI app. Keep the train worker's concurrency low: a launch holds its slot for minutes while Modal builds the image and uploads datasets.

For a quick look without workers, CELERY_TASK_ALWAYS_EAGER=1 python manage.py runserver 8000 runs every task inline.

Two Python environments

Django and solarian live in separate environments. Base runs the solarian CLI as a subprocess for dataset ops, deployment builds, training launches, relays and controller sessions.

# Base: Django, Celery, and the modal client that polls training jobs
conda create -n solarian_base python=3.10 -y && conda activate solarian_base
cd backend && pip install -e ".[dev]"

# solarian: the CLI Base runs, with the plugins training needs
conda create -n solarian python=3.10 -y && conda activate solarian
pip install solarian solarian-modal solarian-base

Base finds the CLI in CONTROLLER_SOLARIAN_BIN, then on PATH, then in a conda env named solarian next to the one Django runs in.

Configure

Settings come from backend/.env or the process environment, read when each process starts: restart the API and the workers after a change.

VariableDefaultPurpose
FRONTEND_URLhttp://localhost:3000Where solarian base login sends you to approve
PUBLIC_API_URLhttp://localhost:8000Where training jobs report their runs; must be reachable from Modal
MODAL_TOKEN_ID, MODAL_TOKEN_SECRETunsetThe Modal account jobs run under; unset uses ~/.modal.toml
CONTROLLER_SOLARIAN_BINfound automaticallyThe solarian executable
CONTROLLER_LOCAL_PROJECT_DIRunsetProject checkout relays and controller sessions run from
CONTROLLER_RELAY_PUBLIC_HOST127.0.0.1The relay address robots dial
DATASETS_ROOTbackend/datasetsWhere datasets are stored
DJANGO_SECRET_KEYa development keyAlso encrypts project secrets; set it outside development

Then create the database:

python manage.py migrate
python manage.py createsuperuser   # optional, for /admin/

Training on Modal from a local Base

A training job reports to PUBLIC_API_URL. A Modal container cannot reach localhost, nor a Tailscale address, since it is not on your tailnet. Tailscale Funnel publishes the API at a public HTTPS address:

tailscale funnel --bg --set-path /api http://127.0.0.1:8000/api
tailscale funnel status          # https://<machine>.<tailnet>.ts.net/api

Only /api is published. Then:

  1. Set PUBLIC_API_URL=https://<machine>.<tailnet>.ts.net and restart the train worker.

  2. Log the CLI in through the same URL, so trainings started from your machine report there too:

    solarian base login --url https://<machine>.<tailnet>.ts.net
    
  3. Check from outside: curl -i https://<machine>.<tailnet>.ts.net/api/projects/ answers 401.

Check it

See also

Was this page helpful?