本文次要钻研一下dubbo-go的tracingFilter

tracingFilter

dubbo-go-v1.4.2/filter/filter_impl/tracing_filter.go

const (    tracingFilterName = "tracing")// this should be executed before users set their own Tracerfunc init() {    extension.SetFilter(tracingFilterName, newTracingFilter)    opentracing.SetGlobalTracer(opentracing.NoopTracer{})}var (    errorKey   = "ErrorMsg"    successKey = "Success")// if you wish to using opentracing, please add the this filter into your filter attribute in your configure file.// notice that this could be used in both client-side and server-side.type tracingFilter struct {}
  • tracingFilter的init办法设置了newTracingFilter

newTracingFilter

dubbo-go-v1.4.2/filter/filter_impl/tracing_filter.go

func newTracingFilter() filter.Filter {    if tracingFilterInstance == nil {        tracingFilterInstance = &tracingFilter{}    }    return tracingFilterInstance}
  • newTracingFilter办法实例化tracingFilter

Invoke

dubbo-go-v1.4.2/filter/filter_impl/tracing_filter.go

func (tf *tracingFilter) Invoke(ctx context.Context, invoker protocol.Invoker, invocation protocol.Invocation) protocol.Result {    var (        spanCtx context.Context        span    opentracing.Span    )    operationName := invoker.GetUrl().ServiceKey() + "#" + invocation.MethodName()    wiredCtx := ctx.Value(constant.TRACING_REMOTE_SPAN_CTX)    preSpan := opentracing.SpanFromContext(ctx)    if preSpan != nil {        // it means that someone already create a span to trace, so we use the span to be the parent span        span = opentracing.StartSpan(operationName, opentracing.ChildOf(preSpan.Context()))        spanCtx = opentracing.ContextWithSpan(ctx, span)    } else if wiredCtx != nil {        // it means that there has a remote span, usually from client side. so we use this as the parent        span = opentracing.StartSpan(operationName, opentracing.ChildOf(wiredCtx.(opentracing.SpanContext)))        spanCtx = opentracing.ContextWithSpan(ctx, span)    } else {        // it means that there is not any span, so we create a span as the root span.        span, spanCtx = opentracing.StartSpanFromContext(ctx, operationName)    }    defer func() {        span.Finish()    }()    result := invoker.Invoke(spanCtx, invocation)    span.SetTag(successKey, result.Error() != nil)    if result.Error() != nil {        span.LogFields(log.String(errorKey, result.Error().Error()))    }    return result}
  • Invoke办法首先构建operationName,而后应用opentracing.StartSpan开启span,之后defer执行span.Finish(),而后执行invoker.Invoke(spanCtx, invocation),最初设置span.SetTag及span.LogFields

OnResponse

dubbo-go-v1.4.2/filter/filter_impl/tracing_filter.go

func (tf *tracingFilter) OnResponse(ctx context.Context, result protocol.Result,    invoker protocol.Invoker, invocation protocol.Invocation) protocol.Result {    return result}
  • OnResponse办法间接返回result

小结

tracingFilter的Invoke办法首先构建operationName,而后应用opentracing.StartSpan开启span,之后defer执行span.Finish(),而后执行invoker.Invoke(spanCtx, invocation),最初设置span.SetTag及span.LogFields

doc

  • tracing_filter