Dashboard: replace datasource name with a reference object (#33817)
Co-authored-by: Torkel Ödegaard <torkel@grafana.com> Co-authored-by: Elfo404 <me@giordanoricci.com>
This commit is contained in:
co-authored by
Torkel Ödegaard
Elfo404
parent
61fbdb60ff
commit
7319efe077
+8
-7
@@ -7,7 +7,6 @@ import (
|
||||
|
||||
"github.com/grafana/grafana/pkg/expr/mathexp"
|
||||
|
||||
"gonum.org/v1/gonum/graph"
|
||||
"gonum.org/v1/gonum/graph/simple"
|
||||
"gonum.org/v1/gonum/graph/topo"
|
||||
)
|
||||
@@ -129,9 +128,11 @@ func (s *Service) buildGraph(req *Request) (*simple.DirectedGraph, error) {
|
||||
for _, query := range req.Queries {
|
||||
rawQueryProp := make(map[string]interface{})
|
||||
queryBytes, err := query.JSON.MarshalJSON()
|
||||
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
err = json.Unmarshal(queryBytes, &rawQueryProp)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
@@ -145,23 +146,23 @@ func (s *Service) buildGraph(req *Request) (*simple.DirectedGraph, error) {
|
||||
DatasourceUID: query.DatasourceUID,
|
||||
}
|
||||
|
||||
dsName, err := rn.GetDatasourceName()
|
||||
isExpr, err := rn.IsExpressionQuery()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
dsUID := rn.DatasourceUID
|
||||
var node Node
|
||||
|
||||
var node graph.Node
|
||||
switch {
|
||||
case dsName == DatasourceName || dsUID == DatasourceUID:
|
||||
if isExpr {
|
||||
node, err = buildCMDNode(dp, rn)
|
||||
default: // If it's not an expression query, it's a data source query.
|
||||
} else {
|
||||
node, err = s.buildDSNode(dp, rn, req)
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
dp.AddNode(node)
|
||||
}
|
||||
return dp, nil
|
||||
|
||||
@@ -195,6 +195,33 @@ func TestServicebuildPipeLine(t *testing.T) {
|
||||
},
|
||||
expectErrContains: "classic conditions may not be the input for other expressions",
|
||||
},
|
||||
{
|
||||
name: "Queries with new datasource ref object",
|
||||
req: &Request{
|
||||
Queries: []Query{
|
||||
{
|
||||
RefID: "A",
|
||||
JSON: json.RawMessage(`{
|
||||
"datasource": {
|
||||
"uid": "MyDS"
|
||||
}
|
||||
}`),
|
||||
},
|
||||
{
|
||||
RefID: "B",
|
||||
JSON: json.RawMessage(`{
|
||||
"datasource": {
|
||||
"uid": "MyDS"
|
||||
},
|
||||
"expression": "A",
|
||||
"reducer": "mean",
|
||||
"type": "reduce"
|
||||
}`),
|
||||
},
|
||||
},
|
||||
},
|
||||
expectedOrder: []string{"B", "A"},
|
||||
},
|
||||
}
|
||||
s := Service{}
|
||||
for _, tt := range tests {
|
||||
|
||||
+53
-10
@@ -33,16 +33,59 @@ type rawNode struct {
|
||||
DatasourceUID string
|
||||
}
|
||||
|
||||
func (rn *rawNode) GetDatasourceName() (string, error) {
|
||||
func (rn *rawNode) GetDatasourceUID() (string, error) {
|
||||
if rn.DatasourceUID != "" {
|
||||
return rn.DatasourceUID, nil
|
||||
}
|
||||
|
||||
rawDs, ok := rn.Query["datasource"]
|
||||
if !ok {
|
||||
return "", nil
|
||||
return "", fmt.Errorf("no datasource property found in query model")
|
||||
}
|
||||
dsName, ok := rawDs.(string)
|
||||
|
||||
// For old queries with string datasource prop representing data source name
|
||||
if dsName, ok := rawDs.(string); ok {
|
||||
return dsName, nil
|
||||
}
|
||||
|
||||
dsRef, ok := rawDs.(map[string]interface{})
|
||||
if !ok {
|
||||
return "", fmt.Errorf("expted datasource identifier to be a string, got %T", rawDs)
|
||||
return "", fmt.Errorf("data source property is not an object nor string, got %T", rawDs)
|
||||
}
|
||||
return dsName, nil
|
||||
|
||||
if dsUid, ok := dsRef["uid"].(string); ok {
|
||||
return dsUid, nil
|
||||
}
|
||||
|
||||
return "", fmt.Errorf("no datasource uid found for query, got %T", rn.Query)
|
||||
}
|
||||
|
||||
func (rn *rawNode) IsExpressionQuery() (bool, error) {
|
||||
if rn.DatasourceUID != "" {
|
||||
return rn.DatasourceUID == DatasourceUID, nil
|
||||
}
|
||||
|
||||
rawDs, ok := rn.Query["datasource"]
|
||||
if !ok {
|
||||
return false, fmt.Errorf("no datasource property found in query model")
|
||||
}
|
||||
|
||||
// For old queries with string datasource prop representing data source name
|
||||
dsName, ok := rawDs.(string)
|
||||
if ok && dsName == DatasourceName {
|
||||
return true, nil
|
||||
}
|
||||
|
||||
dsRef, ok := rawDs.(map[string]interface{})
|
||||
if !ok {
|
||||
return false, nil
|
||||
}
|
||||
|
||||
if dsRef["uid"].(string) == DatasourceUID {
|
||||
return true, nil
|
||||
}
|
||||
|
||||
return false, nil
|
||||
}
|
||||
|
||||
func (rn *rawNode) GetCommandType() (c CommandType, err error) {
|
||||
@@ -171,18 +214,18 @@ func (s *Service) buildDSNode(dp *simple.DirectedGraph, rn *rawNode, req *Reques
|
||||
}
|
||||
|
||||
rawDsID, ok := rn.Query["datasourceId"]
|
||||
switch ok {
|
||||
case true:
|
||||
if ok {
|
||||
floatDsID, ok := rawDsID.(float64)
|
||||
if !ok {
|
||||
return nil, fmt.Errorf("expected datasourceId to be a float64, got type %T for refId %v", rawDsID, rn.RefID)
|
||||
}
|
||||
dsNode.datasourceID = int64(floatDsID)
|
||||
default:
|
||||
if rn.DatasourceUID == "" {
|
||||
} else {
|
||||
dsUid, err := rn.GetDatasourceUID()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("neither datasourceId or datasourceUid in expression data source request for refId %v", rn.RefID)
|
||||
}
|
||||
dsNode.datasourceUID = rn.DatasourceUID
|
||||
dsNode.datasourceUID = dsUid
|
||||
}
|
||||
|
||||
var floatIntervalMS float64
|
||||
|
||||
Reference in New Issue
Block a user