mirror of https://github.com/grafana/grafana.git
				
				
				
			
		
			
				
	
	
		
			161 lines
		
	
	
		
			5.1 KiB
		
	
	
	
		
			Go
		
	
	
	
			
		
		
	
	
			161 lines
		
	
	
		
			5.1 KiB
		
	
	
	
		
			Go
		
	
	
	
| package expr
 | |
| 
 | |
| import (
 | |
| 	"fmt"
 | |
| 	"testing"
 | |
| 
 | |
| 	"github.com/grafana/grafana-plugin-sdk-go/data"
 | |
| 	"github.com/stretchr/testify/require"
 | |
| )
 | |
| 
 | |
| func TestExtractNumberSetFromSQLForAlerting(t *testing.T) {
 | |
| 	t.Run("SingleRowNoLabels", func(t *testing.T) {
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLValueFieldName, nil, []*float64{fp(3.14)}),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.NoError(t, err)
 | |
| 		require.Len(t, numbers, 1)
 | |
| 
 | |
| 		got := numbers[0]
 | |
| 		require.Equal(t, fp(3.14), got.GetFloat64Value())
 | |
| 		require.Equal(t, data.Labels{}, got.GetLabels())
 | |
| 	})
 | |
| 
 | |
| 	t.Run("TwoRowsWithLabelsAndDisplay", func(t *testing.T) {
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLMetricFieldName, nil, []string{"cpu", "cpu"}),
 | |
| 			data.NewField(SQLValueFieldName, nil, []*float64{fp(1.0), fp(2.0)}),
 | |
| 			data.NewField(SQLDisplayFieldName, nil, []*string{sp("CPU A"), sp("CPU B")}),
 | |
| 			data.NewField("host", nil, []*string{sp("a"), sp("b")}),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.NoError(t, err)
 | |
| 		require.Len(t, numbers, 2)
 | |
| 
 | |
| 		require.Equal(t, fp(1.0), numbers[0].GetFloat64Value())
 | |
| 		require.Equal(t, data.Labels{
 | |
| 			SQLMetricFieldName:  "cpu",
 | |
| 			SQLDisplayFieldName: "CPU A",
 | |
| 			"host":              "a",
 | |
| 		}, numbers[0].GetLabels())
 | |
| 
 | |
| 		require.Equal(t, fp(2.0), numbers[1].GetFloat64Value())
 | |
| 		require.Equal(t, data.Labels{
 | |
| 			SQLMetricFieldName:  "cpu",
 | |
| 			SQLDisplayFieldName: "CPU B",
 | |
| 			"host":              "b",
 | |
| 		}, numbers[1].GetLabels())
 | |
| 	})
 | |
| 
 | |
| 	t.Run("TwoFieldsWithSparseLabels", func(t *testing.T) {
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLMetricFieldName, nil, []string{"cpu", "cpu"}),
 | |
| 			data.NewField(SQLValueFieldName, nil, []*float64{fp(1.0), fp(2.0)}),
 | |
| 			data.NewField("env", nil, []*string{nil, sp("prod")}),
 | |
| 			data.NewField("host", nil, []*string{sp("a"), sp("b")}),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.NoError(t, err)
 | |
| 		require.Len(t, numbers, 2)
 | |
| 
 | |
| 		require.Equal(t, fp(1.0), numbers[0].GetFloat64Value())
 | |
| 		require.Equal(t, data.Labels{
 | |
| 			SQLMetricFieldName: "cpu",
 | |
| 			"host":             "a",
 | |
| 		}, numbers[0].GetLabels())
 | |
| 
 | |
| 		require.Equal(t, fp(2.0), numbers[1].GetFloat64Value())
 | |
| 		require.Equal(t, data.Labels{
 | |
| 			SQLMetricFieldName: "cpu",
 | |
| 			"host":             "b",
 | |
| 			"env":              "prod",
 | |
| 		}, numbers[1].GetLabels())
 | |
| 	})
 | |
| }
 | |
| 
 | |
