A RetroSearch Logo

Home - News ( United States | United Kingdom | Italy | Germany ) - Football scores

Search Query:

Showing content from https://docs.sentry.io/platforms/python/tracing/span-lifecycle/ below:

Span Lifecycle | Sentry for Python

Span Lifecycle Learn how to add attributes to spans in Sentry to monitor performance and debug applications.

To capture transactions and spans customized to your organization's needs, you must first set up tracing.

To add custom performance data to your application, you need to add custom instrumentation in the form of spans. Spans are a way to measure the time it takes for a specific action to occur. For example, you can create a span to measure the time it takes for a function to execute.

Span Lifecycle

In Python, spans are typically created using a context manager, which automatically manages the span's lifecycle. When you create a span using a context manager, the span automatically starts when entering the context and ends when exiting it. This is the recommended approach for most scenarios.

Copied

import sentry_sdk


with sentry_sdk.start_span(op="task", name="Create User"):
    
    
    user = create_user(email="user@example.com")
    send_welcome_email(user)
    

You can call the context manager's __enter__ and __exit__ methods to more explicitly control the span's lifecycle.

Span Context and Nesting

When you create a span, it becomes the child of the current active span. This allows you to build a hierarchy of spans that represent the execution path of your application:

Copied

import sentry_sdk

with sentry_sdk.start_span(op="process", name="Process Data"):
    

    with sentry_sdk.start_span(op="task", name="Validate Input"):
        
        validate_data()

    with sentry_sdk.start_span(op="task", name="Transform Data"):
        
        transform_data()
Span Starting Options

The following options can be used when creating spans:

Option Type Description op string The operation of the span. name string The name of the span. start_timestamp datetime/float The start time of the span. Using the Context Manager

For most scenarios, we recommend using the context manager approach with sentry_sdk.start_span(). This creates a new span that automatically starts when entering the context and ends when exiting it.

Copied

import sentry_sdk

with sentry_sdk.start_span(op="db", name="Query Users") as span:
    
    users = db.query("SELECT * FROM users")

    
    span.set_data("user_count", len(users))

The context manager also correctly handles exceptions, marking the span as failed if an exception occurs:

Copied

import sentry_sdk

try:
    with sentry_sdk.start_span(op="http", name="Call External API"):
        
        response = requests.get("https://api.example.com/data")
        response.raise_for_status()
except Exception:
    
    pass
Getting the Current Span

You can access the currently active span using sentry_sdk.get_current_span():

Copied

import sentry_sdk


current_span = sentry_sdk.get_current_span()
if current_span:
    current_span.set_data("key", "value")
Working with Transactions

Transactions are a special type of span that represent a complete operation in your application, such as a web request. You can create transactions explicitly:

Copied

import sentry_sdk

with sentry_sdk.start_transaction(name="Background Task", op="task") as transaction:
    

    
    with sentry_sdk.start_span(op="subtask", name="Data Processing"):
        
        pass
Improving Span Data Adding Span Attributes

Span attributes customize information you can get through tracing. This information can be found in the traces views in Sentry, once you drill into a span. You can capture additional context with span attributes. These can be key-value pairs of various Python types.

Copied

import sentry_sdk

with sentry_sdk.start_span(op="db", name="Query Users") as span:
    
    users = db.query("SELECT * FROM users WHERE active = true")

    
    span.set_data("result_count", len(users))

You can also add attributes to an existing span:

Copied

import sentry_sdk


span = sentry_sdk.get_current_span()
if span:
    
    span.set_data("user_id", user.id)
    span.set_data("request_size", len(request.body))
Adding Attributes to All Spans

To add attributes to all spans, use the before_send_transaction callback:

Copied

import sentry_sdk
from sentry_sdk.types import Event, Hint

def before_send_transaction(event: Event, hint: Hint) -> Event | None:
    
    if "trace" in event.get("contexts", {}):
        if "data" not in event["contexts"]["trace"]:
            event["contexts"]["trace"]["data"] = {}

        event["contexts"]["trace"]["data"].update({
            "app_version": "1.2.3",
            "environment_region": "us-west-2"
        })

    
    for span in event.get("spans", []):
        if "data" not in span:
            span["data"] = {}

        span["data"].update({
            "component_version": "2.0.0",
            "deployment_stage": "production"
        })

    return event

sentry_sdk.init(
    
    before_send_transaction=before_send_transaction
)
Adding Span Operations ("op")

Spans can have an operation associated with them, which helps Sentry understand the context of the span. For example, database related spans have the db operation, while HTTP requests use http.client.

Sentry maintains a list of well-known span operations that you should use when applicable:

Copied

import sentry_sdk


with sentry_sdk.start_span(op="http.client", name="Fetch User Data"):
    response = requests.get("https://api.example.com/users")


with sentry_sdk.start_span(op="db", name="Save User"):
    db.execute(
        "INSERT INTO users (name, email) VALUES (%s, %s)",
        (user.name, user.email),
    )


with sentry_sdk.start_span(op="file.read", name="Read Config"):
    with open("config.json", "r") as f:
        config = json.load(f)
Updating the Span Status

You can update the status of a span to indicate whether it succeeded or failed:

Copied

import sentry_sdk

with sentry_sdk.start_span(op="task", name="Process Payment") as span:
    try:
        result = process_payment(payment_id)
        if result.success:
            
            span.set_status("ok")
        else:
            
            span.set_status("error")
            span.set_data("error_reason", result.error)
    except Exception:
        
        raise
Help improve this content
Our documentation is open source and available on GitHub. Your contributions are welcome, whether fixing a typo (drat!) or suggesting an update ("yeah, this would be better").

RetroSearch is an open source project built by @garambo | Open a GitHub Issue

Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo

HTML: 3.2 | Encoding: UTF-8 | Version: 0.7.4