grafana_json_server

package module
v0.7.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Apr 20, 2024 License: MIT Imports: 12 Imported by: 2

README

grafana-json-server

GitHub tag (latest by date) Codecov Test Go Report Card GitHub GoDoc

Go implementation of simPod's Grafana JSON datasource.

Works with:

Documentation

Overview

Package grafana_json_server provides a Go implementation of the JSON API Grafana Datasource, which provides a way of sending JSON-formatted data into Grafana dataframes.

Creating a JSON API server for a metric

A metric is the source of data to be sent to Grafana. In its simplest form, running a JSON API server for a metric requires creating a server for that metric and starting an HTTP listener:

s := grafana_json_server.NewServer(
	grafana_json_server.WithHandler("metric1", query),
)
_ = http.ListenAndServe(":8080", s)

This starts a JSON API server for a single metric, called 'metric1' and a query, which implements the Query interface and will generate the data for the metric.

To provide more configuration options for the metric, use WithMetric instead:

metric := grafana_json_server.Metric{
	Label: "My first metric",
	Value: "metric1",
}

s := grafana_json_server.NewServer(
	grafana_json_server.WithMetric(metric, query, nil),
)
_ = http.ListenAndServe(":8080", s)

Writing query functions

The query function produces the data to be sent to Grafana. Queries can be of one of two types:

  • time series queries return values as a list of timestamp/value tuples.
  • table queries return data organized in columns and rows. Each column needs to have the same number of rows

Time series queries can therefore only return a single set of values. If your query involves returning multiple sets of data, use table queries instead.

Writing time series queries

A time series query returns a TimeSeriesResponse:

func Query(_ context.Context, target string, req grafanaJSONServer.QueryRequest) (grafanaJSONServer.QueryResponse, error) {
	return grafanaJSONServer.TimeSeriesResponse{
		Target: target,
		DataPoints: []grafanaJSONServer.DataPoint{
			{Timestamp: time.Date(2020, 1, 1, 0, 0, 0, 0, time.UTC), Value: 100},
			{Timestamp: time.Date(2020, 1, 1, 0, 1, 0, 0, time.UTC), Value: 101},
			{Timestamp: time.Date(2020, 1, 1, 0, 2, 0, 0, time.UTC), Value: 103},
		},
	}, nil
}

Writing table queries

A table query returns a TableResponse:

func Query(_ context.Context, _ string, _ grafanaJSONServer.QueryRequest) (grafanaJSONServer.QueryResponse, error) {
	return grafanaJSONServer.TableResponse{
		Columns: []grafanaJSONServer.Column{
			{Text: "Time", Data: grafanaJSONServer.TimeColumn{
				time.Date(2020, 1, 1, 0, 0, 0, 0, time.UTC),
				time.Date(2020, 1, 1, 0, 1, 0, 0, time.UTC)}},
			{Text: "Label", Data: grafanaJSONServer.StringColumn{"foo", "bar"}},
			{Text: "Series A", Data: grafanaJSONServer.NumberColumn{42, 43}},
			{Text: "Series B", Data: grafanaJSONServer.NumberColumn{64.5, 100.0}},
		},
	}, nil
}

Note that the table must be 'complete', i.e. each column should have the same number of entries.

Metric Payload Options

The JSON API Grafana Datasource allows each metric to have a number of user-selectable options. In the Grafana Edit panel, these are shown in the Payload section of the metric.

To add payload options to the metric, configure these when creating the metric:

metric := grafanaJSONServer.Metric{
	Label: "my advanced metric",
	Value: "metric1",
	Payloads: []grafanaJSONServer.MetricPayload{
		{
			Label: "Option",
			Name:  "option",
			Type:  "multi-select",
			Width: 40,
			Options: []grafanaJSONServer.MetricPayloadOption{
				{Label: "Option 1", Value: "option1"},
				{Label: "Option 2", Value: "option2"},
			},
		},
	},
}

The above example configures a new metric, with one payload option, called "option". The option allows multiple values to be selected. Two possible options are configured: option1 and option2.

When performing the query, the query function can check which options are selected by reading the request's payload:

var payload struct {
	Option []string
}
_ = req.GetPayload(target, &payload)

The payload Option field will contain all selected options, i.e. option1, option2. If no options are selected, Option will be an empty slice.

Note: the payload structure must match the metric's payload definition. Otherwise GetPayload returns an error. With the above metric definition, the following will fail:

