Elven.Observability.Instrumentation.EntityFrameworkCore 0.1.8

There is a newer version of this package available.
See the version list below for details.
dotnet add package Elven.Observability.Instrumentation.EntityFrameworkCore --version 0.1.8
                    
NuGet\Install-Package Elven.Observability.Instrumentation.EntityFrameworkCore -Version 0.1.8
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="Elven.Observability.Instrumentation.EntityFrameworkCore" Version="0.1.8" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="Elven.Observability.Instrumentation.EntityFrameworkCore" Version="0.1.8" />
                    
Directory.Packages.props
<PackageReference Include="Elven.Observability.Instrumentation.EntityFrameworkCore" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add Elven.Observability.Instrumentation.EntityFrameworkCore --version 0.1.8
                    
#r "nuget: Elven.Observability.Instrumentation.EntityFrameworkCore, 0.1.8"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package Elven.Observability.Instrumentation.EntityFrameworkCore@0.1.8
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=Elven.Observability.Instrumentation.EntityFrameworkCore&version=0.1.8
                    
Install as a Cake Addin
#tool nuget:?package=Elven.Observability.Instrumentation.EntityFrameworkCore&version=0.1.8
                    
Install as a Cake Tool

Elven Observability .NET

Production-grade OpenTelemetry bootstrap for modern .NET services on the Elven Observability LGTM stack: Loki, Grafana, Tempo, and Mimir.

This distribution wraps the official OpenTelemetry .NET SDK and OpenTelemetry .NET AutoInstrumentation. It does not replace OpenTelemetry. Elven mode always configures traces, metrics, and logs.

Architecture

Applications send OTLP to a Collector deployed in the customer environment. The customer-side Collector then forwards telemetry to the Elven Observability backends.

.NET app
  -> OTLP gRPC or HTTP/protobuf
  -> customer-side OpenTelemetry Collector
  -> Elven Observability backend
  -> Tempo, Mimir, Loki, Grafana

The package default endpoint is http://localhost:4317, which is the common local/sidecar Collector endpoint. In production, set OTEL_EXPORTER_OTLP_ENDPOINT or ELVEN_OTLP_ENDPOINT to the customer Collector address.

Keep Elven backend credentials in the Collector, not in the application. In the recommended Collector path, the app only needs to know where the customer-side Collector is. The Collector is responsible for adding Authorization: Bearer ... and x-scope-orgid when forwarding to Elven Observability.

Start with the lowest-friction rollout path, then move down only when the service needs code-level customization.

Priority Path Use case
1 Docker zero-code Containerized services where no source change is desired.
2 Process zero-code VMs, systemd, or direct dotnet MyApp.dll deployments.
3 Programmatic hosting ASP.NET Core, Worker Services, and generic hosts that need code-level options.
4 No-host API Console apps, CLIs, and short-lived jobs.

Docker Zero-Code

FROM mcr.microsoft.com/dotnet/aspnet:10.0

COPY --from=elvenobservability/dotnet-instrumentation:latest /otel /otel

ENV CORECLR_ENABLE_PROFILING=1 \
    CORECLR_PROFILER={918728DD-259F-4A6A-AC2B-B85E1B658318} \
    CORECLR_PROFILER_PATH=/otel/current/OpenTelemetry.AutoInstrumentation.Native.so \
    DOTNET_ADDITIONAL_DEPS=/otel/AdditionalDeps \
    DOTNET_SHARED_STORE=/otel/store \
    DOTNET_STARTUP_HOOKS=/otel/net/OpenTelemetry.AutoInstrumentation.StartupHook.dll \
    OTEL_DOTNET_AUTO_HOME=/otel \
    OTEL_DOTNET_AUTO_PLUGINS="Elven.Observability.AutoInstrumentation.ElvenPlugin, Elven.Observability.AutoInstrumentation" \
    OTEL_TRACES_EXPORTER=otlp \
    OTEL_METRICS_EXPORTER=otlp \
    OTEL_LOGS_EXPORTER=otlp \
    OTEL_EXPORTER_OTLP_PROTOCOL=grpc \
    OTEL_DOTNET_AUTO_SQLCLIENT_SET_DBSTATEMENT_FOR_TEXT=true \
    OTEL_DOTNET_AUTO_ENTITYFRAMEWORKCORE_SET_DBSTATEMENT_FOR_TEXT=true \
    OTEL_DOTNET_AUTO_ORACLEMDA_SET_DBSTATEMENT_FOR_TEXT=true

