精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

Sentry 開發(fā)者貢獻指南 - SDK 開發(fā)(性能監(jiān)控:Sentry SDK API 演進)

安全 應(yīng)用安全
本文檔的目標是將 Sentry SDK 中性能監(jiān)控功能的演變置于上下文中。我們首先總結(jié)了如何將性能監(jiān)控添加到 Sentry 和 SDK, 然后我們討論 identified issues(已確定的問題) 吸取的經(jīng)驗教訓(xùn)以及解決這些問題的舉措。

[[443315]]

本文檔的目標是將 Sentry SDK 中性能監(jiān)控功能的演變置于上下文中。我們首先總結(jié)了如何將性能監(jiān)控添加到 Sentry 和 SDK, 然后我們討論 identified issues(已確定的問題) 吸取的經(jīng)驗教訓(xùn)以及解決這些問題的舉措。

介紹

早在 2019 年初,Sentry 就開始嘗試向 SDK 添加跟蹤功能。 Python 和 JavaScript SDK 是設(shè)計和開發(fā)第一個概念的測試平臺。概念驗證于 2019 年 4 月 29 日 發(fā)布, 并于 2019 年 5 月 7 日交付給 Sentry。 Python 和 JavaScript 是顯而易見的選擇,因為它們允許我們試驗檢測 Sentry 自己的后端和前端。

  • https://github.com/getsentry/sentry-python/pull/342
  • https://github.com/getsentry/sentry-javascript/pull/1918
  • https://github.com/getsentry/sentry-python/releases/tag/0.7.13
  • https://github.com/getsentry/sentry/pull/12952

請注意,上述工作與 OpenCensus 和 OpenTracing 合并形成 OpenTelemetry 是同時代的。 Sentry 的 API 和 SDK 實現(xiàn)借鑒了 OpenTelemetry 1.0 之前版本的靈感,并結(jié)合了我們自己的想法。例如,我們的 Span 狀態(tài)列表與 2019 年底左右在 OpenTelemetry 規(guī)范中可以找到的匹配。

  • https://medium.com/opentracing/a-roadmap-to-convergence-b074e5815289
  • https://github.com/getsentry/relay/blob/55127c75d4eeebf787848a05a12150ee5c59acd9/relay-common/src/constants.rs#L179-L181

使用 API 后,性能監(jiān)控支持隨后擴展到其他 SDK。Sentry 的性能監(jiān)控 解決方案于 2020 年 7 月普遍可用。 OpenTelemetry 的跟蹤規(guī)范 1.0 版于 2021 年 2 月發(fā)布。

  • https://blog.sentry.io/2020/07/14/see-slow-faster-with-performance-monitoring
  • https://medium.com/opentelemetry/opentelemetry-specification-v1-0-0-tracing-edition-72dd08936978

我們最初的實現(xiàn)重用了我們現(xiàn)有的錯誤報告機制:

  • Event type 擴展了新字段。這意味著我們可以節(jié)省時間并快速開始向 Sentry 發(fā)送事件,而不是設(shè)計和實現(xiàn)全新的攝取管道,這一次,不是 error,而是一種新的 transaction 事件類型。
    • https://develop.sentry.dev/sdk/event-payloads/
  • 由于我們只是發(fā)送一種新型事件,因此也重用了 SDK 傳輸層。
  • 由于我們共享攝取管道(ingestion pipeline),這意味著我們共享存儲以及發(fā)生在所有事件上的處理的許多部分。

我們的實現(xiàn)演變成明確強調(diào) Transaction 和 Span 之間的區(qū)別。部分原因是重用 Event 接口的副作用。

Transaction 與客戶產(chǎn)生了良好的共鳴。他們允許突出顯示代碼中的重要工作塊,例如瀏覽器頁面加載或 http 服務(wù)器請求。客戶可以查看和瀏覽 transaction 列表,而在 transaction 中,span 為更細粒度的工作單元提供詳細的時間安排。

在下一節(jié)中,我們將討論當前模型的一些缺點。

已確定的問題

雖然統(tǒng)一 SDK 架構(gòu)(hub、client、scope) 和 transaction ingestion 模型的重用有其優(yōu)點,但經(jīng)驗揭示了一些我們將其分為兩類的問題。

  • https://develop.sentry.dev/sdk/unified-api/

第一組與 scope 傳播有關(guān),本質(zhì)上是確定 當前 scope 是什么的能力。用戶代碼中的手動檢測以及 SDK 集成中的自動檢測都需要此操作。

第二組是與用于將 transaction 數(shù)據(jù)從 SDK 發(fā)送到 Sentry 的 wire 格式相關(guān)的問題。

Scope 傳播

該問題由 getsentry/sentry-javascript#3751 跟蹤。

  • https://github.com/getsentry/sentry-javascript/issues/3751

Unified SDK 架構(gòu) 基本上是基于每個并發(fā)單元存在一個 hub,每個 hub 有一堆 client 和 scope 對。

  • https://develop.sentry.dev/sdk/unified-api/

Client 保存配置并負責通過 transport 向 Sentry 發(fā)送數(shù)據(jù),而 scope 保存附加到傳出事件(例如 tag 和 breadcrumb)的上下文數(shù)據(jù)。

每個 hub 都知道當前的 scope 是什么。它始終是堆棧頂部的 scope。困難的部分是 “per unit of concurrency(每單位并發(fā))” 有一個 hub。

