Trace 設定¶
Trace 初期設定¶
| メソッド名 | タイプ | 必須 | 説明 |
|---|---|---|---|
| setSamplingRate | Float | いいえ | サンプリングレートを設定します。値の範囲は [0,1] で、0 はサンプリングなし、1 は全サンプリング、デフォルト値は 1 です。 |
| setTraceType | TraceType | いいえ | 分散型トレーシングのタイプを設定します。デフォルトは DDTrace です。現在サポートされているのは Zipkin、Jaeger、DDTrace、Skywalking (8.0+)、TraceParent (W3C) です。OpenTelemetry に接続する際に対応するトレースタイプを選択する場合は、サポートされているタイプと agent の関連設定を確認してください。 |
| setEnableLinkRUMData | Boolean | いいえ | RUM データと関連付けるかどうかを指定します。デフォルトは false です。 |
| setEnableAutoTrace | Boolean | いいえ | 自動 HTTP トレースを有効にするかどうかを設定します。この設定は ft-plugin に依存し、現在は OkHttp の自動トレースのみをサポートしています。デフォルトは false です。 |
| setOkHttpTraceHeaderHandler | Callback | いいえ | ASM でグローバルな FTTraceInterceptor.HeaderHandler を設定します。デフォルトでは設定されません。ft-sdk 1.6.8 以降でサポートされています。ft-sdk 1.6.17 以降では、getTraceContext(Request) をオーバーライドすることで、Header、traceId、spanId を一度に返すことが推奨されます。サンプルはカスタム Trace を参照してください。 |
Tracer ネットワーク分散型トレーシング¶
FTTraceConfig で enableAutoTrace を有効にすると自動的にトレースデータが追加されます。または、手動で FTTraceManager を使用して HTTP リクエストに Propagation Header を追加することもできます。以下に例を示します。
String url = "https://request.url";
String uuid = "uuid";
// トレースヘッダーパラメータを取得
Map<String, String> headers = FTTraceManager.get().getTraceHeader(uuid, url);
OkHttpClient client = new OkHttpClient.Builder().addInterceptor(chain -> {
Request original = chain.request();
Request.Builder requestBuilder = original.newBuilder();
// リクエストにトレースヘッダーパラメータを追加
for (String key : headers.keySet()) {
requestBuilder.header(key, headers.get(key));
}
Request request = requestBuilder.build();
Response response = chain.proceed(request);
if (response != null) {
Map<String, String> requestHeaderMap = new HashMap<>();
Map<String, String> responseHeaderMap = new HashMap<>();
for (Pair<String, String> header : response.request().headers()) {
requestHeaderMap.put(header.first, header.second);
}
for (Pair<String, String> header : response.headers()) {
responseHeaderMap.put(header.first, header.second);
}
}
return response;
}).build();
Request.Builder builder = new Request.Builder().url(url).method(RequestMethod.GET.name(), null);
client.newCall(builder.build()).execute();
val url = "https://request.url"
val uuid = "uuid"
// トレースヘッダーパラメータを取得
val headers = FTTraceManager.get().getTraceHeader(uuid, url)
val client: OkHttpClient = OkHttpClient.Builder().addInterceptor { chain ->
val original = chain.request()
val requestBuilder = original.newBuilder()
// リクエストにトレースヘッダーパラメータを追加
for (key in headers.keys) {
requestBuilder.header(key!!, headers[key]!!)
}
val request = requestBuilder.build()
val response = chain.proceed(request)
if (response != null) {
val requestHeaderMap = HashMap<String, String>()
val responseHeaderMap = HashMap<String, String>()
request.headers.forEach {
requestHeaderMap[it.first] = it.second
}
response.headers.forEach {
responseHeaderMap[it.first] = it.second
}
}
response
}.build()
val builder: Request.Builder = Request.Builder().url(url).method(RequestMethod.GET.name, null)
client.newCall(builder.build()).execute()
OkHttp Interceptor による Resource と TraceHeader のカスタマイズ¶
Resource¶
FTRUMConfig.setEnableTraceUserResource(true) または FTRUMConfig.setOkHttpResourceContentHandler(...) が有効な場合、OkHttp のカスタム Interceptor が優先的に読み込まれます。
new OkHttpClient.Builder()
.addInterceptor(new FTTraceInterceptor())
.addInterceptor(new FTResourceInterceptor(new FTResourceInterceptor.ContentHandlerHelper() {
@Override
public void onRequest(Request request, HashMap<String, Object> extraData) {
String contentType = request.header("Content-Type");
extraData.put("df_request_header", request.headers().toString());
if ("application/json".equals(contentType) ||
"application/x-www-form-urlencoded".equals(contentType) ||
"application/xml".equals(contentType)) {
extraData.put("df_request_body", request.body());
}
}
@Override
public void onResponse(Response response, HashMap<String, Object> extraData) throws IOException {
String contentType = response.header("Content-Type");
extraData.put("df_response_header", response.headers().toString());
if ("application/json".equals(contentType) ||
"application/xml".equals(contentType)) {
// 大量データ処理を避けるため、body の一部をコピーして読み取り
ResponseBody body = response.peekBody(33554432);
extraData.put("df_response_body", body.string());
}
}
@Override
public void onException(Exception e, HashMap<String, Object> extraData) {
}
}))
.eventListenerFactory(new FTResourceEventListener.FTFactory())
.build();
OkHttpClient.Builder()
.addInterceptor(FTTraceInterceptor())
.addInterceptor(FTResourceInterceptor(object : FTResourceInterceptor.ContentHandlerHelper {
override fun onRequest(request: Request, extraData: HashMap<String, Any>) {
val contentType = request.header("Content-Type")
extraData["df_request_header"] = request.headers().toString()
if ("application/json" == contentType ||
"application/x-www-form-urlencoded" == contentType ||
"application/xml" == contentType) {
extraData["df_request_body"] = request.body()
}
}
override fun onResponse(response: Response, extraData: HashMap<String, Any>) {
val contentType = response.header("Content-Type")
extraData["df_response_header"] = response.headers().toString()
if ("application/json" == contentType ||
"application/xml" == contentType) {
// 大量データ処理を避けるため、応答体の一部をコピー
val body = response.peekBody(33554432)
extraData["df_response_body"] = body.string()
}
}
override fun onException(e: Exception, extraData: HashMap<String, Any>) {
// 例外処理
}
}))
.eventListenerFactory(FTResourceEventListener.FTFactory())
.build()
TraceHeader¶
FTTraceConfig.setEnableAutoTrace(true) または FTTraceConfig.setOkHttpTraceHeaderHandler(...) が有効な場合、OkHttp のカスタム Interceptor が優先的に読み込まれます。以下は W3C Trace Context の例です。
ft-sdk < 1.4.1 の場合は、
FTTraceConfig.setEnableAutoTrace(false)で無効にする必要があります。 ft-sdk > 1.6.7 では、カスタム Trace Header と RUM データの関連付けをサポートしています。 ft-sdk >= 1.6.17 では、getTraceContext(Request)が追加され、リクエスト Header、traceId、spanIdを一度に返せるようになりました。この方法を優先的に使用することを推奨します。
推奨方法:getTraceContext(Request) の使用¶
new OkHttpClient.Builder()
.addInterceptor(new FTTraceInterceptor(new FTTraceInterceptor.HeaderHandler() {
@Override
public TraceContext getTraceContext(Request request) {
HashMap<String, String> headers = FTTraceManager.get()
.getTraceHeader(request.url().toString());
return TraceContext.Simple.fromTraceType(headers);
}
}))
.addInterceptor(new FTResourceInterceptor())
.eventListenerFactory(new FTResourceEventListener.FTFactory())
.build();
OkHttpClient.Builder()
.addInterceptor(
FTTraceInterceptor(object : FTTraceInterceptor.HeaderHandler() {
override fun getTraceContext(request: Request): TraceContext? {
val headers = FTTraceManager.get().getTraceHeader(request.url.toString())
return TraceContext.Simple.fromTraceType(headers)
}
})
)
.addInterceptor(FTResourceInterceptor())
.eventListenerFactory(FTResourceEventListener.FTFactory())
.build()
互換性のある旧方式:getTraceHeader / getTraceID / getSpanID の個別実装¶
new OkHttpClient.Builder()
.addInterceptor(new FTTraceInterceptor(new FTTraceInterceptor.HeaderHandler() {
private String[] splits;
@Override
public HashMap<String, String> getTraceHeader(Request request) {
HashMap<String, String> map = new HashMap<>();
String headerString = FTTraceManager.get()
.getTraceHeader(request.url().toString())
// header から propagation header を取得
.get(FTTraceHandler.W3C_TRACEPARENT_KEY);
splits = headerString.split("-");
map.put(W3C_TRACEPARENT_KEY, headerString);
return map;
}
@Override
public String getSpanID() {
if (splits != null) {
return splits[2];
}
return null;
}
@Override
public String getTraceID() {
if (splits != null) {
return splits[1];
}
return null;
}
}))
.addInterceptor(new FTResourceInterceptor())
.eventListenerFactory(new FTResourceEventListener.FTFactory())
.build();
OkHttpClient.Builder()
.addInterceptor(
FTTraceInterceptor(object : FTTraceInterceptor.HeaderHandler {
private var splits: Array<String>? = null
override fun getTraceHeader(request: Request): HashMap<String, String> {
val map = HashMap<String, String>()
val headerString = FTTraceManager.get()
.getTraceHeader(request.url.toString())
// header から propagation header を取得
.get(FTTraceHandler.W3C_TRACEPARENT_KEY)
splits = headerString?.split("-")?.toTypedArray()
headerString?.let {
map[W3C_TRACEPARENT_KEY] = it
}
return map
}
override fun getSpanID(): String? {
return splits?.getOrNull(2)
}
override fun getTraceID(): String? {
return splits?.getOrNull(1)
}
})
)
.addInterceptor(FTResourceInterceptor())
.eventListenerFactory(FTResourceEventListener.FTFactory())
.build()
OkHttp への ResourceID の追加¶
OkHttp Request に uuid を追加します。同じリクエストが高頻度で同時に発生するシナリオでは、有効にすることを推奨します。ft-plugin 1.3.5 以降、ft-sdk 1.6.10 以降で FTSDKConfig.setEnableOkhttpRequestTag(true) を有効にすると、自動的に Request に ResourceID が追加されます。