MCPInstall

sentry-span-streaming-python

Migrate Python SDK to Sentry span streaming (span-first trace lifecycle). Use when asked to "enable span streaming", "migrate to span streaming", "use tracelifecycle stream", or switch from transaction-based to streamed span delivery in a Python project.

Installs
472
Last 24h
—
Trending rank
—
Security
Not audited

Install

Works with every agent the skills CLI supports.

npx skills add https://github.com/getsentry/sentry-for-ai --skill sentry-span-streaming-python
  1. 01

    Install

    Run the command in your project. The CLI asks which agents to install for.

  2. 02

    Describe the task

    Ask your agent for something this skill covers. It loads sentry-span-streaming-python automatically when relevant.

  3. 03

    Review the result

    The agent follows the SKILL.md steps, scripts and references bundled with the skill.

SKILL.md

The instructions your agent reads when the skill is triggered.

All Skills > Feature Setup > Span Streaming (Python)

Sentry Span Streaming Migration (Python)

Migrate from the default transaction-based trace lifecycle (static) to span streaming (stream), where spans are sent individually as they complete instead of being batched into a transaction at the end.

This skill covers the Python SDK. For JavaScript, see Span Streaming (JavaScript). For Dart/Flutter, see Span Streaming (Dart).

Invoke This Skill When

  • User asks to "enable span streaming" or "migrate to span streaming" in a Python project
  • User wants to switch from transaction-based to streamed span delivery
  • User mentions trace_lifecycle, sentry_sdk.traces, or the new start_span API
  • User wants lower latency span delivery or per-span processing

Detect Environment

# Find sentry_sdk.init calls
grep -rn "sentry_sdk\.init\|sentry_sdk\.init(" --include="*.py" -l 2>/dev/null | head -20

# Find existing start_span / start_transaction / start_child usage
grep -rn "start_span\|start_transaction\|start_child" --include="*.py" -l 2>/dev/null | head -20

# Find trace decorator usage
grep -rn "@trace\|from sentry_sdk import trace\|from sentry_sdk.tracing import trace" --include="*.py" -l 2>/dev/null | head -20

# Find continue_trace usage
grep -rn "continue_trace" --include="*.py" -l 2>/dev/null | head -20

# Find before_send_transaction usage
grep -rn "before_send_transaction" --include="*.py" -l 2>/dev/null | head -20

# Find direct Span / Transaction class imports
grep -rn "from sentry_sdk.tracing import\|from sentry_sdk import.*Span\|from sentry_sdk import.*Transaction" --include="*.py" -l 2>/dev/null | head -20

# Find set_data / set_tag / set_context on spans
grep -rn "set_data\|set_tag\|set_context" --include="*.py" -l 2>/dev/null | head -20

# Find scope.span / scope.transaction / containing_transaction access
grep -rn "scope\.span\|scope\.transaction\|containing_transaction" --include="*.py" -l 2>/dev/null | head -20

# Find get_trace_context usage
grep -rn "get_trace_context" --include="*.py" -l 2>/dev/null | head -20

Parallelization

After detecting the environment, assess how many files need changes. If the codebase has many files to migrate (e.g. dozens of files with start_span, start_transaction, set_data, etc.), launch subagents to handle independent migration tasks in parallel — for example, one subagent per migration category (span creation, span data, trace propagation) or per module/package. Each subagent should receive the relevant migration rules from this skill and operate on a distinct set of files.

Enable Span Streaming

Prerequisites: sentry-sdk >=2.66.0 with tracing enabled (traces_sample_rate or traces_sampler configured).

Add the top-level trace_lifecycle option in ALL occurences of sentry_sdk.init():

import sentry_sdk

# Before
sentry_sdk.init(
    dsn="...",
    traces_sample_rate=1.0,
)

# After
sentry_sdk.init(
    dsn="...",
    traces_sample_rate=1.0,
    trace_lifecycle="stream",
)

Span streaming requires using the new sentry_sdk.traces.start_span API. The legacy sentry_sdk.start_span and sentry_sdk.start_transaction APIs will not stream spans.