例如,JavaScript 是具有事件循環(huán)和異步代碼執(zhí)行的單線程。沒有標準的方法來承載跨異步調(diào)用工作的上下文數(shù)據(jù)。因此,對于 JavaScript 瀏覽器應(yīng)用程序,只有一個全局 hub 共享用于同步和異步代碼。

類似的情況出現(xiàn)在 Mobile SDK 上。用戶期望上下文數(shù)據(jù)(例如 tags、current user 是什么、 breadcrumbs 以及存儲在 scope 上的其他信息)可以從任何線程獲得和設(shè)置。因此,在這些 SDK 中,只有一個全局 hub。

在這兩種情況下,當 SDK 必須處理 reporting errors 時,一切都相對較好。隨著跟蹤 transaction 和 span 的額外責任,scope 變得不適合存儲當前的 span,因為它限制了并發(fā) span 的存在。

對于瀏覽器 JavaScript,一個可能的解決方案是使用 Zone.js,Angular 框架的一部分。主要挑戰(zhàn)是它增加了包的大小,并且可能會無意中影響最終用戶應(yīng)用程序,因為它對 JavaScript 運行時引擎的關(guān)鍵部分進行了猴子修補(monkey-patches)。

  • https://github.com/angular/angular/blob/master/packages/zone.js/README.md

當我們嘗試為手動檢測創(chuàng)建更簡單的 API 時,scope 傳播問題變得尤為明顯。這個想法是公開一個 Sentry.trace 函數(shù),該函數(shù)將隱式傳播 tracing 和 scope 數(shù)據(jù), 并支持同步和異步代碼的深度嵌套。

舉個例子,假設(shè)有人想測量搜索 DOM 樹需要多長時間。Tracing(跟蹤) 此操作將如下所示:

  1. await Sentry.trace( 
  2.   { 
  3.     op: 'dom'
  4.     description: 'Walk DOM Tree'
  5.   }, 
  6.   async () => await walkDomTree() 
  7. ); 

使用 Sentry.trace 功能,用戶在添加計時數(shù)據(jù)時不必擔心保留對正確 transaction 或 span 的引用。用戶可以在 walkDomTree 函數(shù)中自由創(chuàng)建子 Span,Span 將在正確的層次結(jié)構(gòu)中排序。

實際 trace 函數(shù)的實現(xiàn)相對簡單 (參見具有示例實現(xiàn)的 PR)。然而,了解異步代碼和全局集成中的當前 span 是一個尚未克服的挑戰(zhàn)。

  • https://github.com/getsentry/sentry-javascript/pull/3697/files#diff-f5bf6e0cdf7709e5675fcdc3b4ff254dd68f3c9d1a399c8751e0fa1846fa85dbR158

以下兩個示例綜合了 scope 傳播問題。

無法確定當前 Span