| func TestExtractNumberSetFromSQLForAlerting_Duplicates(t *testing.T) {
 | |
| 	t.Run("AllDuplicates_ReturnsError", func(t *testing.T) {
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLMetricFieldName, nil, []string{"cpu", "cpu"}),
 | |
| 			data.NewField(SQLValueFieldName, nil, []*float64{fp(1.0), fp(2.0)}),
 | |
| 			data.NewField("host", nil, []*string{sp("a"), sp("a")}),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.Error(t, err)
 | |
| 		require.Nil(t, numbers)
 | |
| 		require.Contains(t, err.Error(), "duplicate values across the string columns")
 | |
| 		require.Contains(t, err.Error(), "host=a")
 | |
| 		require.Contains(t, err.Error(), "GROUP BY or aggregation")
 | |
| 	})
 | |
| 
 | |
| 	t.Run("SomeDuplicates_ReturnsError", func(t *testing.T) {
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLMetricFieldName, nil, []string{"cpu", "cpu", "cpu"}),
 | |
| 			data.NewField(SQLValueFieldName, nil, []*float64{fp(1.0), fp(2.0), fp(3.0)}),
 | |
| 			data.NewField("host", nil, []*string{sp("a"), sp("a"), sp("b")}),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.Error(t, err)
 | |
| 		require.Nil(t, numbers)
 | |
| 		require.Contains(t, err.Error(), "duplicate values across the string columns")
 | |
| 		require.Contains(t, err.Error(), "host=a")
 | |
| 		require.Contains(t, err.Error(), "GROUP BY or aggregation")
 | |
| 	})
 | |
| 
 | |
| 	t.Run("NoDuplicates_Succeeds", func(t *testing.T) {
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLMetricFieldName, nil, []string{"cpu", "cpu"}),
 | |
| 			data.NewField(SQLValueFieldName, nil, []*float64{fp(1.0), fp(2.0)}),
 | |
| 			data.NewField("host", nil, []*string{sp("a"), sp("b")}),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.NoError(t, err)
 | |
| 		require.Len(t, numbers, 2)
 | |
| 
 | |
| 		require.Equal(t, data.Labels{
 | |
| 			SQLMetricFieldName: "cpu",
 | |
| 			"host":             "a",
 | |
| 		}, numbers[0].GetLabels())
 | |
| 		require.Equal(t, data.Labels{
 | |
| 			SQLMetricFieldName: "cpu",
 | |
| 			"host":             "b",
 | |
| 		}, numbers[1].GetLabels())
 | |
| 	})
 | |
| 
 | |
| 	t.Run("MoreThan10DuplicateSets_TruncatesErrorList", func(t *testing.T) {
 | |
| 		const totalRows = 30
 | |
| 		labels := make([]string, totalRows)
 | |
| 		values := make([]*float64, totalRows)
 | |
| 		hosts := make([]*string, totalRows)
 | |
| 
 | |
| 		for i := 0; i < totalRows; i++ {
 | |
| 			labels[i] = "cpu"
 | |
| 			values[i] = fp(float64(i + 1))
 | |
| 			h := fmt.Sprintf("host%d", i%15) // 15 distinct combos, each duplicated
 | |
| 			hosts[i] = &h
 | |
| 		}
 | |
| 
 | |
| 		input := data.NewFrame("",
 | |
| 			data.NewField(SQLMetricFieldName, nil, labels),
 | |
| 			data.NewField(SQLValueFieldName, nil, values),
 | |
| 			data.NewField("host", nil, hosts),
 | |
| 		)
 | |
| 
 | |
| 		numbers, err := extractNumberSetFromSQLForAlerting(input)
 | |
| 		require.Error(t, err)
 | |
| 		require.Nil(t, numbers)
 | |
| 
 | |
| 		require.Contains(t, err.Error(), "duplicate values across the string columns")
 | |
| 		require.Contains(t, err.Error(), "Examples:")
 | |
| 		require.Contains(t, err.Error(), "... and 10 more")
 | |
| 		require.Contains(t, err.Error(), "GROUP BY or aggregation")
 | |
| 	})
 | |
| }
 |