var payload struct {
	Option string
}
_ = req.GetPayload(target, &payload)

Since Option is a multi-select option, a slice is expected.

Dynamic Metric Payload Options

In the previous section, we configured a metric with hard-coded options. If we want to have dynamic options, we use the MetricPayloadOption function when creating the metric. Possible use cases for this could be if runtime conditions determine which options you want to present, or if you want to determine valid options based on what other options are selected.

metric := grafanaJSONServer.Metric{
	Label: "my advanced metric",
	Value: "metric1",
	Payloads: []grafanaJSONServer.MetricPayload{
		{Label: "Option 1", Name: "option1", Type: "select", Width: 40, Options: []grafanaJSONServer.MetricPayloadOption{
			{Label: "Mode 1", Value: "mode1"},
			{Label: "Mode 2", Value: "mode2"},
		}},
		{Label: "Option 2", Name: "option2", Type: "select", Width: 40},
	},
}

s := grafanaJSONServer.NewServer(grafanaJSONServer.WithMetric(metric, metricOptionsDynamicQuery, metricPayloadOptionsFunc))

This creates a single metric, metric1. The metric has two payload options, option1 and option2. The former has two hardcoded options. The latter has no Options configured. This will cause the data source plugin to call metricPayloadOptionsFunc to determine which options to present.

The following is a basic example of such a MetricPayloadOption function:

func Query(req grafanaJSONServer.MetricPayloadOptionsRequest) ([]grafanaJSONServer.MetricPayloadOption, error) {
	var payload struct {
		Option1 string
		Option2 string
	}
	if err := req.GetPayload(&payload); err != nil {
		return nil, err
	}

	// payload will now contain all selected options across all metric's payloads
	// req.Name tells us for which metric the function was called

	return []grafanaJSONServer.MetricPayloadOption{
		{Label: "Value 1", Value: "value1"},
		{Label: "Value 2", Value: "value2"},
	}, nil
}

Variables

The JSON API datasource supports dashboard variable values to be retrieved from an JSON API server. To configure this, add a dashboard variable with the variable type set to "Query" and the data source to your JSON API server.

In the server, create the server with the WithVariable option:

s := grafanaJSONServer.NewServer(
	grafanaJSONServer.WithVariable("query0", variableFunc),
)
_ = http.ListenAndServe(":8080", s)

In the example, "query0" is the name specified in the Query section of the variable definition.

This causes Grafana to call the variableFunc whenever the variable is refreshed. This function returns all possible values for the variable:

func variableFunc(_ grafanaJSONServer.VariableRequest) ([]grafanaJSONServer.Variable, error) {
	return []grafanaJSONServer.Variable{
		{Text: "Value 1", Value: "value1"},
		{Text: "Value 2", Value: "value2"},
	}, nil
}

A Query function can read the value of each variables by examining the ScopedVars in the QueryRequest:

var req grafanaJSONServer.QueryRequest
var scopedVars struct {
	Var1   grafanaJSONServer.ScopedVar[string]
	Query0 grafanaJSONServer.ScopedVar[[]string]
}
_ = req.GetScopedVars(&scopedVars))

Note: in non-Raw JSON mode, GrafanaJSONDatasource stores the Query name in a json payload, with a "target" field holding the Query name.

In Raw JSON mode, a user can specify any JSON structure as payload. To route the request to the correct VariableFunc, add a "target" field with the relevant name. If no "target" field is found, the request is routed to a VariableFunc with a blank ("") target:

  • Query(non-raw): "foo" will route the request to "foo"
  • Query(raw): "{ "target": "bar" }" will route the request to "bar"
  • Query(raw): "{ "args": "some-args" }" will route the request to ""

See the Variable example for more.

Example (BasicTableQuery)
package main

import (
	"context"
	grafanaJSONServer "github.com/clambin/grafana-json-server"
	"net/http"
	"time"
)

func main() {
	s := grafanaJSONServer.NewServer(grafanaJSONServer.WithHandler("metric1", grafanaJSONServer.HandlerFunc(basicTableQueryFunc)))
	_ = http.ListenAndServe(":8080", s)
}