Migrate Span Creation

start_span

Replace sentry_sdk.start_span() with sentry_sdk.traces.start_span():

import sentry_sdk

# Before
with sentry_sdk.start_span(name="flow.checkout") as span:
    ...

# After
with sentry_sdk.traces.start_span(name="flow.checkout") as span:
    ...

Or change the import:

# Before
from sentry_sdk import start_span

# After
from sentry_sdk.traces import start_span

The new API accepts:

  • name (required)
  • attributes — key-value pairs (see Migrate Span Data below)
  • parent_span — explicit parent span; defaults to the currently active span
  • active — defaults to True; if False, the span won't become other spans' parent automatically

The description argument no longer exists — use name instead. The op argument is no longer supported — use the sentry.op attribute instead:

# Before
with sentry_sdk.start_span(op="http.client", description="GET /api/users") as span:
    ...

# After
with sentry_sdk.traces.start_span(
    name="GET /api/users",
    attributes={"sentry.op": "http.client"},
) as span:
    ...

start_transaction

Replace sentry_sdk.start_transaction() with sentry_sdk.traces.start_span():

import sentry_sdk

# Before
with sentry_sdk.start_transaction(name="flow.checkout") as transaction:
    ...

# After
with sentry_sdk.traces.start_span(name="flow.checkout", parent_span=None) as span:
    ...

Setting parent_span=None forces the span to become a root span, which is the equivalent of starting a transaction in the legacy API.

start_child

span.start_child() no longer exists. Start a new span while the parent is active — it becomes a child automatically:

import sentry_sdk

# Before
with sentry_sdk.start_span(name="outer") as parent:
    with parent.start_child(op="db", description="SELECT") as child:
        ...

# After
with sentry_sdk.traces.start_span(name="outer") as parent:
    with sentry_sdk.traces.start_span(
        name="SELECT",
        attributes={"sentry.op": "db"},
    ):
        ...

To control parentage explicitly (e.g. make a span a sibling rather than a child), use parent_span:

with sentry_sdk.traces.start_span(name="outer") as span:
    with sentry_sdk.traces.start_span(name="child 1"):
        with sentry_sdk.traces.start_span(name="child 2", parent_span=span):
            # "child 2" is a sibling of "child 1", not its child
            ...

@trace Decorator

Replace sentry_sdk.trace with sentry_sdk.traces.trace:

# Before
from sentry_sdk import trace

@trace
def checkout():
    ...

# After — just change the import
from sentry_sdk.traces import trace

@trace
def checkout():
    ...

The new decorator also accepts optional name (defaults to the function name), attributes, and active arguments:

from sentry_sdk.traces import trace

@trace(name="checkout", attributes={"flow.pipeline": "legacy"})
def checkout():
    ...

get_current_span

Replace sentry_sdk.get_current_span() with sentry_sdk.traces.get_current_span():

# Before
from sentry_sdk import get_current_span

span = get_current_span()

# After
from sentry_sdk.traces import get_current_span

span = get_current_span()

scope.span and scope.transaction

If the code accesses the current span or transaction through the scope object, migrate to the new APIs:

import sentry_sdk

# Before
scope = sentry_sdk.get_current_scope()
current_span = scope.span

# After
current_span = sentry_sdk.traces.get_current_span()
import sentry_sdk

# Before
scope = sentry_sdk.get_current_scope()
transaction = scope.transaction

# After
root_span = sentry_sdk.traces.get_current_span()._segment

_segment returns the root span of the current trace (the equivalent of what used to be the transaction). It is a private API — prefer restructuring the code to avoid needing the root span where possible.

span.containing_transaction

span.containing_transaction no longer exists. Use span._segment to get the root span:

# Before
transaction = span.containing_transaction

# After
root_span = span._segment

Span and Transaction Classes

If the code imports Span or Transaction directly (e.g. for type annotations), replace both with StreamedSpan:

# Before
from sentry_sdk.tracing import Span, Transaction

def process(span: Span) -> None:
    ...

# After
from sentry_sdk.traces import StreamedSpan

