func BuildSingleHeader(sc model.SpanContext) string {
	header := []string{}
	if !sc.TraceID.Empty() && sc.ID > 0 {
		header = append(header, sc.TraceID.String(), sc.ID.String())
	}
	if sc.Debug {
		header = append(header, "d")
	} else if sc.Sampled != nil {
		if *sc.Sampled {
			header = append(header, "1")
		} else {
			header = append(header, "0")
		}
	}
	if sc.ParentID != nil {
		header = append(header, sc.ParentID.String())
	}
	return strings.Join(header, "-")
}
BuildSingleHeader takes the values from the SpanContext and builds the B3 header
package b3
import (
	"strconv"
	"strings"
	"github.com/openzipkin/zipkin-go/model"
)
func ParseHeaders(
	hdrTraceID, hdrSpanID, hdrParentSpanID, hdrSampled, hdrFlags string,
) (*model.SpanContext, error) {
	var (
		err           error
		spanID        uint64
		requiredCount int
		sc            = &model.SpanContext{}
	)
	switch strings.ToLower(hdrSampled) {
	case "0", "false":
		sampled := false
		sc.Sampled = &sampled
	case "1", "true":
		sampled := true
		sc.Sampled = &sampled
	case "":
	default:
		return nil, ErrInvalidSampledHeader
	}
	if hdrFlags == "1" {
		sc.Debug = true
		sc.Sampled = nil
	}
	if hdrTraceID != "" {
		requiredCount++
		if sc.TraceID, err = model.TraceIDFromHex(hdrTraceID); err != nil {
			return nil, ErrInvalidTraceIDHeader
		}
	}
	if hdrSpanID != "" {
		requiredCount++
		if spanID, err = strconv.ParseUint(hdrSpanID, 16, 64); err != nil {
			return nil, ErrInvalidSpanIDHeader
		}
		sc.ID = model.ID(spanID)
	}
	if requiredCount != 0 && requiredCount != 2 {
		return nil, ErrInvalidScope
	}
	if hdrParentSpanID != "" {
		if requiredCount == 0 {
			return nil, ErrInvalidScopeParent
		}
		if spanID, err = strconv.ParseUint(hdrParentSpanID, 16, 64); err != nil {
			return nil, ErrInvalidParentSpanIDHeader
		}
		parentSpanID := model.ID(spanID)
		sc.ParentID = &parentSpanID
	}
	return sc, nil
}
func ParseSingleHeader(contextHeader string) (*model.SpanContext, error) {
	if contextHeader == "" {
		return nil, ErrEmptyContext
	}
	var (
		sc       = model.SpanContext{}
		sampling string
	)
	headerLen := len(contextHeader)
	if headerLen == 1 {
		sampling = contextHeader
	} else if headerLen == 16 || headerLen == 32 {
		return nil, ErrInvalidScope
	} else if headerLen >= 16+16+1 {
		var high, low uint64
		pos := 0
		if string(contextHeader[16]) != "-" {
			var err error
			high, err = strconv.ParseUint(contextHeader[0:16], 16, 64)
			if err != nil {
				return nil, ErrInvalidTraceIDValue
			}
			pos = 16
		}
		low, err := strconv.ParseUint(contextHeader[pos:pos+16], 16, 64)
		if err != nil {
			return nil, ErrInvalidTraceIDValue
		}
		sc.TraceID = model.TraceID{High: high, Low: low}
		rawID, err := strconv.ParseUint(contextHeader[pos+16+1:pos+16+1+16], 16, 64)
		if err != nil {
			return nil, ErrInvalidSpanIDValue
		}
		sc.ID = model.ID(rawID)
		if headerLen > pos+16+1+16 {
			if headerLen == pos+16+1+16+1 {
				return nil, ErrInvalidSampledByte
			}
			if headerLen == pos+16+1+16+1+1 {
				sampling = string(contextHeader[pos+16+1+16+1])
			} else if headerLen == pos+16+1+16+1+16 {
				return nil, ErrInvalidScopeParentSingle
			} else if headerLen == pos+16+1+16+1+1+1+16 {
				sampling = string(contextHeader[pos+16+1+16+1])
				rawParentID, err := strconv.ParseUint(contextHeader[pos+16+1+16+1+1+1:], 16, 64)
				if err != nil {
					return nil, ErrInvalidParentSpanIDValue
				}
				parentID := model.ID(rawParentID)
				sc.ParentID = &parentID
			} else {
				return nil, ErrInvalidParentSpanIDValue
			}
		}
	} else {
		return nil, ErrInvalidTraceIDValue
	}
	switch sampling {
	case "d":
		sc.Debug = true
	case "1":
		trueVal := true
		sc.Sampled = &trueVal
	case "0":
		falseVal := false
		sc.Sampled = &falseVal
	case "":
	default:
		return nil, ErrInvalidSampledByte
	}
	return &sc, nil
}