func basicTableQueryFunc(_ context.Context, _ string, _ grafanaJSONServer.QueryRequest) (grafanaJSONServer.QueryResponse, error) {
	return grafanaJSONServer.TableResponse{
		Columns: []grafanaJSONServer.Column{
			{Text: "Time", Data: grafanaJSONServer.TimeColumn{
				time.Date(2020, 1, 1, 0, 0, 0, 0, time.UTC),
				time.Date(2020, 1, 1, 0, 1, 0, 0, time.UTC)},
			},
			{Text: "Label", Data: grafanaJSONServer.StringColumn{"foo", "bar"}},
			{Text: "Series A", Data: grafanaJSONServer.NumberColumn{42, 43}},
			{Text: "Series B", Data: grafanaJSONServer.NumberColumn{64.5, 100.0}},
		},
	}, nil
}
Output:

Example (BasicTimeSeriesQuery)
package main

import (
	"context"
	grafanaJSONServer "github.com/clambin/grafana-json-server"
	"net/http"
	"time"
)

func main() {
	s := grafanaJSONServer.NewServer(grafanaJSONServer.WithHandler("metric1", grafanaJSONServer.HandlerFunc(basicTimeSeriesQueryFunc)))
	_ = http.ListenAndServe(":8080", s)
}

func basicTimeSeriesQueryFunc(_ context.Context, target string, _ grafanaJSONServer.QueryRequest) (grafanaJSONServer.QueryResponse, error) {
	return grafanaJSONServer.TimeSeriesResponse{
		Target: target,
		DataPoints: []grafanaJSONServer.DataPoint{
			{Timestamp: time.Date(2020, 1, 1, 0, 0, 0, 0, time.UTC), Value: 100},
			{Timestamp: time.Date(2020, 1, 1, 0, 1, 0, 0, time.UTC), Value: 101},
			{Timestamp: time.Date(2020, 1, 1, 0, 2, 0, 0, time.UTC), Value: 103},
		},
	}, nil
}
Output:

Example (MetricOptions)
package main

import (
	"context"
	grafanaJSONServer "github.com/clambin/grafana-json-server"
	"net/http"
	"time"
)

func main() {
	metric := grafanaJSONServer.Metric{
		Label: "my advanced metric",
		Value: "metric1",
		Payloads: []grafanaJSONServer.MetricPayload{
			{
				Label: "Option",
				Name:  "option",
				Type:  "multi-select",
				Width: 40,
				Options: []grafanaJSONServer.MetricPayloadOption{
					{Label: "Option 1", Value: "option1"},
					{Label: "Option 2", Value: "option2"},
				},
			},
		},
	}

	s := grafanaJSONServer.NewServer(grafanaJSONServer.WithMetric(metric, grafanaJSONServer.HandlerFunc(metricOptionsQueryFunc), nil))
	_ = http.ListenAndServe(":8080", s)
}

func metricOptionsQueryFunc(_ context.Context, target string, req grafanaJSONServer.QueryRequest) (grafanaJSONServer.QueryResponse, error) {
	var payload struct {
		Option []string
	}
	if err := req.GetPayload(target, &payload); err != nil {
		return nil, err
	}
	// payload Option will now contain all selected options, i.e. option1, option2.  If no options are selected, Option will be an empty slice.
	return grafanaJSONServer.TimeSeriesResponse{
		Target: target,
		DataPoints: []grafanaJSONServer.DataPoint{
			{Timestamp: time.Now(), Value: 1.0},
		},
	}, nil
}
Output:

Example (MetricOptionsDynamic)
package main

import (
	"context"
	grafanaJSONServer "github.com/clambin/grafana-json-server"
	"net/http"
	"time"
)

func main() {
	metric := grafanaJSONServer.Metric{
		Label: "my advanced metric",
		Value: "metric1",
		Payloads: []grafanaJSONServer.MetricPayload{
			{Label: "Option 1", Name: "option1", Type: "select", Width: 40, Options: []grafanaJSONServer.MetricPayloadOption{
				{Label: "Mode 1", Value: "mode1"},
				{Label: "Mode 2", Value: "mode2"},
			}},
			{Label: "Option 2", Name: "option2", Type: "select", Width: 40},
		},
	}

	s := grafanaJSONServer.NewServer(grafanaJSONServer.WithMetric(metric, grafanaJSONServer.HandlerFunc(metricOptionsDynamicQueryFunc), metricPayloadOptionsFunc))
	_ = http.ListenAndServe(":8080", s)
}

