Documentation ¶
Overview ¶
Package metric provides primitives for collecting metrics.
Index ¶
- Variables
- func CheapNowNano() int64
- func Disable() error
- func EmitMetricUpdate()
- func GetMetricRegistration() (*pb.MetricRegistration, error)
- func GetSnapshot(options SnapshotOptions) (*prometheus.Snapshot, error)
- func Initialize() error
- func MustRegisterCustomUint64Metric(name string, cumulative, sync bool, description string, ...)
- func RegisterCustomUint64Metric(name string, cumulative, sync bool, units pb.MetricMetadata_Units, ...) error
- func StartProfilingMetrics(profilingMetrics string, profilingRate time.Duration) error
- func StartStage(stage InitStage) func()
- func StopProfilingMetrics()
- type Bucketer
- type DistributionMetric
- type ExponentialBucketer
- type FakeDistributionMetric
- type FakeTimedOperation
- type FakeTimerMetric
- type FakeUint64Metric
- type Field
- type FieldValue
- type InitStage
- type ProfilingDistributionMetric
- type ProfilingTimerMetric
- type ProfilingUint64Metric
- type SnapshotOptions
- type TimedOperation
- type TimerMetric
- type Uint64Metric
- func MustCreateNewUint64Metric(name string, sync bool, description string, fields ...Field) *Uint64Metric
- func MustCreateNewUint64NanosecondsMetric(name string, sync bool, description string) *Uint64Metric
- func NewUint64Metric(name string, sync bool, units pb.MetricMetadata_Units, description string, ...) (*Uint64Metric, error)
Constants ¶
This section is empty.
Variables ¶
var ( // ErrNameInUse indicates that another metric is already defined for // the given name. ErrNameInUse = errors.New("metric name already in use") // ErrInitializationDone indicates that the caller tried to create a // new metric after initialization. ErrInitializationDone = errors.New("metric cannot be created after initialization is complete") // ErrFieldValueContainsIllegalChar indicates that the value of a metric // field had an invalid character in it. ErrFieldValueContainsIllegalChar = errors.New("metric field value contains illegal character") // ErrFieldHasNoAllowedValues indicates that the field needs to define some // allowed values to be a valid and useful field. ErrFieldHasNoAllowedValues = errors.New("metric field does not define any allowed values") // ErrTooManyFieldCombinations indicates that the number of unique // combinations of fields is too large to support. ErrTooManyFieldCombinations = errors.New("metric has too many combinations of allowed field values") )
var ( WeirdnessTypeTimeFallback = FieldValue{"time_fallback"} WeirdnessTypePartialResult = FieldValue{"partial_result"} WeirdnessTypeVsyscallCount = FieldValue{"vsyscall_count"} WeirdnessTypeWatchdogStuckStartup = FieldValue{"watchdog_stuck_startup"} WeirdnessTypeWatchdogStuckTasks = FieldValue{"watchdog_stuck_tasks"} )
Weirdness metric type constants.
var ( // WeirdnessMetric is a metric with fields created to track the number // of weird occurrences such as time fallback, partial_result, vsyscall // count, watchdog startup timeouts and stuck tasks. WeirdnessMetric = MustCreateNewUint64Metric("/weirdness", true, "Increment for weird occurrences of problems such as time fallback, partial result, vsyscalls invoked in the sandbox, watchdog startup timeouts and stuck tasks.", NewField("weirdness_type", &WeirdnessTypeTimeFallback, &WeirdnessTypePartialResult, &WeirdnessTypeVsyscallCount, &WeirdnessTypeWatchdogStuckStartup, &WeirdnessTypeWatchdogStuckTasks, )) // SuspiciousOperationsMetric is a metric with fields created to detect // operations such as opening an executable file to write from a gofer. SuspiciousOperationsMetric = MustCreateNewUint64Metric("/suspicious_operations", true, "Increment for suspicious operations such as opening an executable file to write from a gofer.", NewField("operation_type", &SuspiciousOperationsTypeOpenedWriteExecuteFile, )) )
List of global metrics that are used in multiple places.
var ErrNotYetInitialized = errors.New("metrics are not yet initialized")
ErrNotYetInitialized is returned by GetMetricRegistration if metrics are not yet initialized.
var MustCreateNewProfilingDistributionMetric = MustCreateNewFakeDistributionMetric
MustCreateNewProfilingDistributionMetric is equivalent to MustCreateNewDistributionMetric except it creates a ProfilingDistributionMetric.
var MustCreateNewProfilingTimerMetric = MustCreateNewFakeTimerMetric
MustCreateNewProfilingTimerMetric is equivalent to MustCreateNewTimerMetric except it creates a ProfilingTimerMetric.
var MustCreateNewProfilingUint64Metric = MustCreateNewFakeUint64Metric
MustCreateNewProfilingUint64Metric is equivalent to MustCreateNewUint64Metric except it creates a ProfilingUint64Metric.
var NewProfilingDistributionMetric = NewFakeDistributionMetric
NewProfilingDistributionMetric is equivalent to NewDistributionMetric except it creates a ProfilingDistributionMetric.
var NewProfilingTimerMetric = NewFakeTimerMetric
NewProfilingTimerMetric is equivalent to NewTimerMetric except it creates a ProfilingTimerMetric.
var NewProfilingUint64Metric = NewFakeUint64Metric
NewProfilingUint64Metric is equivalent to NewUint64Metric except it creates a ProfilingUint64Metric
var ( // ProfilingMetricWriter is the output destination to which // ProfilingMetrics will be written to in TSV format. ProfilingMetricWriter *os.File )
var (
SuspiciousOperationsTypeOpenedWriteExecuteFile = FieldValue{"opened_write_execute_file"}
)
Suspicious operations metric type constants.
Functions ¶
func CheapNowNano ¶
func CheapNowNano() int64
CheapNowNano returns the current unix timestamp in nanoseconds.
func Disable ¶
func Disable() error
Disable sends an empty metric registration event over the event channel, disabling metric collection.
Precondition:
- All metrics are registered.
- Initialize/Disable has not been called.
func EmitMetricUpdate ¶
func EmitMetricUpdate()
EmitMetricUpdate emits a MetricUpdate over the event channel.
Only metrics that have changed since the last call are emitted.
EmitMetricUpdate is thread-safe.
Preconditions:
- Initialize has been called.
func GetMetricRegistration ¶
func GetMetricRegistration() (*pb.MetricRegistration, error)
GetMetricRegistration returns the metric registration data for all registered metrics. Must be called after Initialize(). Returns ErrNotYetInitialized if metrics are not yet initialized.
func GetSnapshot ¶
func GetSnapshot(options SnapshotOptions) (*prometheus.Snapshot, error)
GetSnapshot returns a Prometheus snapshot of the metric data. Returns ErrNotYetInitialized if metrics have not yet been initialized.
func Initialize ¶
func Initialize() error
Initialize sends a metric registration event over the event channel.
Precondition:
- All metrics are registered.
- Initialize/Disable has not been called.
func MustRegisterCustomUint64Metric ¶
func MustRegisterCustomUint64Metric(name string, cumulative, sync bool, description string, value func(...*FieldValue) uint64, fields ...Field)
MustRegisterCustomUint64Metric calls RegisterCustomUint64Metric for metrics without fields and panics if it returns an error.
func RegisterCustomUint64Metric ¶
func RegisterCustomUint64Metric(name string, cumulative, sync bool, units pb.MetricMetadata_Units, description string, value func(...*FieldValue) uint64, fields ...Field) error
RegisterCustomUint64Metric registers a metric with the given name.
Register must only be called at init and will return and error if called after Initialized.
Preconditions:
- name must be globally unique.
- Initialize/Disable have not been called.
- value is expected to accept exactly len(fields) arguments.
func StartProfilingMetrics ¶
StartProfilingMetrics checks the ProfilingMetrics runsc flags and creates goroutines responsible for outputting the profiling metric data.
Preconditions:
- All metrics are registered.
- Initialize/Disable has been called.
func StartStage ¶
func StartStage(stage InitStage) func()
StartStage should be called when an initialization stage is started. It returns a function that must be called to indicate that the stage ended. Alternatively, future calls to StartStage will implicitly indicate that the previous stage ended. Stage information will be emitted in the next call to EmitMetricUpdate after a stage has ended.
This function may (and is expected to) be called prior to final initialization of this metric library, as it has to capture early stages of Sentry initialization.
func StopProfilingMetrics ¶
func StopProfilingMetrics()
StopProfilingMetrics stops the profiling metrics goroutines. Call to make sure all metric data has been flushed. Note that calling this function prior to StartProfilingMetrics has no effect.
Types ¶
type Bucketer ¶
type Bucketer interface { // NumFiniteBuckets is the number of finite buckets in the distribution. // This is only called once and never expected to return a different value. NumFiniteBuckets() int // LowerBound takes the index of a bucket (within [0, NumBuckets()]) and // returns the inclusive lower bound of that bucket. // In other words, the lowest value of `x` for which `BucketIndex(x) == i` // should be `x = LowerBound(i)`. // The upper bound of a bucket is the lower bound of the next bucket. // The last bucket (with `bucketIndex == NumFiniteBuckets()`) is infinite, // i.e. it has no upper bound (but it still has a lower bound). LowerBound(bucketIndex int) int64 // BucketIndex takes a sample and returns the index of the bucket that the // sample should fall into. // Must return either: // - A value within [0, NumBuckets() -1] if the sample falls within a // finite bucket // - NumBuckets() if the sample falls within the last (infinite) bucket // - '-1' if the sample is lower than what any bucket can represent, i.e. // the sample should be in the implicit "underflow" bucket. // This function must be go:nosplit-compatible and have no escapes. // +checkescape:all BucketIndex(sample int64) int }
Bucketer is an interface to bucket values into finite, distinct buckets.
func NewDurationBucketer ¶
NewDurationBucketer returns a Bucketer well-suited for measuring durations in nanoseconds. Useful for NewTimerMetric. minDuration and maxDuration are conservative estimates of the minimum and maximum durations expected to be accurately measured by the Bucketer.
type DistributionMetric ¶
type DistributionMetric struct {
// contains filtered or unexported fields
}
DistributionMetric represents a distribution of values in finite buckets. It also separately keeps track of min/max in order to ascertain whether the buckets can faithfully represent the range of values encountered in the distribution.
func MustCreateNewDistributionMetric ¶
func MustCreateNewDistributionMetric(name string, sync bool, bucketer Bucketer, unit pb.MetricMetadata_Units, description string, fields ...Field) *DistributionMetric
MustCreateNewDistributionMetric creates and registers a distribution metric. If an error occurs, it panics.
func NewDistributionMetric ¶
func NewDistributionMetric(name string, sync bool, bucketer Bucketer, unit pb.MetricMetadata_Units, description string, fields ...Field) (*DistributionMetric, error)
NewDistributionMetric creates and registers a new distribution metric.
func (*DistributionMetric) AddSample ¶
func (d *DistributionMetric) AddSample(sample int64, fields ...*FieldValue)
AddSample adds a sample to the distribution. This *must* be called with the correct number of fields, or it will panic. +checkescape:all
type ExponentialBucketer ¶
type ExponentialBucketer struct {
// contains filtered or unexported fields
}
ExponentialBucketer implements Bucketer, with the first bucket starting with 0 as lowest bound with `Width` width, and each subsequent bucket being wider by a scaled exponentially-growing series, until `NumFiniteBuckets` buckets exist.
func NewExponentialBucketer ¶
func NewExponentialBucketer(numFiniteBuckets int, width uint64, scale, growth float64) *ExponentialBucketer
NewExponentialBucketer returns a new Bucketer with exponential buckets.
func (*ExponentialBucketer) BucketIndex ¶
func (b *ExponentialBucketer) BucketIndex(sample int64) int
BucketIndex implements Bucketer.BucketIndex. +checkescape:all
func (*ExponentialBucketer) LowerBound ¶
func (b *ExponentialBucketer) LowerBound(bucketIndex int) int64
LowerBound implements Bucketer.LowerBound.
func (*ExponentialBucketer) NumFiniteBuckets ¶
func (b *ExponentialBucketer) NumFiniteBuckets() int
NumFiniteBuckets implements Bucketer.NumFiniteBuckets.
type FakeDistributionMetric ¶
type FakeDistributionMetric struct{}
FakeDistributionMetric is a type that implements all the methods of a DistributionMetric as a no-op.
func MustCreateNewFakeDistributionMetric ¶
func MustCreateNewFakeDistributionMetric(name string, sync bool, bucketer Bucketer, unit pb.MetricMetadata_Units, description string, fields ...Field) *FakeDistributionMetric
MustCreateNewFakeDistributionMetric is equivalent to MustCreateNewDistributionMetric except it creates a FakeDistributionMetric.
func NewFakeDistributionMetric ¶
func NewFakeDistributionMetric(name string, sync bool, bucketer Bucketer, unit pb.MetricMetadata_Units, description string, fields ...Field) (*FakeDistributionMetric, error)
NewFakeDistributionMetric is equivalent to NewDistributionMetric except it creates a FakeDistributionMetric.
func (*FakeDistributionMetric) AddSample ¶
func (d *FakeDistributionMetric) AddSample(sample int64, fields ...*FieldValue)
AddSample on a FakeUint64Metric does nothing.
type FakeTimedOperation ¶
type FakeTimedOperation struct{}
FakeTimedOperation is a type that implements all the methods of a TimedOperation as a no-op.
func (FakeTimedOperation) Finish ¶
func (o FakeTimedOperation) Finish(extraFields ...*FieldValue)
Finish on a FakeTimedOperation does nothing.
type FakeTimerMetric ¶
type FakeTimerMetric struct{}
FakeTimerMetric is a type that implements all the methods of a TimerMetric as a no-op.
func MustCreateNewFakeTimerMetric ¶
func MustCreateNewFakeTimerMetric(name string, nanoBucketer Bucketer, description string, fields ...Field) *FakeTimerMetric
MustCreateNewFakeTimerMetric is equivalent to MustCreateNewTimerMetric except it creates a FakeTimerMetric.
func NewFakeTimerMetric ¶
func NewFakeTimerMetric(name string, nanoBucketer Bucketer, description string, fields ...Field) (*FakeTimerMetric, error)
NewFakeTimerMetric is equivalent to NewTimerMetric except it creates a FakeTimerMetric.
func (*FakeTimerMetric) Start ¶
func (t *FakeTimerMetric) Start(fields ...*FieldValue) FakeTimedOperation
Start on a FakeUint64Metric returns a FakeTimedOperation struct, which does nothing and does not keep the time.
type FakeUint64Metric ¶
type FakeUint64Metric struct{}
FakeUint64Metric is a type that implements all the methods of a Uint64Metric as a no-op.
func MustCreateNewFakeUint64Metric ¶
func MustCreateNewFakeUint64Metric(name string, sync bool, description string, fields ...Field) *FakeUint64Metric
MustCreateNewFakeUint64Metric is equivalent to MustCreateNewUint64Metric except it creates a FakeUint64Metric.
func NewFakeUint64Metric ¶
func NewFakeUint64Metric(name string, sync bool, units pb.MetricMetadata_Units, description string, fields ...Field) (*FakeUint64Metric, error)
NewFakeUint64Metric is equivalent to NewUint64Metric except it creates a FakeUint64Metric
func (*FakeUint64Metric) Increment ¶
func (m *FakeUint64Metric) Increment(fieldValues ...*FieldValue)
Increment on a FakeUint64Metric does nothing.
func (*FakeUint64Metric) IncrementBy ¶
func (m *FakeUint64Metric) IncrementBy(v uint64, fieldValues ...*FieldValue)
IncrementBy on a FakeUint64Metric does nothing.
func (*FakeUint64Metric) Value ¶
func (m *FakeUint64Metric) Value(fieldValues ...*FieldValue) uint64
Value from a FakeUint64Metric always returns a meaningless value.
type Field ¶
type Field struct {
// contains filtered or unexported fields
}
Field contains the field name and allowed values for the metric which is used in registration of the metric.
func NewField ¶
func NewField(name string, allowedValues ...*FieldValue) Field
NewField defines a new Field that can be used to break down a metric. The set of allowedValues must be unique strings wrapped with `FieldValue`. The *same* `FieldValue` pointers must be used during metric modifications. In practice, in most cases, this means you should declare these `FieldValue`s as package-level `var`s, and always use the address of these package-level `var`s during metric modifications.
type FieldValue ¶
type FieldValue struct {
Value string
}
FieldValue is a string that can be used as a value for a Field. It must be referred to by address when the Field is created and when its metric value is modified. This ensures that the same FieldValue reference is used, which in turn enables the metric code to use the address of a FieldValue as comparison operator, rather than doing string comparisons.
type ProfilingDistributionMetric ¶
type ProfilingDistributionMetric = FakeDistributionMetric
ProfilingDistributionMetric is a metric type that is registered and used only when the "condmetric_profiling" go tag is specified when building runsc.
Otherwise it is exactly like a DistributionMetric.
type ProfilingTimerMetric ¶
type ProfilingTimerMetric = FakeTimerMetric
ProfilingTimerMetric is a metric type that is registered and used only when the "condmetric_profiling" go tag is specified when building runsc.
Otherwise it is exactly like a TimerMetric.
type ProfilingUint64Metric ¶
type ProfilingUint64Metric = FakeUint64Metric
ProfilingUint64Metric is a metric type that is registered and used only when the "condmetric_profiling" go tag is specified when building runsc.
Otherwise it is exactly like a Uint64Metric.
type SnapshotOptions ¶
type SnapshotOptions struct { // Filter, if set, should return true for metrics that should be written to // the snapshot. If unset, all metrics are written to the snapshot. Filter func(*prometheus.Metric) bool }
SnapshotOptions controls how snapshots are exported in GetSnapshot.
type TimedOperation ¶
type TimedOperation struct {
// contains filtered or unexported fields
}
TimedOperation is used by TimerMetric to keep track of the time elapsed between an operation starting and stopping.
func (TimedOperation) Finish ¶
func (o TimedOperation) Finish(extraFields ...*FieldValue)
Finish marks an operation as finished and records its duration. `extraFields` is the rest of the fields appended to the fields passed to `TimerMetric.Start`. The concatenation of these two must be the exact number of fields that the underlying metric has. +checkescape:all
type TimerMetric ¶
type TimerMetric struct {
DistributionMetric
}
TimerMetric wraps a distribution metric with convenience functions for latency measurements, which is a popular specialization of distribution metrics.
func MustCreateNewTimerMetric ¶
func MustCreateNewTimerMetric(name string, nanoBucketer Bucketer, description string, fields ...Field) *TimerMetric
MustCreateNewTimerMetric creates and registers a timer metric. If an error occurs, it panics.
func NewTimerMetric ¶
func NewTimerMetric(name string, nanoBucketer Bucketer, description string, fields ...Field) (*TimerMetric, error)
NewTimerMetric provides a convenient way to measure latencies. The arguments are the same as `NewDistributionMetric`, except:
- `nanoBucketer`: Same as `NewDistribution`'s `bucketer`, expected to hold durations in nanoseconds. Adjust parameters accordingly. NewDurationBucketer may be helpful here.
func (*TimerMetric) Start ¶
func (t *TimerMetric) Start(fields ...*FieldValue) TimedOperation
Start starts a timer measurement for the given combination of fields. It returns a TimedOperation which can be passed around as necessary to measure the duration of the operation. Once the operation is finished, call Finish on the TimedOperation. The fields passed to Start may be partially specified; if so, the remaining fields must be passed to TimedOperation.Finish. This is useful for cases where which path an operation took is only known after it happens. This path can be part of the fields passed to Finish. +checkescape:all
type Uint64Metric ¶
type Uint64Metric struct {
// contains filtered or unexported fields
}
Uint64Metric encapsulates a uint64 that represents some kind of metric to be monitored.
Metrics are not saved across save/restore and thus reset to zero on restore.
func MustCreateNewUint64Metric ¶
func MustCreateNewUint64Metric(name string, sync bool, description string, fields ...Field) *Uint64Metric
MustCreateNewUint64Metric calls NewUint64Metric and panics if it returns an error.
func MustCreateNewUint64NanosecondsMetric ¶
func MustCreateNewUint64NanosecondsMetric(name string, sync bool, description string) *Uint64Metric
MustCreateNewUint64NanosecondsMetric calls NewUint64Metric and panics if it returns an error.
func NewUint64Metric ¶
func NewUint64Metric(name string, sync bool, units pb.MetricMetadata_Units, description string, fields ...Field) (*Uint64Metric, error)
NewUint64Metric creates and registers a new cumulative metric with the given name.
Metrics must be statically defined (i.e., at init).
func (*Uint64Metric) Increment ¶
func (m *Uint64Metric) Increment(fieldValues ...*FieldValue)
Increment increments the metric field by 1. This must be called with the correct number of field values or it will panic.
func (*Uint64Metric) IncrementBy ¶
func (m *Uint64Metric) IncrementBy(v uint64, fieldValues ...*FieldValue)
IncrementBy increments the metric by v. This must be called with the correct number of field values or it will panic.
func (*Uint64Metric) Value ¶
func (m *Uint64Metric) Value(fieldValues ...*FieldValue) uint64
Value returns the current value of the metric for the given set of fields. This must be called with the correct number of field values or it will panic.