Skip to content

fix: prevent azd down from deleting pre-existing resource groups#7603

Open
jongio wants to merge 17 commits intomainfrom
fix/azd-down-rg-safety
Open

fix: prevent azd down from deleting pre-existing resource groups#7603
jongio wants to merge 17 commits intomainfrom
fix/azd-down-rg-safety

Conversation

@jongio
Copy link
Copy Markdown
Member

@jongio jongio commented Apr 9, 2026

Summary

Fixes #4785
Fixes #2916

azd down currently deletes ALL resource groups referenced in a deployment, including pre-existing ones referenced via Bicep's existing keyword. This causes data loss when users reference shared resource groups (e.g., for Cosmos DB role assignments, shared databases, storage accounts).

Root Cause

resourceGroupsFromDeployment() extracts every RG from ARM's outputResources, and DeleteSubscriptionDeployment() deletes them all unconditionally. The Bicep existing keyword is a compile-time construct — invisible to ARM at teardown time.

Solution

Introduces a 4-tier resource group classification pipeline that runs before deletion to distinguish owned vs. external RGs:

Tier Signal API Cost Confidence
1. Deployment Operations Create op = owned; Read/EvaluateDeploymentOutput = external 0 extra calls Highest
2. Tag Verification Both azd-env-name + azd-provision-param-hash tags match → owned 1 call/RG High
3. Interactive Prompt Per-RG prompt for unknown RGs (default: deny). Skipped in --force/CI 0 calls User decision
4. Safety Vetoes Management locks → hard veto; foreign resources → soft veto (promptable) 2 calls/RG Safety net

Only RGs classified as "owned" are deleted. External/unknown RGs are skipped with clear messaging.

Behavior by mode

  • Interactive (no --force): Full 4-tier classification runs. Unknown RGs prompt the user.
  • --force / CI: Classification is bypassed entirely (preserving existing --force semantics). A future enhancement could run the free Tier 1 check even with --force.

Changes

New files

  • cli/azd/pkg/azapi/resource_group_classifier.go — 4-tier classification pipeline (~420 lines)
  • cli/azd/pkg/azapi/resource_group_classifier_test.go — 36 unit tests covering all tiers, edge cases, error-as-veto, ctx cancellation
  • cli/azd/pkg/infra/provisioning/bicep/bicep_destroy.go — Classify-then-delete orchestrator
  • docs/azd-down-resource-group-safety/architecture.md — Design document

Modified files

  • cli/azd/pkg/azapi/deployments.goVoidSubscriptionDeploymentState interface method
  • cli/azd/pkg/azapi/standard_deployments.go — Public VoidSubscriptionDeploymentState, ResourceGroupsFromDeployment
  • cli/azd/pkg/azapi/stack_deployments.go — VoidState no-op stub
  • cli/azd/pkg/infra/provisioning/bicep/bicep_provider.go — Restructured Destroy() flow
  • cli/azd/pkg/infra/provisioning/bicep/bicep_provider_test.go — 5 integration tests
  • cli/azd/pkg/infra/scope.goVoidState on Deployment interface
  • cli/azd/pkg/infra/scope_test.go — VoidState tests
  • cli/azd/pkg/azapi/standard_deployments_test.go — Updated tests

Testing

  • 36 unit tests for the classifier (all tiers, error paths, parallelism, cancellation)
  • 5 integration tests for the destroy orchestrator
  • Live Azure E2E: Confirmed bug on stable azd 1.23.14 (both RGs deleted), verified fix correctly skips external RG
  • All existing tests pass, zero lint issues, full preflight clean

Copilot AI review requested due to automatic review settings April 9, 2026 12:27
@github-actions
Copy link
Copy Markdown

github-actions bot commented Apr 9, 2026

📋 Prioritization Note

Thanks for the contribution! The linked issue isn't in the current milestone yet.
Review may take a bit longer — reach out to @rajeshkamal5050 or @kristenwomack if you'd like to discuss prioritization.

Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR updates the azd down destroy flow (standard deployments) to avoid deleting pre-existing resource groups that were only referenced by an ARM/Bicep deployment (e.g., via Bicep existing) by introducing a resource-group ownership classification step before deletion.

Changes:

  • Adds a multi-tier resource group ownership classifier (Tier 1 deployment ops + Tier 2 tag fallback + Tier 3 prompts + Tier 4 veto hooks) and integrates it into Bicep destroy orchestration.
  • Refactors subscription deployment teardown so “delete deployment” becomes “void deployment state”, and introduces an explicit VoidState operation on the deployment abstraction.
  • Adds tests for the classifier and for the new destroy orchestration behavior, plus an architecture design doc.

Reviewed changes

Copilot reviewed 12 out of 13 changed files in this pull request and generated 7 comments.

Show a summary per file
File Description
docs/azd-down-resource-group-safety/architecture.md Design doc describing the multi-tier RG classification approach and intended behaviors.
cli/azd/pkg/infra/scope.go Adds VoidState to the Deployment interface and implements it for subscription/RG deployments.
cli/azd/pkg/infra/scope_test.go Adds tests covering the new VoidState behavior on deployments.
cli/azd/pkg/infra/provisioning/bicep/bicep_provider.go Refactors Destroy() to classify RGs, delete only selected RGs, then void state and scope purge targets.
cli/azd/pkg/infra/provisioning/bicep/bicep_provider_test.go Updates existing destroy tests and adds coverage for the classify+delete orchestration.
cli/azd/pkg/infra/provisioning/bicep/bicep_destroy.go New destroy helper implementing classify-then-delete, tag lookup, and void-state orchestration.
cli/azd/pkg/azapi/standard_deployments.go Exposes ResourceGroupsFromDeployment and adds VoidSubscriptionDeploymentState; subscription “delete” now voids state.
cli/azd/pkg/azapi/standard_deployments_test.go Updates sorting to slices.Sort and adds compilation/behavior checks for new public methods.
cli/azd/pkg/azapi/stack_deployments.go Implements VoidSubscriptionDeploymentState as a no-op for stacks.
cli/azd/pkg/azapi/resource_group_classifier.go New classifier implementation for owned vs skipped RGs with tiered signals and veto hooks.
cli/azd/pkg/azapi/resource_group_classifier_test.go New unit test suite for classifier tiers, error handling, and prompting behavior.
cli/azd/pkg/azapi/deployments.go Extends DeploymentService interface with VoidSubscriptionDeploymentState.
.gitignore Ignores cli/azd/coverage-* artifacts.

@jongio jongio force-pushed the fix/azd-down-rg-safety branch from 92c3856 to 9de3860 Compare April 9, 2026 12:36
@jongio jongio marked this pull request as draft April 9, 2026 12:57
@jongio jongio force-pushed the fix/azd-down-rg-safety branch from bd92475 to e56b87a Compare April 9, 2026 18:10
@jongio jongio marked this pull request as ready for review April 9, 2026 18:10
@vhvb1989
Copy link
Copy Markdown
Member

vhvb1989 commented Apr 9, 2026

Consider an alternative approach to swich azd down to delete by resource instead of by rg.
Make azd pull all resources and generate a parallel deletion order - allowing folks to secelt/unselect things to keep if they want.

Copy link
Copy Markdown
Contributor

@wbreza wbreza left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review — PR #7603

fix: prevent azd down from deleting pre-existing resource groups by @jongio

Summary

Impressive 4-tier classification pipeline with solid engineering and thorough design documentation. The classifier's fail-safe behavior (errors → vetoes, not deletions) is the right default. Unit test suite is excellent (55 subtests covering all tiers). Six supplementary findings focused on safety edge cases and testing gaps — all prior copilot-bot feedback resolved.

Prior Review Status

# Prior Finding Author Status
1-7 All copilot-bot findings @copilot-pull-request-reviewer ✅ Resolved

New Findings

Priority Count
High 2
Medium 3
Low 1
Total 6

🔴 High (2 findings)

  1. Tier 1 operations failure → silent fallthrough → potential unsafe deletion — If deployment.Operations() fails, all RGs become Tier 1 unknown and fall to Tier 2 (tag check). An external RG with matching azd tags from a previous deployment to the same environment would be classified as "owned" and deleted. The code logs a WARNING but proceeds. For a safety-critical feature, consider: when Tier 1 is unavailable without --force, downgrade ALL RGs to Tier 3 (prompt each) rather than trusting Tier 2 alone.
  2. Missing integration tests for Tier 4 safety vetoes — 55 unit tests prove the classifier works; but bicep_provider_test.go doesn't test the end-to-end classify → veto → skip flow. For a data-loss prevention feature: add tests for "lock veto prevents deletion", "user declines → state preserved", and "mixed owned/external → only owned deleted".

