In this lesson, you will learn how to stitch together raw database query execution metrics with your distributed traces to pinpoint the exact request causing slow database performance.
When a distributed trace shows a "bottleneck" in a database span, it usually only tells you which query ran and how long it took. It doesn’t tell you why that query was slow—was it a missing index, a table scan, or a lock contention? By integrating a database profiler (like pg_stat_statements for PostgreSQL or MongoDB’s explain() output) directly into your tracing spans, you gain deep diagnostic insight without leaving your observability dashboard.
Connecting Profiler Data to Traces
To achieve this, you must correlate the metadata captured by your database driver with the active OpenTelemetry span. When you execute a query, your instrumentation wrapper should capture the database's execution plan or profiling statistics and inject them as span attributes.
Consider this example using a hypothetical database wrapper:
const span = tracer.startSpan('db.query');
try {
const result = await db.query('SELECT * FROM users WHERE email = $1', [email]);
// Capture the profiling info (e.g., execution plan cost)
const profile = await db.query('EXPLAIN (FORMAT JSON) SELECT * FROM users WHERE email = $1', [email]);
// Attach profiler data as a span attribute for the tracing backend
span.setAttribute('db.query.profile.cost', profile[0].Plan.Total_Cost);
span.setAttribute('db.query.profile.is_sequential_scan', profile[0].Plan.Node_Type === 'Seq Scan');
return result;
} catch (error) {
span.setStatus({ code: SpanStatusCode.ERROR });
} finally {
span.end();
}
By attaching these details as attributes, your APM (Application Performance Monitoring) tool can aggregate these metrics. Instead of just seeing that a query took 500ms, you can now filter your traces by db.query.profile.is_sequential_scan = true. This allows you to immediately identify problematic queries across thousands of requests, bridging the gap between high-level service requests and low-level database engine behavior.
Key Takeaway: Integrating database profilers into your spans transforms distributed traces from simple latency trackers into powerful diagnostic tools capable of revealing internal query execution inefficiencies.