Skip to content

Commit 1062973

Browse files
committed
refactor: move exporter flags to main package
This refactoring makes flags handling more similar to postgres_exporter, moving `exporter.` flags to the main package and using an "opts" pattern for building the Exporter instance. Signed-off-by: Cristian Greco <[email protected]>
1 parent 23c6c73 commit 1062973

File tree

4 files changed

+140
-29
lines changed

4 files changed

+140
-29
lines changed

collector/exporter.go

Lines changed: 41 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,6 @@ import (
2121
"sync"
2222
"time"
2323

24-
"github.com/alecthomas/kingpin/v2"
2524
"github.com/go-sql-driver/mysql"
2625
"github.com/prometheus/client_golang/prometheus"
2726
)
@@ -40,22 +39,6 @@ const (
4039
timeoutParam = `lock_wait_timeout=%d`
4140
)
4241

43-
// Tunable flags.
44-
var (
45-
exporterLockTimeout = kingpin.Flag(
46-
"exporter.lock_wait_timeout",
47-
"Set a lock_wait_timeout (in seconds) on the connection to avoid long metadata locking.",
48-
).Default("2").Int()
49-
enableExporterLockTimeout = kingpin.Flag(
50-
"exporter.enable_lock_wait_timeout",
51-
"Enable the lock_wait_timeout MySQL connection parameter.",
52-
).Default("true").Bool()
53-
slowLogFilter = kingpin.Flag(
54-
"exporter.log_slow_filter",
55-
"Add a log_slow_filter to avoid slow query logging of scrapes. NOTE: Not supported by Oracle MySQL.",
56-
).Default("false").Bool()
57-
)
58-
5942
// metric definition
6043
var (
6144
mysqlUp = prometheus.NewDesc(
@@ -87,19 +70,53 @@ type Exporter struct {
8770
dsn string
8871
scrapers []Scraper
8972
instance *instance
73+
74+
enableLockWaitTimeout bool
75+
lockWaitTimeout int
76+
slowLogFilter bool
77+
}
78+
79+
type ExporterOpt func(*Exporter)
80+
81+
func EnableLockWaitTimeout(b bool) ExporterOpt {
82+
return func(e *Exporter) {
83+
e.enableLockWaitTimeout = b
84+
}
85+
}
86+
87+
func SetLockWaitTimeout(timeout int) ExporterOpt {
88+
return func(e *Exporter) {
89+
e.lockWaitTimeout = timeout
90+
}
91+
}
92+
93+
func SetSlowLogFilter(b bool) ExporterOpt {
94+
return func(e *Exporter) {
95+
e.slowLogFilter = b
96+
}
9097
}
9198

9299
// New returns a new MySQL exporter for the provided DSN.
93-
func New(ctx context.Context, dsn string, scrapers []Scraper, logger *slog.Logger) *Exporter {
100+
func New(ctx context.Context, dsn string, scrapers []Scraper, logger *slog.Logger, opts ...ExporterOpt) *Exporter {
101+
e := &Exporter{
102+
ctx: ctx,
103+
logger: logger,
104+
scrapers: scrapers,
105+
}
106+
107+
for _, opt := range opts {
108+
opt(e)
109+
}
110+
94111
// Setup extra params for the DSN
95112
dsnParams := []string{}
96113

97114
// Only set lock_wait_timeout if it is enabled
98-
if *enableExporterLockTimeout {
99-
dsnParams = append(dsnParams, fmt.Sprintf(timeoutParam, *exporterLockTimeout))
115+
if e.enableLockWaitTimeout {
116+
dsnParams = append(dsnParams, fmt.Sprintf(timeoutParam, e.lockWaitTimeout))
100117
}
101118

102-
if *slowLogFilter {
119+
if e.slowLogFilter {
103120
dsnParams = append(dsnParams, sessionSettingsParam)
104121
}
105122

@@ -110,12 +127,9 @@ func New(ctx context.Context, dsn string, scrapers []Scraper, logger *slog.Logge
110127
}
111128
dsn += strings.Join(dsnParams, "&")
112129

113-
return &Exporter{
114-
ctx: ctx,
115-
logger: logger,
116-
dsn: dsn,
117-
scrapers: scrapers,
118-
}
130+
e.dsn = dsn
131+
132+
return e
119133
}
120134

121135
// Describe implements prometheus.Collector.

collector/exporter_test.go

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,3 +65,80 @@ func TestExporter(t *testing.T) {
6565
}
6666
})
6767
}
68+
69+
func TestExporterWithOpts(t *testing.T) {
70+
convey.Convey("DSN changes with options", t, func() {
71+
convey.Convey("without any option", func() {
72+
exporter := New(
73+
context.Background(),
74+
dsn,
75+
[]Scraper{},
76+
promslog.NewNopLogger(),
77+
)
78+
convey.So(exporter.dsn, convey.ShouldEqual, "root@/mysql?")
79+
})
80+
81+
convey.Convey("SetSlowLogFilter enabled", func() {
82+
exporter := New(
83+
context.Background(),
84+
dsn,
85+
[]Scraper{},
86+
promslog.NewNopLogger(),
87+
SetSlowLogFilter(true),
88+
)
89+
convey.So(exporter.dsn, convey.ShouldEqual, "root@/mysql?log_slow_filter=%27tmp_table_on_disk,filesort_on_disk%27")
90+
})
91+
92+
convey.Convey("EnableLockWaitTimeout enabled and SetLockWaitTimeout", func() {
93+
exporter := New(
94+
context.Background(),
95+
dsn,
96+
[]Scraper{},
97+
promslog.NewNopLogger(),
98+
EnableLockWaitTimeout(true),
99+
SetLockWaitTimeout(30),
100+
)
101+
convey.So(exporter.dsn, convey.ShouldEqual, "root@/mysql?lock_wait_timeout=30")
102+
})
103+
104+
convey.Convey("EnableLockWaitTimeout disabled", func() {
105+
exporter := New(
106+
context.Background(),
107+
dsn,
108+
[]Scraper{},
109+
promslog.NewNopLogger(),
110+
EnableLockWaitTimeout(false),
111+
SetLockWaitTimeout(30),
112+
SetSlowLogFilter(true),
113+
)
114+
convey.So(exporter.dsn, convey.ShouldEqual, "root@/mysql?log_slow_filter=%27tmp_table_on_disk,filesort_on_disk%27")
115+
})
116+
117+
convey.Convey("All options enabled", func() {
118+
exporter := New(
119+
context.Background(),
120+
dsn,
121+
[]Scraper{},
122+
promslog.NewNopLogger(),
123+
EnableLockWaitTimeout(true),
124+
SetLockWaitTimeout(30),
125+
SetSlowLogFilter(true),
126+
)
127+
convey.So(exporter.dsn, convey.ShouldEqual, "root@/mysql?lock_wait_timeout=30&log_slow_filter=%27tmp_table_on_disk,filesort_on_disk%27")
128+
})
129+
130+
convey.Convey("All options with existing query parameter", func() {
131+
dsnWithParams := "root@/mysql?parseTime=true"
132+
exporter := New(
133+
context.Background(),
134+
dsnWithParams,
135+
[]Scraper{},
136+
promslog.NewNopLogger(),
137+
EnableLockWaitTimeout(true),
138+
SetLockWaitTimeout(30),
139+
SetSlowLogFilter(true),
140+
)
141+
convey.So(exporter.dsn, convey.ShouldEqual, "root@/mysql?parseTime=true&lock_wait_timeout=30&log_slow_filter=%27tmp_table_on_disk,filesort_on_disk%27")
142+
})
143+
})
144+
}

mysqld_exporter.go

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,18 @@ var (
6161
"tls.insecure-skip-verify",
6262
"Ignore certificate and server verification when using a tls connection.",
6363
).Bool()
64+
exporterLockTimeout = kingpin.Flag(
65+
"exporter.lock_wait_timeout",
66+
"Set a lock_wait_timeout (in seconds) on the connection to avoid long metadata locking.",
67+
).Default("2").Int()
68+
enableExporterLockTimeout = kingpin.Flag(
69+
"exporter.enable_lock_wait_timeout",
70+
"Enable the lock_wait_timeout MySQL connection parameter.",
71+
).Default("true").Bool()
72+
slowLogFilter = kingpin.Flag(
73+
"exporter.log_slow_filter",
74+
"Add a log_slow_filter to avoid slow query logging of scrapes. NOTE: Not supported by Oracle MySQL.",
75+
).Default("false").Bool()
6476
toolkitFlags = webflag.AddFlags(kingpin.CommandLine, ":9104")
6577
c = config.MySqlConfigHandler{
6678
Config: &config.Config{},
@@ -200,7 +212,11 @@ func newHandler(scrapers []collector.Scraper, logger *slog.Logger) http.HandlerF
200212

201213
registry := prometheus.NewRegistry()
202214

203-
registry.MustRegister(collector.New(ctx, dsn, filteredScrapers, logger))
215+
registry.MustRegister(collector.New(ctx, dsn, filteredScrapers, logger,
216+
collector.EnableLockWaitTimeout(*enableExporterLockTimeout),
217+
collector.SetLockWaitTimeout(*exporterLockTimeout),
218+
collector.SetSlowLogFilter(*slowLogFilter),
219+
))
204220

205221
gatherers := prometheus.Gatherers{
206222
prometheus.DefaultGatherer,

probe.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,11 @@ func handleProbe(scrapers []collector.Scraper, logger *slog.Logger) http.Handler
7272
filteredScrapers := filterScrapers(scrapers, collectParams)
7373

7474
registry := prometheus.NewRegistry()
75-
registry.MustRegister(collector.New(ctx, dsn, filteredScrapers, logger))
75+
registry.MustRegister(collector.New(ctx, dsn, filteredScrapers, logger,
76+
collector.EnableLockWaitTimeout(*enableExporterLockTimeout),
77+
collector.SetLockWaitTimeout(*exporterLockTimeout),
78+
collector.SetSlowLogFilter(*slowLogFilter),
79+
))
7680

7781
h := promhttp.HandlerFor(registry, promhttp.HandlerOpts{})
7882
h.ServeHTTP(w, r)

0 commit comments

Comments
 (0)