@datadog/apps-cli
Interactive CLI for authenticating, building, and deploying Datadog Apps.
Usage
npx @datadog/apps-cli
With no arguments, in an interactive terminal, this opens a menu of the available commands. In non-interactive contexts (CI, scripts, AI agents) it instead prints a plain command listing and exits.
Commands can also be run directly, bypassing the menu:
npx @datadog/apps-cli auth login
npx @datadog/apps-cli upload --site datadoghq.com
Run npx @datadog/apps-cli --help, or npx @datadog/apps-cli <command> --help,
for full usage and options.
Inside a project that has this CLI as a dev dependency (the setup that
@datadog/create-apps creates), npx @datadog/apps-cli <command> uses the
project's own copy. After a global install (npm install -g @datadog/apps-cli), the binary is on your PATH as datadog-apps; the
CLI's own output shows commands in that form.
Commands
auth login— Log in to Datadog via OAuthauth status— Show Datadog authentication statusauth logout— Log out of Datadog, revoking and clearing stored OAuth tokensauth default— Set the default org to use for a Datadog sitebuild— Build your Datadog App locallyupload— Build, upload, and publish your Datadog App bundle livedev— Start the project dev server with Datadog credentials resolved for it
Authentication
auth login opens a browser to authorize this CLI against a Datadog org via
OAuth. It supports being logged in to multiple orgs at once — run it again to
log in to a second org on the same (or a different) site. Each org is
identified by its UUID.
The Datadog site to authenticate against is resolved in this order:
- An explicit
--siteflag (e.g.--site datadoghq.eu, or a full URL/custom subdomain likemyorg.datadoghq.com) - The
DD_SITEorDATADOG_SITEenvironment variable (DATADOG_-prefixed wins if both are set to different values) - The
datadogSitefield in the working directory'sdatadog-app.config.json(the app configuration) - In interactive sessions, from the site prompt.
This means that inside a Datadog App project directory that has a
datadog-app.config.json, datadog-apps auth login works with no flags at
all. If your project predates datadog-app.config.json, ask your coding agent
to upgrade it following the instructions in docs/agents/upgrading.md.
A command that needs an OAuth login starts the browser login flow on the spot when no login is saved for its site, or the saved one expired and cannot be refreshed — but only in an interactive terminal. Non-interactive contexts (CI, scripts, AI agents) exit with an error instead; use API and application keys there.
API and application keys
The deployment command (upload) and dev also accept DD_API_KEY and
DD_APP_KEY — or DATADOG_API_KEY and DATADOG_APP_KEY.
When both keys are set, the CLI sends them with every request and skips OAuth
entirely: no stored login selects the request's org — the keys decide which
org each request reaches. This makes the commands work in CI and other
non-interactive contexts, where a browser login is not possible.
When only one of the two keys is set, both are ignored. The CLI then uses OAuth, as described above.
The site is resolved the same way for both methods: --site, then
DATADOG_SITE, then DD_SITE, then the datadogSite field in the working
directory's datadog-app.config.json — or, when --org names a logged-in
org, the site stored for that org.
With API and application keys, there is no stored session. Thus, for an org
outside US1 that has a custom subdomain on datadoghq.com, give the
datacenter site (for example --site us3.datadoghq.com), not the custom
subdomain host.
Dev server
dev starts the project's dev server (npx vite, with --mode when given,
or --mode dev-verify for --verify) with credentials resolved for it: the
DD_API_KEY/DD_APP_KEY pair when both are set, or the selected org's OAuth
access token as DD_OAUTH_ACCESS_TOKEN otherwise. The dev server reads that
token to call the Datadog API on your behalf — you do not need to configure
credentials in the dev server itself.
A dev session runs for hours, so dev refreshes the OAuth access token before
starting when it has less than 22 hours of validity left, and stores the new
one. The token therefore starts with at least 22 hours of validity — enough
for a working day, though a dev server left open for days may outlive it and
need a restart.
To check who you're logged in as, run auth status — it prints everything
stored for every site/org, including each org's UUID. To sign out, run
auth logout — with a single login stored it logs out immediately; with more
than one, it prompts you to pick which ones. To skip the prompt, pass
--org <uuid> to log out of exactly that org, --site to log out of every org
on one site, or --all to clear every stored login.
Logging out revokes the OAuth session at Datadog, not just locally, so the
tokens stop working even if a copy of them leaked. If Datadog can't be reached
— you're offline, or the request times out — auth logout still clears the
credentials on this machine, but warns that the session may still be active. To
revoke the session afterwards, you can revoke this CLI's authorization directly
in Datadog under Personal Settings > Apps.
If more than one org is logged in on a site, commands that need a single
token pick the one set as default for that site (auth default), or the
sole org if only one is logged in. Run auth default — or auth default --site <site> — to pick which org that is; if more than one is logged in on
that site, it prompts you to choose. To set it without a prompt, pass the
org's UUID: auth default --org <uuid>.
Where credentials are stored
Logins are written in credentials.json under this directory, whichever of these resolves first:
$DD_APPS_CONFIG_DIR or $DATADOG_APPS_CONFIG_DIR # if set
$XDG_CONFIG_HOME/datadog-apps # if set to an absolute path;
# a relative value is ignored
~/.config/datadog-apps
Treat credentials.json as a secret — anything that can read it can use
these tokens — and use auth logout to clear them rather than deleting files
by hand.
Build
build and upload run vite build with the resolved site as both DD_SITE
and DATADOG_SITE, replacing any inherited value, so upload --site builds
against the site it uploads to. build reads the site from DATADOG_SITE,
then DD_SITE, then datadog-app.config.json. Like upload, it stops on an
invalid site, or on a malformed datadog-app.config.json when it reads that
file. Unlike upload, it builds with the inherited environment when no source
names a site.
License
Apache-2.0