考慮一些需要獲取對當前 span 的引用的自動檢測代碼,在這種情況下,手動 scope 傳播不可用。

  1. // SDK code 
  2. function fetchWrapper(/* ... */) { 
  3.   /* 
  4.     ... some code omitted for simplicity ... 
  5.   */ 
  6.   const parent = getCurrentHub().getScope().getSpan(); // <1> 
  7.   const span = parent.startChild({ 
  8.     data: { type: 'fetch' }, 
  9.     description: `${method} ${url}`, 
  10.     op: 'http.client'
  11.   }); 
  12.   try { 
  13.     // ... 
  14.     // return fetch(...); 
  15.   } finally { 
  16.     span.finish(); 
  17.   } 
  18. window.fetch = fetchWrapper; 
  19.  
  20. // User code 
  21. async function f1() { 
  22.   const hub = getCurrentHub(); 
  23.   let t = hub.startTransaction({ name't1' }); 
  24.   hub.getScope().setSpan(t); 
  25.   try { 
  26.     await fetch('https://example.com/f1'); 
  27.   } finally { 
  28.     t.finish(); 
  29.   } 
  30. async function f2() { 
  31.   const hub = getCurrentHub(); 
  32.   let t = hub.startTransaction({ name't2' }); 
  33.   hub.getScope().setSpan(t); 
  34.   try { 
  35.     await fetch('https://example.com/f2'); 
  36.   } finally { 
  37.     t.finish(); 
  38.   } 
  39. Promise.all([f1(), f2()]); // run f1 and f2 concurrently 

在上面的例子中,幾個并發(fā)的 fetch 請求觸發(fā)了 fetchWrapper helper 的執(zhí)行。行 <1> 必須能夠根據(jù)當前的執(zhí)行流程觀察到不同的 span,導(dǎo)致如下兩個 span 樹:

  1. t1 
  2.   |- http.client GET https://example.com/f1 
  3. t2 
  4.   |- http.client GET https://example.com/f2 

這意味著,當 f1 運行時,parent 必須引用 t1,而當 f2 運行時,parent 必須是 t2。不幸的是,上面的所有代碼都在爭先恐后地更新和讀取單個 hub 實例,因此觀察到的 span 樹不是確定性的。例如,結(jié)果可能錯誤地為:

  1. t1 
  2. t2 
  3.   |- http.client GET https://example.com/f1 
  4.   |- http.client GET https://example.com/f2 

作為無法正確確定當前 span 的副作用, fetch 集成的顯示實現(xiàn)(和其他)在JavaScript 瀏覽器 SDK 中選擇創(chuàng)建 flat transactions, 其中所有子 span 都是 transaction 的直接子代(而不是具有適當?shù)亩嗉墭浣Y(jié)構(gòu))。

  • https://github.com/getsentry/sentry-javascript/blob/61eda62ed5df5654f93e34a4848fc9ae3fcac0f7/packages/tracing/src/browser/request.ts#L169-L178

請注意,其他跟蹤庫也面臨同樣的挑戰(zhàn)。在 OpenTelemetry for JavaScript 中有幾個(在開放時)問題與確定父跨度和正確的上下文傳播(包括異步代碼)相關(guān):

  • 如果使用多個 TracerProvider 實例,則上下文泄漏 #1932

https://github.com/open-telemetry/opentelemetry-js/issues/1932

  • 如何在不傳遞 parent 的情況下創(chuàng)建嵌套 span #1963

https://github.com/open-telemetry/opentelemetry-js/issues/1963

  • 嵌套的子 span 沒有得到正確的父級 #1940

https://github.com/open-telemetry/opentelemetry-js/issues/1940

  • OpenTracing shim 不會改變上下文 #2016

https://github.com/open-telemetry/opentelemetry-js/issues/2016

  • Http Span 未鏈接/未設(shè)置父 Span #2333

https://github.com/open-telemetry/opentelemetry-js/issues/2333

相互沖突的數(shù)據(jù)傳播預(yù)期

每當我們添加前面討論過的 trace 函數(shù),或者只是嘗試使用 Zones 解決 scope 傳播時,就會出現(xiàn)預(yù)期沖突。

當前的 span 與 tags、breadcrumbs 等一起存儲在 scope 中的事實使數(shù)據(jù)傳播變得混亂, 因為 scope 的某些部分旨在僅傳播到內(nèi)部函數(shù)調(diào)用中(例如,tags), 而其他人預(yù)計會傳播回調(diào)用者(例如,breadcrumbs),尤其是在出現(xiàn) error 時。

這是一個例子:

  1. function a() { 
  2.   trace((span, scope) => { 
  3.     scope.setTag('func''a'); 
  4.     scope.setTag('id''123'); 
  5.     scope.addBreadcrumb('was in a'); 
  6.     try { 
  7.       b(); 
  8.     } catch(e) { 
  9.       // How to report the SpanID from the span in b? 
  10.     } finally { 
  11.       captureMessage('hello from a'); 
  12.       // tags: {func: 'a', id: '123'
  13.       // breadcrumbs: ['was in a''was in b'
  14.     } 
  15.   }) 
  16.  
  17. function b() { 
  18.   trace((span, scope) => { 
  19.     const fail = Math.random() > 0.5; 
  20.     scope.setTag('func''b'); 
  21.     scope.setTag('fail', fail.toString()); 
  22.     scope.addBreadcrumb('was in b'); 
  23.     captureMessage('hello from b'); 
  24.     // tags: {func: 'b', id: '123', fail: ?} 
  25.     // breadcrumbs: ['was in a''was in b'
  26.     if (fail) { 
  27.       throw Error('b failed'); 
  28.     } 
  29.   }); 

在上面的示例中,如果 error 在調(diào)用堆棧中冒泡,我們希望能夠報告 error 發(fā)生在哪個 span(通過引用 SpanID)。我們希望有面包屑來描述發(fā)生的一切,無論哪個 Zones 正在執(zhí)行, 我們希望在內(nèi)部 Zone 中設(shè)置一個 tag 來覆蓋來自父 Zone 的同名 tag, 同時繼承來自父 Zone 的所有其他 tag。每個 Zone 都有自己的 "current span"。

所有這些不同的期望使得很難以一種可以理解的方式重用當前的 scope 概念、面包屑的記錄方式以及這些不同的概念如何相互作用。

最后,值得注意的是,在不破壞現(xiàn)有 SDK API 的情況下,重組 scope 管理的更改很可能無法完成。現(xiàn)有的 SDK 概念 — 如 hubs、scopes、breadcrumbs、user、tags 和 contexts — 都必須重新建模。

Span 攝取模型

考慮由以下 span 樹描述的跟蹤:

  1. F* 
  2. ├─ B* 
  3. │  ├─ B 
  4. │  ├─ B 
  5. │  ├─ B 
  6. │  │  ├─ S* 
  7. │  │  ├─ S* 
  8. │  ├─ B 
  9. │  ├─ B 
  10. │  │  ├─ S* 
  11. │  ├─ B 
  12. │  ├─ B 
  13. │  ├─ B 
  14. │  │  ├─ S* 
  15.  
  16. where 
  17. F: span created on frontend service 
  18. B: span created on backend service 
  19. S: span created on storage service 

此跟蹤說明了 3 個被檢測的服務(wù),當用戶單擊網(wǎng)頁上的按鈕 (F) 時,后端 (B) 執(zhí)行一些工作,然后需要對存儲服務(wù) (S) 進行多次查詢。位于給定服務(wù)入口點的 Span 標有 * 以表示它們是 transaction。

我們可以通過這個例子來比較和理解 Sentry 的 span 攝取模型與 OpenTelemetry 和其他類似跟蹤系統(tǒng)使用的模型之間的區(qū)別。

在 Sentry 的 span 攝取模型中,屬于 transaction 的所有 span 必須在單個請求中一起發(fā)送。這意味著在整個 B* transaction 期間,所有 B span 都必須保存在內(nèi)存中,包括在下游服務(wù)(示例中的存儲服務(wù))上花費的時間。

在 OpenTelemetry 的模型中,span 在完成時被一起批處理,并且一旦 a) 批次中有一定數(shù)量的 span 或 b) 過了一定的時間就會發(fā)送批次。在我們的示例中,這可能意味著前 3 個 B 跨度將一起批處理并發(fā)送, 而第一個 S* 事務(wù)仍在存儲服務(wù)中進行。隨后,其他 B span 將一起批處理并在完成時發(fā)送,直到最終 B* transaction span 也被發(fā)送。

雖然 transaction 作為將 span 組合在一起并探索 Sentry 中感興趣的操作的一種方式特別有用, 但它們目前存在的形式會帶來額外的認知負擔。 SDK 維護人員和最終用戶在編寫檢測代碼時都必須了解并在 transaction 或 span 之間進行選擇。

在當前的攝取模型中已經(jīng)確定了接下來幾節(jié)中的問題,并且都與這種二分法有關(guān)。

事務(wù)的復(fù)雜 JSON 序列化

在 OpenTelemetry 的模型中, 所有跨度都遵循相同的邏輯格式。用戶和檢測庫可以通過將 key-value 屬性附加到任何 span 來為其提供更多含義。 wire 協(xié)議使用 span 列表將數(shù)據(jù)從一個系統(tǒng)發(fā)送到另一個系統(tǒng)。

  • https://github.com/open-telemetry/opentelemetry-proto/blob/ebef7c999f4dea62b5b033e92a221411c49c0966/opentelemetry/proto/trace/v1/trace.proto#L56-L235

與 OpenTelemetry 不同,Sentry 的模型對兩種類型的 span 進行了嚴格區(qū)分:transaction span(通常稱為 transactions)和 regular span。

在內(nèi)存中,transaction span 和 regular span 有一個區(qū)別:transaction span 有一個額外的屬性,即 transaction name。

但是,當序列化為 JSON 時,差異更大。 Sentry SDK 以直接類似于內(nèi)存中的 span 的格式將常規(guī) span 序列化為 JSON。相比之下,transaction span 的序列化需要將其 span 屬性映射到 Sentry Event (最初用于 report errors,擴展為專門用于 transactions 的新字段),并將所有子 span 作為列表嵌入 Event 中。

Transaction Span 獲取 Event 屬性

當 transaction 從其內(nèi)存表示轉(zhuǎn)換為 Event 時, 它會獲得更多無法分配給 regular span 的屬性, 例如 breadcrumbs, extra, contexts, event_id, fingerprint, release, environment, user 等。

生命周期鉤子

Sentry SDK 為 error 事件公開了一個 BeforeSend hook,允許用戶在將事件發(fā)送到 Sentry 之前修改和/或丟棄事件。

當引入新的 transaction 類型事件時,很快就決定此類事件不會通過 BeforeSend hook,主要有兩個原因:

  • 防止用戶代碼依賴 transaction 的雙重形式(有時看起來像一個 span,有時像一個 event,如前幾節(jié)所述);
  • 為了防止現(xiàn)有的 BeforeSend 函數(shù)在編寫時只考慮到 error 而干擾 transaction,無論是意外地改變它們、完全丟棄它們,還是導(dǎo)致一些其他意想不到的副作用。

然而,也很明顯需要某種形式的 lifecycle hook,以允許用戶執(zhí)行諸如更新 transaction 名稱之類的操作。

我們最終達成了中間立場,即通過使用 EventProcessor(一種更通用的 BeforeSend 形式)來允許更改/丟棄 transaction 事件。這通過在數(shù)據(jù)離開 SDK 之前讓用戶立即訪問他們的數(shù)據(jù)來解決問題,但它也有缺點,它比 BeforeSend 使用起來更復(fù)雜,并且還暴露了從未打算泄漏的 transaction 二元性。

相比之下,在 OpenTelemetry 中,span 通過 span processor,這是兩個生命周期鉤子:一個是在 span 開始時,一個是在它結(jié)束時。

嵌套事務(wù)

Sentry 的攝取模型不是為服務(wù)中的嵌套 transaction 而設(shè)計的。Transaction 旨在標記服務(wù)轉(zhuǎn)換。

在實踐中,SDK 無法防止 transaction 嵌套。最終結(jié)果可能會讓用戶感到驚訝,因為每筆 transaction 都會開始一棵新樹。關(guān)聯(lián)這些樹的唯一方法是通過 trace_id。

Sentry 的計費模型是針對每個事件的,無論是 error 事件還是 transaction 事件。這意味著 transaction 中的 transaction 會生成兩個可計費事件。

在 SDK 中,在 transaction 中進行 transaction 將導(dǎo)致內(nèi)部 span 被圍繞它們的最內(nèi)層 transaction “吞噬”。在這些情況下,創(chuàng)建 span 的代碼只會將它們添加到兩個 transaction 之一,從而導(dǎo)致另一個 transaction 中的檢測間隙。

Sentry 的 UI 并非旨在以有用的方式處理嵌套 transaction。當查看任何一個 transaction 時,就好像 transaction 中的所有其他 transaction 都不存在(樹視圖上沒有直接表示其他 transaction)。有一個 trace view 功能來可視化共享一個 trace_id 的所有 transaction, 但 trace view 僅通過顯示 transaction 而不是子 span 來提供跟蹤的概述。如果不先訪問某個 transaction,就無法導(dǎo)航到 trace view。

對于這種情況(偽代碼),用戶對 UI 中的期望也存在混淆:

  1. # if do_a_database_query returns 10 results, is the user 
  2. #   - seeing 11 transactions in the UI? 
  3. #   - billed for 11 transactions? 
  4. #   - see spans within create_thumbnail in the innermost transaction only
  5. with transaction("index-page"): 
  6.     results = do_a_database_query() 
  7.     for result in results: 
  8.         if result["needs_thumbnail"]: 
  9.             with transaction("create-thumbnail", {"resource": result["id"]}): 
  10.                 create_thumbnail(result) 

跨度不能存在于事務(wù)之外

Sentry 的追蹤體驗完全圍繞著存在于 transaction 中的 trace 部分。這意味著數(shù)據(jù)不能存在于 transaction 之外,即使它存在于 trace 中。

如果 SDK 沒有進行 transaction,則由 instrumentation 創(chuàng)建的 regular span 將完全丟失。也就是說,這對 Web server 來說不是什么問題,因為自動檢測的 transaction 隨著每個傳入請求開始和結(jié)束。

Transaction 的要求在前端(瀏覽器、移動和桌面應(yīng)用程序)上尤其具有挑戰(zhàn)性, 因為在這些情況下,自動檢測的 transaction 不太可靠地捕獲所有 span,因為它們在自動完成之前只持續(xù)有限的時間。

在 trace 以僅作為 span 而不是 transaction 進行檢測的操作開始的情況下,會出現(xiàn)另一個問題。在我們的 示例跟蹤中,產(chǎn)生 trace 的第一個 span 是由于單擊按鈕。如果按鈕點擊 F* 被檢測為常規(guī)的 span 而不是 transaction,則很可能不會捕獲來自前端的數(shù)據(jù)。然而,仍會捕獲 B 和 S span,導(dǎo)致不完整的蹤跡。

在 Sentry 的模型中,如果一個 span 不是一個 transaction 并且沒有作為 transaction 的祖先 span,那么該 span 將不會被攝取。反過來,這意味著在很多情況下,跟蹤丟失了有助于調(diào)試問題的關(guān)鍵信息,特別是在前端,transaction 需要在某個時刻結(jié)束但執(zhí)行可能會繼續(xù)。

自動和手動檢測面臨著決定是開始 span 還是 transaction 的挑戰(zhàn),考慮到以下因素,決定尤其困難:

如果沒有 transaction,則 span 丟失。

如果已經(jīng)存在 transaction,則存在嵌套事務(wù)問題。

缺少 Web Vitals 測量

Sentry 的瀏覽器工具收集 Web Vitals 測量值。但是,因為這些測量值是使用自動檢測的 transaction 作為載體發(fā)送到 Sentry 的,所以在自動 transaction 完成后由瀏覽器提供的測量值將丟失。

這會導(dǎo)致 transaction 丟失一些 Web Vitals 或?qū)?LCP 等指標進行非最終測量。

前端事務(wù)持續(xù)時間不可靠

因為所有的數(shù)據(jù)都必須在一個 transaction 中。Sentry 的瀏覽器 SDK 為每個頁面加載和每個導(dǎo)航創(chuàng)建一個 transaction。這些 transaction 必須在某個時間結(jié)束。

如果在 transaction 完成之前關(guān)閉瀏覽器選項卡并將其發(fā)送到 Sentry,則所有收集的數(shù)據(jù)都會丟失。因此,SDK 需要平衡丟失所有數(shù)據(jù)的風險與收集不完整和可能不準確的數(shù)據(jù)的風險。

在觀察到最后一個活動(例如傳出的 HTTP 請求)后空閑了一段時間后,Transaction 就完成了。這意味著頁面加載或?qū)Ш?transaction 的持續(xù)時間是一個相當隨意的值,不一定能改進或與其他事務(wù)相比,因為它不能準確代表任何具體和可理解的過程的持續(xù)時間。

我們通過將 LCP Web Vital 作為瀏覽器的默認性能指標來應(yīng)對這一限制。但是,如上所述,LCP 值可能會在最終確定之前發(fā)送,因此這不是理想的解決方案。

內(nèi)存緩沖影響服務(wù)器

如前所述,當前的攝取模型需要 Sentry SDK 來觀察內(nèi)存中的完整 span 樹。以恒定的并發(fā) transaction 流運行的應(yīng)用程序?qū)⑿枰罅康南到y(tǒng)資源來收集和處理跟蹤數(shù)據(jù)。Web 服務(wù)器是出現(xiàn)此問題的典型案例。

這意味著記錄 100% 的 span 和 100% 的 transaction 對于許多服務(wù)器端應(yīng)用程序來說是不可行的,因為所產(chǎn)生的開銷太高了。

無法批處理事務(wù)

Sentry 的攝取模型不支持一次攝取多個事件。特別是,SDK 不能將多個 transaction 批處理為一個請求。

因此,當多筆 transaction 幾乎同時完成時,SDK 需要為每個 transaction 發(fā)出單獨的請求。這種行為在最好的情況下是非常低效的,在最壞的情況下是對資源(如網(wǎng)絡(luò)帶寬和CPU周期)的嚴重且有問題的消耗。

