-
Notifications
You must be signed in to change notification settings - Fork 58
/
data.go
136 lines (111 loc) · 4.82 KB
/
data.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
package backend
import (
"context"
"encoding/json"
"time"
"github.com/grafana/grafana-plugin-sdk-go/data"
jsoniter "github.com/json-iterator/go"
)
// QueryDataHandler handles data queries.
type QueryDataHandler interface {
// QueryData handles multiple queries and returns multiple responses.
// req contains the queries []DataQuery (where each query contains RefID as a unique identifier).
// The QueryDataResponse contains a map of RefID to the response for each query, and each response
// contains Frames ([]*Frame).
//
// The Frames' RefID property, when it is an empty string, will be automatically set to
// the RefID in QueryDataResponse.Responses map. This is done before the QueryDataResponse is
// sent to Grafana. Therefore one does not need to be set that property on frames when using this method.
QueryData(ctx context.Context, req *QueryDataRequest) (*QueryDataResponse, error)
}
// QueryDataHandlerFunc is an adapter to allow the use of
// ordinary functions as backend.QueryDataHandler. If f is a function
// with the appropriate signature, QueryDataHandlerFunc(f) is a
// Handler that calls f.
type QueryDataHandlerFunc func(ctx context.Context, req *QueryDataRequest) (*QueryDataResponse, error)
// QueryData calls fn(ctx, req).
func (fn QueryDataHandlerFunc) QueryData(ctx context.Context, req *QueryDataRequest) (*QueryDataResponse, error) {
return fn(ctx, req)
}
// QueryDataRequest contains a single request which contains multiple queries.
// It is the input type for a QueryData call.
type QueryDataRequest struct {
PluginContext PluginContext
Headers map[string]string
Queries []DataQuery
}
// DataQuery represents a single query as sent from the frontend.
// A slice of DataQuery makes up the Queries property of a QueryDataRequest.
type DataQuery struct {
// RefID is the unique identifier of the query, set by the frontend call.
RefID string
// QueryType is an optional identifier for the type of query.
// It can be used to distinguish different types of queries.
QueryType string
// MaxDataPoints is the maximum number of datapoints that should be returned from a time series query.
MaxDataPoints int64
// Interval is the suggested duration between time points in a time series query.
Interval time.Duration
// TimeRange is the Start and End of the query as sent by the frontend.
TimeRange TimeRange
// JSON is the raw JSON query and includes the above properties as well as custom properties.
JSON json.RawMessage
}
// QueryDataResponse contains the results from a QueryDataRequest.
// It is the return type of a QueryData call.
type QueryDataResponse struct {
// Responses is a map of RefIDs (Unique Query ID) to *DataResponse.
Responses Responses
}
// MarshalJSON writes the results as json
func (r QueryDataResponse) MarshalJSON() ([]byte, error) {
cfg := jsoniter.ConfigCompatibleWithStandardLibrary
stream := cfg.BorrowStream(nil)
defer cfg.ReturnStream(stream)
writeQueryDataResponseJSON(&r, stream)
return append([]byte(nil), stream.Buffer()...), stream.Error
}
// UnmarshalJSON will read JSON into a QueryDataResponse
func (r *QueryDataResponse) UnmarshalJSON(b []byte) error {
iter := jsoniter.ParseBytes(jsoniter.ConfigDefault, b)
readQueryDataResultsJSON(r, iter)
return iter.Error
}
// NewQueryDataResponse returns a QueryDataResponse with the Responses property initialized.
func NewQueryDataResponse() *QueryDataResponse {
return &QueryDataResponse{
Responses: make(Responses),
}
}
// Responses is a map of RefIDs (Unique Query ID) to DataResponses.
// The QueryData method the QueryDataHandler method will set the RefId
// property on the DataRespones' frames based on these RefIDs.
type Responses map[string]DataResponse
// DataResponse contains the results from a DataQuery.
// A map of RefIDs (unique query identifers) to this type makes up the Responses property of a QueryDataResponse.
// The Error property is used to allow for partial success responses from the containing QueryDataResponse.
type DataResponse struct {
// The data returned from the Query. Each Frame repeats the RefID.
Frames data.Frames
// Error is a property to be set if the the corresponding DataQuery has an error.
Error error
}
// MarshalJSON writes the results as json
func (r DataResponse) MarshalJSON() ([]byte, error) {
cfg := jsoniter.ConfigCompatibleWithStandardLibrary
stream := cfg.BorrowStream(nil)
defer cfg.ReturnStream(stream)
writeDataResponseJSON(&r, stream)
return append([]byte(nil), stream.Buffer()...), stream.Error
}
// TimeRange represents a time range for a query and is a property of DataQuery.
type TimeRange struct {
// From is the start time of the query.
From time.Time
// To is the end time of the query.
To time.Time
}
// Duration returns a time.Duration representing the amount of time between From and To.
func (tr TimeRange) Duration() time.Duration {
return tr.To.Sub(tr.From)
}