diff --git a/CHANGELOG.md b/CHANGELOG.md index ece2ef0f178..14702312833 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,8 +6,13 @@ - `confighttp`: add client-side compression support. (#4441) - Each exporter should remove `compression` field if they have and should use `confighttp.HTTPClientSettings` -- Allow more zap logger configs: `disable_caller`, `disable_stacktrace`, `output_paths`, `error_output_paths`, `initial_fields` (#1048) +- Allow more zap logger configs: `disable_caller`, `disable_stacktrace`, `output_paths`, `error_output_paths`, `initial_fields` (#1048) - `configauth`: add ServerAuthenticator interfaces for HTTP receivers. (#4506) +- Collector self-metrics may now be configured through the configuration file. (#4069) + - CLI flags for configuring self-metrics are deprecated and will be removed + in a future release. + - `service.telemetry.metrics.level` and `service.telemetry.metrics.address` + should be used to configure collector self-metrics. ## v0.41.0 Beta @@ -69,6 +74,13 @@ - Move `config.WatchableRetrieved` and `config.Retrieved` interfaces to `config/configmapprovider` package (#4337) - Remove `config.Pipeline.InputDataType` (#4343) - otlpexporter: Do not retry on PermissionDenied and Unauthenticated (#4349) +- Enable configuring collector metrics through service config file. (#4069) + - New `service::telemetry::metrics` structure added to configuration + - Existing metrics configuration CLI flags are deprecated and to be + removed in the future. + - `--metrics-prefix` is no longer operative; the prefix is determined by + the value of `service.buildInfo.Command`. + - `--add-instance-id` is no longer operative; an instance ID will always be added. - Remove deprecated funcs `consumererror.As[Traces|Metrics|Logs]` (#4364) - Remove support to expand env variables in default configs (#4366) diff --git a/component/componenttest/nop_telemetry.go b/component/componenttest/nop_telemetry.go index 265b8f0a3d4..d872b45cc83 100644 --- a/component/componenttest/nop_telemetry.go +++ b/component/componenttest/nop_telemetry.go @@ -20,6 +20,7 @@ import ( "go.uber.org/zap" "go.opentelemetry.io/collector/component" + "go.opentelemetry.io/collector/config/configtelemetry" ) // NewNopTelemetrySettings returns a new nop telemetry settings for Create* functions. @@ -28,5 +29,6 @@ func NewNopTelemetrySettings() component.TelemetrySettings { Logger: zap.NewNop(), TracerProvider: trace.NewNoopTracerProvider(), MeterProvider: metric.NewNoopMeterProvider(), + MetricsLevel: configtelemetry.LevelNone, } } diff --git a/component/telemetry.go b/component/telemetry.go index 52c77e85240..22d5557fd77 100644 --- a/component/telemetry.go +++ b/component/telemetry.go @@ -18,6 +18,8 @@ import ( "go.opentelemetry.io/otel/metric" "go.opentelemetry.io/otel/trace" "go.uber.org/zap" + + "go.opentelemetry.io/collector/config/configtelemetry" ) type TelemetrySettings struct { @@ -30,4 +32,8 @@ type TelemetrySettings struct { // MeterProvider that the factory can pass to other instrumented third-party libraries. MeterProvider metric.MeterProvider + + // MetricsLevel controls the level of detail for metrics emitted by the collector. + // Experimental: *NOTE* this field is experimental and may be changed or removed. + MetricsLevel configtelemetry.Level } diff --git a/config/config_test.go b/config/config_test.go index fccd126735a..adfe391f079 100644 --- a/config/config_test.go +++ b/config/config_test.go @@ -21,6 +21,8 @@ import ( "github.com/stretchr/testify/assert" "go.uber.org/zap/zapcore" + + "go.opentelemetry.io/collector/config/configtelemetry" ) var errInvalidRecvConfig = errors.New("invalid receiver config") @@ -255,15 +257,22 @@ func generateConfig() *Config { }, }, Service: Service{ - Telemetry: ServiceTelemetry{Logs: ServiceTelemetryLogs{ - Level: zapcore.DebugLevel, - Development: true, - Encoding: "console", - DisableCaller: true, - DisableStacktrace: true, - OutputPaths: []string{"stderr", "./output-logs"}, - ErrorOutputPaths: []string{"stderr", "./error-output-logs"}, - InitialFields: map[string]interface{}{"fieldKey": "filed-value"}}}, + Telemetry: ServiceTelemetry{ + Logs: ServiceTelemetryLogs{ + Level: zapcore.DebugLevel, + Development: true, + Encoding: "console", + DisableCaller: true, + DisableStacktrace: true, + OutputPaths: []string{"stderr", "./output-logs"}, + ErrorOutputPaths: []string{"stderr", "./error-output-logs"}, + InitialFields: map[string]interface{}{"fieldKey": "filed-value"}, + }, + Metrics: ServiceTelemetryMetrics{ + Level: configtelemetry.LevelNormal, + Address: ":8080", + }, + }, Extensions: []ComponentID{NewComponentID("nop")}, Pipelines: map[ComponentID]*Pipeline{ NewComponentID("traces"): { diff --git a/config/configtelemetry/configtelemetry.go b/config/configtelemetry/configtelemetry.go index 04d28d1fe01..195ce6fb922 100644 --- a/config/configtelemetry/configtelemetry.go +++ b/config/configtelemetry/configtelemetry.go @@ -36,11 +36,15 @@ const ( levelDetailedStr = "detailed" metricsLevelCfg = "metrics-level" + metricsAddrCfg = "metrics-addr" ) const UseOpenTelemetryForInternalMetrics = false -var metricsLevelPtr = new(Level) +var ( + metricsLevelPtr = new(Level) + metricsAddrPtr = new(string) +) // Flags is a helper function to add telemetry config flags to the service that exposes // the application flags. @@ -48,7 +52,14 @@ func Flags(flags *flag.FlagSet) { flags.Var( metricsLevelPtr, metricsLevelCfg, - "Output level of telemetry metrics (none, basic, normal, detailed)") + "Deprecated. Define the metrics configuration as part of the configuration file, under the 'service' section.") + + // At least until we can use a generic, i.e.: OpenCensus, metrics exporter + // we default to Prometheus at port 8888, if not otherwise specified. + metricsAddrPtr = flags.String( + metricsAddrCfg, + GetMetricsAddrDefault(), + "Deprecated. Define the metrics configuration as part of the configuration file, under the 'service' section.") } // Level is the level of internal telemetry (metrics, logs, traces about the component itself) @@ -57,8 +68,8 @@ type Level int32 var _ flag.Value = (*Level)(nil) -func (l *Level) String() string { - switch *l { +func (l Level) String() string { + switch l { case LevelNone: return levelNoneStr case LevelBasic: @@ -81,37 +92,17 @@ func (l *Level) Set(s string) error { return nil } -// GetMetricsLevelFlagValue returns the value of the "--metrics-level" flag. -// IMPORTANT: This must be used only in the core collector code for the moment. -func GetMetricsLevelFlagValue() Level { - return *metricsLevelPtr -} - -// TelemetrySetting exposes the common Telemetry configuration for one component. -type TelemetrySetting struct { - // MetricsLevelStr is the level of telemetry metrics, the possible values are: - // - "none" indicates that no telemetry data should be collected; - // - "basic" is the recommended and covers the basics of the service telemetry. - // - "normal" adds some other indicators on top of basic. - // - "detailed" adds dimensions and views to the previous levels. - MetricsLevelStr string `mapstructure:"metrics_level"` -} - -// DefaultTelemetrySetting returns the default TelemetrySetting. -// The level is set to the "--metrics-level" flag if set, otherwise the default "basic" level. -func DefaultTelemetrySetting() TelemetrySetting { - return TelemetrySetting{ - MetricsLevelStr: metricsLevelPtr.String(), +// UnmarshalText unmarshals text to a Level. +func (l *Level) UnmarshalText(text []byte) error { + if l == nil { + return fmt.Errorf("cannot unmarshal to a nil *Level") } + var err error + *l, err = parseLevel(string(text)) + return err } -// GetMetricsLevel returns the parsed level, or error if unknown value. -// Empty string is consider unknown value. -func (ts TelemetrySetting) GetMetricsLevel() (Level, error) { - return parseLevel(ts.MetricsLevelStr) -} - -// ParseLevel returns the Level represented by the string. The parsing is case-insensitive +// parseLevel returns the Level represented by the string. The parsing is case-insensitive // and it returns error if the string value is unknown. func parseLevel(str string) (Level, error) { str = strings.ToLower(str) @@ -128,3 +119,22 @@ func parseLevel(str string) (Level, error) { } return LevelNone, fmt.Errorf("unknown metrics level %q", str) } + +// GetMetricsAddrDefault returns the default metrics bind address and port depending on +// the current build type. +// Deprecated: This function will be removed in the future. +func GetMetricsAddrDefault() string { + return ":8888" +} + +// Deprecated: This function will be removed in the future. +func GetMetricsAddr() string { + return *metricsAddrPtr +} + +// GetMetricsLevelFlagValue returns the value of the "--metrics-level" flag. +// IMPORTANT: This must be used only in the core collector code for the moment. +// Deprecated: This function will be removed in the future. +func GetMetricsLevelFlagValue() Level { + return *metricsLevelPtr +} diff --git a/config/configtelemetry/configtelemetry_test.go b/config/configtelemetry/configtelemetry_test.go index 4512bb5750b..ea303bac7ed 100644 --- a/config/configtelemetry/configtelemetry_test.go +++ b/config/configtelemetry/configtelemetry_test.go @@ -18,7 +18,6 @@ import ( "testing" "github.com/stretchr/testify/assert" - "github.com/stretchr/testify/require" ) func TestParseFrom(t *testing.T) { @@ -149,19 +148,3 @@ func TestLevelString(t *testing.T) { }) } } - -func TestTelemetrySettings(t *testing.T) { - ts := &TelemetrySetting{ - MetricsLevelStr: "unknown", - } - _, err := ts.GetMetricsLevel() - assert.Error(t, err) -} - -func TestDefaultTelemetrySettings(t *testing.T) { - ts := DefaultTelemetrySetting() - assert.Equal(t, levelBasicStr, ts.MetricsLevelStr) - lvl, err := ts.GetMetricsLevel() - require.NoError(t, err) - assert.Equal(t, LevelBasic, lvl) -} diff --git a/config/configunmarshaler/defaultunmarshaler.go b/config/configunmarshaler/defaultunmarshaler.go index a1e44c899ee..eca9343e84b 100644 --- a/config/configunmarshaler/defaultunmarshaler.go +++ b/config/configunmarshaler/defaultunmarshaler.go @@ -21,6 +21,7 @@ import ( "go.opentelemetry.io/collector/component" "go.opentelemetry.io/collector/config" + "go.opentelemetry.io/collector/config/configtelemetry" ) // These are errors that can be returned by Unmarshal(). Note that error codes are not part @@ -177,6 +178,7 @@ func unmarshalService(srvRaw map[string]interface{}) (config.Service, error) { DisableStacktrace: false, InitialFields: map[string]interface{}(nil), }, + Metrics: defaultServiceTelemetryMetricsSettings(), }, } @@ -192,6 +194,21 @@ func unmarshalService(srvRaw map[string]interface{}) (config.Service, error) { return srv, nil } +func defaultServiceTelemetryMetricsSettings() config.ServiceTelemetryMetrics { + // These deprecated functions are still needed here so that the values provided through the CLI flags + // can be used as a baseline if no values are provided in configuration. This will eventually return + // a static default configuration when the CLI flags are removed. + addr := configtelemetry.GetMetricsAddr() //nolint:staticcheck + if addr == "" { + addr = configtelemetry.GetMetricsAddrDefault() //nolint:staticcheck + } + + return config.ServiceTelemetryMetrics{ + Level: configtelemetry.GetMetricsLevelFlagValue(), //nolint:staticcheck + Address: addr, + } +} + // LoadReceiver loads a receiver config from componentConfig using the provided factories. func LoadReceiver(componentConfig *config.Map, id config.ComponentID, factory component.ReceiverFactory) (config.Receiver, error) { // Create the default config for this receiver. diff --git a/config/configunmarshaler/defaultunmarshaler_test.go b/config/configunmarshaler/defaultunmarshaler_test.go index a738a337cb0..b4dc4b5e018 100644 --- a/config/configunmarshaler/defaultunmarshaler_test.go +++ b/config/configunmarshaler/defaultunmarshaler_test.go @@ -28,6 +28,7 @@ import ( "go.opentelemetry.io/collector/config" "go.opentelemetry.io/collector/config/configmapprovider" "go.opentelemetry.io/collector/config/confignet" + "go.opentelemetry.io/collector/config/configtelemetry" "go.opentelemetry.io/collector/internal/testcomponents" ) @@ -100,16 +101,22 @@ func TestDecodeConfig(t *testing.T) { // Verify Service Telemetry assert.Equal(t, - config.ServiceTelemetry{Logs: config.ServiceTelemetryLogs{ - Level: zapcore.DebugLevel, - Development: true, - Encoding: "console", - DisableCaller: true, - DisableStacktrace: true, - OutputPaths: []string{"stderr", "./output-logs"}, - ErrorOutputPaths: []string{"stderr", "./error-output-logs"}, - InitialFields: map[string]interface{}{"field_key": "filed_value"}, - }}, cfg.Service.Telemetry) + config.ServiceTelemetry{ + Logs: config.ServiceTelemetryLogs{ + Level: zapcore.DebugLevel, + Development: true, + Encoding: "console", + DisableCaller: true, + DisableStacktrace: true, + OutputPaths: []string{"stderr", "./output-logs"}, + ErrorOutputPaths: []string{"stderr", "./error-output-logs"}, + InitialFields: map[string]interface{}{"field_key": "filed_value"}, + }, + Metrics: config.ServiceTelemetryMetrics{ + Level: configtelemetry.LevelNormal, + Address: ":8081", + }, + }, cfg.Service.Telemetry) // Verify Service Extensions assert.Equal(t, 2, len(cfg.Service.Extensions)) @@ -177,6 +184,7 @@ func TestDecodeConfig_Invalid(t *testing.T) { {name: "invalid-pipeline-sub-config", expected: errUnmarshalService}, {name: "invalid-logs-level", expected: errUnmarshalService}, + {name: "invalid-metrics-level", expected: errUnmarshalService}, } factories, err := testcomponents.ExampleComponents() diff --git a/config/configunmarshaler/testdata/invalid-metrics-level.yaml b/config/configunmarshaler/testdata/invalid-metrics-level.yaml new file mode 100644 index 00000000000..814e6307062 --- /dev/null +++ b/config/configunmarshaler/testdata/invalid-metrics-level.yaml @@ -0,0 +1,19 @@ +receivers: + examplereceiver: +processors: + exampleprocessor: +exporters: + exampleexporter: +extensions: + exampleextension: +service: + telemetry: + metrics: + level: "unknown" + extensions: [exampleextension] + pipelines: + traces: + receivers: [examplereceiver] + processors: [exampleprocessor] + exporters: [exampleexporter] + diff --git a/config/configunmarshaler/testdata/valid-config.yaml b/config/configunmarshaler/testdata/valid-config.yaml index 54ce5b98bbc..1b753fdff69 100644 --- a/config/configunmarshaler/testdata/valid-config.yaml +++ b/config/configunmarshaler/testdata/valid-config.yaml @@ -29,8 +29,11 @@ service: disable_stacktrace: true output_paths: ["stderr", "./output-logs"] error_output_paths: ["stderr", "./error-output-logs"] - initial_fields: + initial_fields: field_key: "filed_value" + metrics: + level: "normal" + address: ":8081" extensions: [exampleextension/0, exampleextension/1] pipelines: traces: diff --git a/config/service.go b/config/service.go index 3445040e362..10542f1322f 100644 --- a/config/service.go +++ b/config/service.go @@ -18,6 +18,8 @@ import ( "fmt" "go.uber.org/zap/zapcore" + + "go.opentelemetry.io/collector/config/configtelemetry" ) // Service defines the configurable components of the service. @@ -34,11 +36,16 @@ type Service struct { // ServiceTelemetry defines the configurable settings for service telemetry. type ServiceTelemetry struct { - Logs ServiceTelemetryLogs `mapstructure:"logs"` + Logs ServiceTelemetryLogs `mapstructure:"logs"` + Metrics ServiceTelemetryMetrics `mapstructure:"metrics"` } func (srvT *ServiceTelemetry) validate() error { - return srvT.Logs.validate() + if err := srvT.Logs.validate(); err != nil { + return err + } + + return srvT.Metrics.validate() } // ServiceTelemetryLogs defines the configurable settings for service telemetry logs. @@ -107,6 +114,24 @@ func (srvTL *ServiceTelemetryLogs) validate() error { return nil } +// ServiceTelemetryMetrics exposes the common Telemetry configuration for one component. +// Experimental: *NOTE* this structure is subject to change or removal in the future. +type ServiceTelemetryMetrics struct { + // Level is the level of telemetry metrics, the possible values are: + // - "none" indicates that no telemetry data should be collected; + // - "basic" is the recommended and covers the basics of the service telemetry. + // - "normal" adds some other indicators on top of basic. + // - "detailed" adds dimensions and views to the previous levels. + Level configtelemetry.Level `mapstructure:"level"` + + // Address is the [address]:port that metrics exposition should be bound to. + Address string `mapstructure:"address"` +} + +func (s ServiceTelemetryMetrics) validate() error { + return nil +} + // DataType is a special Type that represents the data types supported by the collector. We currently support // collecting metrics, traces and logs, this can expand in the future. type DataType = Type diff --git a/exporter/exporterhelper/common.go b/exporter/exporterhelper/common.go index 7c7f1e4a164..0310296c2f4 100644 --- a/exporter/exporterhelper/common.go +++ b/exporter/exporterhelper/common.go @@ -21,7 +21,6 @@ import ( "go.opentelemetry.io/collector/component" "go.opentelemetry.io/collector/component/componenthelper" "go.opentelemetry.io/collector/config" - "go.opentelemetry.io/collector/config/configtelemetry" "go.opentelemetry.io/collector/consumer" "go.opentelemetry.io/collector/consumer/consumerhelper" "go.opentelemetry.io/collector/exporter/exporterhelper/internal" @@ -180,7 +179,7 @@ func newBaseExporter(cfg config.Exporter, set component.ExporterCreateSettings, } be.obsrep = newObsExporter(obsreport.ExporterSettings{ - Level: configtelemetry.GetMetricsLevelFlagValue(), + Level: set.MetricsLevel, ExporterID: cfg.ID(), ExporterCreateSettings: set, }, globalInstruments) diff --git a/processor/batchprocessor/factory.go b/processor/batchprocessor/factory.go index a3638326ad8..cc932893339 100644 --- a/processor/batchprocessor/factory.go +++ b/processor/batchprocessor/factory.go @@ -20,7 +20,6 @@ import ( "go.opentelemetry.io/collector/component" "go.opentelemetry.io/collector/config" - "go.opentelemetry.io/collector/config/configtelemetry" "go.opentelemetry.io/collector/consumer" "go.opentelemetry.io/collector/processor/processorhelper" ) @@ -57,7 +56,7 @@ func createTracesProcessor( cfg config.Processor, nextConsumer consumer.Traces, ) (component.TracesProcessor, error) { - level := configtelemetry.GetMetricsLevelFlagValue() + level := set.MetricsLevel return newBatchTracesProcessor(set, nextConsumer, cfg.(*Config), level) } @@ -67,7 +66,7 @@ func createMetricsProcessor( cfg config.Processor, nextConsumer consumer.Metrics, ) (component.MetricsProcessor, error) { - level := configtelemetry.GetMetricsLevelFlagValue() + level := set.MetricsLevel return newBatchMetricsProcessor(set, nextConsumer, cfg.(*Config), level) } @@ -77,6 +76,6 @@ func createLogsProcessor( cfg config.Processor, nextConsumer consumer.Logs, ) (component.LogsProcessor, error) { - level := configtelemetry.GetMetricsLevelFlagValue() + level := set.MetricsLevel return newBatchLogsProcessor(set, nextConsumer, cfg.(*Config), level) } diff --git a/processor/memorylimiterprocessor/memorylimiter.go b/processor/memorylimiterprocessor/memorylimiter.go index a8ca86f4fdf..e8e1656cad9 100644 --- a/processor/memorylimiterprocessor/memorylimiter.go +++ b/processor/memorylimiterprocessor/memorylimiter.go @@ -25,7 +25,6 @@ import ( "go.uber.org/zap" "go.opentelemetry.io/collector/component" - "go.opentelemetry.io/collector/config/configtelemetry" "go.opentelemetry.io/collector/extension/ballastextension" "go.opentelemetry.io/collector/internal/iruntime" "go.opentelemetry.io/collector/model/pdata" @@ -115,7 +114,7 @@ func newMemoryLimiter(set component.ProcessorCreateSettings, cfg *Config) (*memo readMemStatsFn: runtime.ReadMemStats, logger: logger, obsrep: obsreport.NewProcessor(obsreport.ProcessorSettings{ - Level: configtelemetry.GetMetricsLevelFlagValue(), + Level: set.MetricsLevel, ProcessorID: cfg.ID(), ProcessorCreateSettings: set, }), diff --git a/service/collector.go b/service/collector.go index 81c9db35d63..3c393d9e349 100644 --- a/service/collector.go +++ b/service/collector.go @@ -199,6 +199,7 @@ func (col *Collector) setupConfigurationComponents(ctx context.Context) error { Logger: col.logger, TracerProvider: col.tracerProvider, MeterProvider: col.meterProvider, + MetricsLevel: col.cfgW.cfg.Telemetry.Metrics.Level, }, ZPagesSpanProcessor: col.zPagesSpanProcessor, AsyncErrorChannel: col.asyncErrorChannel, @@ -234,7 +235,7 @@ func (col *Collector) Run(ctx context.Context) error { return err } - if err := collectorTelemetry.init(col.asyncErrorChannel, getBallastSize(col.service), col.logger); err != nil { + if err := collectorTelemetry.init(col); err != nil { return err } diff --git a/service/collector_test.go b/service/collector_test.go index c593550e987..ca95d1928b1 100644 --- a/service/collector_test.go +++ b/service/collector_test.go @@ -101,11 +101,9 @@ func TestCollector_Start(t *testing.T) { }) require.NoError(t, err) - const testPrefix = "a_test" metricsPort := testutil.GetAvailablePort(t) require.NoError(t, flags().Parse([]string{ "--metrics-addr=localhost:" + strconv.FormatUint(uint64(metricsPort), 10), - "--metrics-prefix=" + testPrefix, })) colDone := make(chan struct{}) @@ -129,7 +127,7 @@ func TestCollector_Start(t *testing.T) { mandatoryLabels := []string{ "service_instance_id", } - assertMetrics(t, testPrefix, metricsPort, mandatoryLabels) + assertMetrics(t, metricsPort, mandatoryLabels) assertZPages(t) @@ -142,7 +140,7 @@ func TestCollector_Start(t *testing.T) { type mockColTelemetry struct{} -func (tel *mockColTelemetry) init(chan<- error, uint64, *zap.Logger) error { +func (tel *mockColTelemetry) init(*Collector) error { return nil } @@ -182,7 +180,7 @@ func TestCollector_ReportError(t *testing.T) { }, time.Second*2, time.Millisecond*200) } -func assertMetrics(t *testing.T, prefix string, metricsPort uint16, mandatoryLabels []string) { +func assertMetrics(t *testing.T, metricsPort uint16, mandatoryLabels []string) { client := &http.Client{} resp, err := client.Get(fmt.Sprintf("http://localhost:%d/metrics", metricsPort)) require.NoError(t, err) @@ -194,6 +192,7 @@ func assertMetrics(t *testing.T, prefix string, metricsPort uint16, mandatoryLab parsed, err := parser.TextToMetricFamilies(reader) require.NoError(t, err) + prefix := "otelcol" for metricName, metricFamily := range parsed { // require is used here so test fails with a single message. require.True( diff --git a/service/flags.go b/service/flags.go index 66221157be3..f22f3e7cb8c 100644 --- a/service/flags.go +++ b/service/flags.go @@ -23,18 +23,11 @@ import ( ) var ( - defaultMetricsAddr = ":8888" - defaultMetricsPrefix = "otelcol" - defaultAddInstanceID = true - defaultConfig = "" + defaultConfig = "" // Command-line flag that control the configuration file. configFlag = &defaultConfig setFlag = new(stringArrayValue) - // Command-line flags that control publication of telemetry data. - metricsAddrPtr = &defaultMetricsAddr - metricsPrefixPtr = &defaultMetricsPrefix - addInstanceIDPtr = &defaultAddInstanceID ) type stringArrayValue struct { @@ -55,23 +48,6 @@ func flags() *flag.FlagSet { configtelemetry.Flags(flagSet) featuregate.Flags(flagSet) - // At least until we can use a generic, i.e.: OpenCensus, metrics exporter - // we default to Prometheus at port 8888, if not otherwise specified. - metricsAddrPtr = flagSet.String( - "metrics-addr", - defaultMetricsAddr, - "[address]:port for exposing collector telemetry.") - - metricsPrefixPtr = flagSet.String( - "metrics-prefix", - defaultMetricsPrefix, - "Prefix to the metrics generated by the collector.") - - addInstanceIDPtr = flagSet.Bool( - "add-instance-id", - defaultAddInstanceID, - "Flag to control the addition of 'service.instance.id' to the collector metrics.") - configFlag = flagSet.String("config", defaultConfig, "Path to the config file") flagSet.Var(setFlag, "set", @@ -89,15 +65,3 @@ func getConfigFlag() string { func getSetFlag() []string { return setFlag.values } - -func getAddInstanceID() bool { - return *addInstanceIDPtr -} - -func getMetricsAddr() string { - return *metricsAddrPtr -} - -func getMetricsPrefix() string { - return *metricsPrefixPtr -} diff --git a/service/internal/builder/exporters_builder.go b/service/internal/builder/exporters_builder.go index ca0ff12cf3b..5576ac4009a 100644 --- a/service/internal/builder/exporters_builder.go +++ b/service/internal/builder/exporters_builder.go @@ -151,6 +151,7 @@ func BuildExporters( Logger: logger.With(zap.String(components.ZapNameKey, expID.String())), TracerProvider: settings.TracerProvider, MeterProvider: settings.MeterProvider, + MetricsLevel: cfg.Telemetry.Metrics.Level, }, BuildInfo: buildInfo, } diff --git a/service/internal/builder/pipelines_builder.go b/service/internal/builder/pipelines_builder.go index 6a380e2682a..3f488bb195e 100644 --- a/service/internal/builder/pipelines_builder.go +++ b/service/internal/builder/pipelines_builder.go @@ -168,6 +168,7 @@ func (pb *pipelinesBuilder) buildPipeline(ctx context.Context, pipelineID config zap.String(components.ZapNameKey, procID.String())), TracerProvider: pb.settings.TracerProvider, MeterProvider: pb.settings.MeterProvider, + MetricsLevel: pb.config.Telemetry.Metrics.Level, }, BuildInfo: pb.buildInfo, } diff --git a/service/internal/builder/receivers_builder.go b/service/internal/builder/receivers_builder.go index 0ff9cdc1736..f083f47b46c 100644 --- a/service/internal/builder/receivers_builder.go +++ b/service/internal/builder/receivers_builder.go @@ -101,6 +101,7 @@ func BuildReceivers( zap.String(components.ZapNameKey, recvID.String())), TracerProvider: settings.TracerProvider, MeterProvider: settings.MeterProvider, + MetricsLevel: cfg.Telemetry.Metrics.Level, }, BuildInfo: buildInfo, } diff --git a/service/internal/extensions/extensions.go b/service/internal/extensions/extensions.go index 15e67bb48ff..060a24b643b 100644 --- a/service/internal/extensions/extensions.go +++ b/service/internal/extensions/extensions.go @@ -135,6 +135,7 @@ func Build( zap.String(components.ZapNameKey, extID.String())), TracerProvider: settings.TracerProvider, MeterProvider: settings.MeterProvider, + MetricsLevel: config.Telemetry.Metrics.Level, }, BuildInfo: buildInfo, } diff --git a/service/telemetry.go b/service/telemetry.go index efa462242fc..75be2d403a6 100644 --- a/service/telemetry.go +++ b/service/telemetry.go @@ -53,7 +53,7 @@ const ( ) type collectorTelemetryExporter interface { - init(asyncErrorChannel chan<- error, ballastSizeBytes uint64, logger *zap.Logger) error + init(col *Collector) error shutdown() error } @@ -63,11 +63,11 @@ type colTelemetry struct { doInitOnce sync.Once } -func (tel *colTelemetry) init(asyncErrorChannel chan<- error, ballastSizeBytes uint64, logger *zap.Logger) error { +func (tel *colTelemetry) init(col *Collector) error { var err error tel.doInitOnce.Do( func() { - err = tel.initOnce(asyncErrorChannel, ballastSizeBytes, logger) + err = tel.initOnce(col) }, ) if err != nil { @@ -76,9 +76,12 @@ func (tel *colTelemetry) init(asyncErrorChannel chan<- error, ballastSizeBytes u return nil } -func (tel *colTelemetry) initOnce(asyncErrorChannel chan<- error, ballastSizeBytes uint64, logger *zap.Logger) error { - level := configtelemetry.GetMetricsLevelFlagValue() - metricsAddr := getMetricsAddr() +func (tel *colTelemetry) initOnce(col *Collector) error { + logger := col.logger + cfg := col.service.config.Telemetry + + level := cfg.Metrics.Level + metricsAddr := cfg.Metrics.Address if level == configtelemetry.LevelNone || metricsAddr == "" { logger.Info( @@ -91,12 +94,8 @@ func (tel *colTelemetry) initOnce(asyncErrorChannel chan<- error, ballastSizeByt logger.Info("Setting up own telemetry...") - var instanceID string - - if getAddInstanceID() { - instanceUUID, _ := uuid.NewRandom() - instanceID = instanceUUID.String() - } + instanceUUID, _ := uuid.NewRandom() + instanceID := instanceUUID.String() var pe http.Handler if configtelemetry.UseOpenTelemetryForInternalMetrics { @@ -106,7 +105,7 @@ func (tel *colTelemetry) initOnce(asyncErrorChannel chan<- error, ballastSizeByt } pe = otelHandler } else { - ocHandler, err := tel.initOpenCensus(level, instanceID, ballastSizeBytes) + ocHandler, err := tel.initOpenCensus(col, instanceID) if err != nil { return err } @@ -132,21 +131,21 @@ func (tel *colTelemetry) initOnce(asyncErrorChannel chan<- error, ballastSizeByt go func() { serveErr := tel.server.ListenAndServe() if serveErr != nil && serveErr != http.ErrServerClosed { - asyncErrorChannel <- serveErr + col.asyncErrorChannel <- serveErr } }() return nil } -func (tel *colTelemetry) initOpenCensus(level configtelemetry.Level, instanceID string, ballastSizeBytes uint64) (http.Handler, error) { - processMetricsViews, err := telemetry2.NewProcessMetricsViews(ballastSizeBytes) +func (tel *colTelemetry) initOpenCensus(col *Collector, instanceID string) (http.Handler, error) { + processMetricsViews, err := telemetry2.NewProcessMetricsViews(getBallastSize(col.service)) if err != nil { return nil, err } var views []*view.View - obsMetrics := obsreportconfig.Configure(level) + obsMetrics := obsreportconfig.Configure(col.service.config.Telemetry.Metrics.Level) views = append(views, batchprocessor.MetricViews()...) views = append(views, obsMetrics.Views...) views = append(views, processMetricsViews.Views()...) @@ -160,14 +159,12 @@ func (tel *colTelemetry) initOpenCensus(level configtelemetry.Level, instanceID // Until we can use a generic metrics exporter, default to Prometheus. opts := prometheus.Options{ - Namespace: getMetricsPrefix(), + Namespace: "otelcol", } opts.ConstLabels = make(map[string]string) - if getAddInstanceID() { - opts.ConstLabels[sanitizePrometheusKey(semconv.AttributeServiceInstanceID)] = instanceID - } + opts.ConstLabels[sanitizePrometheusKey(semconv.AttributeServiceInstanceID)] = instanceID if AddCollectorVersionTag { opts.ConstLabels[sanitizePrometheusKey(semconv.AttributeServiceVersion)] = version.Version