WORKDIR /app
COPY . /app
ENTRYPOINT ["dotnet", "/app/MyApp.dll"]

Runtime configuration:

docker run --rm \
  -e OTEL_SERVICE_NAME=billing-api \
  -e OTEL_SERVICE_VERSION=1.0.0 \
  -e ELVEN_SERVICE_NAMESPACE=payments \
  -e ELVEN_ENVIRONMENT=production \
  -e OTEL_EXPORTER_OTLP_ENDPOINT=http://otel-collector.observability.svc.cluster.local:4317 \
  -e OTEL_EXPORTER_OTLP_PROTOCOL=grpc \
  -e OTEL_TRACES_EXPORTER=otlp \
  -e OTEL_METRICS_EXPORTER=otlp \
  -e OTEL_LOGS_EXPORTER=otlp \
  my-app:latest

Database statements are collected by default when the underlying .NET instrumentation supports them. Elven redacts db.statement, db.query.text, and database query parameter attributes to [REDACTED] before export, while keeping safe attributes such as db.query.summary, db.operation.name, db.system.name, duration, status, and errors.

Process Zero-Code

./scripts/install.sh
. "$HOME/.otel-dotnet-auto/instrument.sh"

export OTEL_DOTNET_AUTO_PLUGINS="Elven.Observability.AutoInstrumentation.ElvenPlugin, Elven.Observability.AutoInstrumentation"
export OTEL_SERVICE_NAME=billing-api
export OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4317
export OTEL_EXPORTER_OTLP_PROTOCOL=grpc
export OTEL_TRACES_EXPORTER=otlp
export OTEL_METRICS_EXPORTER=otlp
export OTEL_LOGS_EXPORTER=otlp

dotnet Billing.Api.dll

Programmatic Setup

Install:

dotnet add package Elven.Observability

ASP.NET Core:

var builder = WebApplication.CreateBuilder(args);

builder.AddElvenObservability(options =>
{
    options.ServiceName = "billing-api";
    options.ServiceNamespace = "payments";
    options.Endpoint = new Uri("http://localhost:4317");
    options.SamplingRatio = 1.0;
});

var app = builder.Build();
app.UseElvenObservability();
app.MapElvenObservabilityHealthCheck();
app.Run();

Generic Host / Worker:

var builder = Host.CreateApplicationBuilder(args);
builder.AddElvenObservability();
await builder.Build().RunAsync();

Console / No Host:

await using var observability = ElvenObservability.Initialize(options =>
{
    options.ServiceName = "batch-job";
});

using var activity = ElvenTelemetry.ActivitySource.StartActivity("job.run");
ElvenTelemetry.Meter.CreateCounter<long>("jobs.started").Add(1);
observability.LoggerFactory.CreateLogger("Batch.Job").LogInformation("Job started.");
await observability.ForceFlushAsync();

WCF And CoreWCF

Elven.Observability includes WCF client and CoreWCF server instrumentation. Use 0.1.8 or newer for CoreWCF inbound spans in production migrations.

Use this when a modern .NET service still calls SOAP/WCF dependencies, or when a migrated service exposes SOAP endpoints through CoreWCF. The instrumentation never captures SOAP payloads by default. It captures operation metadata, latency, status/fault information, exceptions, correlation, and W3C propagation.

Captured WCF attributes include:

  • rpc.system=wcf
  • rpc.service
  • rpc.method
  • wcf.contract
  • wcf.action
  • wcf.binding
  • wcf.endpoint
  • wcf.route / http.route
  • url.path
  • server.address
  • http.response.status_code
  • wcf.is_fault
  • correlation_id
  • error.category and error.type when an error is detected

WCF client:

using Elven.Observability.Instrumentation.Wcf;

var client = new AereoClient(binding, endpoint);
client.AddElvenObservability(
    serviceName: "dsg-servicos-web",
    bindingName: "basicHttp");

