> Source: https://www.ymotongpoo.com/works/oteps/otep-0005/


# OTEP-0005: グローバルなSDKの初期化

**ステータス**: 提案中

OpenTelemetry APIと実装の起動時の動作を指定します。

## 動機

OpenTelemetryは、APIとそれを実装するSDKを分離して設計されており、アプリケーションはランタイムに互換性のあるSDKを設定しバインドできます。
OpenTelemetryは、グローバルインスタンスの使用により、サードパーティーライブラリの「ゼロタッチ」計装をサポートするように設計されています。

多くのプログラミング環境では、コードのライブラリが自動で初期化され、静的なプログラム状態を初期化している間などに、メインプログラムと同時に動作を開始することが可能です。
これには次のような相反する要件があります。
(1) APIは設定可能なSDKをサポートすること。
(2) サードパーティーのライブラリは設定なしでOpenTelemetryを使用できます。

## 解説

この状況に対処するには、いくつかの受け入れ可能な方法があります。
各アプローチの実現可能性は言語によって異なります。
実装は、以下の戦略のいずれかを選択しなければなりません。

### サービスプロバイダー機構

言語がSDKコンポーネントを注入する一般的に認められた方法を提供する場合、それが優先されるべきです。
Java SPIは、最初に使用される前にグローバルSDKをロードして設定することをサポートしています。
この特性により、サービスプロバイダー機構の場合は、他にほとんど指定するものがありません。

### 明示的なイニシャライザ

APIが最初に使用される前にSDKがインストールされ設定されていることを保証できない場合、[Ruby issue 19](https://github.com/open-telemetry/opentelemetry-ruby/issues/19)で述べられているように、SDKのロードは「適切なタイミングで」ユーザーに引き渡されます。
この場合、次に説明するように、多くの要件を指定する必要があります。

## 要件: 明示的なイニシャライザ

OpenTelemetryは、デフォルトの実装がノンオペレーション（すなわち、「no-op」）であることを明記しており、APIメソッド呼び出しの結果、計装のオーバーヘッドが事実上ゼロになることを要求しています。
私たちは、サードパーティーのライブラリが、インストールされる前にグローバルSDKを使用することを期待しており、これは以下で述べる要件で扱います。

明示的なイニシャライザは、独立した `Tracer` オブジェクトと `Meter` オブジェクトを取る必要があります（例:
`opentelemetry.Init(Tracer, Meter)`）。
SDKのインストールは1回までとします。
最初にSDKをインストールした後、明示的なイニシャライザを呼び出すと、ログコンソールに警告が表示されます。

平易に言えば、グローバルSDKインスタンス（すなわち、TracerとMeter）の使用は、SDKがインストールされると、以下の規定で「動作を開始」しなければなりません。

### Tracer

起動時にスパンが喪失するかもしれません。

SDKがインストールされる前に開始されたスパンは回復されず、No-opスパンとして継続されます。

### Meter

起動時にメトリクスが喪失するかもしれません。

SDKがインストールされる前に初期化されたメトリクスのサブ計測オブジェクト（つまり、事前定義されたラベルを持つメトリクス）は、インストール後にグローバルSDKにリダイレクトされます。

### 具象型

キー、タグ、属性、ラベル、リソース、スパンコンテキスト、分散コンテキストは、純粋なAPIオブジェクトとして指定されるため、インストールされているSDKに依存しません。

## トレードオフと緩和策

### テストのサポート

テストは、グローバルSDKに依存することなく実行されるべきです。

### 同期

グローバルなTracerオブジェクトとMeterオブジェクトは、SDKがインストールされると動作を開始する必要があるため、起動時に暗黙の同期オーバーヘッドが発生します。
このオーバーヘッドは、SDKがインストールされた後には低下すると見込んでいます。
計装を完全に無効にするには、OpenTelemetryライブラリを未初期化のままにしておくよりもオーバーヘッドが低くなるため、明示的にNo-op SDKをインストールすることをお勧めします。

## 先行技術と代替技術

「一般的に受け入れられている」とは言えない例として、[Go issue 52](https://github.com/open-telemetry/opentelemetry-go/issues/52) を参照してください。
この例では、最初の使用前に設定可能なSDKをロードするために、Go `plugin` パッケージを使用しています。

## 未解決の問題

明示的なグローバルイニシャライザには、他にどのようなオプションを渡すべきでしょうか。

「SDKがインストールされているか、それは no-op か」の公開テストは存在するでしょうか。