def process(span: StreamedSpan) -> None:
    ...

get_trace_context

span.get_trace_context() no longer exists on streaming spans. Migrate based on what you actually need from the trace context:

If the code only reads specific fields (like trace_id, span_id, or parent_span_id), access them directly as span properties:

# Before
ctx = span.get_trace_context()
trace_id = ctx["trace_id"]
span_id = ctx["span_id"]

# After
trace_id = span.trace_id
span_id = span.span_id

If the code genuinely needs the full trace context dict (e.g. to pass it to an external system or serialize it), use the private method span._get_trace_context():

# Before
ctx = span.get_trace_context()

# After
ctx = span._get_trace_context()

Prefer the direct property access where possible — _get_trace_context() is a private API and may change.

Migrate Span Data

In span streaming mode, spans have no contexts, data, or tags. Everything is a span attribute. Attribute keys are strings; values must be int, bool, str, float, or an array of these types. None is not supported.

Important: Unlike the old set_data / set_tag APIs, set_attribute only supports primitive types. Non-primitive values must be either stringified or broken down into multiple primitive-typed attributes:

# Before — set_data accepted any type
span.set_data("request", {"method": "POST", "path": "/api/checkout"})
span.set_data("response_headers", response.headers)

# After — flatten dicts into separate attributes
span.set_attributes({
    "request.method": "POST",
    "request.path": "/api/checkout",
})

# After — stringify objects that can't be flattened
span.set_attribute("response_headers", str(response.headers))

Replace set_data

# Before
span.set_data("flow.step", "submit_payment")

# After
span.set_attribute("flow.step", "submit_payment")

Replace set_tag

# Before
span.set_tag("http.status_code", 201)

# After
span.set_attribute("http.response.status_code", 201)

When migrating multiple consecutive set_data / set_tag calls, combine them into a single set_attributes() call:

# Before
span.set_data("flow.step", "submit_payment")
span.set_data("flow.version", "0.35")
span.set_tag("http.status_code", 201)

# After
span.set_attributes({
    "flow.step": "submit_payment",
    "flow.version": "0.35",
    "http.response.status_code": 201,
})

Replace set_context

Dictionaries are not supported as attribute values. Flatten them into separate attributes:

# Before
span.set_context("flow", {"id": "123456789", "pipeline": "legacy"})

# After
span.set_attributes({"flow.id": "123456789", "flow.pipeline": "legacy"})

Scope-Level Tags

Tags set on the scope with sentry_sdk.set_tag() are not applied to streaming spans. Use sentry_sdk.set_attribute() to apply data to spans:

import sentry_sdk

sentry_sdk.set_tag("region", "Europe")       # applied to errors and other tag-supporting telemetry
sentry_sdk.set_attribute("region", "Europe")  # applied to spans, logs, metrics

Bulk Operations

with sentry_sdk.traces.start_span(name="flow.checkout") as span:
    span.set_attribute("flow.version", "0.35")
    span.set_attributes({"flow.conversion": 1.0, "flow.use_new_pipeline": True})
    span.remove_attribute("flow.conversion")

Span Status

Status can only be ok (default) or error:

from sentry_sdk.traces import start_span

with start_span(name="process") as span:
    try:
        ...
    except Exception:
        span.status = "error"

Migrate Trace Propagation

sentry_sdk.traces.continue_trace() replaces the legacy sentry_sdk.continue_trace(). It is no longer a context manager — it sets the propagation context, and the next span picks it up automatically:

import sentry_sdk

headers = {
    "sentry-trace": "4bf92f3577b34da6a3ce929d0e0e4736-00f067aa0ba902b7-1",
    "baggage": "sentry-trace_id=...",
}

# Before
with sentry_sdk.continue_trace(headers) as transaction:
    ...

# After
sentry_sdk.traces.continue_trace(headers)
with sentry_sdk.traces.start_span(name="handle request"):
    ...

To start a completely new trace, use sentry_sdk.traces.new_trace():

import sentry_sdk

with sentry_sdk.traces.start_span(name="span in trace 1"):
    ...