兼容性

Transaction Span 的特殊處理與 OpenTelemetry 不兼容。使用 OpenTelemetry SDK 檢測現(xiàn)有應(yīng)用程序的用戶無法輕松使用 Sentry 來獲取和分析他們的數(shù)據(jù)。

Sentry 確實為 OpenTelemetry Collector 提供了一個 Sentry Exporter,但是,由于當前的攝取模型,Sentry Exporter 有一個主要的正確性限制。

https://github.com/open-telemetry/opentelemetry-collector-contrib/tree/main/exporter/sentryexporter#known-limitations

總結(jié)

通過在 Sentry 中構(gòu)建當前的跟蹤實現(xiàn),我們學(xué)到了很多。本文檔試圖捕捉許多已知的限制,以作為未來改進的基礎(chǔ)。

追蹤是一個復(fù)雜的主題,馴服這種復(fù)雜性并非易事。

第一組中的問題 - 與 scope propagation(作用域傳播) 相關(guān)的問題 - 是 SDK 及其設(shè)計方式獨有的問題。解決這些問題將需要對所有 SDK 進行內(nèi)部架構(gòu)更改,包括重新設(shè)計面包屑等舊功能, 但進行此類更改是實現(xiàn)簡單易用的 tracing helper(如可在任何上下文中工作并捕獲準確可靠的性能數(shù)據(jù)的 trace 函數(shù))的先決條件。請注意,此類更改幾乎肯定意味著發(fā)布新的主要 SDK 版本,這會破壞與現(xiàn)有版本的兼容性。

