Skip to content

Commit

Permalink
Merge pull request #94 from metrico/extension/pyroscope
Browse files Browse the repository at this point in the history
pyroscope client extension
  • Loading branch information
akvlad authored Aug 23, 2024
2 parents 28ca99e + e13ca34 commit 0ea91ae
Show file tree
Hide file tree
Showing 6 changed files with 152 additions and 2 deletions.
2 changes: 2 additions & 0 deletions cmd/otel-collector/components.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package main

import (
"github.com/metrico/otel-collector/extension/pyroscope"
"github.com/open-telemetry/opentelemetry-collector-contrib/connector/countconnector"
"github.com/open-telemetry/opentelemetry-collector-contrib/connector/datadogconnector"
"github.com/open-telemetry/opentelemetry-collector-contrib/connector/exceptionsconnector"
Expand Down Expand Up @@ -204,6 +205,7 @@ func components() (otelcol.Factories, error) {
jsonlogencodingextension.NewFactory(),
textencodingextension.NewFactory(),
zipkinencodingextension.NewFactory(),
pyroscope.NewFactory(),
}
for _, ext := range factories.Extensions {
extensions = append(extensions, ext)
Expand Down
42 changes: 42 additions & 0 deletions extension/pyroscope/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
# Pyroscope client

| Status | |
|---------------------------|--------|
| Stability | [beta] |


The Extension provides the functionality to export the opentelementry collector profiles into a pyroscope compatible
server.


The following settings can be configured:

- application_name (default = "opentelemetry-collector"): The name of the application as it will appear in Pyroscope.
- tags (default = empty map): A map of key-value pairs for additional tags to be associated with the profiles.
- server_address (default = "http://localhost:8062"): The URL of the Pyroscope server to which the profiles will be sent.
- basic_auth (default = empty): Basic authentication configuration for connecting to the Pyroscope server.
- username: The username for basic authentication.
- password: The password for basic authentication.
- profile_types (default = ["cpu", "alloc_objects", "alloc_space", "inuse_objects", "inuse_space"]):
An array of profile types to collect and send to Pyroscope.
- tenant_id (default = ""): The tenant ID to use when sending profiles to Pyroscope, for multi-tenancy support.

Example:
```yaml
extensions:
pyroscope:
application_name: "my-collector"
tags:
environment: "production"
region: "us-west-2"
server_address: "http://localhost:8062"
basic_auth:
username: "user"
password: "secret"
profile_types:
- "cpu"
- "alloc_objects"
- "inuse_space"
service:
extensions: [pyroscope]
```
27 changes: 27 additions & 0 deletions extension/pyroscope/config.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package pyroscope

import "go.opentelemetry.io/collector/component"

type Config struct {
ApplicationName string `json:"application_name"`
Tags map[string]string `json:"tags"`
ServerAddress string `json:"server_address"`
BasicAuth BasicAuth `json:"basic_auth"`
ProfileTypes []string `json:"profile_types"`
TenantID string `json:"tenant_id"`
}

type BasicAuth struct {
Username string `json:"username"`
Password string `json:"password"`
}

func defaultConfig() component.Config {
return &Config{
ApplicationName: "opentelemetry-collector",
ServerAddress: "http://localhost:8062",
Tags: map[string]string{},
BasicAuth: BasicAuth{},
ProfileTypes: []string{"cpu", "alloc_objects", "alloc_space", "inuse_objects", "inuse_space"},
}
}
74 changes: 74 additions & 0 deletions extension/pyroscope/extension.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
// Copyright The OpenTelemetry Authors
// SPDX-License-Identifier: Apache-2.0

package pyroscope

import (
"context"

"github.com/google/uuid"
"github.com/grafana/pyroscope-go"
"go.opentelemetry.io/collector/component"
"go.opentelemetry.io/collector/component/componenttest"
"go.opentelemetry.io/collector/extension"
)

var pyroscopeType = component.MustNewType("pyroscope")

// NewNopCreateSettings returns a new nop settings for extension.Factory Create* functions.
func NewPyroscopeCreateSettings() extension.CreateSettings {
return extension.CreateSettings{
ID: component.NewIDWithName(pyroscopeType, uuid.NewString()),
TelemetrySettings: componenttest.NewNopTelemetrySettings(),
BuildInfo: component.NewDefaultBuildInfo(),
}
}

// NewNopFactory returns an extension.Factory that constructs nop extensions.
func NewFactory() extension.Factory {
return extension.NewFactory(
pyroscopeType,
defaultConfig,
func(ctx context.Context, settings extension.CreateSettings, config component.Config) (extension.Extension, error) {
return &PyroscopeExtension{
config: config.(*Config),
}, nil
},
component.StabilityLevelStable)
}

type PyroscopeExtension struct {
config *Config
settings extension.CreateSettings
ctx context.Context
profiler *pyroscope.Profiler
}

func (p PyroscopeExtension) Start(ctx context.Context, host component.Host) error {
cfg := pyroscope.Config{
ApplicationName: p.config.ApplicationName,

// replace this with the address of pyroscope server
ServerAddress: p.config.ServerAddress,

// you can disable logging by setting this to nil
Logger: pyroscope.StandardLogger,

// Optional HTTP Basic authentication (Grafana Cloud)
BasicAuthUser: p.config.BasicAuth.Username,
BasicAuthPassword: p.config.BasicAuth.Password,
Tags: p.config.Tags,
TenantID: p.config.TenantID,
ProfileTypes: nil,
}
for _, profileType := range p.config.ProfileTypes {
cfg.ProfileTypes = append(cfg.ProfileTypes, pyroscope.ProfileType(profileType))
}
var err error
p.profiler, err = pyroscope.Start(cfg)
return err
}

func (p PyroscopeExtension) Shutdown(ctx context.Context) error {
return p.profiler.Stop()
}
4 changes: 3 additions & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,10 @@ require (
github.com/go-faster/city v1.0.1
github.com/go-logfmt/logfmt v0.6.0
github.com/google/pprof v0.0.0-20240320155624-b11c3daa6f07
github.com/google/uuid v1.6.0
github.com/gorilla/mux v1.8.1
github.com/grafana/jfr-parser v0.8.0
github.com/grafana/pyroscope-go v1.1.2
github.com/grafana/pyroscope/api v0.4.0
github.com/open-telemetry/opentelemetry-collector-contrib/connector/countconnector v0.98.0
github.com/open-telemetry/opentelemetry-collector-contrib/connector/datadogconnector v0.98.0
Expand Down Expand Up @@ -369,13 +371,13 @@ require (
github.com/google/go-querystring v1.1.0 // indirect
github.com/google/gofuzz v1.2.0 // indirect
github.com/google/s2a-go v0.1.7 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/googleapis/enterprise-certificate-proxy v0.3.2 // indirect
github.com/googleapis/gax-go/v2 v2.12.3 // indirect
github.com/gophercloud/gophercloud v1.8.0 // indirect
github.com/gorilla/websocket v1.5.1 // indirect
github.com/gosnmp/gosnmp v1.37.0 // indirect
github.com/grafana/loki/pkg/push v0.0.0-20231127162423-bd505f8e2d37 // indirect
github.com/grafana/pyroscope-go/godeltaprof v0.1.8 // indirect
github.com/grafana/regexp v0.0.0-20221122212121-6b5c0a4cb7fd // indirect
github.com/grobie/gomemcache v0.0.0-20230213081705-239240bbc445 // indirect
github.com/grpc-ecosystem/grpc-gateway/v2 v2.19.1 // indirect
Expand Down
5 changes: 4 additions & 1 deletion go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -718,7 +718,10 @@ github.com/grafana/jfr-parser v0.8.0 h1:/uo2wZNXrxw7tKLFwP2omJ3EQGMkD9wzhPsRogVo
github.com/grafana/jfr-parser v0.8.0/go.mod h1:M5u1ux34Qo47ZBWksbMYVk40s7dvU3WMVYpxweEu4R0=
github.com/grafana/loki/pkg/push v0.0.0-20231127162423-bd505f8e2d37 h1:w59bmBeLOk4enGtyX4kTBNY3FCw/nwDTYUqcjC4vKhg=
github.com/grafana/loki/pkg/push v0.0.0-20231127162423-bd505f8e2d37/go.mod h1:f3JSoxBTPXX5ec4FxxeC19nTBSxoTz+cBgS3cYLMcr0=
github.com/grafana/pyroscope v1.5.0/go.mod h1:rg53VGcqOf3FawAcAUpkcNNF7+gV1VZFbZY9Gfxry+c=
github.com/grafana/pyroscope-go v1.1.2 h1:7vCfdORYQMCxIzI3NlYAs3FcBP760+gWuYWOyiVyYx8=
github.com/grafana/pyroscope-go v1.1.2/go.mod h1:HSSmHo2KRn6FasBA4vK7BMiQqyQq8KSuBKvrhkXxYPU=
github.com/grafana/pyroscope-go/godeltaprof v0.1.8 h1:iwOtYXeeVSAeYefJNaxDytgjKtUuKQbJqgAIjlnicKg=
github.com/grafana/pyroscope-go/godeltaprof v0.1.8/go.mod h1:2+l7K7twW49Ct4wFluZD3tZ6e0SjanjcUUBPVD/UuGU=
github.com/grafana/pyroscope/api v0.4.0 h1:J86DxoNeLOvtJhB1Cn65JMZkXe682D+RqeoIUiYc/eo=
github.com/grafana/pyroscope/api v0.4.0/go.mod h1:MFnZNeUM4RDsDOnbgKW3GWoLSBpLzMMT9nkvhHHo81o=
github.com/grafana/regexp v0.0.0-20221122212121-6b5c0a4cb7fd h1:PpuIBO5P3e9hpqBD0O/HjhShYuM6XE0i/lbE6J94kww=
Expand Down

0 comments on commit 0ea91ae

Please sign in to comment.