Add `TextMapPropagator` to instrumentation context (#1401)
This commit is contained in:
parent
c632d960a5
commit
2c1da9aaec
|
@ -8,8 +8,6 @@ use Nevay\SPI\ServiceLoader;
|
||||||
use OpenTelemetry\API\Globals;
|
use OpenTelemetry\API\Globals;
|
||||||
use OpenTelemetry\API\Instrumentation\AutoInstrumentation\ExtensionHookManager;
|
use OpenTelemetry\API\Instrumentation\AutoInstrumentation\ExtensionHookManager;
|
||||||
use OpenTelemetry\API\Instrumentation\AutoInstrumentation\Instrumentation;
|
use OpenTelemetry\API\Instrumentation\AutoInstrumentation\Instrumentation;
|
||||||
use OpenTelemetry\API\Logs\NoopLoggerProvider;
|
|
||||||
use OpenTelemetry\API\Metrics\Noop\NoopMeterProvider;
|
|
||||||
use OpenTelemetry\Config\SDK\Configuration;
|
use OpenTelemetry\Config\SDK\Configuration;
|
||||||
use OpenTelemetry\Config\SDK\Configuration\Context;
|
use OpenTelemetry\Config\SDK\Configuration\Context;
|
||||||
use OpenTelemetry\Example\Example;
|
use OpenTelemetry\Example\Example;
|
||||||
|
@ -25,7 +23,7 @@ require __DIR__ . '/../../vendor/autoload.php';
|
||||||
Configuration::parseFile(__DIR__ . '/otel-sdk.yaml')->create(new Context())->setAutoShutdown(true)->buildAndRegisterGlobal();
|
Configuration::parseFile(__DIR__ . '/otel-sdk.yaml')->create(new Context())->setAutoShutdown(true)->buildAndRegisterGlobal();
|
||||||
$configuration = \OpenTelemetry\Config\SDK\Instrumentation::parseFile(__DIR__ . '/otel-sdk.yaml')->create();
|
$configuration = \OpenTelemetry\Config\SDK\Instrumentation::parseFile(__DIR__ . '/otel-sdk.yaml')->create();
|
||||||
$hookManager = new ExtensionHookManager();
|
$hookManager = new ExtensionHookManager();
|
||||||
$context = new \OpenTelemetry\API\Instrumentation\AutoInstrumentation\Context(Globals::tracerProvider(), new NoopMeterProvider(), new NoopLoggerProvider());
|
$context = new \OpenTelemetry\API\Instrumentation\AutoInstrumentation\Context(Globals::tracerProvider(), Globals::meterProvider(), Globals::loggerProvider(), Globals::propagator());
|
||||||
|
|
||||||
foreach (ServiceLoader::load(Instrumentation::class) as $instrumentation) {
|
foreach (ServiceLoader::load(Instrumentation::class) as $instrumentation) {
|
||||||
$instrumentation->register($hookManager, $configuration, $context);
|
$instrumentation->register($hookManager, $configuration, $context);
|
||||||
|
|
|
@ -10,6 +10,8 @@ use OpenTelemetry\API\Metrics\MeterProviderInterface;
|
||||||
use OpenTelemetry\API\Metrics\Noop\NoopMeterProvider;
|
use OpenTelemetry\API\Metrics\Noop\NoopMeterProvider;
|
||||||
use OpenTelemetry\API\Trace\NoopTracerProvider;
|
use OpenTelemetry\API\Trace\NoopTracerProvider;
|
||||||
use OpenTelemetry\API\Trace\TracerProviderInterface;
|
use OpenTelemetry\API\Trace\TracerProviderInterface;
|
||||||
|
use OpenTelemetry\Context\Propagation\NoopTextMapPropagator;
|
||||||
|
use OpenTelemetry\Context\Propagation\TextMapPropagatorInterface;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Context used for component creation.
|
* Context used for component creation.
|
||||||
|
@ -20,6 +22,7 @@ final class Context
|
||||||
public readonly TracerProviderInterface $tracerProvider = new NoopTracerProvider(),
|
public readonly TracerProviderInterface $tracerProvider = new NoopTracerProvider(),
|
||||||
public readonly MeterProviderInterface $meterProvider = new NoopMeterProvider(),
|
public readonly MeterProviderInterface $meterProvider = new NoopMeterProvider(),
|
||||||
public readonly LoggerProviderInterface $loggerProvider = new NoopLoggerProvider(),
|
public readonly LoggerProviderInterface $loggerProvider = new NoopLoggerProvider(),
|
||||||
|
public readonly TextMapPropagatorInterface $propagator = new NoopTextMapPropagator(),
|
||||||
) {
|
) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,53 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
namespace OpenTelemetry\SDK\Propagation;
|
||||||
|
|
||||||
|
use Closure;
|
||||||
|
use OpenTelemetry\Context\ContextInterface;
|
||||||
|
use OpenTelemetry\Context\Propagation\PropagationGetterInterface;
|
||||||
|
use OpenTelemetry\Context\Propagation\PropagationSetterInterface;
|
||||||
|
use OpenTelemetry\Context\Propagation\TextMapPropagatorInterface;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @internal
|
||||||
|
*/
|
||||||
|
final class LateBindingTextMapPropagator implements TextMapPropagatorInterface
|
||||||
|
{
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param TextMapPropagatorInterface|Closure(): TextMapPropagatorInterface $propagator
|
||||||
|
*/
|
||||||
|
public function __construct(
|
||||||
|
private TextMapPropagatorInterface|Closure $propagator,
|
||||||
|
) {
|
||||||
|
}
|
||||||
|
|
||||||
|
public function fields(): array
|
||||||
|
{
|
||||||
|
if (!$this->propagator instanceof TextMapPropagatorInterface) {
|
||||||
|
$this->propagator = ($this->propagator)();
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this->propagator->fields();
|
||||||
|
}
|
||||||
|
|
||||||
|
public function inject(mixed &$carrier, ?PropagationSetterInterface $setter = null, ?ContextInterface $context = null): void
|
||||||
|
{
|
||||||
|
if (!$this->propagator instanceof TextMapPropagatorInterface) {
|
||||||
|
$this->propagator = ($this->propagator)();
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->propagator->inject($carrier, $setter, $context);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function extract($carrier, ?PropagationGetterInterface $getter = null, ?ContextInterface $context = null): ContextInterface
|
||||||
|
{
|
||||||
|
if (!$this->propagator instanceof TextMapPropagatorInterface) {
|
||||||
|
$this->propagator = ($this->propagator)();
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this->propagator->extract($carrier, $getter, $context);
|
||||||
|
}
|
||||||
|
}
|
|
@ -23,12 +23,14 @@ use OpenTelemetry\API\Trace\TracerProviderInterface;
|
||||||
use OpenTelemetry\Config\SDK\Configuration as SdkConfiguration;
|
use OpenTelemetry\Config\SDK\Configuration as SdkConfiguration;
|
||||||
use OpenTelemetry\Config\SDK\Instrumentation as SdkInstrumentation;
|
use OpenTelemetry\Config\SDK\Instrumentation as SdkInstrumentation;
|
||||||
use OpenTelemetry\Context\Context;
|
use OpenTelemetry\Context\Context;
|
||||||
|
use OpenTelemetry\Context\Propagation\TextMapPropagatorInterface;
|
||||||
use OpenTelemetry\SDK\Common\Configuration\Configuration;
|
use OpenTelemetry\SDK\Common\Configuration\Configuration;
|
||||||
use OpenTelemetry\SDK\Common\Configuration\Variables;
|
use OpenTelemetry\SDK\Common\Configuration\Variables;
|
||||||
use OpenTelemetry\SDK\Common\Util\ShutdownHandler;
|
use OpenTelemetry\SDK\Common\Util\ShutdownHandler;
|
||||||
use OpenTelemetry\SDK\Logs\EventLoggerProviderFactory;
|
use OpenTelemetry\SDK\Logs\EventLoggerProviderFactory;
|
||||||
use OpenTelemetry\SDK\Logs\LoggerProviderFactory;
|
use OpenTelemetry\SDK\Logs\LoggerProviderFactory;
|
||||||
use OpenTelemetry\SDK\Metrics\MeterProviderFactory;
|
use OpenTelemetry\SDK\Metrics\MeterProviderFactory;
|
||||||
|
use OpenTelemetry\SDK\Propagation\LateBindingTextMapPropagator;
|
||||||
use OpenTelemetry\SDK\Propagation\PropagatorFactory;
|
use OpenTelemetry\SDK\Propagation\PropagatorFactory;
|
||||||
use OpenTelemetry\SDK\Resource\ResourceInfoFactory;
|
use OpenTelemetry\SDK\Resource\ResourceInfoFactory;
|
||||||
use OpenTelemetry\SDK\Trace\AutoRootSpan;
|
use OpenTelemetry\SDK\Trace\AutoRootSpan;
|
||||||
|
@ -154,7 +156,8 @@ class SdkAutoloader
|
||||||
$tracerProvider = self::createLateBindingTracerProvider();
|
$tracerProvider = self::createLateBindingTracerProvider();
|
||||||
$meterProvider = self::createLateBindingMeterProvider();
|
$meterProvider = self::createLateBindingMeterProvider();
|
||||||
$loggerProvider = self::createLateBindingLoggerProvider();
|
$loggerProvider = self::createLateBindingLoggerProvider();
|
||||||
$context = new InstrumentationContext($tracerProvider, $meterProvider, $loggerProvider);
|
$propagator = self::createLateBindingTextMapPropagator();
|
||||||
|
$context = new InstrumentationContext($tracerProvider, $meterProvider, $loggerProvider, $propagator);
|
||||||
|
|
||||||
foreach (ServiceLoader::load(Instrumentation::class) as $instrumentation) {
|
foreach (ServiceLoader::load(Instrumentation::class) as $instrumentation) {
|
||||||
/** @var Instrumentation $instrumentation */
|
/** @var Instrumentation $instrumentation */
|
||||||
|
@ -204,6 +207,19 @@ class SdkAutoloader
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static function createLateBindingTextMapPropagator(): TextMapPropagatorInterface
|
||||||
|
{
|
||||||
|
return new LateBindingTextMapPropagator(static function (): TextMapPropagatorInterface {
|
||||||
|
$scope = Context::getRoot()->activate();
|
||||||
|
|
||||||
|
try {
|
||||||
|
return Globals::propagator();
|
||||||
|
} finally {
|
||||||
|
$scope->detach();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
private static function getHookManager(): HookManagerInterface
|
private static function getHookManager(): HookManagerInterface
|
||||||
{
|
{
|
||||||
/** @var HookManagerInterface $hookManager */
|
/** @var HookManagerInterface $hookManager */
|
||||||
|
|
|
@ -8,6 +8,7 @@ use OpenTelemetry\API\Instrumentation\AutoInstrumentation\Context;
|
||||||
use OpenTelemetry\API\Logs\NoopLoggerProvider;
|
use OpenTelemetry\API\Logs\NoopLoggerProvider;
|
||||||
use OpenTelemetry\API\Metrics\Noop\NoopMeterProvider;
|
use OpenTelemetry\API\Metrics\Noop\NoopMeterProvider;
|
||||||
use OpenTelemetry\API\Trace\NoopTracerProvider;
|
use OpenTelemetry\API\Trace\NoopTracerProvider;
|
||||||
|
use OpenTelemetry\Context\Propagation\NoopTextMapPropagator;
|
||||||
use PHPUnit\Framework\Attributes\CoversClass;
|
use PHPUnit\Framework\Attributes\CoversClass;
|
||||||
use PHPUnit\Framework\TestCase;
|
use PHPUnit\Framework\TestCase;
|
||||||
|
|
||||||
|
@ -20,5 +21,6 @@ class ContextTest extends TestCase
|
||||||
$this->assertInstanceOf(NoopTracerProvider::class, $context->tracerProvider);
|
$this->assertInstanceOf(NoopTracerProvider::class, $context->tracerProvider);
|
||||||
$this->assertInstanceOf(NoopMeterProvider::class, $context->meterProvider);
|
$this->assertInstanceOf(NoopMeterProvider::class, $context->meterProvider);
|
||||||
$this->assertInstanceOf(NoopLoggerProvider::class, $context->loggerProvider);
|
$this->assertInstanceOf(NoopLoggerProvider::class, $context->loggerProvider);
|
||||||
|
$this->assertInstanceOf(NoopTextMapPropagator::class, $context->propagator);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,6 +4,7 @@ declare(strict_types=1);
|
||||||
|
|
||||||
namespace OpenTelemetry\Tests\Unit\API\Instrumentation\AutoInstrumentation;
|
namespace OpenTelemetry\Tests\Unit\API\Instrumentation\AutoInstrumentation;
|
||||||
|
|
||||||
|
use function assert;
|
||||||
use Nevay\SPI\ServiceLoader;
|
use Nevay\SPI\ServiceLoader;
|
||||||
use OpenTelemetry\API\Behavior\Internal\Logging;
|
use OpenTelemetry\API\Behavior\Internal\Logging;
|
||||||
use OpenTelemetry\API\Configuration\ConfigProperties;
|
use OpenTelemetry\API\Configuration\ConfigProperties;
|
||||||
|
@ -25,11 +26,13 @@ use OpenTelemetry\API\Trace\LateBindingTracer;
|
||||||
use OpenTelemetry\API\Trace\LateBindingTracerProvider;
|
use OpenTelemetry\API\Trace\LateBindingTracerProvider;
|
||||||
use OpenTelemetry\API\Trace\TracerInterface;
|
use OpenTelemetry\API\Trace\TracerInterface;
|
||||||
use OpenTelemetry\API\Trace\TracerProviderInterface;
|
use OpenTelemetry\API\Trace\TracerProviderInterface;
|
||||||
|
use OpenTelemetry\Context\Propagation\TextMapPropagatorInterface;
|
||||||
use OpenTelemetry\SDK\Common\Configuration\Variables;
|
use OpenTelemetry\SDK\Common\Configuration\Variables;
|
||||||
use OpenTelemetry\SDK\SdkAutoloader;
|
use OpenTelemetry\SDK\SdkAutoloader;
|
||||||
use OpenTelemetry\Tests\TestState;
|
use OpenTelemetry\Tests\TestState;
|
||||||
use PHPUnit\Framework\Attributes\CoversClass;
|
use PHPUnit\Framework\Attributes\CoversClass;
|
||||||
use PHPUnit\Framework\TestCase;
|
use PHPUnit\Framework\TestCase;
|
||||||
|
use Prophecy\PhpUnit\ProphecyTrait;
|
||||||
|
|
||||||
#[CoversClass(LateBindingLoggerProvider::class)]
|
#[CoversClass(LateBindingLoggerProvider::class)]
|
||||||
#[CoversClass(LateBindingLogger::class)]
|
#[CoversClass(LateBindingLogger::class)]
|
||||||
|
@ -45,6 +48,7 @@ use PHPUnit\Framework\TestCase;
|
||||||
class LateBindingProviderTest extends TestCase
|
class LateBindingProviderTest extends TestCase
|
||||||
{
|
{
|
||||||
use TestState;
|
use TestState;
|
||||||
|
use ProphecyTrait;
|
||||||
|
|
||||||
public function setUp(): void
|
public function setUp(): void
|
||||||
{
|
{
|
||||||
|
@ -77,6 +81,12 @@ class LateBindingProviderTest extends TestCase
|
||||||
|
|
||||||
return self::$context->loggerProvider->getLogger('test');
|
return self::$context->loggerProvider->getLogger('test');
|
||||||
}
|
}
|
||||||
|
public function getPropagator(): TextMapPropagatorInterface
|
||||||
|
{
|
||||||
|
assert(self::$context !== null);
|
||||||
|
|
||||||
|
return self::$context->propagator;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
$this->setEnvironmentVariable(Variables::OTEL_PHP_AUTOLOAD_ENABLED, 'true');
|
$this->setEnvironmentVariable(Variables::OTEL_PHP_AUTOLOAD_ENABLED, 'true');
|
||||||
$tracer_accessed = false;
|
$tracer_accessed = false;
|
||||||
|
@ -101,14 +111,17 @@ class LateBindingProviderTest extends TestCase
|
||||||
|
|
||||||
return $this->createMock(LoggerInterface::class);
|
return $this->createMock(LoggerInterface::class);
|
||||||
});
|
});
|
||||||
|
$propagator = $this->prophesize(TextMapPropagatorInterface::class);
|
||||||
|
|
||||||
ServiceLoader::register(Instrumentation::class, $instrumentation::class);
|
ServiceLoader::register(Instrumentation::class, $instrumentation::class);
|
||||||
$this->assertTrue(SdkAutoloader::autoload());
|
$this->assertTrue(SdkAutoloader::autoload());
|
||||||
//initializer added _after_ autoloader has run and instrumentation registered
|
//initializer added _after_ autoloader has run and instrumentation registered
|
||||||
Globals::registerInitializer(function (Configurator $configurator) use ($tracerProvider, $loggerProvider, $meterProvider): Configurator {
|
Globals::registerInitializer(function (Configurator $configurator) use ($tracerProvider, $loggerProvider, $meterProvider, $propagator): Configurator {
|
||||||
return $configurator
|
return $configurator
|
||||||
->withTracerProvider($tracerProvider)
|
->withTracerProvider($tracerProvider)
|
||||||
->withMeterProvider($meterProvider)
|
->withMeterProvider($meterProvider)
|
||||||
->withLoggerProvider($loggerProvider)
|
->withLoggerProvider($loggerProvider)
|
||||||
|
->withPropagator($propagator->reveal())
|
||||||
;
|
;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -129,5 +142,11 @@ class LateBindingProviderTest extends TestCase
|
||||||
$this->assertFalse($logger_accessed);
|
$this->assertFalse($logger_accessed);
|
||||||
$logger->emit(new LogRecord()); /** @phpstan-ignore-next-line */
|
$logger->emit(new LogRecord()); /** @phpstan-ignore-next-line */
|
||||||
$this->assertTrue($logger_accessed);
|
$this->assertTrue($logger_accessed);
|
||||||
|
|
||||||
|
/** @phpstan-ignore-next-line */
|
||||||
|
$propagator->fields()->shouldNotHaveBeenCalled();
|
||||||
|
$instrumentation->getPropagator()->fields();
|
||||||
|
/** @phpstan-ignore-next-line */
|
||||||
|
$propagator->fields()->shouldHaveBeenCalledOnce();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue