Skip to content

Stackdriver exporter: Allow overriding client options via config #1010

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 4 commits into from
Sep 15, 2020
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions exporter/stackdriverexporter/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ package stackdriverexporter
import (
"go.opentelemetry.io/collector/config/configmodels"
"go.opentelemetry.io/collector/exporter/exporterhelper"
"google.golang.org/api/option"
)

// Config defines configuration for Stackdriver exporter.
Expand All @@ -33,6 +34,11 @@ type Config struct {
// Timeout for all API calls. If not set, defaults to 12 seconds.
exporterhelper.TimeoutSettings `mapstructure:",squash"` // squash ensures fields are correctly decoded in embedded struct.
ResourceMappings []ResourceMapping `mapstructure:"resource_mappings"`
// GetClientOptions returns additional options to be passed
// to the underlying Google Cloud API client.
// Must be set programmatically (no support via declarative config).
// Optional.
GetClientOptions func() []option.ClientOption
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Switched to callback function to make it clear that this field can only be set programmatically.

}

// ResourceMapping defines mapping of resources from source (OpenCensus) to target (Stackdriver).
Expand Down
58 changes: 30 additions & 28 deletions exporter/stackdriverexporter/stackdriver.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,16 +65,29 @@ func (me *metricsExporter) Shutdown(context.Context) error {
return nil
}

func generateClientOptions(cfg *Config, dialOpts ...grpc.DialOption) ([]option.ClientOption, error) {
func generateClientOptions(cfg *Config, userAgent string) ([]option.ClientOption, error) {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Consolidated all logic initializing client options in one place.

var copts []option.ClientOption
if cfg.UseInsecure {
conn, err := grpc.Dial(cfg.Endpoint, append(dialOpts, grpc.WithInsecure())...)
if err != nil {
return nil, fmt.Errorf("cannot configure grpc conn: %w", err)
if userAgent != "" {
copts = append(copts, option.WithUserAgent(userAgent))
}
if cfg.Endpoint != "" {
if cfg.UseInsecure {
// WithGRPCConn option takes precedent over all other supplied options so need to provide user agent here as well
var dialOpts []grpc.DialOption
if userAgent != "" {
dialOpts = append(dialOpts, grpc.WithUserAgent(userAgent))
}
conn, err := grpc.Dial(cfg.Endpoint, append(dialOpts, grpc.WithInsecure())...)
if err != nil {
return nil, fmt.Errorf("cannot configure grpc conn: %w", err)
}
copts = append(copts, option.WithGRPCConn(conn))
} else {
copts = append(copts, option.WithEndpoint(cfg.Endpoint))
}
copts = append(copts, option.WithGRPCConn(conn))
} else {
copts = append(copts, option.WithEndpoint(cfg.Endpoint))
}
if cfg.GetClientOptions != nil {
copts = append(copts, cfg.GetClientOptions()...)
}
return copts, nil
}
Expand All @@ -84,13 +97,11 @@ func newStackdriverTraceExporter(cfg *Config) (component.TraceExporter, error) {
cloudtrace.WithProjectID(cfg.ProjectID),
cloudtrace.WithTimeout(cfg.Timeout),
}
if cfg.Endpoint != "" {
copts, err := generateClientOptions(cfg)
if err != nil {
return nil, err
}
topts = append(topts, cloudtrace.WithTraceClientOptions(copts))
copts, err := generateClientOptions(cfg, "")
if err != nil {
return nil, err
}
topts = append(topts, cloudtrace.WithTraceClientOptions(copts))
if cfg.NumOfWorkers > 0 {
topts = append(topts, cloudtrace.WithMaxNumberOfWorkers(cfg.NumOfWorkers))
}
Expand Down Expand Up @@ -126,21 +137,12 @@ func newStackdriverMetricsExporter(cfg *Config, version string) (component.Metri
}

userAgent := strings.ReplaceAll(cfg.UserAgent, "{{version}}", version)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Bring this line into generateClientOptions as well?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, had to change the trace exporter constructor though (which is probably for the better).

if cfg.Endpoint != "" {
// WithGRPCConn option takes precedent over all other supplied options so need to provide user agent here as well
dialOpts := []grpc.DialOption{}
if userAgent != "" {
dialOpts = append(dialOpts, grpc.WithUserAgent(userAgent))
}

copts, err := generateClientOptions(cfg, dialOpts...)
if err != nil {
return nil, err
}
options.TraceClientOptions = copts
options.MonitoringClientOptions = copts
copts, err := generateClientOptions(cfg, userAgent)
if err != nil {
return nil, err
}
options.MonitoringClientOptions = append(options.MonitoringClientOptions, option.WithUserAgent(options.UserAgent))
options.TraceClientOptions = copts
options.MonitoringClientOptions = copts

if cfg.NumOfWorkers > 0 {
options.NumberOfWorkers = cfg.NumOfWorkers
Expand Down
17 changes: 16 additions & 1 deletion exporter/stackdriverexporter/stackdriver_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ import (
"go.opentelemetry.io/collector/consumer/pdata"
"go.opentelemetry.io/collector/testutil/metricstestutil"
"go.opentelemetry.io/collector/translator/internaldata"
"google.golang.org/api/option"
cloudmetricpb "google.golang.org/genproto/googleapis/api/metric"
cloudtracepb "google.golang.org/genproto/googleapis/devtools/cloudtrace/v2"
cloudmonitoringpb "google.golang.org/genproto/googleapis/monitoring/v3"
Expand Down Expand Up @@ -144,7 +145,21 @@ func TestStackdriverMetricExport(t *testing.T) {

go srv.Serve(lis)

sde, err := newStackdriverMetricsExporter(&Config{ProjectID: "idk", Endpoint: "127.0.0.1:8080", UserAgent: "MyAgent {{version}}", UseInsecure: true}, "v0.0.1")
// Example with overridden client options
clientOptions := []option.ClientOption{
option.WithoutAuthentication(),
option.WithTelemetryDisabled(),
}

sde, err := newStackdriverMetricsExporter(&Config{
ProjectID: "idk",
Endpoint: "127.0.0.1:8080",
UserAgent: "MyAgent {{version}}",
UseInsecure: true,
GetClientOptions: func() []option.ClientOption {
return clientOptions
},
}, "v0.0.1")
require.NoError(t, err)
defer func() { require.NoError(t, sde.Shutdown(context.Background())) }()

Expand Down