@@ -12,11 +12,12 @@ import (
1212 "sync"
1313 "time"
1414
15+ "github.com/SkyAPM/go2sky"
1516 cloudevents "github.com/cloudevents/sdk-go/v2"
17+ dapr "github.com/dapr/go-sdk/client"
1618 "github.com/dapr/go-sdk/service/common"
1719 "k8s.io/klog/v2"
18-
19- dapr "github.com/dapr/go-sdk/client"
20+ agentv3 "skywalking.apache.org/repo/goapi/collect/language/agent/v3"
2021)
2122
2223var (
@@ -54,6 +55,7 @@ const (
5455 SelfHostMode = "self-host"
5556 TestModeOn = "on"
5657 innerEventTypePrefix = "io.openfunction.function"
58+ tracingProviderSkywalking = "skywalking"
5759)
5860
5961type Runtime string
@@ -154,6 +156,9 @@ type RuntimeContext interface {
154156
155157 // GetPluginsTracingCfg returns the TracingConfig interface.
156158 GetPluginsTracingCfg () TracingConfig
159+
160+ // HasPluginsTracingCfg returns nil if there is no TracingConfig.
161+ HasPluginsTracingCfg () bool
157162}
158163
159164type Context interface {
@@ -361,6 +366,12 @@ func (ctx *FunctionContext) Send(outputName string, data []byte) ([]byte, error)
361366 ie := NewInnerEvent (ctx )
362367 ie .MergeMetadata (ctx .GetInnerEvent ())
363368 ie .SetUserData (data )
369+
370+ // Set the exit span for tracing
371+ if err := setExitSpan (ctx , ie , outputName ); err != nil {
372+ klog .Warningf ("failed to set exit span: %v" , err )
373+ }
374+
364375 payload = ie .GetCloudEventJSON ()
365376 }
366377
@@ -573,6 +584,10 @@ func (ctx *FunctionContext) GetPluginsTracingCfg() TracingConfig {
573584 return ctx .PluginsTracing
574585}
575586
587+ func (ctx * FunctionContext ) HasPluginsTracingCfg () bool {
588+ return ctx .PluginsTracing != nil
589+ }
590+
576591func (ctx * FunctionContext ) WithOut (out * FunctionOut ) RuntimeContext {
577592 ctx .mu .Lock ()
578593 defer ctx .mu .Unlock ()
@@ -824,6 +839,35 @@ func getBuildingBlockType(componentType string) (ResourceType, error) {
824839 return "" , errors .New ("invalid component type" )
825840}
826841
842+ func setExitSpan (ctx * FunctionContext , innerEvent InnerEvent , target string ) error {
843+ if ! ctx .HasPluginsTracingCfg () || ! ctx .GetPluginsTracingCfg ().IsEnabled () {
844+ return nil
845+ }
846+
847+ switch ctx .GetPluginsTracingCfg ().ProviderName () {
848+ case tracingProviderSkywalking :
849+ tracer := go2sky .GetGlobalTracer ()
850+ if tracer == nil {
851+ return errors .New ("skywalking is not enabled" )
852+ }
853+
854+ span , err := tracer .CreateExitSpan (ctx .GetNativeContext (), ctx .GetName (), target , func (headerKey , headerValue string ) error {
855+ innerEvent .SetMetadata (headerKey , headerValue )
856+ return nil
857+ })
858+ if err != nil {
859+ return err
860+ }
861+ defer span .End ()
862+
863+ span .SetSpanLayer (agentv3 .SpanLayer_FAAS )
864+ span .SetComponent (5013 )
865+ return nil
866+ default :
867+ return nil
868+ }
869+ }
870+
827871func ConvertUserDataToBytes (data interface {}) []byte {
828872 if d , ok := data .([]byte ); ok {
829873 return d
0 commit comments