Skip to content

Commit

Permalink
Add B3 trace IDs to cf cli commands
Browse files Browse the repository at this point in the history
  • Loading branch information
Samze committed Nov 19, 2024
1 parent dfe2201 commit 1683294
Show file tree
Hide file tree
Showing 6 changed files with 217 additions and 0 deletions.
54 changes: 54 additions & 0 deletions api/cloudcontroller/wrapper/b3_trace_request.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
package wrapper

import (
"code.cloudfoundry.org/cli/api/cloudcontroller"
)

// TODO
// 1. tests
// 2. do not overwrite headers if explicitly set (cf curl)
// 3. headers should go on other clients (uaa/routing) as well (with same value)
// 4. environment variable override

const (
// B3TraceIDHeader is the header key for the b3 trace id.
B3TraceIDHeader = "X-B3-Traceid"

// B3SpanIDHeader is the header key for the b3 span id.
B3SpanIDHeader = "X-B3-Spanid"
)

// TraceHeaderRequest is a wrapper that adds b3 trace headers to requests.
type TraceHeaderRequest struct {
b3trace string
b3span string
connection cloudcontroller.Connection
}

// NewTraceHeaderRequest returns a pointer to a TraceHeaderRequest wrapper.
func NewTraceHeaderRequest(trace, span string) *TraceHeaderRequest {
return &TraceHeaderRequest{
b3trace: trace,
b3span: span,
}
}

// Add tracing headers if they are not already set.
func (t *TraceHeaderRequest) Make(request *cloudcontroller.Request, passedResponse *cloudcontroller.Response) error {

// todo
// only override the trace headers if they are not already set (e.g. already explicitly set by cf curl)
if request.Header.Get(B3TraceIDHeader) != "" {
request.Header.Add(B3TraceIDHeader, t.b3trace)
}
if request.Header.Get(B3SpanIDHeader) != "" {
request.Header.Add(B3SpanIDHeader, t.b3span)
}
return t.connection.Make(request, passedResponse)
}

// Wrap sets the connection in the TraceHeaderRequest and returns itself.
func (t *TraceHeaderRequest) Wrap(innerconnection cloudcontroller.Connection) cloudcontroller.Connection {
t.connection = innerconnection
return t
}
130 changes: 130 additions & 0 deletions command/commandfakes/fake_config.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions command/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ type Config interface {
AddPluginRepository(name string, url string)
AuthorizationEndpoint() string
APIVersion() string
B3TraceID() string
B3SpanID() string
BinaryName() string
BinaryVersion() string
CFPassword() string
Expand Down
1 change: 1 addition & 0 deletions command/v7/shared/new_clients.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ func NewWrappedCloudControllerClient(config command.Config, ui command.UI, extra
ccWrappers = append(ccWrappers, ccWrapper.NewRequestLogger(ui.RequestLoggerFileWriter(location)))
}

ccWrappers = append(ccWrappers, ccWrapper.NewTraceHeaderRequest(config.B3TraceID(), config.B3SpanID()))
ccWrappers = append(ccWrappers, extraWrappers...)
ccWrappers = append(ccWrappers, ccWrapper.NewRetryRequest(config.RequestRetryCount()))

Expand Down
28 changes: 28 additions & 0 deletions util/configv3/env.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
package configv3

import (
"crypto/rand"
"encoding/hex"
"encoding/json"
"strconv"
"strings"
Expand All @@ -20,6 +22,8 @@ type EnvOverride struct {
CFStartupTimeout string
CFTrace string
CFUsername string
CFB3TraceID string
CFB3SpanID string
DockerPassword string
CNBCredentials string
Experimental string
Expand Down Expand Up @@ -160,3 +164,27 @@ func (config *Config) StartupTimeout() time.Duration {

return DefaultStartupTimeout
}

func (config *Config) B3TraceID() string {
if config.ENV.CFB3TraceID == "" {
return generateHex(16)
}
return config.ENV.CFB3TraceID
}

func (config *Config) B3SpanID() string {
if config.ENV.CFB3SpanID == "" {
return generateHex(8)
}
return config.ENV.CFB3SpanID
}

// todo
func generateHex(bytes int) string {
b := make([]byte, bytes)
if _, err := rand.Read(b); err != nil {
panic(err)
}

return hex.EncodeToString(b)
}
2 changes: 2 additions & 0 deletions util/configv3/load_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,8 @@ func LoadConfig(flags ...FlagOverride) (*Config, error) {
CFStartupTimeout: os.Getenv("CF_STARTUP_TIMEOUT"),
CFTrace: os.Getenv("CF_TRACE"),
CFUsername: os.Getenv("CF_USERNAME"),
CFB3TraceID: os.Getenv("CF_B3_TRACE_ID"),
CFB3SpanID: os.Getenv("CF_B3_SPAN_ID"),
DockerPassword: os.Getenv("CF_DOCKER_PASSWORD"),
CNBCredentials: os.Getenv("CNB_REGISTRY_CREDS"),
Experimental: os.Getenv("CF_CLI_EXPERIMENTAL"),
Expand Down

0 comments on commit 1683294

Please sign in to comment.