🟡 Medium (3 findings)

  1. --force bypasses Tier 1 (zero-cost) classification--force skips ALL tiers, including Tier 1 (deployment operations) which has zero extra API cost. The PR acknowledges this as a future enhancement. Running Tier 1 even with --force would catch the most obvious cases (Read vs Create) at no cost.
  2. Backward compatibility: old deployments trigger Tier 3 prompts — Deployments from older azd versions lack azd-provision-param-hash tags. After upgrading, azd down classifies all RGs as "unknown" → Tier 3 prompts for every RG. In CI without --force, this may fail. Consider: detect old tag schema (env-name only) and fall back to env-name-only Tier 2 match with a logged warning.
  3. Hash comparison is case-sensitive while tag key lookup is case-insensitivetagValue() uses strings.EqualFold for key lookup but hash value comparison uses !=. Low practical risk (azd generates consistent formats), but the inconsistency could cause subtle failures with manually set tags.

🟢 Low (1 finding)

  1. Log Analytics force-delete may execute twice per RGforceDeleteLogAnalyticsIfPurge() appears to run both globally and per-RG inside deleteRGList. Second call fails silently. Code smell indicating unclear cleanup separation.

✅ What Looks Good

  • 4-tier classification pipeline — clear escalation with well-documented decision rationale
  • Fail-safe by default — API errors (500/429/403) cause vetoes, not deletions
  • Excellent unit test suite — 55 subtests covering all tiers, error paths, context cancellation, parallelism
  • Clean Destroy() restructure — stacks vs standard vs empty paths clearly separated
  • Safe concurrency — Tier 4 semaphore + wg.Go() + defer release pattern is correct
  • Architecture document — thorough design rationale for each tier and decision
  • Prior feedback fully addressed — every copilot-bot finding resolved with evidence and test references

