Java HTTP 整合
Telemetry 不發布本機 Java SDK。當 Java 或 JVM 服務需要結構化事件攝取或 SQL 查詢時,透過一個應用程式擁有的 java.net.http.HttpClient 使用 HTTP API。
此邊界將連線重用、超時、重試、序列化和故障策略保持在服務的控制之下。
建立一個共享客戶端
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.time.Duration;
HttpClient telemetryHttp = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(2))
.build();
在應用程式啟動期間建立一次客戶端。使用僅攝取 API 金鑰進行攝取,使用單獨的讀取範圍的金鑰進行報告或查詢自動化。
傳送一個結構化事件
使用應用程式已批准的 JSON 庫。此範例假設 eventJson 是從白名單物件序列化的,而不是從請求正文組裝的:
只在應用程式結果已確定後傳送。使用實際的正規化 routeTemplate、requestMethod、數值 statusCode 和 latencyMs,不要在正式環境複製虛構的成功狀態。Map.of 的所有值必須非空。下方的盡力傳送有逾時限制,會捕捉傳輸和序列化失敗,並保留執行緒中斷狀態;不會重試,也不保證資料已儲存。本機診斷不包含金鑰、回應本文或例外文字。
診斷輸出中的非受檢例外也會被捕捉。傳送仍然同步執行,可能增加應用程式路徑的延遲。
java.util.function.Consumer<String> deliveryDiagnostic = message -> {
try {
System.err.println(message);
} catch (RuntimeException diagnosticFailure) {
// Diagnostics must not replace the application outcome.
}
};
try {
String eventJson = objectMapper.writeValueAsString(Map.of(
"table", "api_request_completed",
"data", Map.of(
"event_id", eventId,
"route_template", routeTemplate,
"method", requestMethod,
"status_code", statusCode,
"status", statusCode >= 500 ? "failed" : "success",
"latency_ms", latencyMs,
"request_id", requestId,
"release", release
)
));
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create("https://api.telemetry.sh/log"))
.timeout(Duration.ofSeconds(3))
.header("Authorization", telemetryApiKey)
.header("Content-Type", "application/json")
.POST(HttpRequest.BodyPublishers.ofString(eventJson))
.build();
HttpResponse<Void> response = telemetryHttp.send(
request,
HttpResponse.BodyHandlers.discarding()
);
if (response.statusCode() < 200 || response.statusCode() >= 300) {
deliveryDiagnostic.accept("Telemetry delivery failed (non-2xx response).");
}
} catch (InterruptedException error) {
Thread.currentThread().interrupt();
deliveryDiagnostic.accept("Telemetry delivery interrupted.");
} catch (java.io.IOException | RuntimeException error) {
deliveryDiagnostic.accept("Telemetry delivery failed (transport, serialization or configuration error).");
}
使用路由範本和受控錯誤類別。請勿序列化標頭、cookie、憑據、請求正文、SQL 參數、堆疊追蹤、提示、生成的內容或不受限制的異常訊息。
執行SQL
使用讀取範圍的金鑰將包含 query 的 JSON 正文發布到 https://api.telemetry.sh/query:
String queryJson = objectMapper.writeValueAsString(Map.of(
"query", """
SELECT route_template, COUNT(*) AS requests
FROM api_request_completed
WHERE timestamp_utc >= now() - INTERVAL '24 hours'
GROUP BY route_template
ORDER BY requests DESC
"""
));
HttpRequest queryRequest = HttpRequest.newBuilder()
.uri(URI.create("https://api.telemetry.sh/query"))
.timeout(Duration.ofSeconds(15))
.header("Authorization", telemetryReadApiKey)
.header("Content-Type", "application/json")
.POST(HttpRequest.BodyPublishers.ofString(queryJson))
.build();
檢查HTTP狀態以及回應status、data和key_order欄位。將空結果視為有效狀態而不是解析失敗。
失敗和重試策略
僅重試有限的瞬時故障,例如連線錯誤、429、502、503 和 504。使用帶有抖動的指數退避,限制執行時間,並在嘗試中保留相同的 event_id。請勿重試未更改的 400、401 或 403 回應。
對於普通的產品分析,遙測失敗不應取代完整的客戶回應。如果計費或批准的稽核事件必須持久,請在與業務狀態相同的事務中寫入發件箱記錄,並從工作人員處交付。
驗證整合
傳送受控的成功、失敗、重試和超時裝置,然後檢查最近的行:
SELECT timestamp_utc, event_id, route_template, status, latency_ms
FROM api_request_completed
ORDER BY timestamp_utc DESC
LIMIT 20;
確認事件粒度、資料表名稱、欄位型別、單位、UTC 時間和隱私邊界。在將交付置於高流量路徑上之前,測試 Telemetry 超時和處理程序關閉。
繼續使用 Spring Boot 整合、日誌API、速率限制和錯誤 和 事件傳遞和冪等性。