sentry_sdk.traces.new_trace()

with sentry_sdk.traces.start_span(name="span in trace 2"):
    # This span is the root of a new, separate trace
    ...

Migrate Sampling

If you use traces_sample_rate, no changes are needed — it works the same way.

If you use a custom traces_sampler, the sampling context has a different structure in streaming mode:

def traces_sampler(sampling_context):
    # sampling_context["span_context"] contains:
    #   name, trace_id, parent_span_id, parent_sampled, attributes
    if sampling_context["span_context"]["name"] in IGNORED_SPAN_NAMES:
        return 0.0
    return 1.0

sentry_sdk.init(
    traces_sampler=traces_sampler,
    trace_lifecycle="stream",
)

The sampling decision is made when start_span() is called. Child spans inherit the parent's sampling decision unless filtered by ignore_spans.

Custom Sampling Context

Custom sampling context is no longer an argument to start_span. Set it on the scope before starting the span:

import sentry_sdk

def traces_sampler(sampling_context):
    if sampling_context["asgi_scope"].method not in ("GET", "POST"):
        return 0.0
    return 1.0

# Before
with sentry_sdk.start_span(
    name="handle request",
    custom_sampling_context={"asgi_scope": asgi_scope},
):
    ...

# After
sentry_sdk.Scope.set_custom_sampling_context({"asgi_scope": asgi_scope})
with sentry_sdk.traces.start_span(name="handle request"):
    ...

Custom sampling context must be set after continue_trace (which resets propagation context) and before start_span (which is when sampling happens).

Configure ignore_spans (Optional)

ignore_spans filters spans at creation time. Rules can be strings, compiled regexes, or dictionaries with name and/or attributes conditions:

import re
import sentry_sdk

sentry_sdk.init(
    trace_lifecycle="stream",
    ignore_spans=[
        # String match against span name
        "/health",

        # Regex match against span name
        re.compile(r"/flow/.*"),

        # Match by attributes (all must match)
        {
            "attributes": {
                "service.id": "15def9a",
                "flow.pipeline": "legacy",
            }
        },

        # Match by name and attributes
        {
            "name": re.compile(r"/flow/.*"),
            "attributes": {
                "service.id": re.compile(r".*\.facade"),
            },
        },
    ],
)

ignore_spans only takes effect when trace_lifecycle="stream" is enabled. If it is set without span streaming, the SDK emits a warning and the option is ignored.

Only the span name and attributes set at creation time are available for matching — attributes added later in the span's lifetime are not considered.

If an ignored span is a top-level span, its entire subtree is also ignored. If a non-top-level span is ignored, its children are not automatically ignored unless they match a rule themselves.

Migrate before_send_transaction

before_send_transaction has no effect in streaming mode. Spans are sent individually as they complete, not batched into transactions.

Important: In the legacy transaction-based model, before_send_transaction ran after the entire transaction finished, so it had access to all data set during the span's lifetime (e.g. HTTP status codes, response sizes, final results). In streaming mode, the replacements (ignore_spans and before_send_span) can only work with attributes set at span start time. Attributes added later during the span's lifetime (like http.response.status_code, response body size, or other late-set data) are not available.

If your before_send_transaction logic depends on attributes not set at span start, that filtering logic cannot be replicated in streaming mode and must be removed. Consider moving such filtering to a server-side mechanism (e.g. Sentry inbound data filters or Relay rules) instead.

Use CaseStreaming Replacement
Drop spans by name/routeUse ignore_spans
Drop/filter by late-set attributes (e.g. HTTP status code)Cannot be replicated — remove the logic or use server-side filtering
Modify span data before sendUse before_send_span
Filter by transaction nameUse ignore_spans with string/regex pattern

Remove the before_send_transaction option from sentry_sdk.init() after migrating its logic.

Configure before_send_span (Optional)

before_send_span lets you modify spans before they leave the SDK, for example to sanitize sensitive values. It receives span and hint arguments and must return a span:

import sentry_sdk

