forked from sourcegraph/appdash
-
Notifications
You must be signed in to change notification settings - Fork 0
/
header.go
76 lines (66 loc) · 2.1 KB
/
header.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
package httptrace
import (
"net/http"
"sourcegraph.com/sourcegraph/appdash"
)
const (
// HeaderSpanID is the name of the HTTP header by which the trace
// and span IDs are passed along.
HeaderSpanID = "Span-ID"
// HeaderParentSpanID is the name of the HTTP header by which the
// parent trace and span IDs are passed along. It should only be
// set by clients that are incapable of creating their own span
// IDs (e.g., JavaScript API clients in a web page, which can
// easily pass along an existing parent span ID but not create a
// new child span ID).
HeaderParentSpanID = "Parent-Span-ID"
)
// SetSpanIDHeader sets the Span-ID header.
func SetSpanIDHeader(h http.Header, e appdash.SpanID) {
h.Set(HeaderSpanID, e.String())
}
// GetSpanID returns the SpanID for the current request, based on the
// values in the HTTP headers. If a Span-ID header is provided, it is
// parsed; if a Parent-Span-ID header is provided, a new child span is
// created and it is returned; otherwise a new root SpanID is created.
func GetSpanID(h http.Header) (*appdash.SpanID, error) {
spanID, _, err := getSpanID(h)
return spanID, err
}
func getSpanID(h http.Header) (spanID *appdash.SpanID, fromHeader string, err error) {
// Check for Span-ID.
fromHeader = HeaderSpanID
spanID, err = getSpanIDHeader(h, HeaderSpanID)
if err != nil {
return nil, fromHeader, err
}
// Check for Parent-Span-ID.
if spanID == nil {
fromHeader = HeaderParentSpanID
spanID, err = getSpanIDHeader(h, HeaderParentSpanID)
if err != nil {
return nil, fromHeader, err
}
if spanID != nil {
newSpanID := appdash.NewSpanID(*spanID)
spanID = &newSpanID
}
}
// Create a new root span ID.
if spanID == nil {
fromHeader = ""
newSpanID := appdash.NewRootSpanID()
spanID = &newSpanID
}
return spanID, fromHeader, nil
}
// getSpanIDHeader returns the SpanID in the header (specified by
// key), nil if no such header was provided, or an error if the value
// was unparseable.
func getSpanIDHeader(h http.Header, key string) (*appdash.SpanID, error) {
s := h.Get(key)
if s == "" {
return nil, nil
}
return appdash.ParseSpanID(s)
}