CLI
EmbedHub has a CLI for managing files and todos in your projects from your laptop or CI environment (GitHub Actions, GitLab Runners, etc.).
Installation
Download a prebuilt binary
| Platform | Architecture | Download |
|---|---|---|
| macOS (Apple Silicon) | arm64 | embedhub-darwin-arm64 |
| macOS (Intel) | amd64 | embedhub-darwin-amd64 |
| Linux | amd64 | embedhub-linux-amd64 |
| Linux | arm64 | embedhub-linux-arm64 |
| Windows | amd64 | embedhub-windows-amd64.exe |
After downloading, chmod +x it (macOS/Linux) and move it onto your
PATH:
chmod +x embedhub-darwin-arm64
sudo mv embedhub-darwin-arm64 /usr/local/bin/embedhub
embedhub --version
Configure your API key
Before using the CLI you need to give it an API key. The key tells EmbedHub which user the CLI is acting as and which projects it has access to.
1. Create a key in the web UI
- Log in to embedhub.com and click your name in the top right → Settings.
- Open the API Keys tab.
- Click Create API Key, name it (e.g. "laptop", "ci"), and tick which organizations the key should have access to.
- Copy the full key — it's shown only once. Treat it like a password.
API keys look like ehk_<16-char-prefix>_<40-char-secret>.
2. Tell the CLI about it
embedhub config set api-key ehk_1234567890123456_abcdef1234567890abcdef1234567890abcdef12
This writes the key to ~/.embedhub/config.yaml (file mode 0600). Confirm
it stuck:
embedhub config list
The key will be shown masked.
Alternative: environment variables
If you'd rather not write the key to disk (CI runners, ephemeral containers), set it in the environment instead:
| Variable | Purpose |
|---|---|
EMBEDHUB_API_KEY | API key — overrides the config file. |
EMBEDHUB_VERBOSE | Set to true for verbose output. |
For GitHub Actions, see the GitHub Action integration — it
takes the key as a secret and runs embedhub push for you.
Rotating or revoking
To rotate: create a new key in the web UI, run embedhub config set api-key <new>, then revoke the old one from the API Keys tab.
To revoke a key without replacing it: open the API Keys tab and click Revoke on the row you want to disable. The key stops working immediately.
Command reference
embedhub [command]
Available Commands:
config Manage configuration settings
push Upload a file or folder to a project
pull Download a file from a project
list List files in a project
search Search files by extension or substring
todos Manage project todos
help Help about any command
All commands take the project as org/project-name.
embedhub push
Upload files (with glob support) to a project. The last argument is always the project; any number of files, folders, or glob patterns may precede it.
embedhub push app.bin myorg/myproject --path releases/v1.0.0/
embedhub push *.zip myorg/myproject --path releases/latest/
embedhub push app.bin app.map app.elf myorg/myproject --path releases/v1.0.0/
embedhub push build/ docs/ myorg/myproject
Supported file types
EmbedHub auto-routes uploads into the right section based on the file extension:
| Category | Extensions | Destination | Purpose |
|---|---|---|---|
| Photos | .jpg, .jpeg, .png, .svg, .webp, .gif | photos | Visual assets |
| Documents | .pdf | documents | Specs, guides |
| Releases | .bin, .map, .elf | releases | Firmware, binaries |
.zip files containing PDFs are auto-processed. The folder you pass via
--path is preserved.
embedhub list
embedhub list myorg/myproject
embedhub list myorg/myproject --prefix releases/
embedhub list myorg/myproject --json
embedhub search
embedhub search myorg/myproject .bin # match by extension
embedhub search myorg/myproject firmware # substring match in path
embedhub search myorg/myproject .pdf --prefix documents/
embedhub pull
embedhub pull myorg/myproject releases/app.bin
embedhub pull myorg/myproject releases/app.bin --output ./local-app.bin
embedhub todos
Manage project todos. Each todo is a small markdown file in the project — see the Todos page for the file format.
embedhub todos list myorg/myproject [--status done|wip|cancel] [--json]
embedhub todos add myorg/myproject --title "..." [--notes "..."] [--assignee <user>]
embedhub todos show myorg/myproject <id-or-prefix> [--json]
embedhub todos status myorg/myproject <id-or-prefix> <new> # in_progress | complete | cancelled
embedhub todos assign myorg/myproject <id-or-prefix> <user> # or --unassign
embedhub todos rm myorg/myproject <id-or-prefix> [--yes]
embedhub todos members myorg/myproject [--json]
<id-or-prefix> accepts a full UUID or any unique prefix (8 chars is usually
enough — same as the IDs shown by embedhub todos list). Status accepts the
short aliases done, wip, and cancel.
Examples
# Daily flow
embedhub todos list anuj/firmware
embedhub todos add anuj/firmware --title "review LED driver PR" --assignee tanvi
embedhub todos status anuj/firmware 9f3e2c1d done
# CI pipeline — file a follow-up todo when a build fails
if ! make test; then
embedhub todos add anuj/firmware \
--title "Fix failing test on $(git rev-parse --short HEAD)" \
--notes "$(make test 2>&1 | tail -3)"
fi
# Agent flow — pick up the next in-progress todo and complete it
ID=$(embedhub todos list anuj/firmware --status wip --json | jq -r '.[0].id')
embedhub todos status anuj/firmware "$ID" done
CI/CD example
#!/bin/bash
go build -o app .
embedhub push app john/my-app --path "releases/$(git describe --tags)/"
embedhub push app john/my-app --path "releases/latest/"
echo "✓ Deployed to EmbedHub"
Security
- API keys are stored in
~/.embedhub/config.yamland masked when displayed. - All communication uses HTTPS.
- API keys only work with your personal organization's projects.
Troubleshooting
"API key not configured" — run embedhub config set api-key YOUR_KEY.
"Access denied" — ensure the key is valid and the project belongs to your personal organization.
"Not found" on todos commands — confirm your role on the project grants
read/write/delete on /todos/* (org owners always have full access).