func metricPayloadOptionsFunc(req grafanaJSONServer.MetricPayloadOptionsRequest) ([]grafanaJSONServer.MetricPayloadOption, error) {
	var payload struct {
		Option1 string
		Option2 string
	}
	if err := req.GetPayload(&payload); err != nil {
		return nil, err
	}
	// payload will now contain all selected options across all metric's payloads

	// req.Name tells us for metric payload the function was called

	return []grafanaJSONServer.MetricPayloadOption{
		{Label: "Value 1", Value: "value1"},
		{Label: "Value 2", Value: "value2"},
	}, nil
}

func metricOptionsDynamicQueryFunc(_ context.Context, target string, req grafanaJSONServer.QueryRequest) (grafanaJSONServer.QueryResponse, error) {
	var payload struct {
		Option1 string
		Option2 string
	}
	if err := req.GetPayload(target, &payload); err != nil {
		return nil, err
	}
	// payload will now contain all selected options across all metric's payloads

	return grafanaJSONServer.TimeSeriesResponse{
		Target: target,
		DataPoints: []grafanaJSONServer.DataPoint{
			{Timestamp: time.Now(), Value: 1.0},
		},
	}, nil
}
Output:

Example (Variable)
package main

import (
	grafanaJSONServer "github.com/clambin/grafana-json-server"
	"net/http"
)

func main() {
	s := grafanaJSONServer.NewServer(
		grafanaJSONServer.WithVariable("query0", variableFunc), // this will be called if the payload contains "target": "query0"
		grafanaJSONServer.WithVariable("", variableFunc),       // this will be called if the payload contains no "target"
	)

	_ = http.ListenAndServe(":8080", s)
}

func variableFunc(_ grafanaJSONServer.VariableRequest) ([]grafanaJSONServer.Variable, error) {
	return []grafanaJSONServer.Variable{
		{Text: "Value 1", Value: "value1"},
		{Text: "Value 2", Value: "value2"},
	}, nil
}
Output:

Index

Examples

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Column

type Column struct {
	Text string
	Data any
}

Column is a column returned by a table query. Text holds the column's header, Data holds the slice of values and should be a TimeColumn, a StringColumn or a NumberColumn.

type DataPoint

type DataPoint struct {
	Timestamp time.Time
	Value     float64
}

DataPoint contains one entry of a TimeSeriesResponse.

func (DataPoint) MarshalJSON

func (d DataPoint) MarshalJSON() ([]byte, error)

MarshalJSON converts a DataPoint to JSON.

type Handler added in v0.3.0

type Handler interface {
	Query(ctx context.Context, target string, request QueryRequest) (QueryResponse, error)
}

A Handler responds to a query request from the JSON API datasource.

type HandlerFunc added in v0.3.0

type HandlerFunc func(ctx context.Context, target string, request QueryRequest) (QueryResponse, error)

The HandlerFunc type is an adapter to allow the use of an ordinary function as Handler handlers. If f is a function with the appropriate signature, then HandlerFunc(f) is a Handler that calls f.

func (HandlerFunc) Query added in v0.3.0

func (qf HandlerFunc) Query(ctx context.Context, target string, request QueryRequest) (QueryResponse, error)

Query calls f(ctx, target, request)

type Metric

type Metric struct {
	// Label is the name of the metric, as shown on the screen.
	Label string `json:"label,omitempty"`
	// Value is the internal name of the metric, used in API calls.
	Value string `json:"value"`
	// Payloads configures one or more payload options for the metric.
	Payloads []MetricPayload `json:"payloads"`
}

A Metric represents one data source offered by a JSON API server.

type MetricPayload

type MetricPayload struct {
	// Label is the name of the option, as shown on the screen.
	Label string `json:"label,omitempty"`
	// Name is the internal name of the metric, used in API calls.
	Name string `json:"name"`
	// Type specifies what kind of option should be provided:
	// 		If the value is select, the UI of the payload is a radio box.
	// 		If the value is multi-select, the UI of the payload is a multi selection box.
	// 		If the value is input, the UI of the payload is an input box.
	// 		If the value is textarea, the UI of the payload is a multiline input box.
	// The default is input.
	Type string `json:"type"`
	// Placeholder specifies the input box / selection box prompt information.
	Placeholder string `json:"placeholder,omitempty"`
	// ReloadMetric specifies whether to overload the metrics API after modifying the value of the payload.
	ReloadMetric bool `json:"reloadMetric,omitempty"`
	// Width specifies the width of the input / selection box width to a multiple of 8px.
	Width int `json:"width,omitempty"`
	// Options lists of the configuration of the options list, if the payload type is select / multi-select.
	// If Options is nil, and the type is select / multi-select, Grafana JSON API datasource will call
	// the MetricPayloadOptionFunc provided to WithMetric to populate the options list.
	Options []MetricPayloadOption `json:"options,omitempty"`
}

