Skip to main content

Builder CLI reference

Builder CLI manages App Service Builder resources and deployment history with explicit Azure coordinates. Use builder --version and each command's --help to check the options in your installed release. Use the installation guide to install the latest CLI release.

At a glance​

  • Public executable: builder; Node.js requirement: 22 or later.
  • Azure and GitHub account selections are cached independently.
  • One portable npm archive includes the repository analyzer and all of its published dependencies.
  • A compatible .NET runtime is needed only for local builder manifest commands. Install it separately and keep dotnet on PATH. The generated analyzer runtime configuration currently requires Microsoft.NETCore.App 10.0.0 or a compatible runtime. A .NET SDK is not required.
  • init is setup, not deployment or local-source upload.
  • Install the same azure-builder-cli-<version>.tgz on every supported OS/CPU. npm installs the local archive and JavaScript dependencies. The installation guide explains the optional local-validation runtime prerequisite.

You can install Builder and run builder login, builder init, and builder app deploy without .NET.

Command groups​

CommandArguments / important flags
builder loginOptional --tenant <id>
builder logoutForget selected local Builder account
builder account showOptional --json
builder source login githubOptional --account <login>; uses GitHub CLI
builder init [name]Interactive setup from an app's Git worktree; optional explicit Azure and repository selectors
builder manifest validate [path]Validate an existing manifest; optional --build, --json; path defaults to the current directory
builder doctorOptional app/subscription/resource group coordinates; connected repository inferred; paired --repository and --repository-id overrides; --json
builder config getInspect effective configuration
builder config update--endpoint-resource-manager <url>
builder config reset--endpoint-resource-manager

builder login uses browser sign-in without requiring a tenant ID. Use --tenant only when you explicitly need to select a specific Azure/Entra directory. It is an optional account selector, not a prerequisite for the standard sign-in flow.

The CLI defaults to Azure public-cloud ARM. Endpoint overrides must be trusted HTTPS management.azure.com origins or subdomains, without custom port or path. They change request routing, not the ARM token audience. Do not derive available preview endpoints or regions from this configuration.

For app-specific doctor checks, provide --app, --subscription, and --resource-group. The CLI reads the repository name and numeric ID from the app's connected GitHub source, including when the current directory is not a Git worktree. To diagnose an explicit repository, provide both --repository and --repository-id; a mismatch with the app's connection is reported rather than silently replaced. Without app coordinates, doctor runs local configuration and sign-in checks only.

Agent integration​

Agent skills are versioned and distributed separately from Builder CLI. Use the public App Service Builder repository for current plugin installation instructions. The plugin invokes the commands documented here; CLI help and JSON output remain authoritative.

App operations​

App operations require --subscription <id> (-s), except operation status, which can infer it from the operation URL. Except subscription-wide list and operation status, app operations also require --name <name> and --resource-group <name> (-g). Commands that expose --tenant use it to check the selected account context; use builder <command> --help for each command's options.

CommandAdditional arguments / flags
builder app listSubscription only; --json
builder app show --name <name>--json
builder app create --name <name>Required --location <region> (-l); creates without source
builder app source connect github --name <name>Required --repository; --repository-id required in 0.0.2 and optional in builds with automatic lookup; optional --branch (default main), --root-directory, --tenant, --json
builder app update --name <name>Required --auto-deploy-enabled true or --auto-deploy-enabled false; --json
builder app deploy --name <name>One selector: --rebuild, --commit <sha>, --version <id>, --previous, --source <directory>, or --source-archive <path> --manifest <path>; --request-id, --no-wait, --json
builder app status <operation-url>Subscription inferred from the URL; optional --subscription, tenant, --wait, --json
builder app scale update --name <name>Required --component; either --min/--max or --disable; --cpu-percent, --memory-percent, --http / --no-http; --json
builder app scale show --name <name>Required --component; reads the saved policy; --json
builder app delete --name <name>Confirmation; --yes (-y) skips it; --no-wait, --json
builder app deploymentlog <deployment-id> --name <name>Deployment ID remains positional; --json

See scaling for runtime prerequisites and request-interruption risks.

The published CLI 0.0.2 requires --repository-id for builder app source connect github. In builds with automatic repository lookup, the command resolves the ID from --repository using the selected GitHub account. It does not require a local Git worktree. Supplying --repository-id explicitly works with either form; repository access and existing-connection checks still apply.

Every deploy command uses an app name, subscription, and resource group even when run from a previously initialized worktree. There is no saved local app binding. Deployment waits by default. With --no-wait, track the returned operation with app status. For a status URL without a subscription segment, pass --subscription; an explicit value must match the URL when both are present. The operation URL must use the configured ARM origin.

While waiting, the CLI retries temporary HTTP 429 responses from ARM status reads using Retry-After, within the operation timeout. It does not resubmit the deployment or deletion request. If a wait still stops, check the existing operation and app state before repeating a write; see status-polling recovery.

Deployment JSON​

When a waited builder app deploy --json result includes an observed ARM operation, the top-level status, operation.status, and deployment.status report the same operation status. The nested deployment receipt preserves its accepted deployment ID, operation URL, and retry interval. If the first status read fails, the receipt keeps the acceptance status and reports terminal: false. --no-wait --json returns the initial acceptance result, not a completed deployment.

ZIP source input​

Use builder app deploy to upload source from a local directory or an existing ZIP. Follow Deploy ZIP source with Builder CLI for a complete PowerShell walkthrough without a GitHub connection. For raw ARM requests, see the ZIP API walkthrough.