var response = await client.DisponibilidadeAereoAsync(request);

ChannelFactory<T>:

using Elven.Observability.Instrumentation.Wcf;

var factory = new ChannelFactory<IAereo>(binding, endpoint);
factory.AddElvenObservability(
    serviceName: "dsg-servicos-web",
    bindingName: "basicHttp");

var channel = factory.CreateChannel();

CoreWCF server:

Install the ASP.NET Core middleware package explicitly in CoreWCF hosts:

dotnet add package Elven.Observability --version 0.1.8
dotnet add package Elven.Observability.AspNetCore --version 0.1.8
dotnet add package Elven.Observability.Instrumentation.CoreWcf --version 0.1.8
using Elven.Observability.Instrumentation.CoreWcf;

app.UseServiceModel(serviceBuilder =>
{
    serviceBuilder
        .AddService<AereoService>()
        .AddElvenObservability<AereoService>(
            serviceName: "dsg-servicos-web",
            bindingName: "basicHttp");

    serviceBuilder.AddServiceEndpoint<AereoService, IAereo>(
        new BasicHttpBinding(),
        "/Aereo.svc");
});

BasicHttpBinding and WSHttpBinding(SecurityMode.None) are supported for CoreWCF server instrumentation.

From 0.1.8, UseElvenObservability() also includes a hardened SOAP/.svc fallback. If CoreWCF does not call the dispatch message inspector in a specific hosting shape, the middleware creates an exportable Elven.Observability server span named WCF <contract>/<method> around the SOAP request so downstream SQL, HTTP, and logs are not trace roots. When ASP.NET Core already created Microsoft.AspNetCore.Hosting.HttpRequestIn, the fallback creates the WCF span as a child of that request activity instead of relying on the HTTP activity itself to be exported. When the inspector does run later in the CoreWCF pipeline, it reuses and enriches the active WCF span instead of creating a duplicate. The fallback uses request metadata such as path, SOAPAction, Content-Type action, traceparent, and correlation headers. It does not read or export SOAP/XML payloads.

Manual fallback for unusual bindings:

using Elven.Observability.Instrumentation.Wcf;

using var span = ElvenWcfManual.StartOperation(
    service: "dsg-servicos-web",
    contract: "IAereo",
    operation: "DisponibilidadeAereo",
    correlationId: correlationId);

Propagation:

  • Outbound WCF client injects traceparent, tracestate, baggage, and x-correlation-id into SOAP headers and HTTP headers when the binding exposes HTTP message properties.
  • Inbound CoreWCF extracts traceparent, tracestate, baggage, x-correlation-id, and x-request-id from SOAP headers and HTTP headers.
  • If an upstream service sends W3C context, the CoreWCF span keeps the same trace id instead of becoming a new root span.

Kill switches:

ELVEN_ENABLE_WCF=false
ELVEN_ENABLE_COREWCF=false
ELVEN_WCF_CLIENT_ACTIVITY_TIMEOUT_MS=300000

Runtime diagnostics:

Console.WriteLine(ElvenStartupDiagnostics.InstrumentationHookCount);
Console.WriteLine(ElvenStartupDiagnostics.LastInstrumentationHook);
Console.WriteLine(ElvenStartupDiagnostics.InstrumentationFailureCount);
Console.WriteLine(ElvenStartupDiagnostics.LastInstrumentationFailure);

If SQL spans arrive as trace roots and LastInstrumentationHook does not include corewcf.dispatch, the CoreWCF dispatch inspector was not installed.

For fallback checks, LastInstrumentationHook should include:

corewcf.middleware_fallback: <service-name>

Business Telemetry

Install:

dotnet add package Elven.Observability

Use business spans and metrics when the service needs journey-level observability:

using Elven.Observability.Business;
using Elven.Observability.Business.AirTravel;

using var op = ElvenAirTravel.StartAvailability(
    provider: "sabre",
    source: "sabre_bfm",
    correlationId: correlationId);

op.SetStatus("success");
ElvenBusinessMetrics.OperationTotal.Add(1, op.Tags(status: "success"));
ElvenBusinessMetrics.OperationDuration.Record(elapsed, op.Tags(status: "success"));

