Diagnosing azure deployment failures
Skill alexpizarro/azure-lean-stack-skills/skills/diagnosing-azure-deployment-failures
Matches Azure deploy / CI / runtime failures against 37+ documented gotchas with verified fixes (BCP258, AADSTS70021, sqlcmd-not-found, FC1-CLI-silent-fallback, ACS dataLocation quirks, SSE timeouts, and more). Delegates to Microsoft's azure-diagnostics for live log/metric queries. Use when a deploy fails, a deployed app misbehaves, or a CI step errors.From its SKILL.md
npx -y skills add alexpizarro/azure-lean-stack-skills --skill diagnosing-azure-deployment-failuresAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
One thing to look at
- 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.
SKILL.md
7.1 KB, ~1.7k tokens by cl100k_base, as published. Nobody here has run it
Diagnosing Azure Deployment Failures
Lookup-first triage against documented gotchas. If the symptom doesn't match a known entry, escalate to Microsoft's azure-diagnostics for live log/metric queries.
How to use this skill
- Get the failing symptom (error code, stack trace, observed behaviour)
- Match against the table below
- Apply the documented fix
- If no match, see references/gotchas.md for the full catalogue
- If still no match, capture a new gotcha via curating-azure-deployment-learnings
Quick symptom table
| Symptom | Likely cause | Fix |
|---|---|---|
BCP258: sqlAdminPassword missing | Using .bicepparam instead of .parameters.json | Keep params as .parameters.json; use @ prefix |
LocationNotAvailableForResourceType for SWA | australiaeast not supported | Hard-code swaLocation = 'eastasia' |
Multiple files found matching pattern *.sql | azure/sql-action accepts only one file | Replace with sqlcmd bash loop |
sqlcmd: command not found (exit 127) | Not pre-installed on ubuntu-24.04 | Install mssql-tools18 via Microsoft apt repo |
gpg: cannot open /dev/tty | gpg --dearmor without --batch in CI | Use gpg --batch --yes --dearmor | sudo tee |
OIDC fails AADSTS70021 | Federated credential subject mismatch | Must match repo:owner/repo:ref:refs/heads/branch exactly |
AZURE_CREDENTIALS auth fails silently | WARNING: text prepended to SP JSON | Strip with 2>/dev/null | python3 pipeline |
| Bicep runs on every push (slow) | No change detection | Add git diff check, conditional steps |
error TS7016: no declaration for 'mssql' | @types/mssql missing | Add "@types/mssql": "^9.1.5" |
| New function returns 404 after deploy | Not imported in api/src/index.ts | Add import './functions/{name}' |
| Functions return 500 on first request | SQL serverless auto-paused | Wait 30–60s, retry |
| Placeholder strings cause cryptic errors | Non-empty placeholders fool if (!value) | Use "" in example files |
az functionapp create creates wrong plan | CLI silently falls back to Y1/Dynamic | Use ARM REST API or Bicep for FC1 |
az appservice plan create --sku FC1 fails | CLI doesn't support FC1 reliably | Use ARM REST API |
| ARM PUT doesn't change hosting plan | Can't migrate existing app | Delete and recreate |
FUNCTIONS_WORKER_RUNTIME causes failure | Forbidden on FC1 | Remove from app settings |
az functionapp cors add returns Bad Request | CLI CORS broken on FC1 | Use ARM REST API |
"main": "dist/functions/*.js" doesn't work | Glob not resolved | Use "main": "dist/index.js" |
Missing package-lock.json breaks CI | cache-dependency-path points to missing file | Commit lock file |
| Publish profile auth 401 on FC1 | Kudu auth different on FC1 | Use SP auth with azure/login@v2 |
| Cold start 15-30s on ACA | Large Docker image | Use Alpine, prune devDeps |
| SSE connections drop after 4 min | Default 240s request timeout | --request-timeout 1800 |
az containerapp update has no effect | Unchanged secret values skip restart | az containerapp revision restart |
| Secrets not available in app | Env var not linked | --set-env-vars "VAR=secretref:secret-name" |
| Docker Hub image not pulled | Rate limit (100/6h anonymous) | Authenticated pulls or move to GHCR/ACR |
DeploymentModelNotSupported (Azure OpenAI) | Model version not available in region | Verify: az cognitiveservices model list --location ... |
EMAIL_FROM unknown before first deploy | Azure-managed domain hash auto-generated | Retrieve post-deploy with az communication email domain show |
| Email send crashes HTTP handler | pollUntilDone() throws | Use safeSend() wrapper |
| ACS resources fail with location error | Microsoft.Communication/* requires location: 'global' | Hardcode location: 'global' |
ACS dataLocation fails | Uses plain English, not region IDs | dataLocation: 'Australia' |
| ACS circular dependency | linkedDomains + dependsOn conflict | Declare order: emailService → domain → acs |
403 on roleAssignments | OIDC SP only has Contributor | Grant User Access Administrator at RG scope |
listSecrets output warning | Bicep linter flags secrets in outputs | #disable-next-line outputs-should-not-contain-secrets |
| SWA self-referencing URL needed | APP_BASE_URL unknown before first deploy | Use 'https://${swa.properties.defaultHostname}' |
| Can't test before Azure provisioned | No mock pattern | Check if (!process.env.KEY) → return mock |
local.settings.json placeholder strings | Fake strings are truthy | Use "" for all user-input values |
| SQL Serverless bill higher than expected; DB never pauses | Health endpoint or scheduler polls the DB, keeping it awake 24/7 | DB-free shallow health check; or switch to flat Basic tier (~$5/mo). See cost-guardrails Guardrail #11 |
For the full catalogue with explanations, see references/gotchas.md.
When to delegate to Microsoft's azure-diagnostics
This skill is a static catalogue — known failure modes with known fixes. For dynamic failures, delegate:
| Symptom | Use Microsoft's skill |
|---|---|
| "My deployed app returns 500 — what's in the logs?" | azure-diagnostics + Azure MCP for live log queries |
| "Performance is slow — what's the bottleneck?" | azure-diagnostics + appinsights-instrumentation |
| "What's running in my subscription right now?" | azure-resource-lookup |
| "Why is this resource costing so much?" | azure-cost |
See composition-with-azure-diagnostics.md.
General rules
- Template + architecture must stay in sync — when behaviour changes, update the templates in the same commit.
- Always add
@types/*for packages that don't bundle their own.d.tsfiles. - GPG in CI always needs
--batch --yesand pipe throughsudo tee. - Verify Azure OpenAI / Cognitive model versions per region before writing Bicep.
- Every new SWA function must be imported in
index.ts— compilation and deployment alone are insufficient. - ACS resources are always
location: 'global'regardless of where the RG is. - Email failures should log, not crash — use
safeSend()wrapper. - Conditional Bicep saves 3–5 min per code-only deploy.
Composes with
- curating-azure-deployment-learnings — capture new gotchas as you find them
- Microsoft's
azure-diagnostics— live log/metric queries - Microsoft's
appinsights-instrumentation— adding telemetry to a running app - Microsoft's
azure-resource-lookup— "what's actually deployed"
What ships with it: 2 files
12.7 KB alongside SKILL.md
references/
- composition-with-azure-diagnostics.md2.4 KB
- gotchas.md10.3 KB