This path uses the CLI's existing Azure Resource Manager access token. It does not introduce another sign-in or consent flow, and dedicated Builder-audience tokens are not accepted for uploads.

The command provides two mutually exclusive source inputs: --source <directory> with optional --root-directory <path>, and --source-archive <path> --manifest <path>. Direct archive input uploads an existing ZIP unchanged; it does not create a temporary archive or delete the caller's files. Directory packaging creates a temporary ZIP32 archive and supports up to 65,535 files, each smaller than 4 GiB; larger inputs require an externally created ZIP64 archive. Packaging streams file contents and enforces the compressed limit while writing, without loading the whole source tree into memory. On POSIX systems, ordinary file permissions, including executable bits, are preserved; privileged permission bits are stripped. Windows packaging uses regular non-executable file permissions. Use a POSIX-created archive when executable bits matter.

The compressed upload limit is 100 MiB. The separately supplied planning manifest is bounded to 1 MiB of UTF-8 and must match root builder.yaml in the ZIP byte for byte, including line endings and a BOM. Ordinary unencrypted stored/deflated ZIPs use standard extractor support, including ZIP64 and ordinary archive metadata. Upload acceptance verifies length and digest; an invalid ZIP or mismatched root manifest fails later during deployment checkout. Token acquisition and the streaming upload are bounded by the session's absolute upload deadline. If a claimed upload loses its response, the CLI polls its state rather than sending another PUT. An explicit --request-id is used unchanged for upload-session and deployment idempotency. Otherwise, GitHub Actions derives a stable ID from the app, run/attempt, and archive digest; other runs use a generated UUID. JSON requestId reports the ID actually sent to the APIs. See feature availability before choosing a deployment path.

History and build logs​

These commands require subscription and resource group and support --json.

CommandArguments / flags
builder app version list --name <name>Optional --page, --page-size (1–100)
builder app version show --name <name> <version-id>Read a built version and its resolved components; version ID remains positional
builder app version build-log --name <name> <version-id>Optional --component <name> (-c)
builder app deployment list --name <name>Reads all continuation pages
builder app deployment show --name <name> <deployment-id>Read a deployment; deployment ID remains positional

Use build logs for build failure and deployment logs for activation failure. The CLI connects to the appropriate history and logging service automatically.

For ZIP deployments, version JSON identifies uploaded source with both source.kind and source.provider set to uploadedArtifact. Its source.revision is the archive SHA-256, not a Git commit. GitHub versions retain github for both fields.

Desired version configuration​

These commands require --name, --subscription, and --resource-group and support --json.

CommandArguments / behavior
builder app version-config show --name <name>Read desired configuration
builder app version-config variables list --name <name>List saved variable names, not values
builder app version-config variables update --name <name>Use --variable-name <name> with --variable-value <value>, or --settings @file with a JSON object; merge into existing variables
builder app version-config variables delete --name <name>Required --variable-name <name>; remove that variable
builder app version-config components list --name <name>Read saved per-component version configuration, not built-version components

An empty [] from version-config components list --json means the app has no saved per-component configuration entries. It does not mean that the app's built versions have no components. Use builder app version show --name <name> <version-id> --json with the same subscription and resource group to inspect resolved components.

Variable writes change desired configuration without creating a version or deployment. Request a new build to capture those values. See application variables for safe input and deployment steps.

Local manifest validation​

From the repository containing your existing manifest, run:

builder manifest validate

builder manifest validate [path] checks an existing builder.yaml using the manifest parser, topology rules, and build planner. The path is a repository directory and defaults to the current directory. By default, validation is read-only and does not execute repository code. It does not generate, repair, or overwrite a manifest.

Use --json for machine-readable output. Analyzer input failures use an error object and a nonzero exit code, for example:

{"error":{"code":"BuilderAnalyzerFailed","message":"..."},"exitCode":2}

Optional --build runs the resolved build through Docker/Oryx and requires Docker. Use it only for trusted source: Docker is not a security boundary for hostile repository code. Neither validation mode deploys the app or confirms that it will serve successfully in your preview environment.

Non-interactive setup​

Run this command from inside your app's initialized Git worktree. Explicit flags select the setup values; they do not remove the checkout requirement. Supply every value and pre-establish both management and source accounts:

builder init "<app-name>" \
--subscription "<subscription-id>" --resource-group "<resource-group>" \
--location "<qualified-location>" \
--repository "<owner>/<repository>" --repository-id "<numeric-repository-id>" \
--branch "<branch>" --yes

--yes cannot approve values autodetected from Git. It does not bypass missing credentials or source permissions and does not open a browser in non-interactive setup. This contract does not establish a service-principal or unattended CI login workflow. Setup does not require a manifest, a clean worktree, or a local commit matching the pushed branch. init does not automatically analyze or modify builder.yaml; validate it separately and commit and push changes before deployment.

Surface differences​

Use Portal or ARM for deployed-app authentication; the CLI does not configure it. Identity is configured in the Portal Identity page or through ARM; the CLI does not configure identity settings. Variable editing is available through app version-config variables. Download the published .tgz using the installation guide. Install that archive directly rather than guessing an npm-registry package release or extracting it. Agent skills are distributed separately. Development-only commands are outside this customer reference, and package metadata alone does not establish public availability.

The CLI quickstart completes a first deployment and cleanup journey. Language tutorials include a Builder CLI tab with the same client procedures and runtime-specific verification. Deployments explains selector semantics; scaling explains valid policy values.