Configuration¶
The controller reads one YAML config file and then overlays environment variable overrides.
Minimal poll-mode config¶
github:
token: YOUR_GITHUB_PAT
owner: YOUR_GITHUB_OWNER
repository: YOUR_REPOSITORY
jeballto:
base_url: http://127.0.0.1:8011/v1
controller:
mode: poll
poll_interval: 10s
webhook_listen: :9090
labels:
jeballto-macos:
image: ghcr.io/jeballto/macos-ci:latest
lifetime_seconds: 3600
GitHub authentication¶
GitHub App¶
Recommended for production:
github:
app_id: 12345
app_private_key_path: /path/to/private-key.pem
installation_id: 67890
Personal Access Token¶
Useful for development or the first test:
github:
token: ghp_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
PAT scope guidance:
- repo-level runners:
repoor equivalent fine-grained permissions - org-level runners:
admin:orgor equivalent fine-grained permissions
Jeballto section¶
jeballto:
base_url: http://127.0.0.1:8011/v1
# token: your-token
# token_file: ~/Library/Application Support/Jeballto/config.json
If the controller runs on the same host as the Jeballto Agent, token auto-discovery is usually enough.
127.0.0.1 is the controller default for same-host deployments. The Jeballto Agent itself binds to 0.0.0.0:8011 by default unless api.host is changed.
Controller settings¶
controller:
mode: poll
poll_interval: 10s
webhook_listen: :9090
max_concurrent_vms: 2
vm_idle_timeout: 5m
gc_interval: 60s
vm_name_prefix: gh
Set max_concurrent_vms to the current host limit. Today that is two VM slots, and both RUNNING and PAUSED VMs consume a slot.
Runner settings¶
runner:
ssh_user: admin
ssh_password: admin
install_path: /Users/admin/actions-runner
connect_timeout: 20s
The image must contain the runner binaries at install_path.
Labels map jobs to VM specs¶
labels:
jeballto-macos:
image: ghcr.io/your-org/macos-ci:latest
jeballto-xcode26:
image: ghcr.io/your-org/macos-ci:xcode-26
cpu: 6
memory: 12GB
disk: 256GB
lifetime_seconds: 7200
Jobs only provision if their runs-on label matches one of these entries.
lifetime_seconds is optional. 0 or omitted means no VM lifetime limit. Positive values are passed to Jeballto as lifetimeSeconds and must be between 1 and 604800 seconds.
Use lifetime as a CI/CD safety guard. Set it slightly higher than the GitHub job timeout because the VM still needs time to boot, register the runner, and start the job after creation. Image pull happens before VM creation, so it does not need to be included in this buffer. For example, if jobs can run for 60 minutes, use a VM lifetime such as 3900 or 4200 seconds.
CPU, memory, disk, and lifetime are selected by the matched label. Omitted CPU, memory, or disk values keep the image defaults. Workflow env: variables do not change VM sizing. To provide small, medium, and large machines, define separate labels and use the desired label in runs-on.
When a label sets custom CPU, memory, or disk together with an image, the controller creates the VM from the image first and then applies resource overrides with PATCH /v1/vms/{id} before start. The Jeballto API does not accept image and resources together on create.
Timeouts and retry¶
timeouts:
prepare: 150m
image_pull: 120m
image_pull_lock: 130m
state_wait: 10m
ssh_wait: 5m
stop: 2m
delete: 2m
runner_verify: 90s
toolchain_probe: 90s
retry:
max_attempts: 6
initial_backoff: 1s
max_backoff: 20s
Environment variable overrides¶
| Variable | Config path |
|---|---|
GITHUB_APP_ID |
github.app_id |
GITHUB_APP_PRIVATE_KEY_PATH |
github.app_private_key_path |
GITHUB_INSTALLATION_ID |
github.installation_id |
GITHUB_TOKEN |
github.token |
GITHUB_WEBHOOK_SECRET |
github.webhook_secret |
GITHUB_OWNER |
github.owner |
GITHUB_REPOSITORY |
github.repository |
JEBALLTO_BASE_URL |
jeballto.base_url |
JEBALLTO_TOKEN |
jeballto.token |
JEBALLTO_TOKEN_FILE |
jeballto.token_file |
Mode-specific rules¶
pollrequiresgithub.repositorywebhookrequiresgithub.webhook_secretbothrequires both repository polling support and a webhook secret
The controller rejects invalid combinations during config loading.