A MetricPayload configures a payload options for a metric.

If the metric is of Type "select", or "multi-select", Options should contain all possible values for the metric. Alternatively, it may be nil, in which case you should pass a MetricPayloadOptionFunc when calling WithMetric.

type MetricPayloadOption

type MetricPayloadOption struct {
	Label string `json:"label"`
	Value string `json:"value"`
}

MetricPayloadOption contains one option of a MetricPayload. Label is the value to display on the screen, while Value is the internal name used in API calls.

type MetricPayloadOptionFunc

type MetricPayloadOptionFunc func(MetricPayloadOptionsRequest) ([]MetricPayloadOption, error)

MetricPayloadOptionFunc is the function signature of the metric payload option function, provided to WithMetric. It is called when a metric has a payload with a nil Options field and returns the possible options for the requested Metric payload.

type MetricPayloadOptionsRequest

type MetricPayloadOptionsRequest struct {
	Metric  string          `json:"metric"`
	Name    string          `json:"name"`
	Payload json.RawMessage `json:"payload"`
}

MetricPayloadOptionsRequest is the request provided to MetricPayloadOptionFunc.

func (MetricPayloadOptionsRequest) GetPayload

func (r MetricPayloadOptionsRequest) GetPayload(payload any) error

GetPayload unmarshals the json object from the MetricPayloadOptionsRequest in the provided payload.

type NumberColumn

type NumberColumn []float64

NumberColumn holds a slice of float64 values (one per row).

type Option

type Option func(*Server)

Option configures a Server.

func WithHTTPHandler added in v0.3.0

func WithHTTPHandler(method, path string, handler http.Handler) Option

WithHTTPHandler adds a http.Handler to its http router.

func WithHandler added in v0.3.0

func WithHandler(target string, handler Handler) Option

WithHandler is a convenience function to create a simple metric (i.e. one without any payload options).

func WithLogger

func WithLogger(l *slog.Logger) Option

WithLogger sets the slog Logger. The default is slog.Default().

func WithMetric

func WithMetric(m Metric, handler Handler, payloadOption MetricPayloadOptionFunc) Option

WithMetric adds a new metric to the server. See Metric for more configuration options for a metric.

func WithPrometheusQueryMetrics added in v0.2.0

func WithPrometheusQueryMetrics(metrics PrometheusQueryMetrics) Option

WithPrometheusQueryMetrics adds Prometheus metrics to the server's Queries. The caller must register the metrics with the Prometheus registry.

See NewDefaultPrometheusQueryMetrics for the default implementation of Prometheus metrics.

func WithVariable

func WithVariable(name string, v VariableFunc) Option

WithVariable adds a new dashboard variable to the server.

type PrometheusQueryMetrics added in v0.7.0

type PrometheusQueryMetrics interface {
	Measure(target string, duration time.Duration, err error)
	prometheus.Collector
}

func NewDefaultPrometheusQueryMetrics added in v0.7.0

func NewDefaultPrometheusQueryMetrics(namespace, subsystem, application string) PrometheusQueryMetrics

NewDefaultPrometheusQueryMetrics returns the default PrometheusQueryMetrics implementation. It created two Prometheus metrics:

  • json_query_duration_seconds records the duration of each query
  • json_query_error_count counts the total number of errors executing a query

If namespace and/or subsystem are not blank, they are prepended to the metric name. Application is added as a label "application". The query target is added as a label "target".

type QueryRequest

type QueryRequest struct {
	App           string               `json:"app"`
	Timezone      string               `json:"timezone"`
	StartTime     int64                `json:"startTime"`
	Interval      string               `json:"interval"`
	IntervalMs    int                  `json:"intervalMs"`
	PanelID       any                  `json:"panelId"`
	Targets       []QueryRequestTarget `json:"targets"`
	Range         Range                `json:"range"`
	RequestID     string               `json:"requestId"`
	RangeRaw      RawRange             `json:"rangeRaw"`
	ScopedVars    json.RawMessage      `json:"scopedVars"`
	MaxDataPoints int                  `json:"maxDataPoints"`
	LiveStreaming bool                 `json:"liveStreaming"`
	AdhocFilters  []interface{}        `json:"adhocFilters"`
}

