KevinStephenson
Adding in weaviate code
b110593
raw
history blame
6.74 kB
// _ _
// __ _____ __ ___ ___ __ _| |_ ___
// \ \ /\ / / _ \/ _` \ \ / / |/ _` | __/ _ \
// \ V V / __/ (_| |\ V /| | (_| | || __/
// \_/\_/ \___|\__,_| \_/ |_|\__,_|\__\___|
//
// Copyright © 2016 - 2024 Weaviate B.V. All rights reserved.
//
// CONTACT: [email protected]
//
package test
import (
"context"
"math/big"
"strings"
"testing"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
pb "github.com/weaviate/weaviate/grpc/generated/protocol/v1"
"github.com/weaviate/weaviate/test/helper"
"github.com/weaviate/weaviate/test/helper/sample-schema/books"
"google.golang.org/grpc/health/grpc_health_v1"
)
func idByte(id string) []byte {
hexInteger, _ := new(big.Int).SetString(strings.Replace(id, "-", "", -1), 16)
return hexInteger.Bytes()
}
func TestGRPC(t *testing.T) {
conn, err := helper.CreateGrpcConnectionClient(":50051")
require.NoError(t, err)
require.NotNil(t, conn)
grpcClient := helper.CreateGrpcWeaviateClient(conn)
require.NotNil(t, grpcClient)
// delete if exists and then re-create Books class
booksClass := books.ClassContextionaryVectorizer()
helper.DeleteClass(t, booksClass.Class)
helper.CreateClass(t, booksClass)
defer helper.DeleteClass(t, booksClass.Class)
t.Run("Health Check", func(t *testing.T) {
client := grpc_health_v1.NewHealthClient(conn)
check, err := client.Check(context.TODO(), &grpc_health_v1.HealthCheckRequest{})
require.NoError(t, err)
require.NotNil(t, check)
assert.Equal(t, grpc_health_v1.HealthCheckResponse_SERVING.Enum().Number(), check.Status.Number())
})
t.Run("Batch import", func(t *testing.T) {
resp, err := grpcClient.BatchObjects(context.TODO(), &pb.BatchObjectsRequest{
Objects: books.BatchObjects(),
})
require.NoError(t, err)
require.NotNil(t, resp)
})
tests := []struct {
name string
req *pb.SearchRequest
}{
{
name: "Search with props",
req: &pb.SearchRequest{
Collection: booksClass.Class,
Properties: &pb.PropertiesRequest{
NonRefProperties: []string{"title"},
ObjectProperties: []*pb.ObjectPropertiesRequest{
{
PropName: "meta",
PrimitiveProperties: []string{"isbn"},
ObjectProperties: []*pb.ObjectPropertiesRequest{
{
PropName: "obj",
PrimitiveProperties: []string{"text"},
},
{
PropName: "objs",
PrimitiveProperties: []string{"text"},
},
},
},
{PropName: "reviews", PrimitiveProperties: []string{"tags"}},
},
},
Metadata: &pb.MetadataRequest{
Uuid: true,
},
Uses_123Api: true,
},
},
{
name: "Search without props",
req: &pb.SearchRequest{
Collection: booksClass.Class,
Metadata: &pb.MetadataRequest{
Uuid: true,
},
Uses_123Api: true,
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
scifi := "sci-fi"
resp, err := grpcClient.Search(context.TODO(), tt.req)
require.NoError(t, err)
require.NotNil(t, resp)
require.NotNil(t, resp.Results)
assert.Equal(t, len(books.BatchObjects()), len(resp.Results))
for i := range resp.Results {
res := resp.Results[i]
id := res.Metadata.Id
assert.True(t, id == books.Dune.String() || id == books.ProjectHailMary.String() || id == books.TheLordOfTheIceGarden.String())
titleRaw := res.Properties.NonRefProps.Fields["title"]
require.NotNil(t, titleRaw)
title := titleRaw.GetStringValue()
require.NotNil(t, title)
metaRaw := res.Properties.NonRefProps.Fields["meta"]
require.NotNil(t, metaRaw)
meta := metaRaw.GetObjectValue()
require.NotNil(t, meta)
isbnRaw := meta.GetFields()["isbn"]
require.NotNil(t, isbnRaw)
isbn := isbnRaw.GetStringValue()
require.NotNil(t, isbn)
objRaw := meta.GetFields()["obj"]
require.NotNil(t, objRaw)
obj := objRaw.GetObjectValue()
require.NotNil(t, obj)
objsRaw := meta.GetFields()["objs"]
require.NotNil(t, objsRaw)
objs := objsRaw.GetListValue()
require.NotNil(t, objs)
objEntryRaw := objs.Values[0]
require.NotNil(t, objEntryRaw)
objEntry := objEntryRaw.GetObjectValue()
require.NotNil(t, objEntry)
reviewsRaw := res.Properties.NonRefProps.Fields["reviews"]
require.NotNil(t, reviewsRaw)
reviews := reviewsRaw.GetListValue()
require.NotNil(t, reviews)
require.Len(t, reviews.Values, 1)
review := reviews.Values[0].GetObjectValue()
require.NotNil(t, review)
tags := review.Fields["tags"].GetListValue()
require.NotNil(t, tags)
strTags := make([]string, len(tags.Values))
for i, tag := range tags.Values {
strTags[i] = tag.GetStringValue()
}
expectedTitle := ""
expectedIsbn := ""
expectedTags := []string{}
if id == books.Dune.String() {
expectedTitle = "Dune"
expectedIsbn = "978-0593099322"
expectedTags = []string{scifi, "epic"}
}
if id == books.ProjectHailMary.String() {
expectedTitle = "Project Hail Mary"
expectedIsbn = "978-0593135204"
expectedTags = []string{scifi}
}
if id == books.TheLordOfTheIceGarden.String() {
expectedTitle = "The Lord of the Ice Garden"
expectedIsbn = "978-8374812962"
expectedTags = []string{scifi, "fantasy"}
}
assert.Equal(t, expectedTitle, title)
assert.Equal(t, expectedIsbn, isbn)
assert.Equal(t, expectedTags, strTags)
expectedObj := &pb.Properties{
Fields: map[string]*pb.Value{
"text": {Kind: &pb.Value_StringValue{StringValue: "some text"}},
},
}
assert.Equal(t, expectedObj, obj)
assert.Equal(t, expectedObj, objEntry)
}
})
}
t.Run("Batch delete", func(t *testing.T) {
resp, err := grpcClient.BatchDelete(context.TODO(), &pb.BatchDeleteRequest{
Collection: "Books",
Filters: &pb.Filters{Operator: pb.Filters_OPERATOR_EQUAL, TestValue: &pb.Filters_ValueText{ValueText: "Dune"}, Target: &pb.FilterTarget{Target: &pb.FilterTarget_Property{Property: "title"}}},
DryRun: true,
Verbose: true,
})
require.NoError(t, err)
require.NotNil(t, resp)
require.Equal(t, resp.Matches, int64(1))
require.Equal(t, resp.Successful, int64(1))
require.Equal(t, resp.Failed, int64(0))
require.Equal(t, resp.Objects[0].Uuid, idByte(books.Dune.String()))
})
t.Run("gRPC Search removed", func(t *testing.T) {
_, err := grpcClient.Search(context.TODO(), &pb.SearchRequest{})
require.NotNil(t, err)
})
}