def postprocess_span(span, hint):
    attributes_to_sanitize = [
        "http.request.header.custom-auth",
        "http.request.header.custom-user-id",
    ]
    for attribute in attributes_to_sanitize:
        if span["attributes"].get(attribute):
            span["attributes"][attribute] = "[Sanitized]"
    return span

sentry_sdk.init(
    trace_lifecycle="stream",
    _experiments={
        "before_send_span": postprocess_span,
    },
)

before_send_span cannot be used to drop spans — use ignore_spans for that. If the callback returns anything other than a span dictionary, the return value is ignored.

Verification

Instruct the user to verify:

  1. Check Sentry dashboard: Spans should appear in the Traces view shortly after they complete, without waiting for the full transaction to finish
  2. Check logs: Ensure no SDK warnings about unsupported span operations

Common Issues

SymptomCauseFix
Spans not streamingUsing legacy sentry_sdk.start_spanSwitch to sentry_sdk.traces.start_span
AttributeError on start_childstart_child removed in streaming modeUse sentry_sdk.traces.start_span while parent is active
None attribute value rejectedNone not supported as attribute valueRemove the attribute or use a sentinel string
set_data/set_tag has no effect on spanThese methods don't apply to streaming spansUse span.set_attribute()
Scope tags missing from spansset_tag not applied to streaming spansUse sentry_sdk.set_attribute()
Custom sampling context not available in traces_samplerSet after start_span or before continue_traceSet on scope after continue_trace but before start_span
scope.span returns wrong type or NoneScope-based span access not reliable in streaming modeUse sentry_sdk.traces.get_current_span()
AttributeError on containing_transactionAttribute removed in streaming modeUse span._segment
AttributeError on get_trace_contextMethod removed in streaming modeUse span.trace_id / span.span_id directly, or span._get_trace_context()
before_send_transaction not calledExpected in streaming modeMigrate logic to before_send_span or ignore_spans
Warning: ignore_spans only works with trace_lifecycle set to streamignore_spans set without span streaming enabledEnable streaming with trace_lifecycle="stream", or remove ignore_spans
before_send_transaction logic relied on late-set attributes (e.g. status code)These attributes aren't available at span creation timeRemove the logic or use server-side filtering (Sentry inbound filters / Relay rules)

Quick Reference

Minimal Setup

import sentry_sdk

sentry_sdk.init(
    dsn="__DSN__",
    traces_sample_rate=1.0,
    trace_lifecycle="stream",
)

Creating Spans

from sentry_sdk.traces import start_span

with start_span(name="my operation", attributes={"sentry.op": "task"}) as span:
    span.set_attribute("result.count", 42)

Migration Checklist

  • SDK version is >=2.66.0
  • Added top-level trace_lifecycle="stream" to sentry_sdk.init()
  • sentry_sdk.start_span() migrated to sentry_sdk.traces.start_span()
  • sentry_sdk.start_transaction() migrated to sentry_sdk.traces.start_span()
  • span.start_child() migrated to sentry_sdk.traces.start_span()
  • sentry_sdk.get_current_span() migrated to sentry_sdk.traces.get_current_span()
  • scope.span replaced with sentry_sdk.traces.get_current_span()
  • scope.transaction replaced with sentry_sdk.traces.get_current_span()._segment
  • span.containing_transaction replaced with span._segment
  • @sentry_sdk.trace migrated to @sentry_sdk.traces.trace
  • Span / Transaction class imports replaced with StreamedSpan
  • span.get_trace_context() replaced with direct properties (span.trace_id, etc.) or span._get_trace_context()
  • description replaced with name
  • op replaced with sentry.op attribute
  • set_data() / set_tag() / set_context() replaced with set_attribute()
  • Scope-level set_tag() supplemented with set_attribute() where needed
  • continue_trace migrated to non-context-manager sentry_sdk.traces.continue_trace()
  • custom_sampling_context migrated to Scope.set_custom_sampling_context()
  • (If using traces_sampler) Updated to handle new sampling_context shape
  • before_send_transaction logic migrated to before_send_span or ignore_spans
  • before_send_transaction logic that depends on late-set attributes (e.g. HTTP status code) removed or moved to server-side filtering
  • before_send_transaction removed from config
  • Spans visible in Sentry dashboard

