Skip to content

Commit

Permalink
feat(cloudmonitoring): implement builder
Browse files Browse the repository at this point in the history
  • Loading branch information
jlevesy committed Apr 7, 2024
1 parent 234e2b7 commit 1dacd60
Show file tree
Hide file tree
Showing 2 changed files with 291 additions and 0 deletions.
180 changes: 180 additions & 0 deletions target/cloudmonitoring/cloudmonitoring.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,180 @@
package cloudmonitoring

import "github.com/K-Phoen/sdk"

// AutoAlignmentPeriod lets Google Clound Monitoring decide what it the ideal alignment period.
const AutoAlignmentPeriod = "cloud-monitoring-auto"

// PreprocessorMethod defines the available pre-processing options.
type PreprocessorMethod string

const (
PreprocessNone PreprocessorMethod = "none"
PreprocessRate PreprocessorMethod = "rate"
PreprocessDelta PreprocessorMethod = "delta"
)

// Aligner specifies the operation that will be applied to the data points in
// each alignment period in a time series.
// See https://cloud.google.com/monitoring/api/ref_v3/rest/v3/projects.alertPolicies#Aligner
type Aligner string

const (
AlignNone Aligner = "ALIGN_NONE"
AlignDelta Aligner = "ALIGN_DELTA"
AlignRate Aligner = "ALIGN_RATE"
AlignInterpolate Aligner = "ALIGN_INTERPOLATE"
AlignNextOlder Aligner = "ALIGN_NEXT_OLDER"
AlignMin Aligner = "ALIGN_MIN"
AlignMax Aligner = "ALIGN_MAX"
AlignMean Aligner = "ALIGN_MEAN"
AlignCount Aligner = "ALIGN_COUNT"
AlignSum Aligner = "ALIGN_SUM"
AlignStdDev Aligner = "ALIGN_STDDEV"
AlignCountTrue Aligner = "ALIGN_COUNT_TRUE"
AlignCountFalse Aligner = "ALIGN_COUNT_FALSE"
AlignFractionTrue Aligner = "ALIGN_FRACTION_TRUE"
AlignPercentile99 Aligner = "ALIGN_PERCENTILE_99"
AlignPercentile95 Aligner = "ALIGN_PERCENTILE_95"
AlignPercentile50 Aligner = "ALIGN_PERCENTILE_50"
AlignPercentile05 Aligner = "ALIGN_PERCENTILE_05"
AlignPercentChange Aligner = "ALIGN_PERCENT_CHANGE"
)

// Reducer operation describes how to aggregate data points from multiple time
// series into a single time series, where the value of each data point in the
// resulting series is a function of all the already aligned values in the
// input time series.
// See https://cloud.google.com/monitoring/api/ref_v3/rest/v3/projects.alertPolicies#reducer
type Reducer string

const (
ReduceNone Reducer = "REDUCE_NONE"
ReduceMean Reducer = "REDUCE_MEAN"
ReduceMin Reducer = "REDUCE_MIN"
ReduceMax Reducer = "REDUCE_MAX"
ReduceSum Reducer = "REDUCE_SUM"
ReduceStdDev Reducer = "REDUCE_STDDEV"
ReduceCount Reducer = "REDUCE_COUNT"
ReduceCountTrue Reducer = "REDUCE_COUNT_TRUE"
ReduceCountFalse Reducer = "REDUCE_COUNT_FALSE"
ReduceCountFractionTrue Reducer = "REDUCE_FRACTION_TRUE"
ReducePercentile99 Reducer = "REDUCE_PERCENTILE_99"
ReducePercentile95 Reducer = "REDUCE_PERCENTILE_95"
ReducePercentile50 Reducer = "REDUCE_PERCENTILE_50"
ReducePercentile05 Reducer = "REDUCE_PERCENTILE_05"
)

// FilterOperator describes
type FilterOperator string

const (
FilterOperatorEqual FilterOperator = "="
FilterOperatorNotEqual FilterOperator = "!="
FilterOperatorMatchesRegexp FilterOperator = "=~"
FilterOperatorNotMatchesRegexp FilterOperator = "!=~"
)

// Option represents an option that can be used to configure a cloudmonitoring query.
type Option func(target *CloudMonitoring)

// CloudMonitoring represents a google cloud monitoring query.
type CloudMonitoring struct {
Builder *sdk.Target
}

func New(metricType string, options ...Option) *CloudMonitoring {
stackdriver := &CloudMonitoring{
Builder: &sdk.Target{
QueryType: "timeSeriesList",
TimeSeriesList: &sdk.StackdriverTimeSeriesList{
Filters: []string{
"metric.type", string(FilterOperatorEqual), metricType,
},
},
},
}

for _, opt := range options {
opt(stackdriver)
}

return stackdriver
}

