Add index authorisation test coverage
parent
6851db3fc9
commit
d4cecd7cc7
|
@ -2,11 +2,14 @@ package inmem_test
|
|||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"github.com/influxdata/influxdb/internal"
|
||||
"github.com/influxdata/influxdb/models"
|
||||
"github.com/influxdata/influxdb/query"
|
||||
"github.com/influxdata/influxdb/tsdb"
|
||||
"github.com/influxdata/influxdb/tsdb/index/inmem"
|
||||
"github.com/influxdata/influxql"
|
||||
)
|
||||
|
@ -145,6 +148,76 @@ func TestMeasurement_TagsSet_Deadlock(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestIndex_MeasurementNamesByExpr_Auth(t *testing.T) {
|
||||
idx := NewIndex()
|
||||
idx.AddSeries("cpu", map[string]string{"region": "east"})
|
||||
idx.AddSeries("cpu", map[string]string{"region": "west", "secret": "foo"})
|
||||
idx.AddSeries("disk", map[string]string{"secret": "foo"})
|
||||
idx.AddSeries("mem", map[string]string{"region": "west"})
|
||||
idx.AddSeries("gpu", nil)
|
||||
|
||||
authorizer := &internal.AuthorizerMock{
|
||||
AuthorizeSeriesReadFn: func(database string, measurement []byte, tags models.Tags) bool {
|
||||
if tags.GetString("secret") != "" {
|
||||
t.Logf("Rejecting series db=%s, m=%s, tags=%v", database, measurement, tags)
|
||||
return false
|
||||
}
|
||||
return true
|
||||
},
|
||||
}
|
||||
|
||||
// When no condition is provided, all authorised measurements should be returned.
|
||||
names, err := idx.MeasurementNamesByExpr(authorizer, nil)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(names, [][]byte{[]byte("cpu"), []byte("gpu"), []byte("mem")}) {
|
||||
t.Fatalf("unexpected names: %v", BytesToStrings(names))
|
||||
}
|
||||
|
||||
// When using a tag filter, authorised measurements should be returned that
|
||||
// match the tag filter.
|
||||
names, err = idx.MeasurementNamesByExpr(authorizer, influxql.MustParseExpr(`region = 'west'`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(names, [][]byte{[]byte("mem")}) {
|
||||
t.Fatalf("unexpected names: %v", BytesToStrings(names))
|
||||
}
|
||||
|
||||
// When using a regex on a measurement name, all authorised measurements
|
||||
// should be returned.
|
||||
names, err = idx.MeasurementNamesByExpr(authorizer, influxql.MustParseExpr(`_name =~ /cpu|disk/`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(names, [][]byte{[]byte("cpu")}) {
|
||||
t.Fatalf("unexpected names: %v", BytesToStrings(names))
|
||||
}
|
||||
}
|
||||
|
||||
func BytesToStrings(a [][]byte) []string {
|
||||
s := make([]string, 0, len(a))
|
||||
for _, v := range a {
|
||||
s = append(s, string(v))
|
||||
}
|
||||
return s
|
||||
}
|
||||
|
||||
type Index struct {
|
||||
*inmem.ShardIndex
|
||||
}
|
||||
|
||||
func NewIndex() *Index {
|
||||
options := tsdb.NewEngineOptions()
|
||||
options.InmemIndex = inmem.NewIndex("db0")
|
||||
index := inmem.NewShardIndex(0, "db0", "", options).(*inmem.ShardIndex)
|
||||
return &Index{ShardIndex: index}
|
||||
}
|
||||
|
||||
func (idx *Index) AddSeries(name string, tags map[string]string) error {
|
||||
t := models.NewTags(tags)
|
||||
key := fmt.Sprintf("%s,%s", name, t.HashKey())
|
||||
return idx.CreateSeriesIfNotExists([]byte(key), []byte(name), t)
|
||||
}
|
||||
|
||||
func BenchmarkMeasurement_SeriesIDForExp_EQRegex(b *testing.B) {
|
||||
m := inmem.NewMeasurement("foo", "cpu")
|
||||
for i := 0; i < 100000; i++ {
|
||||
|
|
|
@ -9,6 +9,7 @@ import (
|
|||
"regexp"
|
||||
"testing"
|
||||
|
||||
"github.com/influxdata/influxdb/internal"
|
||||
"github.com/influxdata/influxdb/models"
|
||||
"github.com/influxdata/influxdb/tsdb/index/tsi1"
|
||||
"github.com/influxdata/influxql"
|
||||
|
@ -176,6 +177,61 @@ func TestIndex_MeasurementNamesByExpr(t *testing.T) {
|
|||
})
|
||||
}
|
||||
|
||||
func TestIndex_MeasurementNamesByExpr_Auth(t *testing.T) {
|
||||
idx := MustOpenIndex()
|
||||
defer idx.Close()
|
||||
|
||||
// Add series to index.
|
||||
if err := idx.CreateSeriesSliceIfNotExists([]Series{
|
||||
{Name: []byte("cpu"), Tags: models.NewTags(map[string]string{"region": "east"})},
|
||||
{Name: []byte("cpu"), Tags: models.NewTags(map[string]string{"region": "west", "secret": "foo"})},
|
||||
{Name: []byte("disk"), Tags: models.NewTags(map[string]string{"secret": "foo"})},
|
||||
{Name: []byte("mem"), Tags: models.NewTags(map[string]string{"region": "west", "country": "us"})},
|
||||
}); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
authorizer := &internal.AuthorizerMock{
|
||||
AuthorizeSeriesReadFn: func(database string, measurement []byte, tags models.Tags) bool {
|
||||
if tags.GetString("secret") != "" {
|
||||
t.Logf("Rejecting series db=%s, m=%s, tags=%v", database, measurement, tags)
|
||||
return false
|
||||
}
|
||||
return true
|
||||
},
|
||||
}
|
||||
|
||||
// Retrieve measurements by expression
|
||||
idx.Run(t, func(t *testing.T) {
|
||||
t.Run("No Filter", func(t *testing.T) {
|
||||
names, err := idx.MeasurementNamesByExpr(authorizer, nil)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(names, [][]byte{[]byte("cpu"), []byte("mem")}) {
|
||||
t.Fatalf("unexpected names: %v", BytesToStrings(names))
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("EQ", func(t *testing.T) {
|
||||
names, err := idx.MeasurementNamesByExpr(authorizer, influxql.MustParseExpr(`region = 'west'`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(names, [][]byte{[]byte("mem")}) {
|
||||
t.Fatalf("unexpected names: %v", BytesToStrings(names))
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("EQREGEX", func(t *testing.T) {
|
||||
names, err := idx.MeasurementNamesByExpr(authorizer, influxql.MustParseExpr(`_name =~ /cpu|disk/`))
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(names, [][]byte{[]byte("cpu")}) {
|
||||
t.Fatalf("unexpected names: %v", BytesToStrings(names))
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
// Ensure index can return a list of matching measurements.
|
||||
func TestIndex_MeasurementNamesByRegex(t *testing.T) {
|
||||
idx := MustOpenIndex()
|
||||
|
@ -394,3 +450,11 @@ func (idx *Index) CreateSeriesSliceIfNotExists(a []Series) error {
|
|||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func BytesToStrings(a [][]byte) []string {
|
||||
s := make([]string, 0, len(a))
|
||||
for _, v := range a {
|
||||
s = append(s, string(v))
|
||||
}
|
||||
return s
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue