Skip to content

Integration SqlClient Extension

aryehcitron@gmail.com edited this page May 17, 2026 · 5 revisions

The Kronikol.Extensions.SqlClient package adds SQL Server operation tracking to your test diagrams via Microsoft.Data.SqlClient's built-in DiagnosticSource instrumentation. No production code changes required.

Zero production changes. SqlClient emits diagnostic events automatically. This extension subscribes to them globally, so every SqlConnection in the process is tracked.


How It Works

Microsoft.Data.SqlClient publishes DiagnosticSource events under "SqlClientDiagnosticListener". The SqlClientDiagnosticTracker subscribes and handles both modern (WriteCommandBefore/WriteCommandAfter) and legacy (ExecuteReader.Start/ExecuteReader.Stop) event naming patterns. Commands are correlated via OperationId GUID, classified by UnifiedSqlClassifier, and logged to RequestResponseLogger.


Install

dotnet add package Kronikol.Extensions.SqlClient

Setup

Option A — Dependency Injection

services.AddSqlServerTestTracking(options =>
{
    options.Verbosity = SqlTrackingVerbosityLevel.Detailed;
});

Option B — Static (No DI)

SqlClientTestTracking.EnsureTracking(new SqlClientTrackingOptions
{
    Verbosity = SqlTrackingVerbosityLevel.Detailed
});

// In teardown:
SqlClientTestTracking.Reset();

Configuration

Property Default Description
ServiceName "SQL Server" Participant name in diagrams
Verbosity Detailed Raw, Detailed, or Summarised
LogSqlText false Include full SQL text in Detailed mode
LogParameters false Include parameter values
DependencyCategory "SqlServer" Controls participant shape/colour
UriScheme "sqlserver" URI scheme in diagram URIs
LogResponseContent true Include response data in diagram arrows at all verbosity levels (v2.37.0+)
MaxResponseRows 5 Maximum rows to capture in response content
MaxValueDisplayLength 500 Truncate individual cell values beyond this length
ResponseDetail RowCountAndColumns RowCountOnly, RowCountAndColumns, or FullRows

All options inherit from SqlTrackingOptionsBase.


Verbosity Levels

Level Arrow label URI
Raw Full SQL text sqlserver://host/database
Detailed SELECT FROM Users sqlserver://host/database/Users
Summarised SELECT sqlserver:///database/Users

Response Payload Capture (v2.37.0+)

Response arrows in diagrams now show actual data instead of being empty. The ResponseDetail option controls the level of detail:

ResponseDetail Example output
RowCountOnly 3 rows
RowCountAndColumns (default) 3 rows [Name, Preference, CreatedAt]
FullRows JSON row preview (up to MaxResponseRows)

Set LogResponseContent = false to restore previous empty-arrow behaviour.


Wrapping Alternative (v2.37.0+)

In addition to the zero-change DiagnosticSource approach above, the SqlClient extension also provides a connection-wrapping approach. This is useful when DiagnosticSource instrumentation is unavailable, disabled, or when you need response payload capture from ExecuteReader/ExecuteScalar.

Classes

Class Wraps Purpose
TrackingSqlConnection SqlConnection Intercepts command creation and transaction begin
TrackingSqlCommand SqlCommand Intercepts ExecuteReader, ExecuteNonQuery, ExecuteScalar (sync + async)
TrackingSqlTransaction SqlTransaction Logs BEGIN, COMMIT, ROLLBACK

Extension Method

using Microsoft.Data.SqlClient;
using Kronikol.Extensions.SqlClient;

var connection = new SqlConnection(connectionString)
    .WithTestTracking(new SqlClientTrackingOptions
    {
        ServiceName = "SQL Server",
        Verbosity = SqlTrackingVerbosityLevel.Detailed,
        CurrentTestInfoFetcher = CurrentTestInfo.Fetcher
    });

SqlConnection.WithTestTracking() returns a TrackingSqlConnection (which extends DbConnection), so it works transparently with any code that accepts DbConnection — including Dapper, raw ADO.NET, and DI registrations.

DI Registration

builder.ConfigureTestServices(services =>
{
    services.AddScoped<DbConnection>(sp =>
    {
        var inner = new SqlConnection(connectionString);
        return inner.WithTestTracking(new SqlClientTrackingOptions
        {
            ServiceName = "SQL Server",
            Verbosity = SqlTrackingVerbosityLevel.Detailed,
            CurrentTestInfoFetcher = CurrentTestInfo.Fetcher
        });
    });
});

DiagnosticSource vs Wrapping: The DiagnosticSource approach (Option A/B above) requires zero production code changes but cannot capture response payloads. The wrapping approach captures response data from ExecuteReader and ExecuteScalar, but requires the connection to be wrapped. Choose based on your needs — you can use both in the same project for different connections.

Home


Demo


Getting Started

Common Tasks

Integration Guides

Extensions

Configuration

Features

Reference

Clone this wiki locally