Business metric labels are intentionally low-cardinality: client, business_context, journey, business.operation, provider, source, supplier, product, status, result, and error.category. Reservation ids, PNRs, tickets, sessions, passengers, and documents must stay out of metric labels.

Air travel helpers cover the customer journey end to end:

ElvenAirTravel.StartOpenSession(provider, source, correlationId);
ElvenAirTravel.StartAvailability(provider, source, correlationId);
ElvenAirTravel.StartPricing(provider, source, correlationId);
ElvenAirTravel.StartReservation(provider, source, correlationId);
ElvenAirTravel.StartPnr(provider, source, correlationId);
ElvenAirTravel.StartPayment(provider, source, correlationId);
ElvenAirTravel.StartAntifraud(provider, source, correlationId);
ElvenAirTravel.StartGateway(provider, source, correlationId);
ElvenAirTravel.StartCancellation(provider, source, correlationId);

See Business telemetry and Business telemetry PT-BR.

Environment Variables

Elven supports standard OpenTelemetry variables plus Elven extensions.

Recommended app-to-Collector variables:

  • ELVEN_ENVIRONMENT: mapped to deployment.environment.name
  • ELVEN_REGION: mapped to elven.region
  • ELVEN_DEBUG: enables verbose internal diagnostics
  • ELVEN_REDACTION_MODE=default|none: default keeps PCI/LGPD redaction enabled
  • ELVEN_LOG_BODY_MODE=redacted|raw: default redacts log bodies structurally
  • ELVEN_MAX_LOG_BODY_CHARS: default 200000
  • ELVEN_ALLOWED_RAW_ATTRIBUTES: exact attribute allowlist for controlled troubleshooting
  • ELVEN_ENABLE_WCF: disables WCF client instrumentation when set to false
  • ELVEN_ENABLE_COREWCF: disables CoreWCF server instrumentation when set to false
  • ELVEN_WCF_CLIENT_ACTIVITY_TIMEOUT_MS: marks long-lived WCF client spans as timeout/error when a reply never closes the span before the configured limit

Direct-to-Elven variables, only when the application exports straight to an Elven OTLP gateway instead of a customer-side Collector:

  • ELVEN_TENANT_ID: mapped to x-scope-orgid
  • ELVEN_API_KEY: mapped to Authorization: Bearer ...

When using the customer-side Collector, configure tenant and API key in the Collector exporter instead. If the application still needs tenant metadata as a resource attribute, prefer OTEL_RESOURCE_ATTRIBUTES=elven.tenant.id=... so the app does not emit backend authentication headers.

Core OpenTelemetry variables:

  • OTEL_SERVICE_NAME
  • OTEL_SERVICE_VERSION
  • OTEL_RESOURCE_ATTRIBUTES
  • OTEL_EXPORTER_OTLP_ENDPOINT
  • OTEL_EXPORTER_OTLP_PROTOCOL=grpc|http/protobuf
  • OTEL_EXPORTER_OTLP_HEADERS
  • OTEL_TRACES_SAMPLER
  • OTEL_TRACES_SAMPLER_ARG
  • OTEL_TRACES_EXPORTER=otlp
  • OTEL_METRICS_EXPORTER=otlp
  • OTEL_LOGS_EXPORTER=otlp

OTEL_TRACES_EXPORTER=none, OTEL_METRICS_EXPORTER=none, OTEL_LOGS_EXPORTER=none, and OTEL_TRACES_SAMPLER=always_off are rejected in Elven mode. Logs, metrics, and traces are always on.

For http/protobuf, OTEL_EXPORTER_OTLP_ENDPOINT=http://collector:4318 is treated as a base endpoint. Elven expands it to /v1/traces, /v1/metrics, and /v1/logs per signal. If you provide a path explicitly, that path is preserved.

Log bodies are redacted by default with XML/JSON-aware structural redaction. Safe trace context fields such as trace_id, span_id, traceparent, and correlation_id are preserved.