FAQ

What does the sentry-span-streaming-python skill do?

Migrate Python SDK to Sentry span streaming (span-first trace lifecycle). Use when asked to "enable span streaming", "migrate to span streaming", "use tracelifecycle stream", or switch from transaction-based to streamed span delivery in a Python project.

How do I install sentry-span-streaming-python?

Run npx skills add https://github.com/getsentry/sentry-for-ai --skill sentry-span-streaming-python in your project. The skills CLI detects the agents you use and copies the skill into the right folder. For Claude Code you can also place the skill folder at ~/.claude/skills/sentry-span-streaming-python/ (personal) or .claude/skills/sentry-span-streaming-python/ (project).

Which AI agents can use sentry-span-streaming-python?

Any agent that supports the open Agent Skills format (a folder with a SKILL.md file), including Claude Code, Codex, Cursor, GitHub Copilot, Gemini CLI, Windsurf, Cline, OpenCode and more.

Is sentry-span-streaming-python safe to install?

No partner security audit is available yet. Skills can run commands and scripts, so read the SKILL.md and any bundled files before installing.

Who maintains sentry-span-streaming-python?

It is published by getsentry in getsentry/sentry-for-ai. It has 472 recorded installs.

More from getsentry/sentry-for-ai

View all →

sentry-fix-issues

getsentry/sentry-for-ai

Find and fix issues from Sentry using MCP. Use when asked to fix Sentry errors, debug production issues, investigate exceptions, or resolve bugs reported in Sentry. Methodically analyzes stack traces, breadcrumbs, traces, and context to identify root causes.

OfficialDevOps & Cloud10K installs

sentry-react-native-sdk

getsentry/sentry-for-ai

Full Sentry SDK setup for React Native and Expo. Use when asked to "add Sentry to React Native", "install @sentry/react-native", "setup Sentry in Expo", or configure error monitoring, tracing, profiling, session replay, or logging for React Native applications. Supports Expo managed, Expo bare, and vanilla React Native.

OfficialDevOps & Cloud4.1K installs

sentry-create-alert

getsentry/sentry-for-ai

Create Sentry alerts using the workflow engine API. Use when asked to create alerts, set up notifications, configure issue priority alerts, or build workflow automations. Supports email, Slack, PagerDuty, Discord, and other notification actions.

OfficialDevOps & Cloud4.1K installs

sentry-nextjs-sdk

getsentry/sentry-for-ai

Full Sentry SDK setup for Next.js. Use when asked to "add Sentry to Next.js", "install @sentry/nextjs", or configure error monitoring, tracing, session replay, logging, profiling, AI monitoring, or crons for Next.js applications. Supports Next.js 13+ with App Router and Pages Router.

OfficialDevOps & Cloud3.6K installs

sentry-sdk-setup

getsentry/sentry-for-ai

Set up Sentry in any language or framework. Detects the user's platform and loads the right SDK skill. Use when asked to add Sentry, install an SDK, or set up error monitoring in a project.

OfficialDevOps & Cloud3.6K installs

sentry-workflow

getsentry/sentry-for-ai

Keep Sentry SDKs up to date. Use when asked to upgrade the Sentry SDK across major versions, migrate SDK versions, or fix deprecated APIs.

OfficialDevOps & Cloud3.6K installs

Popular devops & cloud skills

View category →

microsoft-foundry

microsoft/azure-skills

