Skip to content

Commit

Permalink
feat: add config option for logs
Browse files Browse the repository at this point in the history
Adds basic configuration option for logs.
  • Loading branch information
andrzej-stencel committed Apr 6, 2023
1 parent ca50a98 commit 03de16d
Show file tree
Hide file tree
Showing 5 changed files with 79 additions and 7 deletions.
35 changes: 33 additions & 2 deletions receiver/sqlqueryreceiver/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,12 +21,41 @@ The configuration supports the following top-level fields:
a driver-specific string usually consisting of at least a database name and connection information. This is sometimes
referred to as the "connection string" in driver documentation.
e.g. _host=localhost port=5432 user=me password=s3cr3t sslmode=disable_
- `queries`(required): A list of queries, where a query is a sql statement and one or more metrics (details below).
- `queries`(required): A list of queries, where a query is a sql statement and one or more `logs` and/or `metrics` sections (details below).
- `collection_interval`(optional): The time interval between query executions. Defaults to _10s_.

### Queries

A _query_ consists of a sql statement and one or more _metrics_, where each metric consists of a
A _query_ consists of a sql statement and one or more `logs` and/or `metrics` section.
At least one `logs` or one `metrics` section is required.
Note that technically you can put both `logs` and `metrics` sections in a single query section,
but it's probably not a real world use case, as the requirements for logs and metrics queries
are quite different.

Example:

```yaml
receivers:
sqlquery:
driver: postgres
datasource: "host=localhost port=5432 user=postgres password=s3cr3t sslmode=disable"
queries:
- sql: "select * from my_logs"
logs:
- {}
- sql: "select count(*) as count, genre from movie group by genre"
metrics:
- metric_name: movie.genres
value_column: "count"
```
#### Logs Queries
The `logs` section currently has no options. This section is in development.

#### Metrics queries

Each `metrics` section consists of a
`metric_name`, a `value_column`, and additional optional fields.
Each _metric_ in the configuration will produce one OTel metric per row returned from its sql query.

Expand All @@ -53,6 +82,8 @@ receivers:
driver: postgres
datasource: "host=localhost port=5432 user=postgres password=s3cr3t sslmode=disable"
queries:
- sql: "select * from my_logs"
logs: {}
- sql: "select count(*) as count, genre from movie group by genre"
metrics:
- metric_name: movie.genres
Expand Down
18 changes: 16 additions & 2 deletions receiver/sqlqueryreceiver/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -52,15 +52,21 @@ func (c Config) Validate() error {
type Query struct {
SQL string `mapstructure:"sql"`
Metrics []MetricCfg `mapstructure:"metrics"`
Logs []LogsCfg `mapstructure:"logs"`
}

func (q Query) Validate() error {
var errs error
if q.SQL == "" {
errs = multierr.Append(errs, errors.New("'query.sql' cannot be empty"))
}
if len(q.Metrics) == 0 {
errs = multierr.Append(errs, errors.New("'query.metrics' cannot be empty"))
if len(q.Logs) == 0 && len(q.Metrics) == 0 {
errs = multierr.Append(errs, errors.New("at least one of 'query.logs' and 'query.metrics' must not be empty"))
}
for _, logs := range q.Logs {
if err := logs.Validate(); err != nil {
errs = multierr.Append(errs, err)
}
}
for _, metric := range q.Metrics {
if err := metric.Validate(); err != nil {
Expand All @@ -70,6 +76,14 @@ func (q Query) Validate() error {
return errs
}

type LogsCfg struct {
}

func (config LogsCfg) Validate() error {
var errs error
return errs
}

type MetricCfg struct {
MetricName string `mapstructure:"metric_name"`
ValueColumn string `mapstructure:"value_column"`
Expand Down
25 changes: 22 additions & 3 deletions receiver/sqlqueryreceiver/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -104,15 +104,34 @@ func TestLoadConfig(t *testing.T) {
errorMessage: "'driver' cannot be empty",
},
{
fname: "config-invalid-missing-metrics.yaml",
fname: "config-invalid-missing-logs-metrics.yaml",
id: component.NewIDWithName(typeStr, ""),
errorMessage: "'query.metrics' cannot be empty",
errorMessage: "at least one of 'query.logs' and 'query.metrics' must not be empty",
},
{
fname: "config-invalid-missing-datasource.yaml",
id: component.NewIDWithName(typeStr, ""),
errorMessage: "'datasource' cannot be empty",
},
{
fname: "config-logs.yaml",
id: component.NewIDWithName(typeStr, ""),
expected: &Config{
ScraperControllerSettings: scraperhelper.ScraperControllerSettings{
CollectionInterval: 10 * time.Second,
},
Driver: "mydriver",
DataSource: "host=localhost port=5432 user=me password=s3cr3t sslmode=disable",
Queries: []Query{
{
SQL: "select * from test_logs",
Logs: []LogsCfg{
{},
},
},
},
},
},
{
fname: "config-unnecessary-aggregation.yaml",
id: component.NewIDWithName(typeStr, ""),
Expand All @@ -121,7 +140,7 @@ func TestLoadConfig(t *testing.T) {
}

for _, tt := range tests {
t.Run(tt.id.String(), func(t *testing.T) {
t.Run(tt.fname, func(t *testing.T) {
cm, err := confmaptest.LoadConf(filepath.Join("testdata", tt.fname))
require.NoError(t, err)

Expand Down
8 changes: 8 additions & 0 deletions receiver/sqlqueryreceiver/testdata/config-logs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
sqlquery:
collection_interval: 10s
driver: mydriver
datasource: "host=localhost port=5432 user=me password=s3cr3t sslmode=disable"
queries:
- sql: "select * from test_logs"
logs:
- {}

0 comments on commit 03de16d

Please sign in to comment.