第二組中的問題 - 與 span ingestion model(跨度攝取模型) 相關(guān)的問題要復(fù)雜得多,因為為解決這些問題所做的任何更改都會影響產(chǎn)品的更多部分,并且需要多個團隊的協(xié)調(diào)努力。

 

盡管如此,對 ingestion model 進行更改將對產(chǎn)品產(chǎn)生不可估量的積極影響,因為這樣做會提高效率,使我們能夠收集更多數(shù)據(jù),并減少 instrumentation 的負擔。

 

責任編輯:武曉燕 來源: 黑客下午茶
相關(guān)推薦

2021-12-25 22:31:55

Sentry 監(jiān)控SDK 開發(fā) 性能監(jiān)控

2022-01-02 23:26:08

開發(fā)SDK Sentry

2022-01-21 21:33:03

開發(fā)JavaScript應(yīng)用

2022-01-03 22:59:30

開發(fā)SDK數(shù)據(jù)

2022-01-17 19:34:43

SentryWeb APISentry API

2022-01-02 06:59:43

SentrySDK 開發(fā)客戶端報告

2022-01-19 19:49:53

Sentry瀏覽器SDK

2022-01-11 20:42:54

開發(fā)Sentry標志

2022-01-15 23:33:47

SentryPyCharm配置

2022-01-18 23:26:45

開發(fā)

2021-12-15 20:06:48

ReactJSSentry開發(fā)者

2022-01-16 22:16:59

數(shù)據(jù)庫Sentry開發(fā)者

2022-01-13 20:13:31

元宇宙搜索引擎

2021-12-16 20:12:37

后端開發(fā)Sentry

2022-01-20 19:49:10

Sentry開發(fā)Scope

2021-12-17 19:15:51

前端蟲洞狀態(tài)

2021-11-17 18:38:32

avaScriptSDK調(diào)試

2020-12-11 09:06:50

異常監(jiān)控云服務(wù)

2021-09-13 05:00:09

監(jiān)控Trends 性能

2021-09-11 21:02:24

監(jiān)控Sentry Web性能
點贊
收藏

51CTO技術(shù)棧公眾號