Build, deploy, evaluate, optimize, fine-tune, and manage Microsoft Foundry agents, models, and resources end to end. USE FOR: foundry, azd ai agent, azd provision/deploy, hosted agent scaffold/develop/run/deploy/troubleshoot, prompt agent create, managed harness agent create, GitHub Copilot harness agent, create agent, update agent, add tool to agent, invoke agent, agent insights, evaluate agent, batch eval, continuous eval, continuous monitoring, agent CI/CD, optimize prompt, improve prompt, optimize agent instructions, Agent Optimizer scaffold, dataset curation from traces, deploy model, model fine-tuning (SFT/DPO/RFT), Foundry project, RBAC, role assignment, permissions, quota, capacity, region, deployment failure, AI Services, create Foundry resource, knowledge index, customize deployment, onboard, availability, training-data, grader, distillation, large file upload. DO NOT USE FOR: Azure Functions, App Service, general Azure deploy (use azure-deploy), general Azure prep (use azure

OfficialDevOps & Cloud579.1K installs

azure-diagnostics

microsoft/azure-skills

Debug Azure production issues on Azure using AppLens, Azure Monitor, resource health, and safe triage. WHEN: debug production issues, troubleshoot app service, app service high CPU, app service deployment failure, troubleshoot container apps, container app 503 or target port mismatch, troubleshoot functions, function telemetry missing or stopped after a config/connection-string change, troubleshoot AKS, VM RDP, Linux SSH, VM black screen, can't connect to VM, reset VM password, NSG or firewall blocking, kubectl cannot connect, kube-system/CoreDNS failures, pod pending, crashloop, node not ready, upgrade failures, analyze logs, KQL, insights, image pull failures, cold start issues, health probe failures, resource health, root cause of errors, troubleshoot event hubs, troubleshoot service bus, messaging SDK error, AMQP connection failure, message lock lost, lock renewal during long-running processing, service bus dead letter.

OfficialDevOps & Cloud569.8K installs

azure-prepare

microsoft/azure-skills

Prepare azd-based Azure projects for deployment: generates azure.yaml, infrastructure (Bicep/Terraform), and Dockerfiles for the Azure Developer CLI (azd) workflow. USE ONLY when the user explicitly wants to use azd as the deployment tool, or the project already has an azure.yaml file. DO NOT USE FOR: non-azd deployments, Python App Service code-only deploys (use python-appservice-deploy), or cross-cloud migration (use azure-cloud-migrate). WHEN: prepare app for azd, create azure.yaml, set up azd infrastructure, modernize app for Azure with azd, deploy with azd, function app, timer trigger, service bus trigger, event-driven function, managed identity, generate Bicep, generate Terraform, create and deploy to Azure.

OfficialDevOps & Cloud569K installs

azure-ai

microsoft/azure-skills

Use for Azure AI: Search, Speech, OpenAI, Document Intelligence. Helps with search, vector/hybrid search, speech-to-text, text-to-speech, transcription, OCR. WHEN: AI Search, query search, vector search, hybrid search, semantic search, speech-to-text, text-to-speech, transcribe, OCR, convert text to speech.

OfficialDevOps & Cloud568.8K installs

azure-deploy

microsoft/azure-skills

Execute Azure deployments for ALREADY-PREPARED applications that have existing .azure/deployment-plan.md and infrastructure files. DO NOT use this skill when the user asks to CREATE a new application — use azure-prepare instead. This skill runs azd up, azd deploy, terraform apply, and az deployment commands with built-in error recovery. Requires .azure/deployment-plan.md from azure-prepare and validated status from azure-validate. WHEN: "run azd up", "run azd deploy", "execute deployment", "push to production", "push to cloud", "go live", "ship it", "bicep deploy", "terraform apply", "publish to Azure", "launch on Azure". DO NOT USE WHEN: "create and deploy", "build and deploy", "create a new app", "set up infrastructure", "create and deploy to Azure using Terraform" — use azure-prepare for these.

OfficialDevOps & Cloud568.6K installs

azure-validate

microsoft/azure-skills

Pre-deployment validation for Azure readiness. Run deep checks on configuration, infrastructure (Bicep or Terraform), RBAC role assignments, managed identity permissions, and prerequisites before deploying. WHEN: validate my app, check deployment readiness, run preflight checks, verify configuration, check if ready to deploy, validate azure.yaml, validate Bicep, test before deploying, troubleshoot deployment errors, validate Azure Functions, validate function app, validate serverless deployment, verify RBAC roles, check role assignments, review managed identity permissions, what-if analysis, validate Container Apps deployment.

OfficialDevOps & Cloud568K installs