Coverage

  • Traces: ASP.NET Core, HttpClient, gRPC client, WCF client, CoreWCF server, SQL Client, EF Core, MongoDB source registration, RabbitMQ/Kafka/MassTransit source registration, AWS/Azure source registration, manual ActivitySource.
  • Metrics: runtime, process, ASP.NET Core/Kestrel, HttpClient, WCF/CoreWCF RPC duration, DNS/TLS/connection meters, Elven internal metrics, trace-based exemplars.
  • Logs: ILogger OTLP exporter, formatted message, scopes, state values, automatic trace/span correlation.
  • Resources: service namespace/version/instance, deployment.environment.name, host, container, Kubernetes, process/runtime, tenant, region.
  • Error mapping: cancellation, timeout, validation, auth, user input, HTTP 4xx/5xx, gRPC status codes, WCF fault/communication/security, DNS, connection refused, network, DB/provider, startup misconfiguration, unhandled exceptions.

Development

dotnet restore
dotnet build Elven.Observability.sln -c Release
dotnet test tests/Elven.Observability.UnitTests/Elven.Observability.UnitTests.csproj -c Release
dotnet pack Elven.Observability.sln -c Release -o artifacts/packages

Native AOT:

dotnet publish samples/NativeAot.WebApi/NativeAot.WebApi.csproj -c Release -r linux-x64

Strict trimming:

dotnet publish samples/NativeAot.WebApi/NativeAot.WebApi.csproj -c Release -r linux-x64 -p:PublishAot=false -p:PublishTrimmed=true -p:SelfContained=true

The facade package is optimized for convenience and broad instrumentation coverage. For strict Native AOT or trim-clean services, compose the lean core/exporter packages as shown in the Native AOT sample and avoid optional instrumentation modules that are not trim-clean in the upstream OpenTelemetry ecosystem.

Build the auto-instrumentation layer:

docker buildx build \
  -f docker/auto-instrumentation/Dockerfile \
  --platform linux/amd64,linux/arm64 \
  -t elvenobservability/dotnet-instrumentation:latest .

Build the OpenTelemetry Operator init-container image:

docker buildx build \
  -f Dockerfile.operator \
  --platform linux/amd64,linux/arm64 \
  -t elvenobservability/dotnet-instrumentation-operator:latest .

Operator setup lives in k8s/otel-operator-instrumentation.yaml. The image follows the OTel Operator .NET contract by exposing /autoinstrumentation with linux-x64 and linux-musl-x64 payloads plus the Elven plugin in /autoinstrumentation/plugins.

Run the local LGTM stack and send the samples to it:

docker compose -f docker-compose.lgtm.yml up -d
export OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4317
export OTEL_EXPORTER_OTLP_PROTOCOL=grpc
export OTEL_SERVICE_NAME=elven-local-sample
dotnet run --project samples/AspNetCore.WebApi/AspNetCore.WebApi.csproj

Open Grafana at http://localhost:3000; the bundled LGTM image receives traces, metrics, and logs over OTLP on 4317 and 4318.

References

  • OpenTelemetry .NET SDK 1.15.3
  • OpenTelemetry .NET AutoInstrumentation 1.15.0
  • OpenTelemetry semantic conventions 1.41.0
  • .NET 8, .NET 9, and .NET 10
Product Compatible and additional computed target framework versions.
.NET net8.0 is compatible.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 is compatible.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 is compatible.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages (1)

Showing the top 1 NuGet packages that depend on Elven.Observability.Instrumentation.EntityFrameworkCore:

Package Downloads
Elven.Observability

Meta-package facade for Elven Observability .NET with always-on OpenTelemetry traces, metrics, logs, OTLP exporters, ASP.NET Core, generic host, and no-host initialization.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
0.1.13 83 8/17/2026
0.1.12 335 7/8/2026
0.1.11 104 7/7/2026
0.1.10 95 7/7/2026
0.1.9 94 7/6/2026
0.1.8 94 7/6/2026
0.1.7 93 7/6/2026
0.1.6 95 7/3/2026
0.1.5 88 7/2/2026
0.1.4 97 7/2/2026
0.1.3 85 7/2/2026
0.1.2 1,370 5/12/2026
0.1.1 108 5/11/2026
0.1.0 363 5/3/2026

Ensures CoreWCF SOAP fallback emits an exportable Elven ActivitySource server span under the active ASP.NET Core request, while preserving WCF tags, metrics, SQL/log parentage, and SOAP POST support.