API keys
Connect a tool to Nova without going through a browser sign-in.
API keys are the alternative to signing into Nova through your browser. Mint one in settings, paste it into your tool's config, and it stays connected.
When to use one
Use OAuth (the default) for the everyday case: a person, a browser, one tool at a time. You sign in once and the tool stays connected until you revoke it.
Pick an API key when you want any of these:
- An unattended pipeline that runs while you're not at the computer.
- Multiple parallel tools or agents using the same Nova account at the same time.
- A shared bot account that several scripts speak through.
OAuth's sign-in needs a person at a browser, and parallel tools sharing one OAuth sign-in fight each other every time their connection refreshes. API keys don't have either problem.
Mint a key
Use it with Claude Code
The setup depends on whether you have the Nova plugin installed.
With the plugin
The plugin reads NOVA_API_KEY from your environment. Set it to your key value and the plugin authenticates with it automatically — no extra commands, no second server entry:
export NOVA_API_KEY="sk-nova-v1-YOUR_KEY_HERE"Replace sk-nova-v1-YOUR_KEY_HERE with your actual key value. Put the export line in your shell profile (~/.zshrc, ~/.bashrc) so it's set every time Claude Code starts.
Leave NOVA_API_KEY unset to use browser sign-in instead — the plugin falls back to the OAuth flow on its own.
Stuck on Needs authentication even with a key set? If an earlier sign-in failed, Claude Code remembers that failed state and keeps skipping the connection — even once the key is valid. Clear it by deleting ~/.claude/mcp-needs-auth-cache.json, then restart Claude Code. (The /mcp → Clear authentication option doesn't clear this one.)
Without the plugin
Add the server directly. Drop a config block in your project's .mcp.json or a user-scope file at ~/.claude.json, with the full key value in the Authorization header:
{
"mcpServers": {
"nova": {
"type": "http",
"url": "https://mcp.commcare.app/mcp",
"headers": {
"Authorization": "Bearer sk-nova-v1-YOUR_KEY_HERE"
}
}
}
}Replace sk-nova-v1-YOUR_KEY_HERE with your actual key value.
To keep the key out of a committed file, set it in your environment and reference it as "Bearer ${NOVA_API_KEY}" — Claude Code fills it in at startup. The variable has to be set: if it's missing, Claude Code won't start the nova server and tells you which variable is unset (a hand-added entry like this has no OAuth fallback to catch you). Want browser sign-in instead? Omit the Authorization header entirely and Claude Code runs the OAuth flow.
Scopes
Each key can have any combination of these:
| Scope | What it grants |
|---|---|
nova.read | List, read, and search apps in your account. Required. |
nova.write | Create and edit apps. Required. |
nova.hq.read | Look up which CommCare HQ project spaces your stored API key can reach. |
nova.hq.write | Upload finished apps to CommCare HQ. |
Set scopes when you mint, change them later from the kebab menu → Edit scopes. Read and write are the floor; nothing in Nova works without them.
Rotating and revoking
Every key in the list shows when it was last used and when it expires. To rotate, mint a new key, point your tool at the new value, then revoke the old one — there's no in-place rotation, because Nova only keeps the hash.
To revoke, click the kebab on the row → Revoke → confirm. The next call from that key fails immediately.
API keys and OAuth sign-ins are independent. Minting a key doesn't disturb any browser sign-ins on the same account, and revoking either kind doesn't touch the other.