Ga naar inhoud

Telemetrie: OpenTelemetry-brug met no-op-terugval

De Telemetry-module vormt de optionele brug tussen de engine en de OpenTelemetry-software development kit (OTel-SDK). Als de SDK is geïnstalleerd, verzendt de module spans en metrieken met gesaneerde attributen. Als de SDK ontbreekt, houdt een volledige set no-op-objecten voor tracer en meter de instrumentatieaanroepen geldig en praktisch kosteloos. Je kunt de instrumentatie veilig in het codepad laten staan.

Terminal window
composer require nextpdf/core:^3

Het ontwerpdoel is observeerbaarheid zonder overhead wanneer de SDK ontbreekt. De hot paths van de engine roepen een tracer en een meter aan zonder vooraf te controleren. Of die aanroepen werk uitvoeren, hangt af van de runtime en niet van een voorwaarde op elke aanroeplocatie.

OpenTelemetryInterceptor is de brug. isAvailable() geeft aan of de OTel-SDK aanwezig is. startSpan(string $name, array $attributes = []) / endSpan(?object $span) omsluiten een getracede bewerking, en recordMetric() registreert een teller- of meterwaarde. Als OTel ontbreekt, geeft de interceptor aan dat hij niet beschikbaar is en blijven de aanroepen inert. TelemetryBridge koppelt de interceptor aan de observatiepunten van de engine.

AttributeSanitizer is de veiligheidslaag. sanitize(array $attributes) schoont de attributenmap op voordat die het proces verlaat. Telemetrieattributen vormen een veelvoorkomend, onbedoeld kanaal voor persoonlijk identificeerbare informatie (PII), dus sanering maakt deel uit van het contract en is geen latere toevoeging. De sanitizer, de interceptor en de brug zijn @since 2.3.0.

NullTracer, NullSpanBuilder, NullSpan, NullMeter, NullCounter en NullHistogram vormen samen de no-op-terugval. Ze ondersteunen dezelfde aanroepvormen als de OTel-SDK: spanBuilder(), setAttribute() (koppelbaar), startSpan(), end(), createHistogram(), createUpDownCounter(), add() en record(). Ze doen niets. Omdat de terugval volledig is, hoeft geïnstrumenteerde code niet op beschikbaarheid te vertakken; die roept de tracer aan en de no-op vangt de aanroep op.

KlasseBelangrijkste ledenRol
OpenTelemetryInterceptorisAvailable(), startSpan(), endSpan(), recordMetric()OTel-brug voor spans en metrieken (@since 2.3.0)
TelemetryBridgeenginekoppelingVerbindt de interceptor met de observatiepunten van de engine (@since 2.3.0)
AttributeSanitizersanitize(array $attributes): arraySchoont attributen op voor PII-veiligheid (@since 2.3.0)
NullTracerspanBuilder(string $name): NullSpanBuilderNo-op-tracer
NullSpanBuildersetAttribute(), startSpan(): NullSpanNo-op-span-builder (koppelbaar)
NullSpanend()No-op-span
NullMetercreateHistogram(), createUpDownCounter()No-op-meter
NullCounter / NullHistogramadd(), record()No-op-instrumenten

Voer composer docs:generate-api-php -- --module=Telemetry uit om de volledige PHPDoc-tabel te genereren.

Bron: examples/33-opentelemetry-observability.php.

<?php
declare(strict_types=1);
require_once __DIR__ . '/../vendor/autoload.php';
use NextPDF\Telemetry\OpenTelemetryInterceptor;
$otel = new OpenTelemetryInterceptor(/* optional OTel tracer/meter */);
$span = $otel->startSpan('pdf.render', ['doc.pages' => 12]);
// ... render work ...
$otel->endSpan($span);
$otel->recordMetric('pdf.render.bytes', 482_113, ['profile' => 'pdfa4']);

Als de OTel-SDK ontbreekt, is elke bovenstaande aanroep een no-op. De code blijft identiek en de kosten zijn nul.

Omhul een renderbewerking met gesaneerde attributen, zodat metadata die door de aanroeper is aangeleverd niet in een span kan lekken.

<?php
declare(strict_types=1);
require_once __DIR__ . '/../vendor/autoload.php';
use NextPDF\Telemetry\AttributeSanitizer;
use NextPDF\Telemetry\OpenTelemetryInterceptor;
final readonly class InstrumentedRenderer
{
public function __construct(
private OpenTelemetryInterceptor $otel,
private AttributeSanitizer $sanitizer,
) {}
/**
* @param callable():string $render Returns the rendered PDF bytes.
* @param array<string, mixed> $attributes Caller-supplied span attributes.
*/
public function render(callable $render, array $attributes): string
{
$span = $this->otel->startSpan('pdf.render', $this->sanitizer->sanitize($attributes));
try {
return $render();
} finally {
$this->otel->endSpan($span);
}
}
}
  • De no-op-terugval is bewust volledig. Bescherm instrumentatie niet met isAvailable() “om werk te besparen”. De no-op kost al niets, en de beschermingscontrole voegt juist de vertakking toe die dit ontwerp verwijdert.
  • Laat door de aanroeper aangeleverde attributen altijd door AttributeSanitizer lopen voordat je ze aan een span of metriek koppelt. Telemetrieattributen vormen een onbedoeld PII-kanaal.
  • endSpan(null) is geldig: een null-span is het no-op-geval. Koppel elke startSpan() aan een endSpan() in een finally.
  • NullSpanBuilder::setAttribute() retourneert static zodat je kunt koppelen. In de no-op-variant is de keten bewust inert.
  • Het reproduceerbaarheidsprofiel is structural: spans bevatten tijdstempels en trace-identificatoren, dus twee uitvoeringen verschillen op die velden.

Als OTel ontbreekt, blijven de kosten beperkt tot een methode-aanroep naar een no-op; dat is praktisch kosteloos. Als OTel aanwezig is, komen de kosten van de OTel-SDK; de brug voegt attribuutsanering toe, die lineair is in het aantal attributen. Het performance_budget van 1500 ms wandkloktijd / 64 MB piek is het referentiebudget van de engine, geen service-level agreement (SLA) voor telemetrie.

Telemetrie is een oppervlak voor data-uitvoer. AttributeSanitizer houdt geheimen en PII uit spans en metrieken. Beschouw sanering als verplicht voor elk attribuut dat door de aanroeper wordt beïnvloed; dat is de veiligheidsverplichting van het project voor telemetrie. De OTel-exporter verzendt gegevens naar een externe backend, en die backend is een vertrouwensgrens. Configureer het endpoint en de inloggegevens vanuit een secret manager, niet vanuit ingecheckte configuratie. Ga ervan uit dat span- en metriekgegevens een log-sink bereiken, en schoon ze dienovereenkomstig op. Raadpleeg het dreigingsmodel van de engine in /modules/core/security/.

Deze module doet geen normatieve uitspraak over de Portable Document Format-specificatie (PDF). De module vormt een brug naar het OpenTelemetry-datamodel, een externe observeerbaarheidsspecificatie, niet naar een PDF-clausule. De no-op-terugval weerspiegelt het API-oppervlak van OpenTelemetry, zodat geïnstrumenteerde code overdraagbaar blijft. Dat is een eigenschap van API-compatibiliteit, geen verklaring van PDF-conformiteit. De conformiteit van de engine wordt gevalideerd door de oracle- en golden-suites die worden beschreven in /modules/core/conformance/.