欧美激情另类| 色尼玛亚洲综合影院| 涩涩视频免费看| 九九精品久久| 欧美三级乱人伦电影| 中国成人亚色综合网站| 俄罗斯嫩小性bbwbbw| 久久不射网站| 欧美刺激性大交免费视频| 中文字幕乱码在线| 欧美91在线|欧美| 亚洲一区av在线| 视频在线99| 好吊色在线观看| 奇米精品一区二区三区在线观看一| 久久久国产精品一区| 变态另类丨国产精品| 日本久久二区| 粉嫩av一区二区三区免费野| 婷婷视频在线播放| 日本成人一区| 国产精品77777| 国产精品h片在线播放| 婷婷在线精品视频| 欧美一区三区| 亚洲精品mp4| 婷婷中文字幕在线观看| 伊人色综合一区二区三区影院视频 | 国产www在线| 综合久久婷婷| 丝袜一区二区三区| 中文字幕一区二区三区人妻不卡| 亚洲精品无播放器在线播放| 欧美性20hd另类| 91视频 - 88av| 美女写真理伦片在线看| 久久精品水蜜桃av综合天堂| 国产精品一国产精品最新章节| 国产精品毛片一区二区在线看舒淇| 午夜在线观看免费一区| 色综合久久88| 希岛爱理中文字幕| 日韩电影免费网站| 国产午夜精品免费一区二区三区 | 久久久久久久久久久综合| 最近高清中文在线字幕在线观看| 91丨九色porny丨蝌蚪| 国产99在线免费| 国产人妖在线播放| 久久99深爱久久99精品| 国产精品美女www爽爽爽视频| 在线能看的av| 国产日韩欧美一区在线| 97在线观看免费| 国产成人在线免费观看视频| 亚洲五月婷婷| 久久久亚洲网站| 精品少妇theporn| 欧美视频日韩| 欧美大片免费观看| 久久成人国产精品入口| 欧美日韩国产免费观看| 九九精品在线视频| 久久无码精品丰满人妻| 亚洲高清av| 91av成人在线| 日本中文字幕第一页| 久久成人国产| 国产精品久久久久av| 在线免费一区二区| 久久99精品一区二区三区三区| 国产欧美最新羞羞视频在线观看| 一级全黄少妇性色生活片| 极品少妇一区二区| 99国产视频| 神马午夜精品95| 久久久久88色偷偷免费| 青娱乐国产91| 黄网站免费在线播放| 亚洲精品成人少妇| 97超碰人人澡| 成人影院大全| 欧美日韩一区二区三区在线| 天天干天天操天天玩| 久久丁香四色| 亚洲高清在线观看| 自拍偷拍视频亚洲| 亚洲一本二本| 91精品国产高清久久久久久91| 精品人妻无码一区二区性色| 蜜臀av性久久久久蜜臀av麻豆| 国产欧美日韩专区发布| 亚洲精品字幕在线观看| 久久视频一区二区| 国产成年人在线观看| 1区2区3区在线| 欧美无乱码久久久免费午夜一区| 国产精品探花在线播放| 青青草原在线亚洲| 爱福利视频一区| 国产网友自拍视频| 蜜臀av性久久久久蜜臀aⅴ四虎| 91入口在线观看| 久草视频在线看| 亚洲免费av高清| 欧美韩国日本在线| 秋霞午夜一区二区三区视频| 精品福利一区二区三区| 超碰人人干人人| 影音先锋久久久| 国产日韩欧美综合| 欧美男男激情freegay| 亚洲人成在线播放网站岛国| 免费观看精品视频| 一区二区三区亚洲变态调教大结局 | 国产精品视频免费在线观看| 亚洲欧美黄色片| 国产精品萝li| 99草草国产熟女视频在线| 亚洲电影一区| zzjj国产精品一区二区| 国产精品va无码一区二区三区| 国产乱人伦精品一区二区在线观看| 免费亚洲一区二区| 18video性欧美19sex高清| 欧美人与性动xxxx| 无码一区二区三区在线| 亚洲午夜极品| 91丝袜美腿美女视频网站| 国产永久免费高清在线观看视频| 亚洲一二三四区不卡| www.色就是色.com| 成人嘿咻视频免费看| 国产91ⅴ在线精品免费观看| 亚洲成熟女性毛茸茸| 国产精品久久福利| 日韩av片网站| 国产一区不卡| 日本一区二区三区四区视频| 亚洲精品一区二区三区不卡| 一区二区在线观看视频在线观看| 亚洲免费av一区| 国产日产精品一区二区三区四区的观看方式 | 99蜜桃在线观看免费视频网站| 天天综合视频在线观看| 欧美在线免费观看视频| 老牛影视av老牛影视av| 国产亚洲毛片在线| 久久国产精品高清| a一区二区三区| 亚洲男人av电影| 国产中文字幕视频| 国产清纯白嫩初高生在线观看91 | 美腿丝袜在线亚洲一区| 日韩欧美一区二区视频在线播放 | 欧美性猛交xxxx免费看漫画 | 欧美肥臀大乳一区二区免费视频| 国产精品无码天天爽视频| 亚洲视频中文字幕| 亚洲精品无码久久久久久久| 综合一区av| 亚洲自拍av在线| 福利在线导航136| 日韩成人av在线播放| 日本熟妇乱子伦xxxx| av中文字幕亚洲| 免费高清在线观看免费| 国产精品美女久久久久久不卡| 国产精品av免费在线观看| 91美女视频在线| 制服丝袜在线91| 欧美日韩在线视频免费播放| 成人一区二区三区在线观看| 久久天天躁日日躁| 国产一区二区在线免费播放| 精品国产乱码| 92国产精品久久久久首页 | 国产剧情一区| 成人黄色av网站| 成人性生交大片免费看在线播放| 精品国产99国产精品| 9i精品福利一区二区三区| 国产精品欧美久久久久无广告| 在线播放免费视频| 最新成人av网站| 性欧美videosex高清少妇| 国产欧美88| 欧美亚洲国产视频| 欧洲不卡视频| 日韩va亚洲va欧洲va国产| 中文无码av一区二区三区| 亚洲男帅同性gay1069| 韩国三级hd两男一女| 日韩在线观看一区二区| 欧美视频在线第一页| 亚洲桃色综合影院| 成人国产精品免费视频| 欧美videossex| 亚洲精品资源美女情侣酒店| 在线观看亚洲一区二区| 亚洲国产精品影院| 国产18无套直看片| proumb性欧美在线观看| www亚洲成人| 在线欧美不卡| 一道精品一区二区三区| 牛牛视频精品一区二区不卡| 国产日韩精品在线| a国产在线视频| 久久天堂电影网| 精品成人一区二区三区免费视频| 日韩一区二区三区免费看| 亚洲大尺度在线观看| 亚洲大型综合色站| 日韩三级久久久| 26uuu欧美日本| 91porn在线| 久99久精品视频免费观看| 欧美网站免费观看| 激情偷拍久久| 天堂а√在线中文在线| 久久中文视频| 日本精品一区二区| 日韩大胆成人| 国产精品免费看一区二区三区| 国产精品亚洲成在人线| 啪一啪鲁一鲁2019在线视频| 韩国日本一区| 欧美老女人在线视频| 日本在线观看视频| 综合av色偷偷网| 精品推荐蜜桃传媒| 亚洲欧美制服第一页| 天天摸夜夜添狠狠添婷婷| 日韩你懂的在线播放| 国产精品视频一二区| 欧美午夜片在线观看| 国产成人无码av| 欧美日韩性视频| 日韩av男人天堂| 夜夜嗨av一区二区三区四季av| 午夜精品久久久久99蜜桃最新版| 欧美极品少妇xxxxⅹ高跟鞋| 偷拍女澡堂一区二区三区| 99久久免费国产| 国产亚洲色婷婷久久99精品91| 成人福利电影精品一区二区在线观看| 色黄视频免费看| 国产一区二区三区久久久| 欧美一级特黄aaa| 韩国三级中文字幕hd久久精品| 日本中文字幕观看| 国精产品一区一区三区mba视频 | 久久女人天堂| 国产精品色午夜在线观看| 黑人巨大精品欧美一区二区桃花岛| 97精品国产91久久久久久| 黑森林国产精品av| 45www国产精品网站| 美女100%一区| 国产精品99久久久久久久久久久久| 日韩网站中文字幕| 国产精品嫩草影院一区二区| 日韩精品一级毛片在线播放| 91午夜理伦私人影院| 秋霞影院一区| 国产区欧美区日韩区| 林ゆな中文字幕一区二区| 蜜桃传媒视频麻豆第一区免费观看| 久久99高清| 一本色道婷婷久久欧美| 欧美国产高清| 国产青青在线视频| 日韩精品乱码av一区二区| 国产wwwxx| 国内外成人在线| 手机免费看av片| 国产亚洲视频系列| 精品无码久久久久成人漫画 | 全部毛片永久免费看| 色爱区综合激月婷婷| 中文字幕+乱码+中文乱码www| 69久久夜色精品国产69蝌蚪网| 亚洲第一视频在线| 亚洲乱码国产乱码精品精天堂 | www.国产精品一区| 你懂的视频在线一区二区| 日韩一区自拍| 欧美这里只有精品| 久久综合九色综合欧美狠狠| 嫩草视频免费在线观看| 成人免费电影视频| 在线观看免费黄色网址| 亚洲最大成人综合| 日本黄色一级视频| 欧美一级艳片视频免费观看| 天堂在线一二区| 国产一区二区三区直播精品电影 | 国内精品中文字幕| 国产激情久久| 久久五月天婷婷| 欧美成人国产| 中文字幕视频在线免费观看| 成人精品亚洲人成在线| 成年人在线免费看片| 五月天一区二区| 国产精品嫩草影院精东| 日韩毛片中文字幕| 在线视频观看国产| 国产精品久久一区| 欧美电影免费网站| 黄色一级大片免费| 久久99精品久久久久久国产越南| 亚洲视频在线播放免费| 亚洲欧美日韩在线不卡| 91porny九色| 亚洲精品国产电影| 怡红院av在线| 91精品国产综合久久香蕉| 欧美女王vk| 国产成人精品视频免费看| 国产91丝袜在线播放| 亚洲少妇xxx| 欧美唯美清纯偷拍| 国产69精品久久app免费版| 91精品国产高清自在线| 99热这里只有精品首页 | 中国毛片在线观看| 亚洲成人av一区二区| 国产女人爽到高潮a毛片| 中文字幕免费精品一区| 中文在线最新版地址| 国产精品综合久久久久久| 欧美1区2区3区| 伊人国产精品视频| 亚洲特黄一级片| 99在线观看精品视频| 久久九九国产精品怡红院| 免费视频成人| 亚洲一卡二卡三卡| 久久99国产精品久久99果冻传媒| 天堂网av2018| 欧美三级欧美一级| 免费**毛片在线| 成人激情av在线| 天天做天天爱综合| 日本高清免费在线视频| 亚洲精品高清视频在线观看| www.av在线.com| 欧美激情在线播放| ccyy激情综合| 欧美啪啪免费视频| 久久午夜免费电影| 色网站在线播放| 亚洲精品视频网上网址在线观看| 在线视频超级| 日本一区二区高清视频| 日韩电影在线免费看| 男人天堂资源网| 91精品国产综合久久福利| 性欧美高清come| 狠狠色噜噜狠狠狠狠色吗综合| 国产视频亚洲| 无码少妇一区二区| 欧美酷刑日本凌虐凌虐| 亚洲区欧洲区| 国内精品久久国产| 日韩精品色哟哟| 亚洲视频重口味| 精品国产91久久久久久久妲己 | 91精品视频在线| 欧美日韩免费| 久久久国产精品无码| 色婷婷久久一区二区三区麻豆| 在线观看av黄网站永久| 92看片淫黄大片看国产片| 伊人狠狠色j香婷婷综合| 五月婷婷综合在线观看| 欧美无砖砖区免费| 蜜臀av在线| 日韩亚洲欧美精品| 国产精品一区二区在线播放| 日韩三级免费看| 最好看的2019年中文视频| 香蕉成人app| 午夜激情福利在线| 亚洲黄色片在线观看| 四虎在线观看| 成人免费激情视频| 国产欧美日韩一级| 四虎永久免费在线| 日韩精品在线影院| 精品国产亚洲一区二区三区在线 | 欧洲精品久久| 国产精品一二三四| 蜜臀精品一区二区三区| 久久影视电视剧免费网站清宫辞电视| 神马日本精品| 少妇愉情理伦片bd| 欧美亚洲动漫精品|