<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          分布式鏈路追蹤續(xù)集

          共 6121字,需瀏覽 13分鐘

           ·

          2021-10-09 18:05

          本文是 分布式鏈路追蹤 的續(xù)集。

          在上一文中提到為了統(tǒng)一各種分布式追蹤系統(tǒng)的實(shí)現(xiàn),CNCF (云原生計(jì)算基金會(huì))下的 OpenTracing 項(xiàng)目定義了一套分布式追蹤的標(biāo)準(zhǔn),可以使用 OpenTracing API 完成代碼的監(jiān)控埋點(diǎn),最后用戶自由選擇遵循 OpenTracing 標(biāo)準(zhǔn)的鏈路追蹤系統(tǒng),比如 jaeger 。

          但是現(xiàn)在訪問 OpenTracing 的 官網(wǎng)[1] ,可以發(fā)現(xiàn)官網(wǎng)提醒 OpenTracing 和 OpenCensus 已經(jīng)被合并成為 OpenTelemetry 。(在上文編寫時(shí)我未發(fā)現(xiàn)到,感謝 Donald Liu 大佬的提醒)

          cncf[2] 上也可以發(fā)現(xiàn) OpenTracing 已經(jīng)被 Archived 了

          相應(yīng)地,OpenTelemetry 已經(jīng)正式成為了 CNCF 的孵化項(xiàng)目 參考[3]

          Both OpenTracing and OpenCensus will be further deprecated in the coming weeks, with OpenTracing being formally archived by the CNCF TOC.

          緣由

          參考[4]

          在 APM (Application Performance Monitoring) 領(lǐng)域,或者說微服務(wù)的可觀察性方面包括有分布式鏈路追蹤,指標(biāo)監(jiān)控和日志。

          OpenTracing 是最早為分布式追蹤制定了一套平臺(tái)無關(guān)、廠商無關(guān)的協(xié)議標(biāo)準(zhǔn)的項(xiàng)目,并以此成為了 CNCF 的孵化項(xiàng)目。

          在之后,谷歌牽頭,微軟加入,創(chuàng)建了 OpenCensus 項(xiàng)目統(tǒng)一 Metrics 基礎(chǔ)指標(biāo)監(jiān)控的使用方式,還做了 OpenTracing 的老本行:分布式追蹤。

          一山不容二虎,OpenTracing 和 OpenCensus 愈打愈烈,對(duì)我們用戶來講,實(shí)在是太不友好了。

          然后 OpenTelemetry 橫空出世了,OpenTracing 和 OpenCensus 既然都這么好,干脆你們合并起來吧,我 OpenTelemetry 來兼容你們。

          OpenTelemetry 的自身定位十分明確:數(shù)據(jù)采集和標(biāo)準(zhǔn)規(guī)范的統(tǒng)一,對(duì)于數(shù)據(jù)如何去使用、存儲(chǔ)、展示、告警,官方是不涉及的。

          OpenTelemetry 的終極目標(biāo)十分偉大:實(shí)現(xiàn) Metrics、Tracing、Logging 的融合及大一統(tǒng),作為 APM 的數(shù)據(jù)采集終極解決方案。

          然后就是現(xiàn)在的故事了,OpenTelemetry 正式成為 CNCF 的孵化項(xiàng)目,OpenTracing 和 OpenCensus 不再維護(hù)。

          兼容性

          這個(gè)放心,大部分的知識(shí)點(diǎn)定義還是一致的 (如數(shù)據(jù)模型:Trace, Span, SpanContext) ,但是 API 的使用會(huì)有所區(qū)別,詳細(xì)可以查看 OpenTelemetry 規(guī)范文檔[5]

          承接上文

          我們現(xiàn)在對(duì)上文的 OpenTracing API 的代碼做出修改,擁抱 OpenTelemetry 吧!

          安裝 OpenTelemetry for Go 依賴

          go?get?go.opentelemetry.io/[email protected]?go.opentelemetry.io/otel/[email protected]?go.opentelemetry.io/otel/exporters/stdout/[email protected]?go.opentelemetry.io/otel/[email protected]

          安裝 OpenTelemetry for jaeger 依賴

          go?get?-u?go.opentelemetry.io/otel/exporters/jaeger

          OpenTelemetry 官方為多種開源框架提供了開箱即用的 Instrumentation Packages ,如 gin , beego , mux , go-kit 等,當(dāng)然也支持 net/http 標(biāo)準(zhǔn)庫 ,更多可瀏覽opentelemetry-go-contrib[6]

          我們使用的是 net/http 標(biāo)準(zhǔn)庫,所以直接導(dǎo)入 otelhttp

          go?get?go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp

          main.go 修改如下:

          package?main

          import?(
          ?"fmt"
          ?"log"
          ?"math/rand"
          ?"net/http"
          ?"time"

          ?"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
          ?"go.opentelemetry.io/otel"
          ?"go.opentelemetry.io/otel/attribute"
          ?"go.opentelemetry.io/otel/exporters/jaeger"
          ?"go.opentelemetry.io/otel/propagation"
          ?"go.opentelemetry.io/otel/sdk/resource"
          ?tracesdk?"go.opentelemetry.io/otel/sdk/trace"
          ?semconv?"go.opentelemetry.io/otel/semconv/v1.4.0"
          ?"go.opentelemetry.io/otel/trace"
          )

          func?init()?{
          ?exp,?err?:=?jaeger.New(jaeger.WithAgentEndpoint())
          ?if?err?!=?nil?{
          ??panic(err)
          ?}
          ?tp?:=?tracesdk.NewTracerProvider(
          ??tracesdk.WithSampler(tracesdk.AlwaysSample()),
          ??tracesdk.WithBatcher(exp),
          ??tracesdk.WithResource(resource.NewWithAttributes(
          ???semconv.SchemaURL,
          ???semconv.ServiceNameKey.String("opentelemetry-example"),?//?服務(wù)名
          ???semconv.ServiceVersionKey.String("0.0.1"),
          ??)),
          ?)
          ?otel.SetTracerProvider(tp)
          ?otel.SetTextMapPropagator(propagation.NewCompositeTextMapPropagator(propagation.TraceContext{},?propagation.Baggage{}))
          }

          func?main()?{
          ?port?:=?8080
          ?addr?:=?fmt.Sprintf(":%d",?port)
          ?mux?:=?http.NewServeMux()
          ?mux.HandleFunc("/",?indexHandler)
          ?mux.Handle("/home",?otelhttp.NewHandler(http.HandlerFunc(homeHandler),?"請(qǐng)求?/home"))
          ?mux.Handle("/async",?otelhttp.NewHandler(http.HandlerFunc(serviceHandler),?"請(qǐng)求?/async"))
          ?mux.Handle("/service",?otelhttp.NewHandler(http.HandlerFunc(serviceHandler),?"請(qǐng)求?/service"))
          ?mux.Handle("/db",?otelhttp.NewHandler(http.HandlerFunc(dbHandler),?"請(qǐng)求?/db"))
          ?fmt.Printf("http://localhost:%d\n",?port)
          ?log.Fatal(http.ListenAndServe(addr,?mux))
          }

          //?主頁?Html
          func?indexHandler(w?http.ResponseWriter,?r?*http.Request)?{
          ?w.Write([]byte(`?點(diǎn)擊開始發(fā)起請(qǐng)求?`))
          }

          func?homeHandler(w?http.ResponseWriter,?r?*http.Request)?{
          ?w.Write([]byte("開始請(qǐng)求...\n"))

          ?ctx?:=?r.Context()
          ?span :=?trace.SpanFromContext(ctx)
          ?defer?span.End()

          ?//?發(fā)起異步請(qǐng)求
          ?asyncReq,?_?:=?http.NewRequest("GET",?"http://localhost:8080/async",?nil)
          ?//?傳遞span的上下文信息
          ?//?將關(guān)于本地追蹤調(diào)用的span context,設(shè)置到http?header上,并傳遞出去
          ?otel.GetTextMapPropagator().Inject(ctx,
          ??propagation.HeaderCarrier(asyncReq.Header),
          ?)
          ?go?func()?{
          ??if?_,?err?:=?http.DefaultClient.Do(asyncReq);?err?!=?nil?{
          ???span.RecordError(err)
          ???span.SetAttributes(
          ????attribute.String("請(qǐng)求?/async?error",?err.Error()),
          ???)
          ??}
          ?}()

          ?time.Sleep(time.Duration(rand.Intn(200))?*?time.Millisecond)

          ?//?發(fā)起同步請(qǐng)求
          ?syncReq,?_?:=?http.NewRequest("GET",?"http://localhost:8080/service",?nil)
          ?otel.GetTextMapPropagator().Inject(ctx,
          ??propagation.HeaderCarrier(syncReq.Header),
          ?)
          ?if?_,?err?:=?http.DefaultClient.Do(syncReq);?err?!=?nil?{
          ??span.RecordError(err)
          ??span.SetAttributes(
          ???attribute.String("請(qǐng)求?/service?error",?err.Error()),
          ??)
          ?}
          ?w.Write([]byte("請(qǐng)求結(jié)束!"))
          }

          //?模擬業(yè)務(wù)請(qǐng)求
          func?serviceHandler(w?http.ResponseWriter,?r?*http.Request)?{
          ?//?通過http?header,提取span元數(shù)據(jù)信息
          ?span :=?trace.SpanFromContext(
          ??otel.GetTextMapPropagator().Extract(r.Context(),?propagation.HeaderCarrier(r.Header)),
          ?)
          ?defer?span.End()

          ?dbReq,?_?:=?http.NewRequest("GET",?"http://localhost:8080/db",?nil)
          ?otel.GetTextMapPropagator().Inject(r.Context(),?propagation.HeaderCarrier(dbReq.Header))
          ?if?_,?err?:=?http.DefaultClient.Do(dbReq);?err?!=?nil?{
          ??span.RecordError(err)
          ??span.SetAttributes(
          ???attribute.String("請(qǐng)求?/db?error",?err.Error()),
          ??)
          ?}

          ?time.Sleep(time.Duration(rand.Intn(200))?*?time.Millisecond)
          }

          //?模擬DB調(diào)用
          func?dbHandler(w?http.ResponseWriter,?r?*http.Request)?{
          ?//?通過http?header,提取span元數(shù)據(jù)信息
          ?span :=?trace.SpanFromContext(
          ??otel.GetTextMapPropagator().Extract(r.Context(),?propagation.HeaderCarrier(r.Header)),
          ?)
          ?defer?span.End()

          ?time.Sleep(time.Duration(rand.Intn(200))?*?time.Millisecond)
          }

          同樣的部署到集群中

          kubectl?apply?-f?https://raw.githubusercontent.com/togettoyou/jaeger-example/master/jaeger-example-opentelemetry.yaml?-n?observability

          訪問后觀察 Jaeger UI 可以發(fā)現(xiàn)調(diào)用鏈和之前的也一致,包含 5 個(gè) Span

          具體 Span 信息

          參考資料

          [1]

          官網(wǎng): https://opentracing.io/

          [2]

          cncf: https://www.cncf.io/archived-projects/

          [3]

          參考: https://www.cncf.io/blog/2021/08/26/opentelemetry-becomes-a-cncf-incubating-project/

          [4]

          參考: https://github.com/open-telemetry/docs-cn/blob/main/OT.md

          [5]

          OpenTelemetry 規(guī)范文檔: https://github.com/open-telemetry/opentelemetry-specification/blob/main/specification/trace/api.md

          [6]

          opentelemetry-go-contrib: https://github.com/open-telemetry/opentelemetry-go-contrib/blob/main/instrumentation/README.md


          瀏覽 94
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  亚洲国产AV电影 | 久热在线观看 | 国产手机在线操你啦 | 免费在线观看视频无码 | 国产三级日本三级韩国三级 |