Overall Assessment: Request Changes — the Tier 1 fallthrough (#1) is a data-loss risk that should be addressed before merge. The integration test gap (#2) should also be closed for a safety-critical feature of this scope. The remaining findings are hardening suggestions.

Review performed with GitHub Copilot CLI

Copy link
Copy Markdown
Contributor

@wbreza wbreza left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review — PR #7603

fix: prevent azd down from deleting pre-existing resource groups by @jongio

Summary

Impressive 4-tier classification pipeline with solid engineering and thorough design documentation. The classifier's fail-safe behavior (errors → vetoes, not deletions) is the right default. Unit test suite is excellent (55 subtests covering all tiers). Six supplementary findings focused on safety edge cases and testing gaps — all prior copilot-bot feedback resolved.

Prior Review Status

# Prior Finding Author Status
1-7 All copilot-bot findings @copilot-pull-request-reviewer ✅ Resolved

New Findings

Priority Count
High 2
Medium 3
Low 1
Total 6

🔴 High (2 findings)

  1. Tier 1 operations failure → silent fallthrough → potential unsafe deletion — If deployment.Operations() fails, all RGs become Tier 1 unknown and fall to Tier 2 (tag check). An external RG with matching azd tags from a previous deployment to the same environment would be classified as "owned" and deleted. The code logs a WARNING but proceeds. For a safety-critical feature, consider: when Tier 1 is unavailable without --force, downgrade ALL RGs to Tier 3 (prompt each) rather than trusting Tier 2 alone.
  2. Missing integration tests for Tier 4 safety vetoes — 55 unit tests prove the classifier works; but bicep_provider_test.go doesn't test the end-to-end classify → veto → skip flow. For a data-loss prevention feature: add tests for "lock veto prevents deletion", "user declines → state preserved", and "mixed owned/external → only owned deleted".

🟡 Medium (3 findings)

  1. --force bypasses Tier 1 (zero-cost) classification--force skips ALL tiers, including Tier 1 (deployment operations) which has zero extra API cost. The PR acknowledges this as a future enhancement. Running Tier 1 even with --force would catch the most obvious cases (Read vs Create) at no cost.
  2. Backward compatibility: old deployments trigger Tier 3 prompts — Deployments from older azd versions lack azd-provision-param-hash tags. After upgrading, azd down classifies all RGs as "unknown" → Tier 3 prompts for every RG. In CI without --force, this may fail. Consider: detect old tag schema (env-name only) and fall back to env-name-only Tier 2 match with a logged warning.
  3. Hash comparison is case-sensitive while tag key lookup is case-insensitivetagValue() uses strings.EqualFold for key lookup but hash value comparison uses !=. Low practical risk (azd generates consistent formats), but the inconsistency could cause subtle failures with manually set tags.

🟢 Low (1 finding)

  1. Log Analytics force-delete may execute twice per RGforceDeleteLogAnalyticsIfPurge() appears to run both globally and per-RG inside deleteRGList. Second call fails silently. Code smell indicating unclear cleanup separation.

✅ What Looks Good

  • 4-tier classification pipeline — clear escalation with well-documented decision rationale
  • Fail-safe by default — API errors (500/429/403) cause vetoes, not deletions
  • Excellent unit test suite — 55 subtests covering all tiers, error paths, context cancellation, parallelism
  • Clean Destroy() restructure — stacks vs standard vs empty paths clearly separated
  • Safe concurrency — Tier 4 semaphore + wg.Go() + defer release pattern is correct
  • Architecture document — thorough design rationale for each tier and decision
  • Prior feedback fully addressed — every copilot-bot finding resolved with evidence and test references

Overall Assessment: Request Changes — the Tier 1 fallthrough (#1) is a data-loss risk that should be addressed before merge. The integration test gap (#2) should also be closed for a safety-critical feature of this scope. The remaining findings are hardening suggestions.

Review performed with GitHub Copilot CLI

@jongio
Copy link
Copy Markdown
Member Author

jongio commented Apr 9, 2026

@wbreza — thanks for the thorough review. Addressed all 6 findings. Here's the breakdown:


✅ Fixed: #3--force bypasses zero-cost Tier 1 (HIGH → FIXED)

You were right — this was the biggest safety gap. The whole point of this PR is preventing accidental RG deletions, yet --force (the most common CI/CD flag) got zero protection.

Fix: --force now runs Tier 1 only (zero extra API calls). External RGs identified by Read/EvaluateDeploymentOutput operations are still protected. Unknown RGs (no matching operation) are treated as owned. Tiers 2/3/4 are skipped entirely (no prompts, no extra API calls). If operations are unavailable, falls back to deleting all RGs (backward compat).

Commit: 3697363e9 — see ClassifyOptions.ForceMode, classifyResourceGroups() restructured.

✅ Fixed: #2 — Missing integration tests for Tier 4 vetoes (HIGH → FIXED)

Valid gap. Added:

  • Tier4LockVetoPreventsDeletion: CanNotDelete lock vetoes deletion even for Tier 1 owned RGs
  • MixedOwnedExternalOnlyOwnedDeleted: end-to-end 3-RG test (Created=deleted, Read=skipped, unknown=skipped in non-interactive)
  • Updated ForceProtectsExternalRGs (renamed from ForceBypassesClassification): verifies operations ARE fetched and external RGs ARE protected with --force
  • Extended classifyMockCfg with per-RG lock and tag mock support

📋 #1 — Tier 1 ops failure → silent fallthrough (HIGH → BY DESIGN)

Architecture doc reference: Risk 1 (line 549-562), Decision 1 (line 224-240)

The multi-tier architecture exists specifically so Tier 2 IS the fallback for Tier 1 failure. If we skip Tier 2 when Tier 1 fails, Tier 2 is pointless.

Worst case: An external RG would need ALL of these simultaneously:

  1. ARM Operations() fails (transient)
  2. External RG has BOTH azd-env-name AND azd-provision-param-hash tags
  3. The azd-env-name matches the current environment name
  4. The azd-provision-param-hash matches the current deployment hash
  5. The RG passes Tier 4 (no locks, no foreign resources)

Even in this essentially-impossible scenario, Tier 4 still runs (locks + foreign resource checks), and interactive mode has the final "Delete N resource group(s)?" confirmation.

📋 #4 — Old deployments trigger Tier 3 prompts (MEDIUM → FAIL-SAFE)

Architecture doc reference: Risk 1 (line 549-562), Risk 4 (line 598-610)

For old deployments without azd-provision-param-hash: Tier 1 operations are still available for 90+ days (ARM retention), so they classify correctly at Tier 1. Only very old deployments with BOTH purged operations AND single tag would hit Tier 3.

Fail-safe direction: The worst case is a legitimate RG NOT being deleted (prompted in interactive, skipped in non-interactive). This errs toward safety, not data loss. Users can use --force (which now runs Tier 1) or re-provision (which adds the new tags).

📋 #5 — Hash comparison case-sensitive vs key lookup case-insensitive (MEDIUM → BY DESIGN)

ARM tag keys are case-insensitive per Azure API → strings.EqualFold is correct.

Tag values are case-preserved and case-sensitive. azd-provision-param-hash contains SHA-256 hex generated by azd (sha256.Sum256() → hex encoding → always lowercase). ARM stores values verbatim. Exact comparison (!=) is correct for hash values.

Even if a mismatch somehow occurred, the worst case is falling to Tier 3 (prompted or skipped) — fail-safe, not data loss.

📋 #6 — Log Analytics force-delete runs twice per RG (LOW → INCORRECT)

forceDeleteLogAnalyticsIfPurge() is called in two mutually exclusive code paths:

  1. Classification path (deleteRGList, line 187): per-RG, only for classification-based destroy
  2. Stacks path (destroyViaDeploymentDelete, line 434): globally, only for deployment-stacks destroy

These paths are selected by options.Deployment.Options.Provider == DeploymentProviderStacks. A single azd down invocation goes through ONE path, never both. No double execution is possible.


Also updated: architecture.md — Decision 4 rewritten, gap section updated, risk mitigations updated, added mermaid classification flow diagram showing all paths including --force.

@jongio
Copy link
Copy Markdown
Member Author

jongio commented Apr 10, 2026

@vhvb1989

Consider an alternative approach to swich azd down to delete by resource instead of by rg.
Make azd pull all resources and generate a parallel deletion order - allowing folks to secelt/unselect things to keep if they want.

Interesting idea — resource-level deletion with a selection UI would give users fine-grained control. For this PR though, RG-level classification is the right fit because:

  1. ARM handles cascading deletion atomically — deleting a RG removes all its resources in the correct dependency order. Resource-level deletion would require us to build and maintain ARM dependency graphs across hundreds of resource types.
  2. The safety problem is RG-scoped — issues Add option to not delete resource group when running azd down command #4785 and [Issue] azd down removes resource groups not created by azd #2916 are about azd deleting RGs it didn't create (referenced via Bicep existing). The 4-tier classifier solves this at the level where the problem exists.
  3. API cost — RG deletion is 1 call per RG. Resource-level would be N calls to enumerate + N calls to delete, with ordering constraints.

That said, resource-level select/unselect could be a great follow-up feature on top of this foundation — the Tier 4 foreign-resource detection already enumerates resources per RG, so extending that to a selection UI would be feasible. Happy to discuss further if you'd like to file a separate issue for it.

@jongio jongio force-pushed the fix/azd-down-rg-safety branch from f55e59a to 8fa6b1f Compare April 10, 2026 02:20
@vhvb1989
Copy link
Copy Markdown
Member

@jongio — Hey Jon, I did a quick investigation and I think there may be a much simpler alternative to the 4-tier classification pipeline for distinguishing created vs. existing resource groups.

Bicep snapshots already solve this. When you run bicep snapshot, the predictedResources output only includes resources that the deployment creates — resources declared with the existing keyword are excluded. So for a subscription-level deployment:

  • RGs in predictedResources with type == "Microsoft.Resources/resourceGroups"created by the deployment (safe to delete)
  • RGs referenced in other resource IDs but absent from predictedResourcesexisting/external (must not delete)

We already have the snapshot logic wired up in core (pkg/infra/provisioning/bicep/local_preflight.go and pkg/tools/bicep/bicep.go), so this would be mostly reusing existing infrastructure.

A few scoping notes:

  1. This only applies to Bicep. For Terraform, azd delegates destroy to terraform destroy, so the problem does not exist there. Same would apply to any ext-provision provider — they own their own teardown.

  2. Resource-group scoped deployments: azd should simply not delete the RG in this case (it was provided by the user, not created by the template).

  3. Subscription-level deployments: This is where the snapshot approach shines. Create a local snapshot, extract the list of Microsoft.Resources/resourceGroups from predictedResources, and only delete those.

  4. Purge / soft-delete resources: We still need to manually query and handle purge for known soft-delete resources (Key Vault, APIM, Cognitive Services, etc.). But the snapshot predictedResources might also help here — it lists all predicted resources with their types, so we may be able to skip the per-RG resource queries and instead use the snapshot to identify which soft-delete-capable resources exist. Worth testing how much detail the snapshot provides (SKUs, names, etc.).

I verified this experimentally — created a subscription-level Bicep with one resource rg ... = { } (created) and one resource rg ... existing = { } (referenced). The snapshot cleanly excludes the existing RG from predictedResources while including the created one.

This approach would be significantly simpler than the multi-tier classification pipeline (no deployment operations API, no tag checks, no interactive prompts for ambiguous RGs) and would give you a deterministic, offline answer from the Bicep compiler itself.

Worth exploring as an alternative?

@jongio
Copy link
Copy Markdown
Member Author

jongio commented Apr 10, 2026

@vhvb1989 — Bicep snapshots already solve this. When you run bicep snapshot, the predictedResources output only includes resources that the deployment creates — resources declared with the existing keyword are excluded.

@vhvb1989 — Really interesting investigation, and I think you're onto something worth exploring as an enhancement. The snapshot approach could work well as a "Tier 0" signal — a fast, offline, deterministic check from the Bicep compiler before we even look at deployment operations.

That said, I don't think it can fully replace the current pipeline for a few reasons:

  1. Requires Bicep source files at destroy time. Today azd down works purely from deployment metadata — if a user deletes their infra/ directory (or runs destroy from a different machine), the pipeline still classifies correctly using deployment operations. Snapshot would fail in that scenario.

  2. Doesn't cover adopted/redeployed RGs. If a user creates an RG externally, then later deploys into it with azd up, the Bicep template declares it as a created resource — but it's actually pre-existing with other workloads. The deployment operations API captures this distinction (the operation type is Create only on first deploy); snapshot cannot.

  3. Bicep-only. The classification pipeline works for any deployment provider. While Terraform delegates its own destroy, future ext-provision providers may not, and the safety net needs to be provider-agnostic at the orchestration layer.

  4. Deployment outputs creating RGs aren't modeled as resources in predictedResources — they'd be missed.

I'd love to explore adding snapshot as a supplementary signal in a follow-up — it could strengthen Tier 1 confidence or even short-circuit the pipeline entirely when source files are available. Want to file an issue so we can track it?

@vhvb1989
Copy link
Copy Markdown
Member

@jongio — Thanks for engaging with the proposal. Let me address the points, grounding them in the current codebase:

1. "Requires Bicep source files at destroy time"

"Today azd down works purely from deployment metadata — if a user deletes their infra/ directory (or runs destroy from a different machine), the pipeline still classifies correctly."

This isn't accurate. Destroy() calls compileBicep(ctx) as its very first step — both on main (bicep_provider.go:960) and in this PR (line 1043). compileBicep() requires the .bicep/.bicepparam files on disk. If a user deletes infra/ or runs from another machine, azd down fails immediately with "creating template" — it never reaches the classification pipeline.

The snapshot approach has the exact same requirement as the current code: Bicep source files must be present. No regression.

I'd ask that we ground counter-arguments in currently supported, validated scenarios. Citing hypothetical scenarios (deleted infra folder, different machine) without first verifying they work today adds noise to the discussion and can bias toward unnecessary complexity. A quick check of the code confirms they don't work — so they shouldn't be used to justify a more complex approach.

2. "Doesn't cover adopted/redeployed RGs"

The existing keyword is the Bicep language's semantic signal for "I reference this but don't own it." That's exactly the distinction we need for safe deletion. The snapshot reads this signal deterministically at compile time. The deployment operations API infers the same thing from runtime state — which is indirect and depends on deployment history (was it the first deploy?).

If a user writes resource rg 'Microsoft.Resources/resourceGroups@...' = { name: 'my-rg' } without existing, they're declaring intent to create that RG. Whether it happened to exist before is the user's responsibility in their template design — not something we should second-guess with a runtime heuristic.

3. "Bicep-only — the classification pipeline works for any deployment provider"

The pipeline is Bicep-specific:

  • Called only from bicep_destroy.go (package bicep)
  • Terraform already handles its own destroy (terraform_provider.go:271 — delegates to terraform destroy)
  • The Tier 1 signals (Create/Read/EvaluateDeploymentOutput) are ARM-specific deployment operation types
  • The Tier 2 tag checks use azd-specific tags set only by the Bicep provider

Building ~4,165 lines of "provider-agnostic" infrastructure (544-line classifier + 1,268-line tests + 471-line orchestrator + 1,882-line architecture doc) for hypothetical future ext-provision providers that don't exist is speculative. If/when such a provider appears, it will likely have its own teardown semantics — just like Terraform does.

4. "Deployment outputs creating RGs aren't in predictedResources"

Could you provide a concrete example? predictedResources contains the fully resolved deployment graph with expressions evaluated, conditions applied, and copy loops expanded. Bicep templates that create resource groups do so via explicit resource declarations, which are included in predictedResources. I'd like to understand the specific scenario before we accept this as a blocker.

The core question

The snapshot gives a deterministic, zero-API-call, compile-time answer to exactly the question we're asking: "which resource groups does this template create vs. reference?" The infrastructure is already wired up in local_preflight.go.

The 4-tier pipeline builds a runtime detection system with multiple API calls per RG, complex parallel execution (goroutines, channels, WaitGroups), interactive prompts for ambiguous cases, and elaborate error handling — but ultimately still requires the same Bicep source files the snapshot does.

I think we should evaluate the simpler approach first before committing to this level of complexity. Let's stick to real, validated scenarios when comparing tradeoffs.

Copy link
Copy Markdown
Member

@vhvb1989 vhvb1989 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Requesting changes to prevent accidental merge while we discuss the approach.

The current 4-tier classification pipeline adds significant complexity (~4,165 new lines across classifier, tests, orchestrator, and architecture doc). We are actively discussing a simpler alternative using local Bicep snapshots (predictedResources), which would provide a deterministic, zero-API-call, compile-time answer to the same question — leveraging infrastructure already wired up in local_preflight.go.

See the ongoing discussion in the comments for details.

jongio and others added 17 commits April 10, 2026 11:42
…, #2916)

Implement a 4-tier resource group classification pipeline in azd down to
distinguish between resource groups created by azd (safe to delete) and
pre-existing resource groups that were merely referenced via Bicep 'existing'
keyword (must not be deleted).

The 4-tier classification pipeline:
- Tier 1: Deployment operations analysis (zero extra API calls) — Create
  operations mark RGs as owned, Read/EvaluateDeploymentOutput marks them
  as external.
- Tier 2: Dual-tag check (azd-env-name + azd-provision-param-hash) for
  RGs with no deployment operations.
- Tier 3: Interactive prompt for remaining unknowns (skipped in CI/--force).
- Tier 4: Safety vetoes (management locks, foreign resources) applied to
  ALL deletion candidates including user-accepted unknowns.

Key changes:
- New resource_group_classifier.go with ClassifyResourceGroups function
  and comprehensive test coverage (33 tests)
- New bicep_destroy.go with classifyAndDeleteResourceGroups orchestrator
- Restructured BicepProvider.Destroy() to classify before deleting
- Added VoidState to Deployment interface (void after delete, not during)
- Added ResourceGroupsFromDeployment public helper
- Removed unused promptDeletion/generateResourcesToDelete (replaced by
  per-RG classification prompts)

Safety properties:
- All API errors treated as vetoes (fail-safe: errors skip deletion)
- --force preserves backward compatibility (bypasses classification)
- Tier 4 prompts executed sequentially (no concurrent terminal output)
- Deployment state voided only after successful classification
- Purge targets collected only from owned (deleted) resource groups

Fixes #4785
Relates to #2916

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Add empty EnvName guard in Tier 4 (critical: prevents bypass)
- Context-aware semaphore with select on ctx.Done()
- Tier 4 helpers return errors on credential failures (fail-safe)
- Lock pager short-circuits on first CanNotDelete/ReadOnly lock
- Fix integration test mocks: register ARM client options, credential
  provider, individual RG GET, and lock endpoint mocks
- Add 10 new classifier unit tests covering edge cases

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Export LockLevelCanNotDelete/LockLevelReadOnly constants
- Replace magic strings in bicep_destroy.go lock short-circuit
- Add Tier2 nil TagReader and Tier3 nil Prompter edge case tests
- Total: 50 classifier unit tests

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Convert wg.Add/go func/wg.Done to wg.Go (Go 1.26 go fix)
- Remove unused destroyDeployment function and async import
- Add armlocks to cspell-azd-dictionary.txt

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
When deployment stacks alpha feature is enabled, use the original
deployment.Delete() path which deletes the stack object (cascading to
managed resources). The new classification pipeline only applies to
standard deployments.

This fixes Test_DeploymentStacks CI failures where the recording proxy
could not find individual RG DELETE calls — stacks use stack DELETE
instead.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Add destroyViaDeploymentDelete tests (0% -> 80%)
- Add deleteRGList partial failure test (65% -> 85%)
- Add operationTargetsRG + tagValue edge case tests (-> 100%)
- Add deployment stacks + credential resolution tests
- 10 new test cases, all passing

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…tests

- Extract collectPurgeItems helper to eliminate 78-line duplication between
  stacks and classification paths in Destroy()
- Extract forceDeleteLogAnalyticsIfPurge helper to DRY Log Analytics cleanup
- Fix data race: use atomic.Int32 for callCount in semaphore cancellation test
- Add vetoedSet size hint for map pre-allocation
- Remove stale tombstone comment about removed functions
- Add 2 security tests: Tier4 500 on resource listing, non-azcore network error

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Add errUserCancelled sentinel so declining confirmation does not void
  deployment state or invalidate env keys (Goldeneye finding)
- Move deployment-stacks check before len(groupedResources)==0 fast-path
  so stacks are always deleted even when ARM shows zero resources
- Add UserCancelPreservesDeploymentState regression test
- Add ZeroResourcesStillDeletesStack regression test

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…cel returns error

- forceDeleteLogAnalyticsIfPurge now returns error (restores fatal behavior)
- Tier 4 skips untaggable extension resource types (Microsoft.Authorization/*, etc.)
- User cancellation returns errUserCancelled instead of nil
- Added Type field to ResourceWithTags, 11 new unit tests

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
…=tags, fix semaphore race

Three issues found in round 2 triple-model code review:

1. CRITICAL: collectPurgeItems was called AFTER RG deletion in both the
   deployment-stacks path and classification path. Since DeleteResourceGroup
   polls to completion (PollUntilDone), getKeyVaults/getManagedHSMs/etc.
   would 404 when querying resources in already-deleted RGs. Fix: split
   classifyAndDeleteResourceGroups into classifyResourceGroups (classify +
   confirm, no delete) so the caller can collect purge targets while RGs
   still exist, then delete, then purge.

2. HIGH: \=tags is not a valid parameter for the ARM
   Resources.ListByResourceGroup API (valid values: createdTime,
   changedTime, provisioningState). Tags are already included by default
   in GenericResourceExpanded. If ARM rejected the invalid expand with 400,
   the classifier would treat it as a fail-safe veto on all owned RGs.
   Fix: remove the \ parameter.

3. LOW: Tier 4 semaphore select race — Go's non-deterministic select could
   choose the semaphore case even when ctx.Done is ready. Fix: add
   ctx.Err() re-check after semaphore acquisition.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
When deleteRGList partially succeeds (e.g., rg-a deleted but rg-b fails),
the soft-deleted resources from rg-a (Key Vaults, Managed HSMs, etc.)
need purging to avoid name collisions on reprovisioning. Previously,
purgeItems was skipped entirely when deleteErr was non-nil, and on retry
those deleted RGs would be classified as 'already deleted' (Tier 2: 404),
losing their purge targets permanently.

Now purgeItems always runs after deletion. Deletion errors are reported
first (primary failure); purge errors for non-deleted RGs are expected
and secondary.
Verifies that purgeItems runs even after deleteRGList partially fails:
- rg-ok (with kv-ok) deleted successfully, rg-fail returns 409
- Assert kv-ok purge was called despite partial deletion failure
- Assert voidDeploymentState skipped on partial failure
- Document known limitation in code comment (iteration order edge case)

Covers the fix from the previous commit and addresses the test coverage
gap identified in CR Round 4.
MQ preflight cspell check flagged this word used in comments.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- --force no longer bypasses all classification. Tier 1 (zero extra API
  calls) still runs to identify external RGs from deployment operations.
  External RGs with Read/EvaluateDeploymentOutput operations are protected
  even with --force. Unknown RGs are treated as owned (backward compat).
  If operations are unavailable, all RGs are deleted (backward compat).

- Added ForceMode to ClassifyOptions with 5 unit tests covering:
  external protection, unknown-as-owned, nil ops fallback, callback
  skip verification, and EvaluateDeploymentOutput detection.

- Added Tier4LockVetoPreventsDeletion integration test verifying that
  a CanNotDelete lock vetoes deletion even for Tier 1 owned RGs.

- Added MixedOwnedExternalOnlyOwnedDeleted integration test verifying
  end-to-end: Created=deleted, Read=skipped, unknown=skipped (non-interactive).

- Updated ForceBypassesClassification -> ForceProtectsExternalRGs test
  to verify operations ARE fetched and external RGs ARE protected with --force.

- Extended classifyMockCfg with per-RG lock support and per-RG tag mocks.

- Updated architecture.md: Decision 4 rewritten (Tier 1 only, not full
  bypass), gap section updated, risk mitigations updated, added mermaid
  classification flow diagram.

Addresses review findings #2 and #3 from @wbreza.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Pre-lowercase extensionResourceTypePrefixes for O(1) lookup
- Add trust-boundary comment at Tier 1 entry
- Correct goroutine invariant comment (sends at most once)
- Log foreign resource names in Tier 4 veto
- Add hash case-sensitivity comment
- Improve Interactive field doc comment
- Use atomic.Bool/Int32 for test concurrency counters
- Remove duplicate 404 test, add non-azcore error test
- Modernize map key collection with slices.Collect(maps.Keys)
- Improve getResourceGroupTags doc (error-handling asymmetry)
- Guard nil env tag pointer in standard_deployments.go
- Fix architecture doc evaluation order
- Add diagnosticsettings to cspell dictionary
- Promote armlocks to direct dependency (go mod tidy)
- Apply gofmt to all changed files

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Replace 20 to.Ptr() calls with new() in bicep_provider_test.go and
remove unused azure-sdk-for-go/sdk/azcore/to import per AGENTS.md
Go 1.26 guidelines.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@jongio jongio force-pushed the fix/azd-down-rg-safety branch from c93aeef to c4b7a94 Compare April 10, 2026 18:43
@azure-sdk
Copy link
Copy Markdown
Collaborator

Azure Dev CLI Install Instructions

Install scripts

MacOS/Linux

May elevate using sudo on some platforms and configurations

bash:

curl -fsSL https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/uninstall-azd.sh | bash;
curl -fsSL https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/install-azd.sh | bash -s -- --base-url https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603 --version '' --verbose --skip-verify

pwsh:

Invoke-RestMethod 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/uninstall-azd.ps1' -OutFile uninstall-azd.ps1; ./uninstall-azd.ps1
Invoke-RestMethod 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/install-azd.ps1' -OutFile install-azd.ps1; ./install-azd.ps1 -BaseUrl 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603' -Version '' -SkipVerify -Verbose

Windows

PowerShell install

powershell -c "Set-ExecutionPolicy Bypass Process; irm 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/uninstall-azd.ps1' > uninstall-azd.ps1; ./uninstall-azd.ps1;"
powershell -c "Set-ExecutionPolicy Bypass Process; irm 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/install-azd.ps1' > install-azd.ps1; ./install-azd.ps1 -BaseUrl 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603' -Version '' -SkipVerify -Verbose;"

MSI install

powershell -c "irm 'https://azuresdkartifacts.z5.web.core.windows.net/azd/standalone/pr/7603/azd-windows-amd64.msi' -OutFile azd-windows-amd64.msi; msiexec /i azd-windows-amd64.msi /qn"

Standalone Binary

MSI

Documentation

learn.microsoft.com documentation

title: Azure Developer CLI reference
description: This article explains the syntax and parameters for the various Azure Developer CLI commands.
author: alexwolfmsft
ms.author: alexwolf
ms.date: 04/10/2026
ms.service: azure-dev-cli
ms.topic: conceptual
ms.custom: devx-track-azdevcli

Azure Developer CLI reference

This article explains the syntax and parameters for the various Azure Developer CLI commands.

azd

The Azure Developer CLI (azd) is an open-source tool that helps onboard and manage your project on Azure

Options

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
      --docs                 Opens the documentation for azd in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for azd.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd add: Add a component to your project.
  • azd auth: Authenticate with Azure.
  • azd completion: Generate shell completion scripts.
  • azd config: Manage azd configurations (ex: default Azure subscription, location).
  • azd copilot: Manage GitHub Copilot agent settings. (Preview)
  • azd deploy: Deploy your project code to Azure.
  • azd down: Delete your project's Azure resources.
  • azd env: Manage environments (ex: default environment, environment variables).
  • azd extension: Manage azd extensions.
  • azd hooks: Develop, test and run hooks for a project.
  • azd infra: Manage your Infrastructure as Code (IaC).
  • azd init: Initialize a new application.
  • azd mcp: Manage Model Context Protocol (MCP) server. (Alpha)
  • azd monitor: Monitor a deployed project.
  • azd package: Packages the project's code to be deployed to Azure.
  • azd pipeline: Manage and configure your deployment pipelines.
  • azd provision: Provision Azure resources for your project.
  • azd publish: Publish a service to a container registry.
  • azd restore: Restores the project's dependencies.
  • azd show: Display information about your project and its resources.
  • azd template: Find and view template details.
  • azd up: Provision and deploy your project to Azure with a single command.
  • azd update: Updates azd to the latest version.
  • azd version: Print the version number of Azure Developer CLI.

azd add

Add a component to your project.

azd add [flags]

Options

      --docs   Opens the documentation for azd add in your web browser.
  -h, --help   Gets help for add.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd auth

Authenticate with Azure.

Options

      --docs   Opens the documentation for azd auth in your web browser.
  -h, --help   Gets help for auth.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd auth login

Log in to Azure.

Synopsis

Log in to Azure.

When run without any arguments, log in interactively using a browser. To log in using a device code, pass
--use-device-code.

To log in as a service principal, pass --client-id and --tenant-id as well as one of: --client-secret,
--client-certificate, or --federated-credential-provider.

To log in using a managed identity, pass --managed-identity, which will use the system assigned managed identity.
To use a user assigned managed identity, pass --client-id in addition to --managed-identity with the client id of
the user assigned managed identity you wish to use.

azd auth login [flags]

Options

      --check-status                           Checks the log-in status instead of logging in.
      --client-certificate string              The path to the client certificate for the service principal to authenticate with.
      --client-id string                       The client id for the service principal to authenticate with.
      --client-secret string                   The client secret for the service principal to authenticate with. Set to the empty string to read the value from the console.
      --docs                                   Opens the documentation for azd auth login in your web browser.
      --federated-credential-provider string   The provider to use to acquire a federated token to authenticate with. Supported values: github, azure-pipelines, oidc
  -h, --help                                   Gets help for login.
      --managed-identity                       Use a managed identity to authenticate.
      --redirect-port int                      Choose the port to be used as part of the redirect URI during interactive login.
      --tenant-id string                       The tenant id or domain name to authenticate with.
      --use-device-code[=true]                 When true, log in by using a device code instead of a browser.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd auth logout

Log out of Azure.

Synopsis

Log out of Azure

azd auth logout [flags]

Options

      --docs   Opens the documentation for azd auth logout in your web browser.
  -h, --help   Gets help for logout.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd auth status

Show the current authentication status.

Synopsis

Display whether you are logged in to Azure and the associated account information.

azd auth status [flags]

Options

      --docs   Opens the documentation for azd auth status in your web browser.
  -h, --help   Gets help for status.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd completion

Generate shell completion scripts.

Synopsis

Generate shell completion scripts for azd.

The completion command allows you to generate autocompletion scripts for your shell,
currently supports bash, zsh, fish and PowerShell.

See each sub-command's help for details on how to use the generated script.

Options

      --docs   Opens the documentation for azd completion in your web browser.
  -h, --help   Gets help for completion.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd completion bash

Generate bash completion script.

azd completion bash

Options

      --docs   Opens the documentation for azd completion bash in your web browser.
  -h, --help   Gets help for bash.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd completion fig

Generate Fig autocomplete spec.

azd completion fig

Options

      --docs   Opens the documentation for azd completion fig in your web browser.
  -h, --help   Gets help for fig.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd completion fish

Generate fish completion script.

azd completion fish

Options

      --docs   Opens the documentation for azd completion fish in your web browser.
  -h, --help   Gets help for fish.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd completion powershell

Generate PowerShell completion script.

azd completion powershell

Options

      --docs   Opens the documentation for azd completion powershell in your web browser.
  -h, --help   Gets help for powershell.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd completion zsh

Generate zsh completion script.

azd completion zsh

Options

      --docs   Opens the documentation for azd completion zsh in your web browser.
  -h, --help   Gets help for zsh.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config

Manage azd configurations (ex: default Azure subscription, location).

Synopsis

Manage the Azure Developer CLI user configuration, which includes your default Azure subscription and location.

Available since azure-dev-cli_0.4.0-beta.1.

The easiest way to configure azd for the first time is to run azd init. The subscription and location you select will be stored in the config.json file located in the config directory. To configure azd anytime afterwards, you'll use azd config set.

The default value of the config directory is:

  • $HOME/.azd on Linux and macOS
  • %USERPROFILE%.azd on Windows

The configuration directory can be overridden by specifying a path in the AZD_CONFIG_DIR environment variable.

Options

      --docs   Opens the documentation for azd config in your web browser.
  -h, --help   Gets help for config.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config get

Gets a configuration.

Synopsis

Gets a configuration in the configuration path.

The default value of the config directory is:

  • $HOME/.azd on Linux and macOS
  • %USERPROFILE%\.azd on Windows

The configuration directory can be overridden by specifying a path in the AZD_CONFIG_DIR environment variable.

azd config get <path> [flags]

Options

      --docs   Opens the documentation for azd config get in your web browser.
  -h, --help   Gets help for get.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config list-alpha

Display the list of available features in alpha stage.

azd config list-alpha [flags]

Options

      --docs   Opens the documentation for azd config list-alpha in your web browser.
  -h, --help   Gets help for list-alpha.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config options

List all available configuration settings.

Synopsis

List all possible configuration settings that can be set with azd, including descriptions and allowed values.

azd config options [flags]

Options

      --docs   Opens the documentation for azd config options in your web browser.
  -h, --help   Gets help for options.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config reset

Resets configuration to default.

Synopsis

Resets all configuration in the configuration path.

The default value of the config directory is:

  • $HOME/.azd on Linux and macOS
  • %USERPROFILE%\.azd on Windows

The configuration directory can be overridden by specifying a path in the AZD_CONFIG_DIR environment variable to the default.

azd config reset [flags]

Options

      --docs    Opens the documentation for azd config reset in your web browser.
  -f, --force   Force reset without confirmation.
  -h, --help    Gets help for reset.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config set

Sets a configuration.

Synopsis

Sets a configuration in the configuration path.

The default value of the config directory is:

  • $HOME/.azd on Linux and macOS
  • %USERPROFILE%\.azd on Windows

The configuration directory can be overridden by specifying a path in the AZD_CONFIG_DIR environment variable.

azd config set <path> <value> [flags]

Examples

azd config set defaults.subscription <yourSubscriptionID>
azd config set defaults.location eastus

Options

      --docs   Opens the documentation for azd config set in your web browser.
  -h, --help   Gets help for set.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config show

Show all the configuration values.

Synopsis

Show all configuration values in the configuration path.

The default value of the config directory is:

  • $HOME/.azd on Linux and macOS
  • %USERPROFILE%\.azd on Windows

The configuration directory can be overridden by specifying a path in the AZD_CONFIG_DIR environment variable.

azd config show [flags]

Options

      --docs   Opens the documentation for azd config show in your web browser.
  -h, --help   Gets help for show.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd config unset

Unsets a configuration.

Synopsis

Removes a configuration in the configuration path.

The default value of the config directory is:

  • $HOME/.azd on Linux and macOS
  • %USERPROFILE%\.azd on Windows

The configuration directory can be overridden by specifying a path in the AZD_CONFIG_DIR environment variable.

azd config unset <path> [flags]

Examples

azd config unset defaults.location

Options

      --docs   Opens the documentation for azd config unset in your web browser.
  -h, --help   Gets help for unset.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd copilot

Manage GitHub Copilot agent settings. (Preview)

Options

      --docs   Opens the documentation for azd copilot in your web browser.
  -h, --help   Gets help for copilot.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd copilot consent

Manage tool consent.

Synopsis

Manage consent rules for tool execution.

Options

      --docs   Opens the documentation for azd copilot consent in your web browser.
  -h, --help   Gets help for consent.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd copilot consent grant

Grant consent trust rules.

Synopsis

Grant trust rules for tools and servers.

This command creates consent rules that allow tools to execute
without prompting for permission. You can specify different permission
levels and scopes for the rules.

Examples:

Grant always permission to all tools globally

azd copilot consent grant --global --permission always

Grant project permission to a specific tool with read-only scope

azd copilot consent grant --server my-server --tool my-tool --permission project --scope read-only

azd copilot consent grant [flags]

Options

      --action string       Action type: 'all' or 'readonly' (default "all")
      --docs                Opens the documentation for azd copilot consent grant in your web browser.
      --global              Apply globally to all servers
  -h, --help                Gets help for grant.
      --operation string    Operation type: 'tool' or 'sampling' (default "tool")
      --permission string   Permission: 'allow', 'deny', or 'prompt' (default "allow")
      --scope string        Rule scope: 'global', or 'project' (default "global")
      --server string       Server name
      --tool string         Specific tool name (requires --server)

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd copilot consent list

List consent rules.

Synopsis

List all consent rules for tools.

azd copilot consent list [flags]

Options

      --action string       Action type to filter by (all, readonly)
      --docs                Opens the documentation for azd copilot consent list in your web browser.
  -h, --help                Gets help for list.
      --operation string    Operation to filter by (tool, sampling)
      --permission string   Permission to filter by (allow, deny, prompt)
      --scope string        Consent scope to filter by (global, project). If not specified, lists rules from all scopes.
      --target string       Specific target to operate on (server/tool format)

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd copilot consent revoke

Revoke consent rules.

Synopsis

Revoke consent rules for tools.

azd copilot consent revoke [flags]

Options

      --action string       Action type to filter by (all, readonly)
      --docs                Opens the documentation for azd copilot consent revoke in your web browser.
  -h, --help                Gets help for revoke.
      --operation string    Operation to filter by (tool, sampling)
      --permission string   Permission to filter by (allow, deny, prompt)
      --scope string        Consent scope to filter by (global, project). If not specified, revokes rules from all scopes.
      --target string       Specific target to operate on (server/tool format)

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd deploy

Deploy your project code to Azure.

azd deploy <service> [flags]

Options

      --all                   Deploys all services that are listed in azure.yaml
      --docs                  Opens the documentation for azd deploy in your web browser.
  -e, --environment string    The name of the environment to use.
      --from-package string   Deploys the packaged service located at the provided path. Supports zipped file packages (file path) or container images (image tag).
  -h, --help                  Gets help for deploy.
      --timeout int           Maximum time in seconds for azd to wait for each service deployment. This stops azd from waiting but does not cancel the Azure-side deployment. (default: 1200) (default 1200)

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd down

Delete your project's Azure resources.

azd down [<layer>] [flags]

Options

      --docs                 Opens the documentation for azd down in your web browser.
  -e, --environment string   The name of the environment to use.
      --force                Does not require confirmation before it deletes resources.
  -h, --help                 Gets help for down.
      --purge                Does not require confirmation before it permanently deletes resources that are soft-deleted by default (for example, key vaults).

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd env

Manage environments (ex: default environment, environment variables).

Options

      --docs   Opens the documentation for azd env in your web browser.
  -h, --help   Gets help for env.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd env config

Manage environment configuration (ex: stored in .azure//config.json).

Options

      --docs   Opens the documentation for azd env config in your web browser.
  -h, --help   Gets help for config.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd env config get

Gets a configuration value from the environment.

Synopsis

Gets a configuration value from the environment's config.json file.

azd env config get <path> [flags]

Options

      --docs                 Opens the documentation for azd env config get in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for get.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd env config set

Sets a configuration value in the environment.

Synopsis

Sets a configuration value in the environment's config.json file.

Values are automatically parsed as JSON types when possible. Booleans (true/false),
numbers (42, 3.14), arrays ([...]), and objects ({...}) are stored with their native
JSON types. Plain text values are stored as strings. To force a JSON-typed value to be
stored as a string, wrap it in JSON quotes (e.g. '"true"' or '"8080"').

azd env config set <path> <value> [flags]

Examples

azd env config set myapp.endpoint https://example.com
azd env config set myapp.debug true
azd env config set myapp.count 42
azd env config set infra.parameters.tags '{"env":"dev"}'
azd env config set myapp.port '"8080"'

Options

      --docs                 Opens the documentation for azd env config set in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for set.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd env config unset

Unsets a configuration value in the environment.

Synopsis

Removes a configuration value from the environment's config.json file.

azd env config unset <path> [flags]

Examples

azd env config unset myapp.endpoint

Options

      --docs                 Opens the documentation for azd env config unset in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for unset.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd env get-value

Get specific environment value.

azd env get-value <keyName> [flags]

Options

      --docs                 Opens the documentation for azd env get-value in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for get-value.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env get-values

Get all environment values.

azd env get-values [flags]

Options

      --docs                 Opens the documentation for azd env get-values in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for get-values.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env list

List environments.

azd env list [flags]

Options

      --docs   Opens the documentation for azd env list in your web browser.
  -h, --help   Gets help for list.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env new

Create a new environment and set it as the default.

azd env new <environment> [flags]

Options

      --docs                  Opens the documentation for azd env new in your web browser.
  -h, --help                  Gets help for new.
  -l, --location string       Azure location for the new environment
      --subscription string   ID of an Azure subscription to use for the new environment

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env refresh

Refresh environment values by using information from a previous infrastructure provision.

azd env refresh <environment> [flags]

Options

      --docs                 Opens the documentation for azd env refresh in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for refresh.
      --hint string          Hint to help identify the environment to refresh
      --layer string         Provisioning layer to refresh the environment from.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env remove

Remove an environment.

azd env remove <environment> [flags]

Options

      --docs                 Opens the documentation for azd env remove in your web browser.
  -e, --environment string   The name of the environment to use.
      --force                Skips confirmation before performing removal.
  -h, --help                 Gets help for remove.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env select

Set the default environment.

azd env select [<environment>] [flags]

Options

      --docs   Opens the documentation for azd env select in your web browser.
  -h, --help   Gets help for select.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env set

Set one or more environment values.

Synopsis

Set one or more environment values using key-value pairs or by loading from a .env formatted file.

azd env set [<key> <value>] | [<key>=<value> ...] | [--file <filepath>] [flags]

Options

      --docs                 Opens the documentation for azd env set in your web browser.
  -e, --environment string   The name of the environment to use.
      --file string          Path to .env formatted file to load environment values from.
  -h, --help                 Gets help for set.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd env set-secret

Set a name as a reference to a Key Vault secret in the environment.

Synopsis

You can either create a new Key Vault secret or select an existing one.
The provided name is the key for the .env file which holds the secret reference to the Key Vault secret.

azd env set-secret <name> [flags]

Options

      --docs                 Opens the documentation for azd env set-secret in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for set-secret.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

  • azd env: Manage environments (ex: default environment, environment variables).
  • Back to top

azd extension

Manage azd extensions.

Options

      --docs   Opens the documentation for azd extension in your web browser.
  -h, --help   Gets help for extension.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension install

Installs specified extensions.

azd extension install <extension-id> [flags]

Options

      --docs             Opens the documentation for azd extension install in your web browser.
  -f, --force            Force installation, including downgrades and reinstalls
  -h, --help             Gets help for install.
  -s, --source string    The extension source to use for installs
  -v, --version string   The version of the extension to install

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension list

List available extensions.

azd extension list [--installed] [flags]

Options

      --docs            Opens the documentation for azd extension list in your web browser.
  -h, --help            Gets help for list.
      --installed       List installed extensions
      --source string   Filter extensions by source
      --tags strings    Filter extensions by tags

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension show

Show details for a specific extension.

azd extension show <extension-id> [flags]

Options

      --docs            Opens the documentation for azd extension show in your web browser.
  -h, --help            Gets help for show.
  -s, --source string   The extension source to use.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension source

View and manage extension sources

Options

      --docs   Opens the documentation for azd extension source in your web browser.
  -h, --help   Gets help for source.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension source add

Add an extension source with the specified name

azd extension source add [flags]

Options

      --docs              Opens the documentation for azd extension source add in your web browser.
  -h, --help              Gets help for add.
  -l, --location string   The location of the extension source
  -n, --name string       The name of the extension source
  -t, --type string       The type of the extension source. Supported types are 'file' and 'url'

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension source list

List extension sources

azd extension source list [flags]

Options

      --docs   Opens the documentation for azd extension source list in your web browser.
  -h, --help   Gets help for list.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension source remove

Remove an extension source with the specified name

azd extension source remove <name> [flags]

Options

      --docs   Opens the documentation for azd extension source remove in your web browser.
  -h, --help   Gets help for remove.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension source validate

Validate an extension source's registry.json file.

Synopsis

Validate an extension source's registry.json file.

Accepts a source name (from 'azd extension source list'), a local file path,
or a URL. Checks required fields, valid capabilities, semver version format,
platform artifact structure, and extension ID format.

azd extension source validate <name-or-path-or-url> [flags]

Options

      --docs     Opens the documentation for azd extension source validate in your web browser.
  -h, --help     Gets help for validate.
      --strict   Enable strict validation (require checksums)

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension uninstall

Uninstall specified extensions.

azd extension uninstall [extension-id] [flags]

Options

      --all    Uninstall all installed extensions
      --docs   Opens the documentation for azd extension uninstall in your web browser.
  -h, --help   Gets help for uninstall.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd extension upgrade

Upgrade specified extensions.

azd extension upgrade [extension-id] [flags]

Options

      --all              Upgrade all installed extensions
      --docs             Opens the documentation for azd extension upgrade in your web browser.
  -h, --help             Gets help for upgrade.
  -s, --source string    The extension source to use for upgrades
  -v, --version string   The version of the extension to upgrade to

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd hooks

Develop, test and run hooks for a project.

Options

      --docs   Opens the documentation for azd hooks in your web browser.
  -h, --help   Gets help for hooks.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd hooks run

Runs the specified hook for the project, provisioning layers, and services

azd hooks run <name> [flags]

Options

      --docs                 Opens the documentation for azd hooks run in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for run.
      --layer string         Only runs hooks for the specified provisioning layer.
      --platform string      Forces hooks to run for the specified platform.
      --service string       Only runs hooks for the specified service.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd infra

Manage your Infrastructure as Code (IaC).

Options

      --docs   Opens the documentation for azd infra in your web browser.
  -h, --help   Gets help for infra.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd infra generate

Write IaC for your project to disk, allowing you to manually manage it.

azd infra generate [flags]

Options

      --docs                 Opens the documentation for azd infra generate in your web browser.
  -e, --environment string   The name of the environment to use.
      --force                Overwrite any existing files without prompting
  -h, --help                 Gets help for generate.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd init

Initialize a new application.

azd init [flags]

Options

  -b, --branch string         The template branch to initialize from. Must be used with a template argument (--template or -t).
      --docs                  Opens the documentation for azd init in your web browser.
  -e, --environment string    The name of the environment to use.
  -f, --filter strings        The tag(s) used to filter template results. Supports comma-separated values.
      --from-code             Initializes a new application from your existing code.
  -h, --help                  Gets help for init.
  -l, --location string       Azure location for the new environment
  -m, --minimal               Initializes a minimal project.
  -s, --subscription string   ID of an Azure subscription to use for the new environment
  -t, --template string       Initializes a new application from a template. You can use a Full URI, <owner>/<repository>, <repository> if it's part of the azure-samples organization, or a local directory path (./dir, ../dir, or absolute path).
      --up                    Provision and deploy to Azure after initializing the project from a template.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd mcp

Manage Model Context Protocol (MCP) server. (Alpha)

Options

      --docs   Opens the documentation for azd mcp in your web browser.
  -h, --help   Gets help for mcp.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd mcp start

Starts the MCP server.

Synopsis

Starts the Model Context Protocol (MCP) server.

This command starts an MCP server that can be used by MCP clients to access
azd functionality through the Model Context Protocol interface.

azd mcp start [flags]

Options

      --docs   Opens the documentation for azd mcp start in your web browser.
  -h, --help   Gets help for start.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd monitor

Monitor a deployed project.

azd monitor [flags]

Options

      --docs                 Opens the documentation for azd monitor in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for monitor.
      --live                 Open a browser to Application Insights Live Metrics. Live Metrics is currently not supported for Python apps.
      --logs                 Open a browser to Application Insights Logs.
      --overview             Open a browser to Application Insights Overview Dashboard.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd package

Packages the project's code to be deployed to Azure.

azd package <service> [flags]

Options

      --all                  Packages all services that are listed in azure.yaml
      --docs                 Opens the documentation for azd package in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for package.
      --output-path string   File or folder path where the generated packages will be saved.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd pipeline

Manage and configure your deployment pipelines.

Options

      --docs   Opens the documentation for azd pipeline in your web browser.
  -h, --help   Gets help for pipeline.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd pipeline config

Configure your deployment pipeline to connect securely to Azure. (Beta)

azd pipeline config [flags]

Options

  -m, --applicationServiceManagementReference string   Service Management Reference. References application or service contact information from a Service or Asset Management database. This value must be a Universally Unique Identifier (UUID). You can set this value globally by running azd config set pipeline.config.applicationServiceManagementReference <UUID>.
      --auth-type string                               The authentication type used between the pipeline provider and Azure for deployment (Only valid for GitHub provider). Valid values: federated, client-credentials.
      --docs                                           Opens the documentation for azd pipeline config in your web browser.
  -e, --environment string                             The name of the environment to use.
  -h, --help                                           Gets help for config.
      --principal-id string                            The client id of the service principal to use to grant access to Azure resources as part of the pipeline.
      --principal-name string                          The name of the service principal to use to grant access to Azure resources as part of the pipeline.
      --principal-role stringArray                     The roles to assign to the service principal. By default the service principal will be granted the Contributor and User Access Administrator roles. (default [Contributor,User Access Administrator])
      --provider string                                The pipeline provider to use (github for Github Actions and azdo for Azure Pipelines).
      --remote-name string                             The name of the git remote to configure the pipeline to run on. (default "origin")

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd provision

Provision Azure resources for your project.

azd provision [<layer>] [flags]

Options

      --docs                  Opens the documentation for azd provision in your web browser.
  -e, --environment string    The name of the environment to use.
  -h, --help                  Gets help for provision.
  -l, --location string       Azure location for the new environment
      --no-state              (Bicep only) Forces a fresh deployment based on current Bicep template files, ignoring any stored deployment state.
      --preview               Preview changes to Azure resources.
      --subscription string   ID of an Azure subscription to use for the new environment

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd publish

Publish a service to a container registry.

azd publish <service> [flags]

Options

      --all                   Publishes all services that are listed in azure.yaml
      --docs                  Opens the documentation for azd publish in your web browser.
  -e, --environment string    The name of the environment to use.
      --from-package string   Publishes the service from a container image (image tag).
  -h, --help                  Gets help for publish.
      --to string             The target container image in the form '[registry/]repository[:tag]' to publish to.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd restore

Restores the project's dependencies.

azd restore <service> [flags]

Options

      --all                  Restores all services that are listed in azure.yaml
      --docs                 Opens the documentation for azd restore in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for restore.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd show

Display information about your project and its resources.

azd show [resource-name|resource-id] [flags]

Options

      --docs                 Opens the documentation for azd show in your web browser.
  -e, --environment string   The name of the environment to use.
  -h, --help                 Gets help for show.
      --show-secrets         Unmask secrets in output.

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template

Find and view template details.

Options

      --docs   Opens the documentation for azd template in your web browser.
  -h, --help   Gets help for template.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template list

Show list of sample azd templates. (Beta)

azd template list [flags]

Options

      --docs             Opens the documentation for azd template list in your web browser.
  -f, --filter strings   The tag(s) used to filter template results. Supports comma-separated values.
  -h, --help             Gets help for list.
  -s, --source string    Filters templates by source.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template show

Show details for a given template. (Beta)

azd template show <template> [flags]

Options

      --docs   Opens the documentation for azd template show in your web browser.
  -h, --help   Gets help for show.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template source

View and manage template sources. (Beta)

Options

      --docs   Opens the documentation for azd template source in your web browser.
  -h, --help   Gets help for source.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template source add

Adds an azd template source with the specified key. (Beta)

Synopsis

The key can be any value that uniquely identifies the template source, with well-known values being:
・default: Default templates
・awesome-azd: Templates from https://aka.ms/awesome-azd

azd template source add <key> [flags]

Options

      --docs              Opens the documentation for azd template source add in your web browser.
  -h, --help              Gets help for add.
  -l, --location string   Location of the template source. Required when using type flag.
  -n, --name string       Display name of the template source.
  -t, --type string       Kind of the template source. Supported types are 'file', 'url' and 'gh'.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template source list

Lists the configured azd template sources. (Beta)

azd template source list [flags]

Options

      --docs   Opens the documentation for azd template source list in your web browser.
  -h, --help   Gets help for list.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd template source remove

Removes the specified azd template source (Beta)

azd template source remove <key> [flags]

Options

      --docs   Opens the documentation for azd template source remove in your web browser.
  -h, --help   Gets help for remove.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd up

Provision and deploy your project to Azure with a single command.

azd up [flags]

Options

      --docs                  Opens the documentation for azd up in your web browser.
  -e, --environment string    The name of the environment to use.
  -h, --help                  Gets help for up.
  -l, --location string       Azure location for the new environment
      --subscription string   ID of an Azure subscription to use for the new environment

Options inherited from parent commands

  -C, --cwd string   Sets the current working directory.
      --debug        Enables debugging and diagnostics logging.
      --no-prompt    Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd update

Updates azd to the latest version.

azd update [flags]

Options

      --channel string             Update channel: stable or daily.
      --check-interval-hours int   Override the update check interval in hours.
      --docs                       Opens the documentation for azd update in your web browser.
  -h, --help                       Gets help for update.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

azd version

Print the version number of Azure Developer CLI.

azd version [flags]

Options

      --docs   Opens the documentation for azd version in your web browser.
  -h, --help   Gets help for version.

Options inherited from parent commands

  -C, --cwd string           Sets the current working directory.
      --debug                Enables debugging and diagnostics logging.
  -e, --environment string   The name of the environment to use.
      --no-prompt            Accepts the default value instead of prompting, or it fails if there is no default.

See also

Copy link
Copy Markdown
Contributor

@wbreza wbreza left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-Review — Prior Findings Status

All 6 findings from my previous CHANGES_REQUESTED (e56b87aa) are addressed:

# Finding Status
1 [HIGH] Tier 1 ops failure → silent fallthrough ✅ Normal mode falls to Tier 2/3; force mode documented
2 [HIGH] Missing integration tests for Tier 4 vetoes ✅ +1,681 test lines + destroy orchestration coverage
3 [Medium] --force bypasses Tier 1 d1a56ac1 — ForceMode now runs Tier 1
4 [Medium] Old deployments trigger Tier 3 prompts ✅ Acceptable: --force works, interactive prompts, non-interactive skips safely
5 [Medium] Hash case sensitivity ✅ Intentional design, documented in comment
6 [Low] Log Analytics double purge ✅ Purge refactored into separate paths

Code quality has improved notably: wg.Go (Go 1.26), errors.AsType, clean semaphore + context cancellation, extension resource type filtering for false-positive prevention, and sequential Tier 4 prompts to avoid concurrent terminal output.

Design Discussion

Worth noting @vhvb1989's proposal to use Bicep predictedResources (from bicep snapshot) as an alternative to the 4-tier runtime classification. The snapshot approach would be deterministic (compiler-level existing vs created distinction), zero API calls, and could reuse the existing local_preflight.go infrastructure. The current implementation is well-engineered, but if the snapshot approach covers the same scenarios with significantly less complexity, it's worth exploring before this lands.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add option to not delete resource group when running azd down command [Issue] azd down removes resource groups not created by azd

5 participants