func ProjectName(projectName string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.ProjectName = projectName
}
}

func CrossSeriesReducer(reducer Reducer) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.CrossSeriesReducer = string(reducer)
}
}

func PerSeriesAligner(aligner Aligner, alignmentPeriod string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.PerSeriesAligner = string(aligner)
target.Builder.TimeSeriesList.AlignmentPeriod = alignmentPeriod
}
}

func GroupBy(field string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.GroupBys = append(
target.Builder.TimeSeriesList.GroupBys,
field,
)
}
}

func Filter(field string, op FilterOperator, value string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.Filters = append(
target.Builder.TimeSeriesList.Filters,
"AND", field, string(op), value,
)
}
}

func View(view string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.View = view
}
}

func Title(title string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.Title = title
}
}

func SecondaryCrossSeriesReducer(reducer Reducer) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.SecondaryCrossSeriesReducer = string(reducer)
}
}

func SecondaryPerSeriesAligner(aligner Aligner, alignmentPeriod string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.SecondaryPerSeriesAligner = string(aligner)
target.Builder.TimeSeriesList.SecondaryAlignmentPeriod = alignmentPeriod
}
}

func SecondaryGroupBy(field string) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.SecondaryGroupBys = append(
target.Builder.TimeSeriesList.SecondaryGroupBys,
field,
)
}
}

func Preprocessor(preprocessor PreprocessorMethod) Option {
return func(target *CloudMonitoring) {
target.Builder.TimeSeriesList.Preprocessor = string(preprocessor)
}
}
111 changes: 111 additions & 0 deletions target/cloudmonitoring/cloudmonitoring_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
package cloudmonitoring

import (
"testing"

"github.com/K-Phoen/sdk"
"github.com/stretchr/testify/assert"
)

func TestCloudMontioring(t *testing.T) {
for _, testCase := range []struct {
desc string
metricType string
options []Option
wantTarget *sdk.Target
}{
{
desc: "default values",
metricType: "pubsub.googleapis.com/subscription/num_undelivered_messages",
wantTarget: &sdk.Target{
QueryType: "timeSeriesList",
TimeSeriesList: &sdk.StackdriverTimeSeriesList{
Filters: []string{
"metric.type",
"=",
"pubsub.googleapis.com/subscription/num_undelivered_messages",
},
},
},
},
{
desc: "multiple filters",
metricType: "pubsub.googleapis.com/subscription/num_undelivered_messages",
options: []Option{
Filter("potato", FilterOperatorEqual, "patata"),
},
wantTarget: &sdk.Target{
QueryType: "timeSeriesList",
TimeSeriesList: &sdk.StackdriverTimeSeriesList{
Filters: []string{
"metric.type",
"=",
"pubsub.googleapis.com/subscription/num_undelivered_messages",
"AND",
"potato",
"=",
"patata",
},
},
},
},
{
desc: "all options",
metricType: "pubsub.googleapis.com/subscription/num_undelivered_messages",
options: []Option{
ProjectName("joe"),
CrossSeriesReducer(ReduceCountTrue),
PerSeriesAligner(AlignMax, "12d"),
GroupBy("foo"),
GroupBy("bar"),
GroupBy("biz"),
View("lafritte"),
Title("banana"),
SecondaryCrossSeriesReducer(ReduceCountFalse),
SecondaryPerSeriesAligner(AlignCount, "12s"),
SecondaryGroupBy("far"),
SecondaryGroupBy("fuz"),
SecondaryGroupBy("fiz"),
Preprocessor(PreprocessDelta),
},
wantTarget: &sdk.Target{
QueryType: "timeSeriesList",
TimeSeriesList: &sdk.StackdriverTimeSeriesList{
ProjectName: "joe",
CrossSeriesReducer: string(ReduceCountTrue),
PerSeriesAligner: string(AlignMax),
AlignmentPeriod: "12d",
GroupBys: []string{
"foo",
"bar",
"biz",
},
View: "lafritte",
Title: "banana",
SecondaryCrossSeriesReducer: string(ReduceCountFalse),
SecondaryPerSeriesAligner: string(AlignCount),
SecondaryAlignmentPeriod: "12s",
SecondaryGroupBys: []string{
"far",
"fuz",
"fiz",
},
Preprocessor: string(PreprocessDelta),
Filters: []string{
"metric.type",
"=",
"pubsub.googleapis.com/subscription/num_undelivered_messages",
},
},
},
},
} {
t.Run(testCase.desc, func(t *testing.T) {
assert.Equal(t,
testCase.wantTarget,
New(testCase.metricType, testCase.options...).Builder,
)
})
}

}

0 comments on commit 1dacd60

Please sign in to comment.