The QueryRequest structure is the query request from Grafana to the data source.

func (QueryRequest) GetPayload

func (r QueryRequest) GetPayload(target string, payload any) error

GetPayload unmarshals the target's raw payload into a provided payload.

func (QueryRequest) GetScopedVars

func (r QueryRequest) GetScopedVars(vars any) error

GetScopedVars unmarshals all variables in a QueryRequest into a Go structure. The vars variable should be struct of ScopedVar structs, matching the type of the variable. E.g. a multi-select variable should be represented by a ScopedVar[[]string].

type QueryRequestTarget

type QueryRequestTarget struct {
	RefID      string `json:"refId"`
	Datasource struct {
		Type string `json:"type"`
		UID  string `json:"uid"`
	} `json:"datasource"`
	EditorMode string          `json:"editorMode"`
	Payload    json.RawMessage `json:"payload"`
	Target     string          `json:"target"`
	Key        string          `json:"key"`
	Type       string          `json:"type"` // TODO: is this really present?
}

QueryRequestTarget is one target in the QueryRequest structure. The main interesting fields are the Target, which is the Metric's name, and the Payload, which contains all selection options in any payload options. Use GetPayload to unmarshal the Payload into a Go structure.

type QueryResponse

type QueryResponse interface {
	json.Marshaler
}

QueryResponse is the output of the query function. Both TimeSeriesResponse and TableResponse implement this interface.

type Range

type Range struct {
	From time.Time `json:"from"`
	To   time.Time `json:"to"`
	Raw  RawRange  `json:"raw"`
}

Range is the time range of the QueryRequest.

type RawRange added in v0.6.0

type RawRange struct {
	From string `json:"from"`
	To   string `json:"to"`
}

RawRange is the raw time range of the QueryRequest.

type ScopedVar

type ScopedVar[T any] struct {
	Selected bool
	Text     string
	Value    T
}

A ScopedVar holds the value of a dashboard variable and is sent to the server as part of the QueryRequest.

type Server

type Server struct {
	chi.Router
	// contains filtered or unexported fields
}

The Server structure implements a JSON API server compatible with the JSON API Grafana datasource.

func NewServer

func NewServer(options ...Option) *Server

NewServer returns a new JSON API server, configured as per the provided Option items.

type StringColumn

type StringColumn []string

StringColumn holds a slice of string values (one per row).

type TableResponse

type TableResponse struct {
	Columns []Column
}

TableResponse is returned by a table query, i.e. a slice of Column structures.

func (TableResponse) MarshalJSON

func (t TableResponse) MarshalJSON() (output []byte, err error)

MarshalJSON converts a TableResponse to JSON.

type TimeColumn

type TimeColumn []time.Time

TimeColumn holds a slice of time.Time values (one per row).

type TimeSeriesResponse

type TimeSeriesResponse struct {
	Target     string      `json:"target"`
	DataPoints []DataPoint `json:"datapoints"`
}

TimeSeriesResponse is the response to a query as a time series. Target should match the Target of the received request.

func (TimeSeriesResponse) MarshalJSON

func (r TimeSeriesResponse) MarshalJSON() ([]byte, error)

MarshalJSON converts a TimeSeriesResponse to JSON.

type Variable

type Variable struct {
	Text  string `json:"__text"`
	Value string `json:"__value"`
}

Variable is one possible value for a dashboard value. Text is the name to be displayed on the screen. Value will be used in API calls.

type VariableFunc

type VariableFunc func(VariableRequest) ([]Variable, error)

VariableFunc is the function signature of function provided to WithVariable. It returns a list of possible values for a dashboard variable.

type VariableRequest

type VariableRequest struct {
	Payload json.RawMessage `json:"payload"`
	Range   Range           `json:"range"`
	Target  string
}

VariableRequest is the request sent to VariableFunc.

Payload and Target are determined by the Grafana definition of the variable:

  • if Raw JSON is off, Payload contains a JSON object with a single field "target", as set in the Variable's Query field.
  • if Raw JSON is on, Payload contains the JSON object set in the Variable's Query field.

In both cases, if the Payload contains a field "target", its value is stored in Target. If no "target" exists, Target is blank. No error is raised.

func (*VariableRequest) UnmarshalJSON added in v0.6.0

func (v *VariableRequest) UnmarshalJSON(bytes []byte) error

Directories

Path Synopsis
examples

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL