Support dynamic schema for create collection (#24176)

Signed-off-by: cai.zhang <cai.zhang@zilliz.com>
pull/24208/head
cai.zhang 2023-05-18 09:33:24 +08:00 committed by GitHub
parent 1a3dca9b5e
commit 008285f849
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
28 changed files with 1482 additions and 673 deletions

2
go.mod
View File

@ -20,7 +20,7 @@ require (
github.com/golang/protobuf v1.5.3
github.com/klauspost/compress v1.14.4
github.com/mgutz/ansi v0.0.0-20200706080929-d51e80ef957d
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230421091228-eaa38c831a61
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230515081521-d963c95b041f
github.com/milvus-io/milvus/pkg v0.0.0-00010101000000-000000000000
github.com/minio/minio-go/v7 v7.0.17
github.com/panjf2000/ants/v2 v2.7.2

2
go.sum
View File

@ -581,6 +581,8 @@ github.com/milvus-io/gorocksdb v0.0.0-20220624081344-8c5f4212846b h1:TfeY0NxYxZz
github.com/milvus-io/gorocksdb v0.0.0-20220624081344-8c5f4212846b/go.mod h1:iwW+9cWfIzzDseEBCCeDSN5SD16Tidvy8cwQ7ZY8Qj4=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230421091228-eaa38c831a61 h1:EX2oknwzltpw6yZ7QZEphVHM3YTysjdbb5keleFjs3M=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230421091228-eaa38c831a61/go.mod h1:148qnlmZ0Fdm1Fq+Mj/OW2uDoEP25g3mjh0vMGtkgmk=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230515081521-d963c95b041f h1:uZzVaSbUtxMdEix9By6z+M/H/XNkXRQJdZQ9HP/wHtc=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230515081521-d963c95b041f/go.mod h1:148qnlmZ0Fdm1Fq+Mj/OW2uDoEP25g3mjh0vMGtkgmk=
github.com/milvus-io/pulsar-client-go v0.6.10 h1:eqpJjU+/QX0iIhEo3nhOqMNXL+TyInAs1IAHZCrCM/A=
github.com/milvus-io/pulsar-client-go v0.6.10/go.mod h1:lQqCkgwDF8YFYjKA+zOheTk1tev2B+bKj5j7+nm8M1w=
github.com/minio/asm2plan9s v0.0.0-20200509001527-cdd76441f9d8 h1:AMFGa4R4MiIpspGNG7Z948v4n35fFGB3RR3G/ry4FWs=

View File

@ -32,9 +32,11 @@ PROTOBUF_CONSTEXPR FieldSchema::FieldSchema(
, /*decltype(_impl_.default_value_)*/nullptr
, /*decltype(_impl_.fieldid_)*/int64_t{0}
, /*decltype(_impl_.data_type_)*/0
, /*decltype(_impl_.state_)*/0
, /*decltype(_impl_.is_primary_key_)*/false
, /*decltype(_impl_.autoid_)*/false
, /*decltype(_impl_.state_)*/0
, /*decltype(_impl_.is_dynamic_)*/false
, /*decltype(_impl_.is_partition_key_)*/false
, /*decltype(_impl_.element_type_)*/0
, /*decltype(_impl_._cached_size_)*/{}} {}
struct FieldSchemaDefaultTypeInternal {
@ -52,6 +54,7 @@ PROTOBUF_CONSTEXPR CollectionSchema::CollectionSchema(
, /*decltype(_impl_.name_)*/{&::_pbi::fixed_address_empty_string, ::_pbi::ConstantInitialized{}}
, /*decltype(_impl_.description_)*/{&::_pbi::fixed_address_empty_string, ::_pbi::ConstantInitialized{}}
, /*decltype(_impl_.autoid_)*/false
, /*decltype(_impl_.enable_dynamic_field_)*/false
, /*decltype(_impl_._cached_size_)*/{}} {}
struct CollectionSchemaDefaultTypeInternal {
PROTOBUF_CONSTEXPR CollectionSchemaDefaultTypeInternal()
@ -300,6 +303,8 @@ const uint32_t TableStruct_schema_2eproto::offsets[] PROTOBUF_SECTION_VARIABLE(p
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::FieldSchema, _impl_.state_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::FieldSchema, _impl_.element_type_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::FieldSchema, _impl_.default_value_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::FieldSchema, _impl_.is_dynamic_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::FieldSchema, _impl_.is_partition_key_),
~0u, // no _has_bits_
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::CollectionSchema, _internal_metadata_),
~0u, // no _extensions_
@ -310,6 +315,7 @@ const uint32_t TableStruct_schema_2eproto::offsets[] PROTOBUF_SECTION_VARIABLE(p
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::CollectionSchema, _impl_.description_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::CollectionSchema, _impl_.autoid_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::CollectionSchema, _impl_.fields_),
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::CollectionSchema, _impl_.enable_dynamic_field_),
~0u, // no _has_bits_
PROTOBUF_FIELD_OFFSET(::milvus::proto::schema::BoolArray, _internal_metadata_),
~0u, // no _extensions_
@ -450,22 +456,22 @@ const uint32_t TableStruct_schema_2eproto::offsets[] PROTOBUF_SECTION_VARIABLE(p
};
static const ::_pbi::MigrationSchema schemas[] PROTOBUF_SECTION_VARIABLE(protodesc_cold) = {
{ 0, -1, -1, sizeof(::milvus::proto::schema::FieldSchema)},
{ 17, -1, -1, sizeof(::milvus::proto::schema::CollectionSchema)},
{ 27, -1, -1, sizeof(::milvus::proto::schema::BoolArray)},
{ 34, -1, -1, sizeof(::milvus::proto::schema::IntArray)},
{ 41, -1, -1, sizeof(::milvus::proto::schema::LongArray)},
{ 48, -1, -1, sizeof(::milvus::proto::schema::FloatArray)},
{ 55, -1, -1, sizeof(::milvus::proto::schema::DoubleArray)},
{ 62, -1, -1, sizeof(::milvus::proto::schema::BytesArray)},
{ 69, -1, -1, sizeof(::milvus::proto::schema::StringArray)},
{ 76, -1, -1, sizeof(::milvus::proto::schema::ArrayArray)},
{ 84, -1, -1, sizeof(::milvus::proto::schema::JSONArray)},
{ 91, -1, -1, sizeof(::milvus::proto::schema::ValueField)},
{ 105, -1, -1, sizeof(::milvus::proto::schema::ScalarField)},
{ 121, -1, -1, sizeof(::milvus::proto::schema::VectorField)},
{ 131, -1, -1, sizeof(::milvus::proto::schema::FieldData)},
{ 143, -1, -1, sizeof(::milvus::proto::schema::IDs)},
{ 152, -1, -1, sizeof(::milvus::proto::schema::SearchResultData)},
{ 19, -1, -1, sizeof(::milvus::proto::schema::CollectionSchema)},
{ 30, -1, -1, sizeof(::milvus::proto::schema::BoolArray)},
{ 37, -1, -1, sizeof(::milvus::proto::schema::IntArray)},
{ 44, -1, -1, sizeof(::milvus::proto::schema::LongArray)},
{ 51, -1, -1, sizeof(::milvus::proto::schema::FloatArray)},
{ 58, -1, -1, sizeof(::milvus::proto::schema::DoubleArray)},
{ 65, -1, -1, sizeof(::milvus::proto::schema::BytesArray)},
{ 72, -1, -1, sizeof(::milvus::proto::schema::StringArray)},
{ 79, -1, -1, sizeof(::milvus::proto::schema::ArrayArray)},
{ 87, -1, -1, sizeof(::milvus::proto::schema::JSONArray)},
{ 94, -1, -1, sizeof(::milvus::proto::schema::ValueField)},
{ 108, -1, -1, sizeof(::milvus::proto::schema::ScalarField)},
{ 124, -1, -1, sizeof(::milvus::proto::schema::VectorField)},
{ 134, -1, -1, sizeof(::milvus::proto::schema::FieldData)},
{ 146, -1, -1, sizeof(::milvus::proto::schema::IDs)},
{ 155, -1, -1, sizeof(::milvus::proto::schema::SearchResultData)},
};
static const ::_pb::Message* const file_default_instances[] = {
@ -490,7 +496,7 @@ static const ::_pb::Message* const file_default_instances[] = {
const char descriptor_table_protodef_schema_2eproto[] PROTOBUF_SECTION_VARIABLE(protodesc_cold) =
"\n\014schema.proto\022\023milvus.proto.schema\032\014com"
"mon.proto\"\251\003\n\013FieldSchema\022\017\n\007fieldID\030\001 \001"
"mon.proto\"\327\003\n\013FieldSchema\022\017\n\007fieldID\030\001 \001"
"(\003\022\014\n\004name\030\002 \001(\t\022\026\n\016is_primary_key\030\003 \001(\010"
"\022\023\n\013description\030\004 \001(\t\0220\n\tdata_type\030\005 \001(\016"
"2\035.milvus.proto.schema.DataType\0226\n\013type_"
@ -500,68 +506,70 @@ const char descriptor_table_protodef_schema_2eproto[] PROTOBUF_SECTION_VARIABLE(
"\022.\n\005state\030\t \001(\0162\037.milvus.proto.schema.Fi"
"eldState\0223\n\014element_type\030\n \001(\0162\035.milvus."
"proto.schema.DataType\0226\n\rdefault_value\030\013"
" \001(\0132\037.milvus.proto.schema.ValueField\"w\n"
"\020CollectionSchema\022\014\n\004name\030\001 \001(\t\022\023\n\013descr"
"iption\030\002 \001(\t\022\016\n\006autoID\030\003 \001(\010\0220\n\006fields\030\004"
" \003(\0132 .milvus.proto.schema.FieldSchema\"\031"
"\n\tBoolArray\022\014\n\004data\030\001 \003(\010\"\030\n\010IntArray\022\014\n"
"\004data\030\001 \003(\005\"\031\n\tLongArray\022\014\n\004data\030\001 \003(\003\"\032"
"\n\nFloatArray\022\014\n\004data\030\001 \003(\002\"\033\n\013DoubleArra"
"y\022\014\n\004data\030\001 \003(\001\"\032\n\nBytesArray\022\014\n\004data\030\001 "
"\003(\014\"\033\n\013StringArray\022\014\n\004data\030\001 \003(\t\"q\n\nArra"
"yArray\022.\n\004data\030\001 \003(\0132 .milvus.proto.sche"
"ma.ScalarField\0223\n\014element_type\030\002 \001(\0162\035.m"
"ilvus.proto.schema.DataType\"\031\n\tJSONArray"
"\022\014\n\004data\030\001 \003(\014\"\254\001\n\nValueField\022\023\n\tbool_da"
"ta\030\001 \001(\010H\000\022\022\n\010int_data\030\002 \001(\005H\000\022\023\n\tlong_d"
"ata\030\003 \001(\003H\000\022\024\n\nfloat_data\030\004 \001(\002H\000\022\025\n\013dou"
"ble_data\030\005 \001(\001H\000\022\025\n\013string_data\030\006 \001(\tH\000\022"
"\024\n\nbytes_data\030\007 \001(\014H\000B\006\n\004data\"\376\003\n\013Scalar"
"Field\0223\n\tbool_data\030\001 \001(\0132\036.milvus.proto."
"schema.BoolArrayH\000\0221\n\010int_data\030\002 \001(\0132\035.m"
"ilvus.proto.schema.IntArrayH\000\0223\n\tlong_da"
"ta\030\003 \001(\0132\036.milvus.proto.schema.LongArray"
"H\000\0225\n\nfloat_data\030\004 \001(\0132\037.milvus.proto.sc"
"hema.FloatArrayH\000\0227\n\013double_data\030\005 \001(\0132 "
".milvus.proto.schema.DoubleArrayH\000\0227\n\013st"
"ring_data\030\006 \001(\0132 .milvus.proto.schema.St"
"ringArrayH\000\0225\n\nbytes_data\030\007 \001(\0132\037.milvus"
".proto.schema.BytesArrayH\000\0225\n\narray_data"
"\030\010 \001(\0132\037.milvus.proto.schema.ArrayArrayH"
"\000\0223\n\tjson_data\030\t \001(\0132\036.milvus.proto.sche"
"ma.JSONArrayH\000B\006\n\004data\"t\n\013VectorField\022\013\n"
"\003dim\030\001 \001(\003\0227\n\014float_vector\030\002 \001(\0132\037.milvu"
"s.proto.schema.FloatArrayH\000\022\027\n\rbinary_ve"
"ctor\030\003 \001(\014H\000B\006\n\004data\"\321\001\n\tFieldData\022+\n\004ty"
"pe\030\001 \001(\0162\035.milvus.proto.schema.DataType\022"
"\022\n\nfield_name\030\002 \001(\t\0223\n\007scalars\030\003 \001(\0132 .m"
"ilvus.proto.schema.ScalarFieldH\000\0223\n\007vect"
"ors\030\004 \001(\0132 .milvus.proto.schema.VectorFi"
"eldH\000\022\020\n\010field_id\030\005 \001(\003B\007\n\005field\"w\n\003IDs\022"
"0\n\006int_id\030\001 \001(\0132\036.milvus.proto.schema.Lo"
"ngArrayH\000\0222\n\006str_id\030\002 \001(\0132 .milvus.proto"
".schema.StringArrayH\000B\n\n\010id_field\"\261\001\n\020Se"
"archResultData\022\023\n\013num_queries\030\001 \001(\003\022\r\n\005t"
"op_k\030\002 \001(\003\0223\n\013fields_data\030\003 \003(\0132\036.milvus"
".proto.schema.FieldData\022\016\n\006scores\030\004 \003(\002\022"
"%\n\003ids\030\005 \001(\0132\030.milvus.proto.schema.IDs\022\r"
"\n\005topks\030\006 \003(\003*\261\001\n\010DataType\022\010\n\004None\020\000\022\010\n\004"
"Bool\020\001\022\010\n\004Int8\020\002\022\t\n\005Int16\020\003\022\t\n\005Int32\020\004\022\t"
"\n\005Int64\020\005\022\t\n\005Float\020\n\022\n\n\006Double\020\013\022\n\n\006Stri"
"ng\020\024\022\013\n\007VarChar\020\025\022\t\n\005Array\020\026\022\010\n\004JSON\020\027\022\020"
"\n\014BinaryVector\020d\022\017\n\013FloatVector\020e*V\n\nFie"
"ldState\022\020\n\014FieldCreated\020\000\022\021\n\rFieldCreati"
"ng\020\001\022\021\n\rFieldDropping\020\002\022\020\n\014FieldDropped\020"
"\003Bf\n\016io.milvus.grpcB\013SchemaProtoP\001Z1gith"
"ub.com/milvus-io/milvus-proto/go-api/sch"
"emapb\240\001\001\252\002\016IO.Milvus.Grpcb\006proto3"
" \001(\0132\037.milvus.proto.schema.ValueField\022\022\n"
"\nis_dynamic\030\014 \001(\010\022\030\n\020is_partition_key\030\r "
"\001(\010\"\225\001\n\020CollectionSchema\022\014\n\004name\030\001 \001(\t\022\023"
"\n\013description\030\002 \001(\t\022\016\n\006autoID\030\003 \001(\010\0220\n\006f"
"ields\030\004 \003(\0132 .milvus.proto.schema.FieldS"
"chema\022\034\n\024enable_dynamic_field\030\005 \001(\010\"\031\n\tB"
"oolArray\022\014\n\004data\030\001 \003(\010\"\030\n\010IntArray\022\014\n\004da"
"ta\030\001 \003(\005\"\031\n\tLongArray\022\014\n\004data\030\001 \003(\003\"\032\n\nF"
"loatArray\022\014\n\004data\030\001 \003(\002\"\033\n\013DoubleArray\022\014"
"\n\004data\030\001 \003(\001\"\032\n\nBytesArray\022\014\n\004data\030\001 \003(\014"
"\"\033\n\013StringArray\022\014\n\004data\030\001 \003(\t\"q\n\nArrayAr"
"ray\022.\n\004data\030\001 \003(\0132 .milvus.proto.schema."
"ScalarField\0223\n\014element_type\030\002 \001(\0162\035.milv"
"us.proto.schema.DataType\"\031\n\tJSONArray\022\014\n"
"\004data\030\001 \003(\014\"\254\001\n\nValueField\022\023\n\tbool_data\030"
"\001 \001(\010H\000\022\022\n\010int_data\030\002 \001(\005H\000\022\023\n\tlong_data"
"\030\003 \001(\003H\000\022\024\n\nfloat_data\030\004 \001(\002H\000\022\025\n\013double"
"_data\030\005 \001(\001H\000\022\025\n\013string_data\030\006 \001(\tH\000\022\024\n\n"
"bytes_data\030\007 \001(\014H\000B\006\n\004data\"\376\003\n\013ScalarFie"
"ld\0223\n\tbool_data\030\001 \001(\0132\036.milvus.proto.sch"
"ema.BoolArrayH\000\0221\n\010int_data\030\002 \001(\0132\035.milv"
"us.proto.schema.IntArrayH\000\0223\n\tlong_data\030"
"\003 \001(\0132\036.milvus.proto.schema.LongArrayH\000\022"
"5\n\nfloat_data\030\004 \001(\0132\037.milvus.proto.schem"
"a.FloatArrayH\000\0227\n\013double_data\030\005 \001(\0132 .mi"
"lvus.proto.schema.DoubleArrayH\000\0227\n\013strin"
"g_data\030\006 \001(\0132 .milvus.proto.schema.Strin"
"gArrayH\000\0225\n\nbytes_data\030\007 \001(\0132\037.milvus.pr"
"oto.schema.BytesArrayH\000\0225\n\narray_data\030\010 "
"\001(\0132\037.milvus.proto.schema.ArrayArrayH\000\0223"
"\n\tjson_data\030\t \001(\0132\036.milvus.proto.schema."
"JSONArrayH\000B\006\n\004data\"t\n\013VectorField\022\013\n\003di"
"m\030\001 \001(\003\0227\n\014float_vector\030\002 \001(\0132\037.milvus.p"
"roto.schema.FloatArrayH\000\022\027\n\rbinary_vecto"
"r\030\003 \001(\014H\000B\006\n\004data\"\321\001\n\tFieldData\022+\n\004type\030"
"\001 \001(\0162\035.milvus.proto.schema.DataType\022\022\n\n"
"field_name\030\002 \001(\t\0223\n\007scalars\030\003 \001(\0132 .milv"
"us.proto.schema.ScalarFieldH\000\0223\n\007vectors"
"\030\004 \001(\0132 .milvus.proto.schema.VectorField"
"H\000\022\020\n\010field_id\030\005 \001(\003B\007\n\005field\"w\n\003IDs\0220\n\006"
"int_id\030\001 \001(\0132\036.milvus.proto.schema.LongA"
"rrayH\000\0222\n\006str_id\030\002 \001(\0132 .milvus.proto.sc"
"hema.StringArrayH\000B\n\n\010id_field\"\261\001\n\020Searc"
"hResultData\022\023\n\013num_queries\030\001 \001(\003\022\r\n\005top_"
"k\030\002 \001(\003\0223\n\013fields_data\030\003 \003(\0132\036.milvus.pr"
"oto.schema.FieldData\022\016\n\006scores\030\004 \003(\002\022%\n\003"
"ids\030\005 \001(\0132\030.milvus.proto.schema.IDs\022\r\n\005t"
"opks\030\006 \003(\003*\261\001\n\010DataType\022\010\n\004None\020\000\022\010\n\004Boo"
"l\020\001\022\010\n\004Int8\020\002\022\t\n\005Int16\020\003\022\t\n\005Int32\020\004\022\t\n\005I"
"nt64\020\005\022\t\n\005Float\020\n\022\n\n\006Double\020\013\022\n\n\006String\020"
"\024\022\013\n\007VarChar\020\025\022\t\n\005Array\020\026\022\010\n\004JSON\020\027\022\020\n\014B"
"inaryVector\020d\022\017\n\013FloatVector\020e*V\n\nFieldS"
"tate\022\020\n\014FieldCreated\020\000\022\021\n\rFieldCreating\020"
"\001\022\021\n\rFieldDropping\020\002\022\020\n\014FieldDropped\020\003Bf"
"\n\016io.milvus.grpcB\013SchemaProtoP\001Z1github."
"com/milvus-io/milvus-proto/go-api/schema"
"pb\240\001\001\252\002\016IO.Milvus.Grpcb\006proto3"
;
static const ::_pbi::DescriptorTable* const descriptor_table_schema_2eproto_deps[1] = {
&::descriptor_table_common_2eproto,
};
static ::_pbi::once_flag descriptor_table_schema_2eproto_once;
const ::_pbi::DescriptorTable descriptor_table_schema_2eproto = {
false, false, 2633, descriptor_table_protodef_schema_2eproto,
false, false, 2710, descriptor_table_protodef_schema_2eproto,
"schema.proto",
&descriptor_table_schema_2eproto_once, descriptor_table_schema_2eproto_deps, 1, 17,
schemas, file_default_instances, TableStruct_schema_2eproto::offsets,
@ -654,9 +662,11 @@ FieldSchema::FieldSchema(const FieldSchema& from)
, decltype(_impl_.default_value_){nullptr}
, decltype(_impl_.fieldid_){}
, decltype(_impl_.data_type_){}
, decltype(_impl_.state_){}
, decltype(_impl_.is_primary_key_){}
, decltype(_impl_.autoid_){}
, decltype(_impl_.state_){}
, decltype(_impl_.is_dynamic_){}
, decltype(_impl_.is_partition_key_){}
, decltype(_impl_.element_type_){}
, /*decltype(_impl_._cached_size_)*/{}};
@ -698,9 +708,11 @@ inline void FieldSchema::SharedCtor(
, decltype(_impl_.default_value_){nullptr}
, decltype(_impl_.fieldid_){int64_t{0}}
, decltype(_impl_.data_type_){0}
, decltype(_impl_.state_){0}
, decltype(_impl_.is_primary_key_){false}
, decltype(_impl_.autoid_){false}
, decltype(_impl_.state_){0}
, decltype(_impl_.is_dynamic_){false}
, decltype(_impl_.is_partition_key_){false}
, decltype(_impl_.element_type_){0}
, /*decltype(_impl_._cached_size_)*/{}
};
@ -867,6 +879,22 @@ const char* FieldSchema::_InternalParse(const char* ptr, ::_pbi::ParseContext* c
} else
goto handle_unusual;
continue;
// bool is_dynamic = 12;
case 12:
if (PROTOBUF_PREDICT_TRUE(static_cast<uint8_t>(tag) == 96)) {
_impl_.is_dynamic_ = ::PROTOBUF_NAMESPACE_ID::internal::ReadVarint64(&ptr);
CHK_(ptr);
} else
goto handle_unusual;
continue;
// bool is_partition_key = 13;
case 13:
if (PROTOBUF_PREDICT_TRUE(static_cast<uint8_t>(tag) == 104)) {
_impl_.is_partition_key_ = ::PROTOBUF_NAMESPACE_ID::internal::ReadVarint64(&ptr);
CHK_(ptr);
} else
goto handle_unusual;
continue;
default:
goto handle_unusual;
} // switch
@ -978,6 +1006,18 @@ uint8_t* FieldSchema::_InternalSerialize(
_Internal::default_value(this).GetCachedSize(), target, stream);
}
// bool is_dynamic = 12;
if (this->_internal_is_dynamic() != 0) {
target = stream->EnsureSpace(target);
target = ::_pbi::WireFormatLite::WriteBoolToArray(12, this->_internal_is_dynamic(), target);
}
// bool is_partition_key = 13;
if (this->_internal_is_partition_key() != 0) {
target = stream->EnsureSpace(target);
target = ::_pbi::WireFormatLite::WriteBoolToArray(13, this->_internal_is_partition_key(), target);
}
if (PROTOBUF_PREDICT_FALSE(_internal_metadata_.have_unknown_fields())) {
target = ::_pbi::WireFormat::InternalSerializeUnknownFieldsToArray(
_internal_metadata_.unknown_fields<::PROTOBUF_NAMESPACE_ID::UnknownFieldSet>(::PROTOBUF_NAMESPACE_ID::UnknownFieldSet::default_instance), target, stream);
@ -1040,6 +1080,12 @@ size_t FieldSchema::ByteSizeLong() const {
::_pbi::WireFormatLite::EnumSize(this->_internal_data_type());
}
// .milvus.proto.schema.FieldState state = 9;
if (this->_internal_state() != 0) {
total_size += 1 +
::_pbi::WireFormatLite::EnumSize(this->_internal_state());
}
// bool is_primary_key = 3;
if (this->_internal_is_primary_key() != 0) {
total_size += 1 + 1;
@ -1050,10 +1096,14 @@ size_t FieldSchema::ByteSizeLong() const {
total_size += 1 + 1;
}
// .milvus.proto.schema.FieldState state = 9;
if (this->_internal_state() != 0) {
total_size += 1 +
::_pbi::WireFormatLite::EnumSize(this->_internal_state());
// bool is_dynamic = 12;
if (this->_internal_is_dynamic() != 0) {
total_size += 1 + 1;
}
// bool is_partition_key = 13;
if (this->_internal_is_partition_key() != 0) {
total_size += 1 + 1;
}
// .milvus.proto.schema.DataType element_type = 10;
@ -1098,14 +1148,20 @@ void FieldSchema::MergeImpl(::PROTOBUF_NAMESPACE_ID::Message& to_msg, const ::PR
if (from._internal_data_type() != 0) {
_this->_internal_set_data_type(from._internal_data_type());
}
if (from._internal_state() != 0) {
_this->_internal_set_state(from._internal_state());
}
if (from._internal_is_primary_key() != 0) {
_this->_internal_set_is_primary_key(from._internal_is_primary_key());
}
if (from._internal_autoid() != 0) {
_this->_internal_set_autoid(from._internal_autoid());
}
if (from._internal_state() != 0) {
_this->_internal_set_state(from._internal_state());
if (from._internal_is_dynamic() != 0) {
_this->_internal_set_is_dynamic(from._internal_is_dynamic());
}
if (from._internal_is_partition_key() != 0) {
_this->_internal_set_is_partition_key(from._internal_is_partition_key());
}
if (from._internal_element_type() != 0) {
_this->_internal_set_element_type(from._internal_element_type());
@ -1173,6 +1229,7 @@ CollectionSchema::CollectionSchema(const CollectionSchema& from)
, decltype(_impl_.name_){}
, decltype(_impl_.description_){}
, decltype(_impl_.autoid_){}
, decltype(_impl_.enable_dynamic_field_){}
, /*decltype(_impl_._cached_size_)*/{}};
_internal_metadata_.MergeFrom<::PROTOBUF_NAMESPACE_ID::UnknownFieldSet>(from._internal_metadata_);
@ -1192,7 +1249,9 @@ CollectionSchema::CollectionSchema(const CollectionSchema& from)
_this->_impl_.description_.Set(from._internal_description(),
_this->GetArenaForAllocation());
}
_this->_impl_.autoid_ = from._impl_.autoid_;
::memcpy(&_impl_.autoid_, &from._impl_.autoid_,
static_cast<size_t>(reinterpret_cast<char*>(&_impl_.enable_dynamic_field_) -
reinterpret_cast<char*>(&_impl_.autoid_)) + sizeof(_impl_.enable_dynamic_field_));
// @@protoc_insertion_point(copy_constructor:milvus.proto.schema.CollectionSchema)
}
@ -1205,6 +1264,7 @@ inline void CollectionSchema::SharedCtor(
, decltype(_impl_.name_){}
, decltype(_impl_.description_){}
, decltype(_impl_.autoid_){false}
, decltype(_impl_.enable_dynamic_field_){false}
, /*decltype(_impl_._cached_size_)*/{}
};
_impl_.name_.InitDefault();
@ -1246,7 +1306,9 @@ void CollectionSchema::Clear() {
_impl_.fields_.Clear();
_impl_.name_.ClearToEmpty();
_impl_.description_.ClearToEmpty();
_impl_.autoid_ = false;
::memset(&_impl_.autoid_, 0, static_cast<size_t>(
reinterpret_cast<char*>(&_impl_.enable_dynamic_field_) -
reinterpret_cast<char*>(&_impl_.autoid_)) + sizeof(_impl_.enable_dynamic_field_));
_internal_metadata_.Clear<::PROTOBUF_NAMESPACE_ID::UnknownFieldSet>();
}
@ -1297,6 +1359,14 @@ const char* CollectionSchema::_InternalParse(const char* ptr, ::_pbi::ParseConte
} else
goto handle_unusual;
continue;
// bool enable_dynamic_field = 5;
case 5:
if (PROTOBUF_PREDICT_TRUE(static_cast<uint8_t>(tag) == 40)) {
_impl_.enable_dynamic_field_ = ::PROTOBUF_NAMESPACE_ID::internal::ReadVarint64(&ptr);
CHK_(ptr);
} else
goto handle_unusual;
continue;
default:
goto handle_unusual;
} // switch
@ -1360,6 +1430,12 @@ uint8_t* CollectionSchema::_InternalSerialize(
InternalWriteMessage(4, repfield, repfield.GetCachedSize(), target, stream);
}
// bool enable_dynamic_field = 5;
if (this->_internal_enable_dynamic_field() != 0) {
target = stream->EnsureSpace(target);
target = ::_pbi::WireFormatLite::WriteBoolToArray(5, this->_internal_enable_dynamic_field(), target);
}
if (PROTOBUF_PREDICT_FALSE(_internal_metadata_.have_unknown_fields())) {
target = ::_pbi::WireFormat::InternalSerializeUnknownFieldsToArray(
_internal_metadata_.unknown_fields<::PROTOBUF_NAMESPACE_ID::UnknownFieldSet>(::PROTOBUF_NAMESPACE_ID::UnknownFieldSet::default_instance), target, stream);
@ -1402,6 +1478,11 @@ size_t CollectionSchema::ByteSizeLong() const {
total_size += 1 + 1;
}
// bool enable_dynamic_field = 5;
if (this->_internal_enable_dynamic_field() != 0) {
total_size += 1 + 1;
}
return MaybeComputeUnknownFieldsSize(total_size, &_impl_._cached_size_);
}
@ -1430,6 +1511,9 @@ void CollectionSchema::MergeImpl(::PROTOBUF_NAMESPACE_ID::Message& to_msg, const
if (from._internal_autoid() != 0) {
_this->_internal_set_autoid(from._internal_autoid());
}
if (from._internal_enable_dynamic_field() != 0) {
_this->_internal_set_enable_dynamic_field(from._internal_enable_dynamic_field());
}
_this->_internal_metadata_.MergeFrom<::PROTOBUF_NAMESPACE_ID::UnknownFieldSet>(from._internal_metadata_);
}
@ -1458,7 +1542,12 @@ void CollectionSchema::InternalSwap(CollectionSchema* other) {
&_impl_.description_, lhs_arena,
&other->_impl_.description_, rhs_arena
);
swap(_impl_.autoid_, other->_impl_.autoid_);
::PROTOBUF_NAMESPACE_ID::internal::memswap<
PROTOBUF_FIELD_OFFSET(CollectionSchema, _impl_.enable_dynamic_field_)
+ sizeof(CollectionSchema::_impl_.enable_dynamic_field_)
- PROTOBUF_FIELD_OFFSET(CollectionSchema, _impl_.autoid_)>(
reinterpret_cast<char*>(&_impl_.autoid_),
reinterpret_cast<char*>(&other->_impl_.autoid_));
}
::PROTOBUF_NAMESPACE_ID::Metadata CollectionSchema::GetMetadata() const {

View File

@ -320,9 +320,11 @@ class FieldSchema final :
kDefaultValueFieldNumber = 11,
kFieldIDFieldNumber = 1,
kDataTypeFieldNumber = 5,
kStateFieldNumber = 9,
kIsPrimaryKeyFieldNumber = 3,
kAutoIDFieldNumber = 8,
kStateFieldNumber = 9,
kIsDynamicFieldNumber = 12,
kIsPartitionKeyFieldNumber = 13,
kElementTypeFieldNumber = 10,
};
// repeated .milvus.proto.common.KeyValuePair type_params = 6;
@ -425,6 +427,15 @@ class FieldSchema final :
void _internal_set_data_type(::milvus::proto::schema::DataType value);
public:
// .milvus.proto.schema.FieldState state = 9;
void clear_state();
::milvus::proto::schema::FieldState state() const;
void set_state(::milvus::proto::schema::FieldState value);
private:
::milvus::proto::schema::FieldState _internal_state() const;
void _internal_set_state(::milvus::proto::schema::FieldState value);
public:
// bool is_primary_key = 3;
void clear_is_primary_key();
bool is_primary_key() const;
@ -443,13 +454,22 @@ class FieldSchema final :
void _internal_set_autoid(bool value);
public:
// .milvus.proto.schema.FieldState state = 9;
void clear_state();
::milvus::proto::schema::FieldState state() const;
void set_state(::milvus::proto::schema::FieldState value);
// bool is_dynamic = 12;
void clear_is_dynamic();
bool is_dynamic() const;
void set_is_dynamic(bool value);
private:
::milvus::proto::schema::FieldState _internal_state() const;
void _internal_set_state(::milvus::proto::schema::FieldState value);
bool _internal_is_dynamic() const;
void _internal_set_is_dynamic(bool value);
public:
// bool is_partition_key = 13;
void clear_is_partition_key();
bool is_partition_key() const;
void set_is_partition_key(bool value);
private:
bool _internal_is_partition_key() const;
void _internal_set_is_partition_key(bool value);
public:
// .milvus.proto.schema.DataType element_type = 10;
@ -476,9 +496,11 @@ class FieldSchema final :
::milvus::proto::schema::ValueField* default_value_;
int64_t fieldid_;
int data_type_;
int state_;
bool is_primary_key_;
bool autoid_;
int state_;
bool is_dynamic_;
bool is_partition_key_;
int element_type_;
mutable ::PROTOBUF_NAMESPACE_ID::internal::CachedSize _cached_size_;
};
@ -612,6 +634,7 @@ class CollectionSchema final :
kNameFieldNumber = 1,
kDescriptionFieldNumber = 2,
kAutoIDFieldNumber = 3,
kEnableDynamicFieldFieldNumber = 5,
};
// repeated .milvus.proto.schema.FieldSchema fields = 4;
int fields_size() const;
@ -668,6 +691,15 @@ class CollectionSchema final :
void _internal_set_autoid(bool value);
public:
// bool enable_dynamic_field = 5;
void clear_enable_dynamic_field();
bool enable_dynamic_field() const;
void set_enable_dynamic_field(bool value);
private:
bool _internal_enable_dynamic_field() const;
void _internal_set_enable_dynamic_field(bool value);
public:
// @@protoc_insertion_point(class_scope:milvus.proto.schema.CollectionSchema)
private:
class _Internal;
@ -680,6 +712,7 @@ class CollectionSchema final :
::PROTOBUF_NAMESPACE_ID::internal::ArenaStringPtr name_;
::PROTOBUF_NAMESPACE_ID::internal::ArenaStringPtr description_;
bool autoid_;
bool enable_dynamic_field_;
mutable ::PROTOBUF_NAMESPACE_ID::internal::CachedSize _cached_size_;
};
union { Impl_ _impl_; };
@ -4060,6 +4093,46 @@ inline void FieldSchema::set_allocated_default_value(::milvus::proto::schema::Va
// @@protoc_insertion_point(field_set_allocated:milvus.proto.schema.FieldSchema.default_value)
}
// bool is_dynamic = 12;
inline void FieldSchema::clear_is_dynamic() {
_impl_.is_dynamic_ = false;
}
inline bool FieldSchema::_internal_is_dynamic() const {
return _impl_.is_dynamic_;
}
inline bool FieldSchema::is_dynamic() const {
// @@protoc_insertion_point(field_get:milvus.proto.schema.FieldSchema.is_dynamic)
return _internal_is_dynamic();
}
inline void FieldSchema::_internal_set_is_dynamic(bool value) {
_impl_.is_dynamic_ = value;
}
inline void FieldSchema::set_is_dynamic(bool value) {
_internal_set_is_dynamic(value);
// @@protoc_insertion_point(field_set:milvus.proto.schema.FieldSchema.is_dynamic)
}
// bool is_partition_key = 13;
inline void FieldSchema::clear_is_partition_key() {
_impl_.is_partition_key_ = false;
}
inline bool FieldSchema::_internal_is_partition_key() const {
return _impl_.is_partition_key_;
}
inline bool FieldSchema::is_partition_key() const {
// @@protoc_insertion_point(field_get:milvus.proto.schema.FieldSchema.is_partition_key)
return _internal_is_partition_key();
}
inline void FieldSchema::_internal_set_is_partition_key(bool value) {
_impl_.is_partition_key_ = value;
}
inline void FieldSchema::set_is_partition_key(bool value) {
_internal_set_is_partition_key(value);
// @@protoc_insertion_point(field_set:milvus.proto.schema.FieldSchema.is_partition_key)
}
// -------------------------------------------------------------------
// CollectionSchema
@ -4224,6 +4297,26 @@ CollectionSchema::fields() const {
return _impl_.fields_;
}
// bool enable_dynamic_field = 5;
inline void CollectionSchema::clear_enable_dynamic_field() {
_impl_.enable_dynamic_field_ = false;
}
inline bool CollectionSchema::_internal_enable_dynamic_field() const {
return _impl_.enable_dynamic_field_;
}
inline bool CollectionSchema::enable_dynamic_field() const {
// @@protoc_insertion_point(field_get:milvus.proto.schema.CollectionSchema.enable_dynamic_field)
return _internal_enable_dynamic_field();
}
inline void CollectionSchema::_internal_set_enable_dynamic_field(bool value) {
_impl_.enable_dynamic_field_ = value;
}
inline void CollectionSchema::set_enable_dynamic_field(bool value) {
_internal_set_enable_dynamic_field(value);
// @@protoc_insertion_point(field_set:milvus.proto.schema.CollectionSchema.enable_dynamic_field)
}
// -------------------------------------------------------------------
// BoolArray

View File

@ -26,6 +26,7 @@ type Collection struct {
Aliases []string // TODO: deprecate this.
Properties []*commonpb.KeyValuePair
State pb.CollectionState
EnableDynamicField bool
}
func (c Collection) Available() bool {
@ -50,6 +51,7 @@ func (c Collection) Clone() *Collection {
Aliases: common.CloneStringList(c.Aliases),
Properties: common.CloneKeyValuePairs(c.Properties),
State: c.State,
EnableDynamicField: c.EnableDynamicField,
}
}
@ -68,7 +70,8 @@ func (c Collection) Equal(other Collection) bool {
c.AutoID == other.AutoID &&
CheckFieldsEqual(c.Fields, other.Fields) &&
c.ShardsNum == other.ShardsNum &&
c.ConsistencyLevel == other.ConsistencyLevel
c.ConsistencyLevel == other.ConsistencyLevel &&
c.EnableDynamicField == other.EnableDynamicField
}
func UnmarshalCollectionModel(coll *pb.CollectionInfo) *Collection {
@ -101,6 +104,7 @@ func UnmarshalCollectionModel(coll *pb.CollectionInfo) *Collection {
StartPositions: coll.StartPositions,
State: coll.State,
Properties: coll.Properties,
EnableDynamicField: coll.Schema.EnableDynamicField,
}
}
@ -139,9 +143,10 @@ func marshalCollectionModelWithConfig(coll *Collection, c *config) *pb.Collectio
}
collSchema := &schemapb.CollectionSchema{
Name: coll.Name,
Description: coll.Description,
AutoID: coll.AutoID,
Name: coll.Name,
Description: coll.Description,
AutoID: coll.AutoID,
EnableDynamicField: coll.EnableDynamicField,
}
if c.withFields {

View File

@ -17,6 +17,7 @@ type Field struct {
IndexParams []*commonpb.KeyValuePair
AutoID bool
State schemapb.FieldState
IsDynamic bool
}
func (f Field) Available() bool {
@ -34,6 +35,7 @@ func (f Field) Clone() *Field {
IndexParams: common.CloneKeyValuePairs(f.IndexParams),
AutoID: f.AutoID,
State: f.State,
IsDynamic: f.IsDynamic,
}
}
@ -58,7 +60,8 @@ func (f Field) Equal(other Field) bool {
f.DataType == other.DataType &&
checkParamsEqual(f.TypeParams, f.TypeParams) &&
checkParamsEqual(f.IndexParams, other.IndexParams) &&
f.AutoID == other.AutoID
f.AutoID == other.AutoID &&
f.IsDynamic == other.IsDynamic
}
func CheckFieldsEqual(fieldsA, fieldsB []*Field) bool {
@ -88,6 +91,7 @@ func MarshalFieldModel(field *Field) *schemapb.FieldSchema {
TypeParams: field.TypeParams,
IndexParams: field.IndexParams,
AutoID: field.AutoID,
IsDynamic: field.IsDynamic,
}
}
@ -117,6 +121,7 @@ func UnmarshalFieldModel(fieldSchema *schemapb.FieldSchema) *Field {
TypeParams: fieldSchema.TypeParams,
IndexParams: fieldSchema.IndexParams,
AutoID: fieldSchema.AutoID,
IsDynamic: fieldSchema.IsDynamic,
}
}

View File

@ -82,7 +82,7 @@ FloatingConstant:
DecimalFloatingConstant
| HexadecimalFloatingConstant;
Identifier: Nondigit (Nondigit | Digit)*;
Identifier: Nondigit (Nondigit | Digit)* | '$meta';
StringLiteral: EncodingPrefix? '"' SCharSequence? '"';
JSONIdentifier: Identifier('[' (StringLiteral | DecimalConstant) ']')+;

File diff suppressed because one or more lines are too long

View File

@ -14,7 +14,7 @@ var _ = fmt.Printf
var _ = unicode.IsLetter
var serializedLexerAtn = []uint16{
3, 24715, 42794, 33075, 47597, 16764, 15335, 30598, 22884, 2, 41, 477,
3, 24715, 42794, 33075, 47597, 16764, 15335, 30598, 22884, 2, 41, 484,
8, 1, 4, 2, 9, 2, 4, 3, 9, 3, 4, 4, 9, 4, 4, 5, 9, 5, 4, 6, 9, 6, 4, 7,
9, 7, 4, 8, 9, 8, 4, 9, 9, 9, 4, 10, 9, 10, 4, 11, 9, 11, 4, 12, 9, 12,
4, 13, 9, 13, 4, 14, 9, 14, 4, 15, 9, 15, 4, 16, 9, 16, 4, 17, 9, 17, 4,
@ -43,198 +43,201 @@ var serializedLexerAtn = []uint16{
3, 33, 3, 33, 3, 33, 3, 33, 3, 33, 3, 33, 3, 33, 3, 33, 3, 33, 3, 33, 5,
33, 271, 10, 33, 3, 34, 3, 34, 3, 34, 3, 34, 5, 34, 277, 10, 34, 3, 35,
3, 35, 5, 35, 281, 10, 35, 3, 36, 3, 36, 3, 36, 7, 36, 286, 10, 36, 12,
36, 14, 36, 289, 11, 36, 3, 37, 5, 37, 292, 10, 37, 3, 37, 3, 37, 5, 37,
296, 10, 37, 3, 37, 3, 37, 3, 38, 3, 38, 3, 38, 3, 38, 5, 38, 304, 10,
38, 3, 38, 3, 38, 6, 38, 308, 10, 38, 13, 38, 14, 38, 309, 3, 39, 3, 39,
3, 39, 5, 39, 315, 10, 39, 3, 40, 6, 40, 318, 10, 40, 13, 40, 14, 40, 319,
3, 41, 3, 41, 3, 41, 3, 41, 3, 41, 3, 41, 3, 41, 5, 41, 329, 10, 41, 3,
42, 3, 42, 3, 43, 3, 43, 3, 44, 3, 44, 3, 44, 6, 44, 338, 10, 44, 13, 44,
14, 44, 339, 3, 45, 3, 45, 7, 45, 344, 10, 45, 12, 45, 14, 45, 347, 11,
45, 3, 45, 5, 45, 350, 10, 45, 3, 46, 3, 46, 7, 46, 354, 10, 46, 12, 46,
14, 46, 357, 11, 46, 3, 47, 3, 47, 3, 47, 3, 47, 3, 48, 3, 48, 3, 49, 3,
49, 3, 50, 3, 50, 3, 51, 3, 51, 3, 51, 3, 51, 3, 51, 3, 52, 3, 52, 3, 52,
3, 52, 3, 52, 3, 52, 3, 52, 3, 52, 3, 52, 3, 52, 5, 52, 384, 10, 52, 3,
53, 3, 53, 5, 53, 388, 10, 53, 3, 53, 3, 53, 3, 53, 5, 53, 393, 10, 53,
3, 54, 3, 54, 3, 54, 3, 54, 5, 54, 399, 10, 54, 3, 54, 3, 54, 3, 55, 5,
55, 404, 10, 55, 3, 55, 3, 55, 3, 55, 3, 55, 3, 55, 5, 55, 411, 10, 55,
3, 56, 3, 56, 5, 56, 415, 10, 56, 3, 56, 3, 56, 3, 57, 6, 57, 420, 10,
57, 13, 57, 14, 57, 421, 3, 58, 5, 58, 425, 10, 58, 3, 58, 3, 58, 3, 58,
3, 58, 3, 58, 5, 58, 432, 10, 58, 3, 59, 6, 59, 435, 10, 59, 13, 59, 14,
59, 436, 3, 60, 3, 60, 5, 60, 441, 10, 60, 3, 60, 3, 60, 3, 61, 3, 61,
3, 61, 3, 61, 3, 61, 5, 61, 450, 10, 61, 3, 61, 5, 61, 453, 10, 61, 3,
61, 3, 61, 3, 61, 3, 61, 3, 61, 5, 61, 460, 10, 61, 3, 62, 6, 62, 463,
10, 62, 13, 62, 14, 62, 464, 3, 62, 3, 62, 3, 63, 3, 63, 5, 63, 471, 10,
63, 3, 63, 5, 63, 474, 10, 63, 3, 63, 3, 63, 2, 2, 64, 3, 3, 5, 4, 7, 5,
9, 6, 11, 7, 13, 8, 15, 9, 17, 10, 19, 11, 21, 12, 23, 13, 25, 14, 27,
15, 29, 16, 31, 17, 33, 18, 35, 19, 37, 20, 39, 21, 41, 22, 43, 23, 45,
24, 47, 25, 49, 26, 51, 27, 53, 28, 55, 29, 57, 30, 59, 31, 61, 32, 63,
33, 65, 34, 67, 35, 69, 36, 71, 37, 73, 38, 75, 39, 77, 2, 79, 2, 81, 2,
83, 2, 85, 2, 87, 2, 89, 2, 91, 2, 93, 2, 95, 2, 97, 2, 99, 2, 101, 2,
103, 2, 105, 2, 107, 2, 109, 2, 111, 2, 113, 2, 115, 2, 117, 2, 119, 2,
121, 2, 123, 40, 125, 41, 3, 2, 17, 5, 2, 78, 78, 87, 87, 119, 119, 6,
2, 12, 12, 15, 15, 36, 36, 94, 94, 5, 2, 67, 92, 97, 97, 99, 124, 3, 2,
50, 59, 4, 2, 68, 68, 100, 100, 3, 2, 50, 51, 4, 2, 90, 90, 122, 122, 3,
2, 51, 59, 3, 2, 50, 57, 5, 2, 50, 59, 67, 72, 99, 104, 4, 2, 71, 71, 103,
103, 4, 2, 45, 45, 47, 47, 4, 2, 82, 82, 114, 114, 12, 2, 36, 36, 41, 41,
65, 65, 94, 94, 99, 100, 104, 104, 112, 112, 116, 116, 118, 118, 120, 120,
4, 2, 11, 11, 34, 34, 2, 504, 2, 3, 3, 2, 2, 2, 2, 5, 3, 2, 2, 2, 2, 7,
3, 2, 2, 2, 2, 9, 3, 2, 2, 2, 2, 11, 3, 2, 2, 2, 2, 13, 3, 2, 2, 2, 2,
15, 3, 2, 2, 2, 2, 17, 3, 2, 2, 2, 2, 19, 3, 2, 2, 2, 2, 21, 3, 2, 2, 2,
2, 23, 3, 2, 2, 2, 2, 25, 3, 2, 2, 2, 2, 27, 3, 2, 2, 2, 2, 29, 3, 2, 2,
2, 2, 31, 3, 2, 2, 2, 2, 33, 3, 2, 2, 2, 2, 35, 3, 2, 2, 2, 2, 37, 3, 2,
2, 2, 2, 39, 3, 2, 2, 2, 2, 41, 3, 2, 2, 2, 2, 43, 3, 2, 2, 2, 2, 45, 3,
2, 2, 2, 2, 47, 3, 2, 2, 2, 2, 49, 3, 2, 2, 2, 2, 51, 3, 2, 2, 2, 2, 53,
3, 2, 2, 2, 2, 55, 3, 2, 2, 2, 2, 57, 3, 2, 2, 2, 2, 59, 3, 2, 2, 2, 2,
61, 3, 2, 2, 2, 2, 63, 3, 2, 2, 2, 2, 65, 3, 2, 2, 2, 2, 67, 3, 2, 2, 2,
2, 69, 3, 2, 2, 2, 2, 71, 3, 2, 2, 2, 2, 73, 3, 2, 2, 2, 2, 75, 3, 2, 2,
2, 2, 123, 3, 2, 2, 2, 2, 125, 3, 2, 2, 2, 3, 127, 3, 2, 2, 2, 5, 129,
3, 2, 2, 2, 7, 131, 3, 2, 2, 2, 9, 133, 3, 2, 2, 2, 11, 135, 3, 2, 2, 2,
13, 137, 3, 2, 2, 2, 15, 139, 3, 2, 2, 2, 17, 142, 3, 2, 2, 2, 19, 144,
3, 2, 2, 2, 21, 147, 3, 2, 2, 2, 23, 150, 3, 2, 2, 2, 25, 161, 3, 2, 2,
2, 27, 175, 3, 2, 2, 2, 29, 177, 3, 2, 2, 2, 31, 179, 3, 2, 2, 2, 33, 181,
3, 2, 2, 2, 35, 183, 3, 2, 2, 2, 37, 185, 3, 2, 2, 2, 39, 187, 3, 2, 2,
2, 41, 190, 3, 2, 2, 2, 43, 193, 3, 2, 2, 2, 45, 196, 3, 2, 2, 2, 47, 198,
3, 2, 2, 2, 49, 200, 3, 2, 2, 2, 51, 207, 3, 2, 2, 2, 53, 213, 3, 2, 2,
2, 55, 215, 3, 2, 2, 2, 57, 221, 3, 2, 2, 2, 59, 223, 3, 2, 2, 2, 61, 226,
3, 2, 2, 2, 63, 233, 3, 2, 2, 2, 65, 270, 3, 2, 2, 2, 67, 276, 3, 2, 2,
2, 69, 280, 3, 2, 2, 2, 71, 282, 3, 2, 2, 2, 73, 291, 3, 2, 2, 2, 75, 299,
3, 2, 2, 2, 77, 314, 3, 2, 2, 2, 79, 317, 3, 2, 2, 2, 81, 328, 3, 2, 2,
2, 83, 330, 3, 2, 2, 2, 85, 332, 3, 2, 2, 2, 87, 334, 3, 2, 2, 2, 89, 349,
3, 2, 2, 2, 91, 351, 3, 2, 2, 2, 93, 358, 3, 2, 2, 2, 95, 362, 3, 2, 2,
2, 97, 364, 3, 2, 2, 2, 99, 366, 3, 2, 2, 2, 101, 368, 3, 2, 2, 2, 103,
383, 3, 2, 2, 2, 105, 392, 3, 2, 2, 2, 107, 394, 3, 2, 2, 2, 109, 410,
3, 2, 2, 2, 111, 412, 3, 2, 2, 2, 113, 419, 3, 2, 2, 2, 115, 431, 3, 2,
2, 2, 117, 434, 3, 2, 2, 2, 119, 438, 3, 2, 2, 2, 121, 459, 3, 2, 2, 2,
123, 462, 3, 2, 2, 2, 125, 473, 3, 2, 2, 2, 127, 128, 7, 42, 2, 2, 128,
4, 3, 2, 2, 2, 129, 130, 7, 43, 2, 2, 130, 6, 3, 2, 2, 2, 131, 132, 7,
93, 2, 2, 132, 8, 3, 2, 2, 2, 133, 134, 7, 46, 2, 2, 134, 10, 3, 2, 2,
2, 135, 136, 7, 95, 2, 2, 136, 12, 3, 2, 2, 2, 137, 138, 7, 62, 2, 2, 138,
14, 3, 2, 2, 2, 139, 140, 7, 62, 2, 2, 140, 141, 7, 63, 2, 2, 141, 16,
3, 2, 2, 2, 142, 143, 7, 64, 2, 2, 143, 18, 3, 2, 2, 2, 144, 145, 7, 64,
2, 2, 145, 146, 7, 63, 2, 2, 146, 20, 3, 2, 2, 2, 147, 148, 7, 63, 2, 2,
148, 149, 7, 63, 2, 2, 149, 22, 3, 2, 2, 2, 150, 151, 7, 35, 2, 2, 151,
152, 7, 63, 2, 2, 152, 24, 3, 2, 2, 2, 153, 154, 7, 110, 2, 2, 154, 155,
7, 107, 2, 2, 155, 156, 7, 109, 2, 2, 156, 162, 7, 103, 2, 2, 157, 158,
7, 78, 2, 2, 158, 159, 7, 75, 2, 2, 159, 160, 7, 77, 2, 2, 160, 162, 7,
71, 2, 2, 161, 153, 3, 2, 2, 2, 161, 157, 3, 2, 2, 2, 162, 26, 3, 2, 2,
2, 163, 164, 7, 103, 2, 2, 164, 165, 7, 122, 2, 2, 165, 166, 7, 107, 2,
2, 166, 167, 7, 117, 2, 2, 167, 168, 7, 118, 2, 2, 168, 176, 7, 117, 2,
2, 169, 170, 7, 71, 2, 2, 170, 171, 7, 90, 2, 2, 171, 172, 7, 75, 2, 2,
172, 173, 7, 85, 2, 2, 173, 174, 7, 86, 2, 2, 174, 176, 7, 85, 2, 2, 175,
163, 3, 2, 2, 2, 175, 169, 3, 2, 2, 2, 176, 28, 3, 2, 2, 2, 177, 178, 7,
45, 2, 2, 178, 30, 3, 2, 2, 2, 179, 180, 7, 47, 2, 2, 180, 32, 3, 2, 2,
2, 181, 182, 7, 44, 2, 2, 182, 34, 3, 2, 2, 2, 183, 184, 7, 49, 2, 2, 184,
36, 3, 2, 2, 2, 185, 186, 7, 39, 2, 2, 186, 38, 3, 2, 2, 2, 187, 188, 7,
44, 2, 2, 188, 189, 7, 44, 2, 2, 189, 40, 3, 2, 2, 2, 190, 191, 7, 62,
2, 2, 191, 192, 7, 62, 2, 2, 192, 42, 3, 2, 2, 2, 193, 194, 7, 64, 2, 2,
194, 195, 7, 64, 2, 2, 195, 44, 3, 2, 2, 2, 196, 197, 7, 40, 2, 2, 197,
46, 3, 2, 2, 2, 198, 199, 7, 126, 2, 2, 199, 48, 3, 2, 2, 2, 200, 201,
7, 96, 2, 2, 201, 50, 3, 2, 2, 2, 202, 203, 7, 40, 2, 2, 203, 208, 7, 40,
2, 2, 204, 205, 7, 99, 2, 2, 205, 206, 7, 112, 2, 2, 206, 208, 7, 102,
2, 2, 207, 202, 3, 2, 2, 2, 207, 204, 3, 2, 2, 2, 208, 52, 3, 2, 2, 2,
209, 210, 7, 126, 2, 2, 210, 214, 7, 126, 2, 2, 211, 212, 7, 113, 2, 2,
212, 214, 7, 116, 2, 2, 213, 209, 3, 2, 2, 2, 213, 211, 3, 2, 2, 2, 214,
54, 3, 2, 2, 2, 215, 216, 7, 128, 2, 2, 216, 56, 3, 2, 2, 2, 217, 222,
7, 35, 2, 2, 218, 219, 7, 112, 2, 2, 219, 220, 7, 113, 2, 2, 220, 222,
7, 118, 2, 2, 221, 217, 3, 2, 2, 2, 221, 218, 3, 2, 2, 2, 222, 58, 3, 2,
2, 2, 223, 224, 7, 107, 2, 2, 224, 225, 7, 112, 2, 2, 225, 60, 3, 2, 2,
2, 226, 227, 7, 112, 2, 2, 227, 228, 7, 113, 2, 2, 228, 229, 7, 118, 2,
2, 229, 230, 7, 34, 2, 2, 230, 231, 7, 107, 2, 2, 231, 232, 7, 112, 2,
2, 232, 62, 3, 2, 2, 2, 233, 238, 7, 93, 2, 2, 234, 237, 5, 123, 62, 2,
235, 237, 5, 125, 63, 2, 236, 234, 3, 2, 2, 2, 236, 235, 3, 2, 2, 2, 237,
240, 3, 2, 2, 2, 238, 236, 3, 2, 2, 2, 238, 239, 3, 2, 2, 2, 239, 241,
3, 2, 2, 2, 240, 238, 3, 2, 2, 2, 241, 242, 7, 95, 2, 2, 242, 64, 3, 2,
2, 2, 243, 244, 7, 118, 2, 2, 244, 245, 7, 116, 2, 2, 245, 246, 7, 119,
2, 2, 246, 271, 7, 103, 2, 2, 247, 248, 7, 86, 2, 2, 248, 249, 7, 116,
2, 2, 249, 250, 7, 119, 2, 2, 250, 271, 7, 103, 2, 2, 251, 252, 7, 86,
2, 2, 252, 253, 7, 84, 2, 2, 253, 254, 7, 87, 2, 2, 254, 271, 7, 71, 2,
2, 255, 256, 7, 104, 2, 2, 256, 257, 7, 99, 2, 2, 257, 258, 7, 110, 2,
2, 258, 259, 7, 117, 2, 2, 259, 271, 7, 103, 2, 2, 260, 261, 7, 72, 2,
2, 261, 262, 7, 99, 2, 2, 262, 263, 7, 110, 2, 2, 263, 264, 7, 117, 2,
2, 264, 271, 7, 103, 2, 2, 265, 266, 7, 72, 2, 2, 266, 267, 7, 67, 2, 2,
267, 268, 7, 78, 2, 2, 268, 269, 7, 85, 2, 2, 269, 271, 7, 71, 2, 2, 270,
243, 3, 2, 2, 2, 270, 247, 3, 2, 2, 2, 270, 251, 3, 2, 2, 2, 270, 255,
3, 2, 2, 2, 270, 260, 3, 2, 2, 2, 270, 265, 3, 2, 2, 2, 271, 66, 3, 2,
2, 2, 272, 277, 5, 89, 45, 2, 273, 277, 5, 91, 46, 2, 274, 277, 5, 93,
47, 2, 275, 277, 5, 87, 44, 2, 276, 272, 3, 2, 2, 2, 276, 273, 3, 2, 2,
2, 276, 274, 3, 2, 2, 2, 276, 275, 3, 2, 2, 2, 277, 68, 3, 2, 2, 2, 278,
281, 5, 105, 53, 2, 279, 281, 5, 107, 54, 2, 280, 278, 3, 2, 2, 2, 280,
279, 3, 2, 2, 2, 281, 70, 3, 2, 2, 2, 282, 287, 5, 83, 42, 2, 283, 286,
5, 83, 42, 2, 284, 286, 5, 85, 43, 2, 285, 283, 3, 2, 2, 2, 285, 284, 3,
2, 2, 2, 286, 289, 3, 2, 2, 2, 287, 285, 3, 2, 2, 2, 287, 288, 3, 2, 2,
2, 288, 72, 3, 2, 2, 2, 289, 287, 3, 2, 2, 2, 290, 292, 5, 77, 39, 2, 291,
290, 3, 2, 2, 2, 291, 292, 3, 2, 2, 2, 292, 293, 3, 2, 2, 2, 293, 295,
7, 36, 2, 2, 294, 296, 5, 79, 40, 2, 295, 294, 3, 2, 2, 2, 295, 296, 3,
2, 2, 2, 296, 297, 3, 2, 2, 2, 297, 298, 7, 36, 2, 2, 298, 74, 3, 2, 2,
2, 299, 307, 5, 71, 36, 2, 300, 303, 7, 93, 2, 2, 301, 304, 5, 73, 37,
2, 302, 304, 5, 89, 45, 2, 303, 301, 3, 2, 2, 2, 303, 302, 3, 2, 2, 2,
304, 305, 3, 2, 2, 2, 305, 306, 7, 95, 2, 2, 306, 308, 3, 2, 2, 2, 307,
300, 3, 2, 2, 2, 308, 309, 3, 2, 2, 2, 309, 307, 3, 2, 2, 2, 309, 310,
3, 2, 2, 2, 310, 76, 3, 2, 2, 2, 311, 312, 7, 119, 2, 2, 312, 315, 7, 58,
2, 2, 313, 315, 9, 2, 2, 2, 314, 311, 3, 2, 2, 2, 314, 313, 3, 2, 2, 2,
315, 78, 3, 2, 2, 2, 316, 318, 5, 81, 41, 2, 317, 316, 3, 2, 2, 2, 318,
319, 3, 2, 2, 2, 319, 317, 3, 2, 2, 2, 319, 320, 3, 2, 2, 2, 320, 80, 3,
2, 2, 2, 321, 329, 10, 3, 2, 2, 322, 329, 5, 121, 61, 2, 323, 324, 7, 94,
2, 2, 324, 329, 7, 12, 2, 2, 325, 326, 7, 94, 2, 2, 326, 327, 7, 15, 2,
2, 327, 329, 7, 12, 2, 2, 328, 321, 3, 2, 2, 2, 328, 322, 3, 2, 2, 2, 328,
323, 3, 2, 2, 2, 328, 325, 3, 2, 2, 2, 329, 82, 3, 2, 2, 2, 330, 331, 9,
4, 2, 2, 331, 84, 3, 2, 2, 2, 332, 333, 9, 5, 2, 2, 333, 86, 3, 2, 2, 2,
334, 335, 7, 50, 2, 2, 335, 337, 9, 6, 2, 2, 336, 338, 9, 7, 2, 2, 337,
336, 3, 2, 2, 2, 338, 339, 3, 2, 2, 2, 339, 337, 3, 2, 2, 2, 339, 340,
3, 2, 2, 2, 340, 88, 3, 2, 2, 2, 341, 345, 5, 95, 48, 2, 342, 344, 5, 85,
43, 2, 343, 342, 3, 2, 2, 2, 344, 347, 3, 2, 2, 2, 345, 343, 3, 2, 2, 2,
345, 346, 3, 2, 2, 2, 346, 350, 3, 2, 2, 2, 347, 345, 3, 2, 2, 2, 348,
350, 7, 50, 2, 2, 349, 341, 3, 2, 2, 2, 349, 348, 3, 2, 2, 2, 350, 90,
3, 2, 2, 2, 351, 355, 7, 50, 2, 2, 352, 354, 5, 97, 49, 2, 353, 352, 3,
2, 2, 2, 354, 357, 3, 2, 2, 2, 355, 353, 3, 2, 2, 2, 355, 356, 3, 2, 2,
2, 356, 92, 3, 2, 2, 2, 357, 355, 3, 2, 2, 2, 358, 359, 7, 50, 2, 2, 359,
360, 9, 8, 2, 2, 360, 361, 5, 117, 59, 2, 361, 94, 3, 2, 2, 2, 362, 363,
9, 9, 2, 2, 363, 96, 3, 2, 2, 2, 364, 365, 9, 10, 2, 2, 365, 98, 3, 2,
2, 2, 366, 367, 9, 11, 2, 2, 367, 100, 3, 2, 2, 2, 368, 369, 5, 99, 50,
2, 369, 370, 5, 99, 50, 2, 370, 371, 5, 99, 50, 2, 371, 372, 5, 99, 50,
2, 372, 102, 3, 2, 2, 2, 373, 374, 7, 94, 2, 2, 374, 375, 7, 119, 2, 2,
375, 376, 3, 2, 2, 2, 376, 384, 5, 101, 51, 2, 377, 378, 7, 94, 2, 2, 378,
379, 7, 87, 2, 2, 379, 380, 3, 2, 2, 2, 380, 381, 5, 101, 51, 2, 381, 382,
5, 101, 51, 2, 382, 384, 3, 2, 2, 2, 383, 373, 3, 2, 2, 2, 383, 377, 3,
2, 2, 2, 384, 104, 3, 2, 2, 2, 385, 387, 5, 109, 55, 2, 386, 388, 5, 111,
56, 2, 387, 386, 3, 2, 2, 2, 387, 388, 3, 2, 2, 2, 388, 393, 3, 2, 2, 2,
389, 390, 5, 113, 57, 2, 390, 391, 5, 111, 56, 2, 391, 393, 3, 2, 2, 2,
392, 385, 3, 2, 2, 2, 392, 389, 3, 2, 2, 2, 393, 106, 3, 2, 2, 2, 394,
395, 7, 50, 2, 2, 395, 398, 9, 8, 2, 2, 396, 399, 5, 115, 58, 2, 397, 399,
5, 117, 59, 2, 398, 396, 3, 2, 2, 2, 398, 397, 3, 2, 2, 2, 399, 400, 3,
2, 2, 2, 400, 401, 5, 119, 60, 2, 401, 108, 3, 2, 2, 2, 402, 404, 5, 113,
57, 2, 403, 402, 3, 2, 2, 2, 403, 404, 3, 2, 2, 2, 404, 405, 3, 2, 2, 2,
405, 406, 7, 48, 2, 2, 406, 411, 5, 113, 57, 2, 407, 408, 5, 113, 57, 2,
408, 409, 7, 48, 2, 2, 409, 411, 3, 2, 2, 2, 410, 403, 3, 2, 2, 2, 410,
407, 3, 2, 2, 2, 411, 110, 3, 2, 2, 2, 412, 414, 9, 12, 2, 2, 413, 415,
9, 13, 2, 2, 414, 413, 3, 2, 2, 2, 414, 415, 3, 2, 2, 2, 415, 416, 3, 2,
2, 2, 416, 417, 5, 113, 57, 2, 417, 112, 3, 2, 2, 2, 418, 420, 5, 85, 43,
2, 419, 418, 3, 2, 2, 2, 420, 421, 3, 2, 2, 2, 421, 419, 3, 2, 2, 2, 421,
422, 3, 2, 2, 2, 422, 114, 3, 2, 2, 2, 423, 425, 5, 117, 59, 2, 424, 423,
3, 2, 2, 2, 424, 425, 3, 2, 2, 2, 425, 426, 3, 2, 2, 2, 426, 427, 7, 48,
2, 2, 427, 432, 5, 117, 59, 2, 428, 429, 5, 117, 59, 2, 429, 430, 7, 48,
2, 2, 430, 432, 3, 2, 2, 2, 431, 424, 3, 2, 2, 2, 431, 428, 3, 2, 2, 2,
432, 116, 3, 2, 2, 2, 433, 435, 5, 99, 50, 2, 434, 433, 3, 2, 2, 2, 435,
436, 3, 2, 2, 2, 436, 434, 3, 2, 2, 2, 436, 437, 3, 2, 2, 2, 437, 118,
3, 2, 2, 2, 438, 440, 9, 14, 2, 2, 439, 441, 9, 13, 2, 2, 440, 439, 3,
2, 2, 2, 440, 441, 3, 2, 2, 2, 441, 442, 3, 2, 2, 2, 442, 443, 5, 113,
57, 2, 443, 120, 3, 2, 2, 2, 444, 445, 7, 94, 2, 2, 445, 460, 9, 15, 2,
2, 446, 447, 7, 94, 2, 2, 447, 449, 5, 97, 49, 2, 448, 450, 5, 97, 49,
2, 449, 448, 3, 2, 2, 2, 449, 450, 3, 2, 2, 2, 450, 452, 3, 2, 2, 2, 451,
453, 5, 97, 49, 2, 452, 451, 3, 2, 2, 2, 452, 453, 3, 2, 2, 2, 453, 460,
3, 2, 2, 2, 454, 455, 7, 94, 2, 2, 455, 456, 7, 122, 2, 2, 456, 457, 3,
2, 2, 2, 457, 460, 5, 117, 59, 2, 458, 460, 5, 103, 52, 2, 459, 444, 3,
2, 2, 2, 459, 446, 3, 2, 2, 2, 459, 454, 3, 2, 2, 2, 459, 458, 3, 2, 2,
2, 460, 122, 3, 2, 2, 2, 461, 463, 9, 16, 2, 2, 462, 461, 3, 2, 2, 2, 463,
464, 3, 2, 2, 2, 464, 462, 3, 2, 2, 2, 464, 465, 3, 2, 2, 2, 465, 466,
3, 2, 2, 2, 466, 467, 8, 62, 2, 2, 467, 124, 3, 2, 2, 2, 468, 470, 7, 15,
2, 2, 469, 471, 7, 12, 2, 2, 470, 469, 3, 2, 2, 2, 470, 471, 3, 2, 2, 2,
471, 474, 3, 2, 2, 2, 472, 474, 7, 12, 2, 2, 473, 468, 3, 2, 2, 2, 473,
472, 3, 2, 2, 2, 474, 475, 3, 2, 2, 2, 475, 476, 8, 63, 2, 2, 476, 126,
3, 2, 2, 2, 44, 2, 161, 175, 207, 213, 221, 236, 238, 270, 276, 280, 285,
287, 291, 295, 303, 309, 314, 319, 328, 339, 345, 349, 355, 383, 387, 392,
398, 403, 410, 414, 421, 424, 431, 436, 440, 449, 452, 459, 464, 470, 473,
3, 8, 2, 2,
36, 14, 36, 289, 11, 36, 3, 36, 3, 36, 3, 36, 3, 36, 3, 36, 5, 36, 296,
10, 36, 3, 37, 5, 37, 299, 10, 37, 3, 37, 3, 37, 5, 37, 303, 10, 37, 3,
37, 3, 37, 3, 38, 3, 38, 3, 38, 3, 38, 5, 38, 311, 10, 38, 3, 38, 3, 38,
6, 38, 315, 10, 38, 13, 38, 14, 38, 316, 3, 39, 3, 39, 3, 39, 5, 39, 322,
10, 39, 3, 40, 6, 40, 325, 10, 40, 13, 40, 14, 40, 326, 3, 41, 3, 41, 3,
41, 3, 41, 3, 41, 3, 41, 3, 41, 5, 41, 336, 10, 41, 3, 42, 3, 42, 3, 43,
3, 43, 3, 44, 3, 44, 3, 44, 6, 44, 345, 10, 44, 13, 44, 14, 44, 346, 3,
45, 3, 45, 7, 45, 351, 10, 45, 12, 45, 14, 45, 354, 11, 45, 3, 45, 5, 45,
357, 10, 45, 3, 46, 3, 46, 7, 46, 361, 10, 46, 12, 46, 14, 46, 364, 11,
46, 3, 47, 3, 47, 3, 47, 3, 47, 3, 48, 3, 48, 3, 49, 3, 49, 3, 50, 3, 50,
3, 51, 3, 51, 3, 51, 3, 51, 3, 51, 3, 52, 3, 52, 3, 52, 3, 52, 3, 52, 3,
52, 3, 52, 3, 52, 3, 52, 3, 52, 5, 52, 391, 10, 52, 3, 53, 3, 53, 5, 53,
395, 10, 53, 3, 53, 3, 53, 3, 53, 5, 53, 400, 10, 53, 3, 54, 3, 54, 3,
54, 3, 54, 5, 54, 406, 10, 54, 3, 54, 3, 54, 3, 55, 5, 55, 411, 10, 55,
3, 55, 3, 55, 3, 55, 3, 55, 3, 55, 5, 55, 418, 10, 55, 3, 56, 3, 56, 5,
56, 422, 10, 56, 3, 56, 3, 56, 3, 57, 6, 57, 427, 10, 57, 13, 57, 14, 57,
428, 3, 58, 5, 58, 432, 10, 58, 3, 58, 3, 58, 3, 58, 3, 58, 3, 58, 5, 58,
439, 10, 58, 3, 59, 6, 59, 442, 10, 59, 13, 59, 14, 59, 443, 3, 60, 3,
60, 5, 60, 448, 10, 60, 3, 60, 3, 60, 3, 61, 3, 61, 3, 61, 3, 61, 3, 61,
5, 61, 457, 10, 61, 3, 61, 5, 61, 460, 10, 61, 3, 61, 3, 61, 3, 61, 3,
61, 3, 61, 5, 61, 467, 10, 61, 3, 62, 6, 62, 470, 10, 62, 13, 62, 14, 62,
471, 3, 62, 3, 62, 3, 63, 3, 63, 5, 63, 478, 10, 63, 3, 63, 5, 63, 481,
10, 63, 3, 63, 3, 63, 2, 2, 64, 3, 3, 5, 4, 7, 5, 9, 6, 11, 7, 13, 8, 15,
9, 17, 10, 19, 11, 21, 12, 23, 13, 25, 14, 27, 15, 29, 16, 31, 17, 33,
18, 35, 19, 37, 20, 39, 21, 41, 22, 43, 23, 45, 24, 47, 25, 49, 26, 51,
27, 53, 28, 55, 29, 57, 30, 59, 31, 61, 32, 63, 33, 65, 34, 67, 35, 69,
36, 71, 37, 73, 38, 75, 39, 77, 2, 79, 2, 81, 2, 83, 2, 85, 2, 87, 2, 89,
2, 91, 2, 93, 2, 95, 2, 97, 2, 99, 2, 101, 2, 103, 2, 105, 2, 107, 2, 109,
2, 111, 2, 113, 2, 115, 2, 117, 2, 119, 2, 121, 2, 123, 40, 125, 41, 3,
2, 17, 5, 2, 78, 78, 87, 87, 119, 119, 6, 2, 12, 12, 15, 15, 36, 36, 94,
94, 5, 2, 67, 92, 97, 97, 99, 124, 3, 2, 50, 59, 4, 2, 68, 68, 100, 100,
3, 2, 50, 51, 4, 2, 90, 90, 122, 122, 3, 2, 51, 59, 3, 2, 50, 57, 5, 2,
50, 59, 67, 72, 99, 104, 4, 2, 71, 71, 103, 103, 4, 2, 45, 45, 47, 47,
4, 2, 82, 82, 114, 114, 12, 2, 36, 36, 41, 41, 65, 65, 94, 94, 99, 100,
104, 104, 112, 112, 116, 116, 118, 118, 120, 120, 4, 2, 11, 11, 34, 34,
2, 512, 2, 3, 3, 2, 2, 2, 2, 5, 3, 2, 2, 2, 2, 7, 3, 2, 2, 2, 2, 9, 3,
2, 2, 2, 2, 11, 3, 2, 2, 2, 2, 13, 3, 2, 2, 2, 2, 15, 3, 2, 2, 2, 2, 17,
3, 2, 2, 2, 2, 19, 3, 2, 2, 2, 2, 21, 3, 2, 2, 2, 2, 23, 3, 2, 2, 2, 2,
25, 3, 2, 2, 2, 2, 27, 3, 2, 2, 2, 2, 29, 3, 2, 2, 2, 2, 31, 3, 2, 2, 2,
2, 33, 3, 2, 2, 2, 2, 35, 3, 2, 2, 2, 2, 37, 3, 2, 2, 2, 2, 39, 3, 2, 2,
2, 2, 41, 3, 2, 2, 2, 2, 43, 3, 2, 2, 2, 2, 45, 3, 2, 2, 2, 2, 47, 3, 2,
2, 2, 2, 49, 3, 2, 2, 2, 2, 51, 3, 2, 2, 2, 2, 53, 3, 2, 2, 2, 2, 55, 3,
2, 2, 2, 2, 57, 3, 2, 2, 2, 2, 59, 3, 2, 2, 2, 2, 61, 3, 2, 2, 2, 2, 63,
3, 2, 2, 2, 2, 65, 3, 2, 2, 2, 2, 67, 3, 2, 2, 2, 2, 69, 3, 2, 2, 2, 2,
71, 3, 2, 2, 2, 2, 73, 3, 2, 2, 2, 2, 75, 3, 2, 2, 2, 2, 123, 3, 2, 2,
2, 2, 125, 3, 2, 2, 2, 3, 127, 3, 2, 2, 2, 5, 129, 3, 2, 2, 2, 7, 131,
3, 2, 2, 2, 9, 133, 3, 2, 2, 2, 11, 135, 3, 2, 2, 2, 13, 137, 3, 2, 2,
2, 15, 139, 3, 2, 2, 2, 17, 142, 3, 2, 2, 2, 19, 144, 3, 2, 2, 2, 21, 147,
3, 2, 2, 2, 23, 150, 3, 2, 2, 2, 25, 161, 3, 2, 2, 2, 27, 175, 3, 2, 2,
2, 29, 177, 3, 2, 2, 2, 31, 179, 3, 2, 2, 2, 33, 181, 3, 2, 2, 2, 35, 183,
3, 2, 2, 2, 37, 185, 3, 2, 2, 2, 39, 187, 3, 2, 2, 2, 41, 190, 3, 2, 2,
2, 43, 193, 3, 2, 2, 2, 45, 196, 3, 2, 2, 2, 47, 198, 3, 2, 2, 2, 49, 200,
3, 2, 2, 2, 51, 207, 3, 2, 2, 2, 53, 213, 3, 2, 2, 2, 55, 215, 3, 2, 2,
2, 57, 221, 3, 2, 2, 2, 59, 223, 3, 2, 2, 2, 61, 226, 3, 2, 2, 2, 63, 233,
3, 2, 2, 2, 65, 270, 3, 2, 2, 2, 67, 276, 3, 2, 2, 2, 69, 280, 3, 2, 2,
2, 71, 295, 3, 2, 2, 2, 73, 298, 3, 2, 2, 2, 75, 306, 3, 2, 2, 2, 77, 321,
3, 2, 2, 2, 79, 324, 3, 2, 2, 2, 81, 335, 3, 2, 2, 2, 83, 337, 3, 2, 2,
2, 85, 339, 3, 2, 2, 2, 87, 341, 3, 2, 2, 2, 89, 356, 3, 2, 2, 2, 91, 358,
3, 2, 2, 2, 93, 365, 3, 2, 2, 2, 95, 369, 3, 2, 2, 2, 97, 371, 3, 2, 2,
2, 99, 373, 3, 2, 2, 2, 101, 375, 3, 2, 2, 2, 103, 390, 3, 2, 2, 2, 105,
399, 3, 2, 2, 2, 107, 401, 3, 2, 2, 2, 109, 417, 3, 2, 2, 2, 111, 419,
3, 2, 2, 2, 113, 426, 3, 2, 2, 2, 115, 438, 3, 2, 2, 2, 117, 441, 3, 2,
2, 2, 119, 445, 3, 2, 2, 2, 121, 466, 3, 2, 2, 2, 123, 469, 3, 2, 2, 2,
125, 480, 3, 2, 2, 2, 127, 128, 7, 42, 2, 2, 128, 4, 3, 2, 2, 2, 129, 130,
7, 43, 2, 2, 130, 6, 3, 2, 2, 2, 131, 132, 7, 93, 2, 2, 132, 8, 3, 2, 2,
2, 133, 134, 7, 46, 2, 2, 134, 10, 3, 2, 2, 2, 135, 136, 7, 95, 2, 2, 136,
12, 3, 2, 2, 2, 137, 138, 7, 62, 2, 2, 138, 14, 3, 2, 2, 2, 139, 140, 7,
62, 2, 2, 140, 141, 7, 63, 2, 2, 141, 16, 3, 2, 2, 2, 142, 143, 7, 64,
2, 2, 143, 18, 3, 2, 2, 2, 144, 145, 7, 64, 2, 2, 145, 146, 7, 63, 2, 2,
146, 20, 3, 2, 2, 2, 147, 148, 7, 63, 2, 2, 148, 149, 7, 63, 2, 2, 149,
22, 3, 2, 2, 2, 150, 151, 7, 35, 2, 2, 151, 152, 7, 63, 2, 2, 152, 24,
3, 2, 2, 2, 153, 154, 7, 110, 2, 2, 154, 155, 7, 107, 2, 2, 155, 156, 7,
109, 2, 2, 156, 162, 7, 103, 2, 2, 157, 158, 7, 78, 2, 2, 158, 159, 7,
75, 2, 2, 159, 160, 7, 77, 2, 2, 160, 162, 7, 71, 2, 2, 161, 153, 3, 2,
2, 2, 161, 157, 3, 2, 2, 2, 162, 26, 3, 2, 2, 2, 163, 164, 7, 103, 2, 2,
164, 165, 7, 122, 2, 2, 165, 166, 7, 107, 2, 2, 166, 167, 7, 117, 2, 2,
167, 168, 7, 118, 2, 2, 168, 176, 7, 117, 2, 2, 169, 170, 7, 71, 2, 2,
170, 171, 7, 90, 2, 2, 171, 172, 7, 75, 2, 2, 172, 173, 7, 85, 2, 2, 173,
174, 7, 86, 2, 2, 174, 176, 7, 85, 2, 2, 175, 163, 3, 2, 2, 2, 175, 169,
3, 2, 2, 2, 176, 28, 3, 2, 2, 2, 177, 178, 7, 45, 2, 2, 178, 30, 3, 2,
2, 2, 179, 180, 7, 47, 2, 2, 180, 32, 3, 2, 2, 2, 181, 182, 7, 44, 2, 2,
182, 34, 3, 2, 2, 2, 183, 184, 7, 49, 2, 2, 184, 36, 3, 2, 2, 2, 185, 186,
7, 39, 2, 2, 186, 38, 3, 2, 2, 2, 187, 188, 7, 44, 2, 2, 188, 189, 7, 44,
2, 2, 189, 40, 3, 2, 2, 2, 190, 191, 7, 62, 2, 2, 191, 192, 7, 62, 2, 2,
192, 42, 3, 2, 2, 2, 193, 194, 7, 64, 2, 2, 194, 195, 7, 64, 2, 2, 195,
44, 3, 2, 2, 2, 196, 197, 7, 40, 2, 2, 197, 46, 3, 2, 2, 2, 198, 199, 7,
126, 2, 2, 199, 48, 3, 2, 2, 2, 200, 201, 7, 96, 2, 2, 201, 50, 3, 2, 2,
2, 202, 203, 7, 40, 2, 2, 203, 208, 7, 40, 2, 2, 204, 205, 7, 99, 2, 2,
205, 206, 7, 112, 2, 2, 206, 208, 7, 102, 2, 2, 207, 202, 3, 2, 2, 2, 207,
204, 3, 2, 2, 2, 208, 52, 3, 2, 2, 2, 209, 210, 7, 126, 2, 2, 210, 214,
7, 126, 2, 2, 211, 212, 7, 113, 2, 2, 212, 214, 7, 116, 2, 2, 213, 209,
3, 2, 2, 2, 213, 211, 3, 2, 2, 2, 214, 54, 3, 2, 2, 2, 215, 216, 7, 128,
2, 2, 216, 56, 3, 2, 2, 2, 217, 222, 7, 35, 2, 2, 218, 219, 7, 112, 2,
2, 219, 220, 7, 113, 2, 2, 220, 222, 7, 118, 2, 2, 221, 217, 3, 2, 2, 2,
221, 218, 3, 2, 2, 2, 222, 58, 3, 2, 2, 2, 223, 224, 7, 107, 2, 2, 224,
225, 7, 112, 2, 2, 225, 60, 3, 2, 2, 2, 226, 227, 7, 112, 2, 2, 227, 228,
7, 113, 2, 2, 228, 229, 7, 118, 2, 2, 229, 230, 7, 34, 2, 2, 230, 231,
7, 107, 2, 2, 231, 232, 7, 112, 2, 2, 232, 62, 3, 2, 2, 2, 233, 238, 7,
93, 2, 2, 234, 237, 5, 123, 62, 2, 235, 237, 5, 125, 63, 2, 236, 234, 3,
2, 2, 2, 236, 235, 3, 2, 2, 2, 237, 240, 3, 2, 2, 2, 238, 236, 3, 2, 2,
2, 238, 239, 3, 2, 2, 2, 239, 241, 3, 2, 2, 2, 240, 238, 3, 2, 2, 2, 241,
242, 7, 95, 2, 2, 242, 64, 3, 2, 2, 2, 243, 244, 7, 118, 2, 2, 244, 245,
7, 116, 2, 2, 245, 246, 7, 119, 2, 2, 246, 271, 7, 103, 2, 2, 247, 248,
7, 86, 2, 2, 248, 249, 7, 116, 2, 2, 249, 250, 7, 119, 2, 2, 250, 271,
7, 103, 2, 2, 251, 252, 7, 86, 2, 2, 252, 253, 7, 84, 2, 2, 253, 254, 7,
87, 2, 2, 254, 271, 7, 71, 2, 2, 255, 256, 7, 104, 2, 2, 256, 257, 7, 99,
2, 2, 257, 258, 7, 110, 2, 2, 258, 259, 7, 117, 2, 2, 259, 271, 7, 103,
2, 2, 260, 261, 7, 72, 2, 2, 261, 262, 7, 99, 2, 2, 262, 263, 7, 110, 2,
2, 263, 264, 7, 117, 2, 2, 264, 271, 7, 103, 2, 2, 265, 266, 7, 72, 2,
2, 266, 267, 7, 67, 2, 2, 267, 268, 7, 78, 2, 2, 268, 269, 7, 85, 2, 2,
269, 271, 7, 71, 2, 2, 270, 243, 3, 2, 2, 2, 270, 247, 3, 2, 2, 2, 270,
251, 3, 2, 2, 2, 270, 255, 3, 2, 2, 2, 270, 260, 3, 2, 2, 2, 270, 265,
3, 2, 2, 2, 271, 66, 3, 2, 2, 2, 272, 277, 5, 89, 45, 2, 273, 277, 5, 91,
46, 2, 274, 277, 5, 93, 47, 2, 275, 277, 5, 87, 44, 2, 276, 272, 3, 2,
2, 2, 276, 273, 3, 2, 2, 2, 276, 274, 3, 2, 2, 2, 276, 275, 3, 2, 2, 2,
277, 68, 3, 2, 2, 2, 278, 281, 5, 105, 53, 2, 279, 281, 5, 107, 54, 2,
280, 278, 3, 2, 2, 2, 280, 279, 3, 2, 2, 2, 281, 70, 3, 2, 2, 2, 282, 287,
5, 83, 42, 2, 283, 286, 5, 83, 42, 2, 284, 286, 5, 85, 43, 2, 285, 283,
3, 2, 2, 2, 285, 284, 3, 2, 2, 2, 286, 289, 3, 2, 2, 2, 287, 285, 3, 2,
2, 2, 287, 288, 3, 2, 2, 2, 288, 296, 3, 2, 2, 2, 289, 287, 3, 2, 2, 2,
290, 291, 7, 38, 2, 2, 291, 292, 7, 111, 2, 2, 292, 293, 7, 103, 2, 2,
293, 294, 7, 118, 2, 2, 294, 296, 7, 99, 2, 2, 295, 282, 3, 2, 2, 2, 295,
290, 3, 2, 2, 2, 296, 72, 3, 2, 2, 2, 297, 299, 5, 77, 39, 2, 298, 297,
3, 2, 2, 2, 298, 299, 3, 2, 2, 2, 299, 300, 3, 2, 2, 2, 300, 302, 7, 36,
2, 2, 301, 303, 5, 79, 40, 2, 302, 301, 3, 2, 2, 2, 302, 303, 3, 2, 2,
2, 303, 304, 3, 2, 2, 2, 304, 305, 7, 36, 2, 2, 305, 74, 3, 2, 2, 2, 306,
314, 5, 71, 36, 2, 307, 310, 7, 93, 2, 2, 308, 311, 5, 73, 37, 2, 309,
311, 5, 89, 45, 2, 310, 308, 3, 2, 2, 2, 310, 309, 3, 2, 2, 2, 311, 312,
3, 2, 2, 2, 312, 313, 7, 95, 2, 2, 313, 315, 3, 2, 2, 2, 314, 307, 3, 2,
2, 2, 315, 316, 3, 2, 2, 2, 316, 314, 3, 2, 2, 2, 316, 317, 3, 2, 2, 2,
317, 76, 3, 2, 2, 2, 318, 319, 7, 119, 2, 2, 319, 322, 7, 58, 2, 2, 320,
322, 9, 2, 2, 2, 321, 318, 3, 2, 2, 2, 321, 320, 3, 2, 2, 2, 322, 78, 3,
2, 2, 2, 323, 325, 5, 81, 41, 2, 324, 323, 3, 2, 2, 2, 325, 326, 3, 2,
2, 2, 326, 324, 3, 2, 2, 2, 326, 327, 3, 2, 2, 2, 327, 80, 3, 2, 2, 2,
328, 336, 10, 3, 2, 2, 329, 336, 5, 121, 61, 2, 330, 331, 7, 94, 2, 2,
331, 336, 7, 12, 2, 2, 332, 333, 7, 94, 2, 2, 333, 334, 7, 15, 2, 2, 334,
336, 7, 12, 2, 2, 335, 328, 3, 2, 2, 2, 335, 329, 3, 2, 2, 2, 335, 330,
3, 2, 2, 2, 335, 332, 3, 2, 2, 2, 336, 82, 3, 2, 2, 2, 337, 338, 9, 4,
2, 2, 338, 84, 3, 2, 2, 2, 339, 340, 9, 5, 2, 2, 340, 86, 3, 2, 2, 2, 341,
342, 7, 50, 2, 2, 342, 344, 9, 6, 2, 2, 343, 345, 9, 7, 2, 2, 344, 343,
3, 2, 2, 2, 345, 346, 3, 2, 2, 2, 346, 344, 3, 2, 2, 2, 346, 347, 3, 2,
2, 2, 347, 88, 3, 2, 2, 2, 348, 352, 5, 95, 48, 2, 349, 351, 5, 85, 43,
2, 350, 349, 3, 2, 2, 2, 351, 354, 3, 2, 2, 2, 352, 350, 3, 2, 2, 2, 352,
353, 3, 2, 2, 2, 353, 357, 3, 2, 2, 2, 354, 352, 3, 2, 2, 2, 355, 357,
7, 50, 2, 2, 356, 348, 3, 2, 2, 2, 356, 355, 3, 2, 2, 2, 357, 90, 3, 2,
2, 2, 358, 362, 7, 50, 2, 2, 359, 361, 5, 97, 49, 2, 360, 359, 3, 2, 2,
2, 361, 364, 3, 2, 2, 2, 362, 360, 3, 2, 2, 2, 362, 363, 3, 2, 2, 2, 363,
92, 3, 2, 2, 2, 364, 362, 3, 2, 2, 2, 365, 366, 7, 50, 2, 2, 366, 367,
9, 8, 2, 2, 367, 368, 5, 117, 59, 2, 368, 94, 3, 2, 2, 2, 369, 370, 9,
9, 2, 2, 370, 96, 3, 2, 2, 2, 371, 372, 9, 10, 2, 2, 372, 98, 3, 2, 2,
2, 373, 374, 9, 11, 2, 2, 374, 100, 3, 2, 2, 2, 375, 376, 5, 99, 50, 2,
376, 377, 5, 99, 50, 2, 377, 378, 5, 99, 50, 2, 378, 379, 5, 99, 50, 2,
379, 102, 3, 2, 2, 2, 380, 381, 7, 94, 2, 2, 381, 382, 7, 119, 2, 2, 382,
383, 3, 2, 2, 2, 383, 391, 5, 101, 51, 2, 384, 385, 7, 94, 2, 2, 385, 386,
7, 87, 2, 2, 386, 387, 3, 2, 2, 2, 387, 388, 5, 101, 51, 2, 388, 389, 5,
101, 51, 2, 389, 391, 3, 2, 2, 2, 390, 380, 3, 2, 2, 2, 390, 384, 3, 2,
2, 2, 391, 104, 3, 2, 2, 2, 392, 394, 5, 109, 55, 2, 393, 395, 5, 111,
56, 2, 394, 393, 3, 2, 2, 2, 394, 395, 3, 2, 2, 2, 395, 400, 3, 2, 2, 2,
396, 397, 5, 113, 57, 2, 397, 398, 5, 111, 56, 2, 398, 400, 3, 2, 2, 2,
399, 392, 3, 2, 2, 2, 399, 396, 3, 2, 2, 2, 400, 106, 3, 2, 2, 2, 401,
402, 7, 50, 2, 2, 402, 405, 9, 8, 2, 2, 403, 406, 5, 115, 58, 2, 404, 406,
5, 117, 59, 2, 405, 403, 3, 2, 2, 2, 405, 404, 3, 2, 2, 2, 406, 407, 3,
2, 2, 2, 407, 408, 5, 119, 60, 2, 408, 108, 3, 2, 2, 2, 409, 411, 5, 113,
57, 2, 410, 409, 3, 2, 2, 2, 410, 411, 3, 2, 2, 2, 411, 412, 3, 2, 2, 2,
412, 413, 7, 48, 2, 2, 413, 418, 5, 113, 57, 2, 414, 415, 5, 113, 57, 2,
415, 416, 7, 48, 2, 2, 416, 418, 3, 2, 2, 2, 417, 410, 3, 2, 2, 2, 417,
414, 3, 2, 2, 2, 418, 110, 3, 2, 2, 2, 419, 421, 9, 12, 2, 2, 420, 422,
9, 13, 2, 2, 421, 420, 3, 2, 2, 2, 421, 422, 3, 2, 2, 2, 422, 423, 3, 2,
2, 2, 423, 424, 5, 113, 57, 2, 424, 112, 3, 2, 2, 2, 425, 427, 5, 85, 43,
2, 426, 425, 3, 2, 2, 2, 427, 428, 3, 2, 2, 2, 428, 426, 3, 2, 2, 2, 428,
429, 3, 2, 2, 2, 429, 114, 3, 2, 2, 2, 430, 432, 5, 117, 59, 2, 431, 430,
3, 2, 2, 2, 431, 432, 3, 2, 2, 2, 432, 433, 3, 2, 2, 2, 433, 434, 7, 48,
2, 2, 434, 439, 5, 117, 59, 2, 435, 436, 5, 117, 59, 2, 436, 437, 7, 48,
2, 2, 437, 439, 3, 2, 2, 2, 438, 431, 3, 2, 2, 2, 438, 435, 3, 2, 2, 2,
439, 116, 3, 2, 2, 2, 440, 442, 5, 99, 50, 2, 441, 440, 3, 2, 2, 2, 442,
443, 3, 2, 2, 2, 443, 441, 3, 2, 2, 2, 443, 444, 3, 2, 2, 2, 444, 118,
3, 2, 2, 2, 445, 447, 9, 14, 2, 2, 446, 448, 9, 13, 2, 2, 447, 446, 3,
2, 2, 2, 447, 448, 3, 2, 2, 2, 448, 449, 3, 2, 2, 2, 449, 450, 5, 113,
57, 2, 450, 120, 3, 2, 2, 2, 451, 452, 7, 94, 2, 2, 452, 467, 9, 15, 2,
2, 453, 454, 7, 94, 2, 2, 454, 456, 5, 97, 49, 2, 455, 457, 5, 97, 49,
2, 456, 455, 3, 2, 2, 2, 456, 457, 3, 2, 2, 2, 457, 459, 3, 2, 2, 2, 458,
460, 5, 97, 49, 2, 459, 458, 3, 2, 2, 2, 459, 460, 3, 2, 2, 2, 460, 467,
3, 2, 2, 2, 461, 462, 7, 94, 2, 2, 462, 463, 7, 122, 2, 2, 463, 464, 3,
2, 2, 2, 464, 467, 5, 117, 59, 2, 465, 467, 5, 103, 52, 2, 466, 451, 3,
2, 2, 2, 466, 453, 3, 2, 2, 2, 466, 461, 3, 2, 2, 2, 466, 465, 3, 2, 2,
2, 467, 122, 3, 2, 2, 2, 468, 470, 9, 16, 2, 2, 469, 468, 3, 2, 2, 2, 470,
471, 3, 2, 2, 2, 471, 469, 3, 2, 2, 2, 471, 472, 3, 2, 2, 2, 472, 473,
3, 2, 2, 2, 473, 474, 8, 62, 2, 2, 474, 124, 3, 2, 2, 2, 475, 477, 7, 15,
2, 2, 476, 478, 7, 12, 2, 2, 477, 476, 3, 2, 2, 2, 477, 478, 3, 2, 2, 2,
478, 481, 3, 2, 2, 2, 479, 481, 7, 12, 2, 2, 480, 475, 3, 2, 2, 2, 480,
479, 3, 2, 2, 2, 481, 482, 3, 2, 2, 2, 482, 483, 8, 63, 2, 2, 483, 126,
3, 2, 2, 2, 45, 2, 161, 175, 207, 213, 221, 236, 238, 270, 276, 280, 285,
287, 295, 298, 302, 310, 316, 321, 326, 335, 346, 352, 356, 362, 390, 394,
399, 405, 410, 417, 421, 428, 431, 438, 443, 447, 456, 459, 466, 471, 477,
480, 3, 8, 2, 2,
}
var lexerChannelNames = []string{

View File

@ -4,12 +4,12 @@ import (
"sync"
"testing"
"github.com/milvus-io/milvus/pkg/common"
"github.com/milvus-io/milvus-proto/go-api/schemapb"
"github.com/milvus-io/milvus/internal/proto/planpb"
"github.com/milvus-io/milvus/pkg/log"
"github.com/milvus-io/milvus/pkg/util/typeutil"
"github.com/stretchr/testify/assert"
"go.uber.org/zap"
)
func newTestSchema() *schemapb.CollectionSchema {
@ -22,20 +22,19 @@ func newTestSchema() *schemapb.CollectionSchema {
newField := &schemapb.FieldSchema{
FieldID: int64(100 + value), Name: name + "Field", IsPrimaryKey: false, Description: "", DataType: dataType,
}
if value == int32(schemapb.DataType_JSON) {
newField = &schemapb.FieldSchema{
FieldID: int64(100 + value), Name: name + "Field", IsPrimaryKey: false, Description: "", DataType: dataType,
//IsDynamic: true,
}
}
fields = append(fields, newField)
}
fields = append(fields, &schemapb.FieldSchema{
FieldID: 199, Name: common.MetaFieldName, IsPrimaryKey: false, Description: "dynamic field", DataType: schemapb.DataType_JSON,
IsDynamic: true,
})
return &schemapb.CollectionSchema{
Name: "test",
Description: "schema for test used",
AutoID: true,
Fields: fields,
Name: "test",
Description: "schema for test used",
AutoID: true,
Fields: fields,
EnableDynamicField: true,
}
}
@ -75,6 +74,8 @@ func TestExpr_Term(t *testing.T) {
`Int64Field not in []`,
`JSONField["A"] in [1, 10]`,
`JSONField["A"] in []`,
`$meta["A"] in [1, 10]`,
`$meta["A"] in []`,
`A in [1, 10]`,
`A in []`,
`A in ["abc", "def"]`,
@ -98,6 +99,7 @@ func TestExpr_Compare(t *testing.T) {
`FloatField == DoubleField`,
`StringField != VarCharField`,
`JSONField["A"] > Int16Field`,
`$meta["A"] > Int16Field`,
}
for _, exprStr := range exprStrs {
assertValidExpr(t, helper, exprStr)
@ -120,6 +122,7 @@ func TestExpr_UnaryRange(t *testing.T) {
`StringField > "str6"`,
`VarCharField <= "str7"`,
`JSONField["A"] > 10`,
`$meta["A"] > 10`,
}
for _, exprStr := range exprStrs {
assertValidExpr(t, helper, exprStr)
@ -135,6 +138,7 @@ func TestExpr_Like(t *testing.T) {
`VarCharField like "prefix%"`,
`VarCharField like "equal"`,
`JSONField["A"] like "name*"`,
`$meta["A"] like "name*"`,
}
for _, exprStr := range exprStrs {
assertValidExpr(t, helper, exprStr)
@ -144,6 +148,7 @@ func TestExpr_Like(t *testing.T) {
unsupported := []string{
`VarCharField like "not_%_supported"`,
`JSONField["A"] like "not_%_supported"`,
`$meta["A"] like "not_%_supported"`,
}
for _, exprStr := range unsupported {
assertInvalidExpr(t, helper, exprStr)
@ -248,6 +253,7 @@ func TestExpr_Identifier(t *testing.T) {
`StringField`,
`VarCharField`,
`JSONField["A"]`,
`$meta["A"]`,
}
for _, exprStr := range exprStrs {
expr := handleExpr(helper, exprStr)
@ -356,14 +362,13 @@ func TestCreateRetrievePlan(t *testing.T) {
func TestCreateSearchPlan(t *testing.T) {
schema := newTestSchema()
plan, err := CreateSearchPlan(schema, `JSONField["A"] != 10`, "FloatVectorField", &planpb.QueryInfo{
_, err := CreateSearchPlan(schema, `$meta["A"] != 10`, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
SearchParams: "",
RoundDecimal: 0,
})
assert.NoError(t, err)
log.Info("plan", zap.Any("plan", plan))
}
func TestExpr_Invalid(t *testing.T) {
@ -564,7 +569,7 @@ func Test_JSONExpr(t *testing.T) {
schema := newTestSchema()
expr := ""
// search
expr = `JSONField["A"] > 90`
expr = `$meta["A"] > 90`
_, err := CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -573,6 +578,15 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] > 90`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
SearchParams: "",
RoundDecimal: 0,
})
assert.NoError(t, err)
expr = `A < 10`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
@ -591,7 +605,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] >= 95`
expr = `$meta["A"] <= 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -600,7 +614,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] == 5`
expr = `$meta["A"] >= 95`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -609,7 +623,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] != 95`
expr = `$meta["A"] == 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -618,7 +632,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] > 90 && JSONField["B"] < 5`
expr = `$meta["A"] != 95`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -627,7 +641,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] > 95 || JSONField["B"] < 5`
expr = `$meta["A"] > 90 && $meta["B"] < 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -636,7 +650,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `A > 95 || JSONField["B"] < 5`
expr = `$meta["A"] > 95 || $meta["B"] < 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -645,7 +659,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `not (JSONField["A"] == 95)`
expr = `A > 95 || $meta["B"] < 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -654,7 +668,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] in [90, 91, 95, 97]`
expr = `not ($meta["A"] == 95)`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -663,7 +677,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] not in [90, 91, 95, 97]`
expr = `$meta["A"] in [90, 91, 95, 97]`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -672,7 +686,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["C"]["0"] in [90, 91, 95, 97]`
expr = `$meta["A"] not in [90, 91, 95, 97]`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -681,7 +695,16 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["C"]["0"] not in [90, 91, 95, 97]`
expr = `$meta["C"]["0"] in [90, 91, 95, 97]`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
SearchParams: "",
RoundDecimal: 0,
})
assert.NoError(t, err)
expr = `$meta["C"]["0"] not in [90, 91, 95, 97]`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -753,7 +776,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `0 <= JSONField["A"] < 5`
expr = `0 <= $meta["A"] < 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -771,7 +794,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] + 5 == 10`
expr = `$meta["A"] + 5 == 10`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -780,7 +803,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField["A"] > 10 + 5`
expr = `$meta["A"] > 10 + 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -789,7 +812,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `100 - 5 < JSONField["A"]`
expr = `100 - 5 < $meta["A"]`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -798,7 +821,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `100 == JSONField["A"] + 6`
expr = `100 == $meta["A"] + 6`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -807,7 +830,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `exists JSONField["A"]`
expr = `exists $meta["A"]`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -816,7 +839,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `exists JSONField["A"]["B"]["C"] `
expr = `exists $meta["A"]["B"]["C"] `
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -843,7 +866,7 @@ func Test_JSONExpr(t *testing.T) {
})
assert.NoError(t, err)
expr = `JSONField[0] > 100`
expr = `$meta[0] > 100`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -875,6 +898,15 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
schema := newTestSchema()
expr := ""
var err error
expr = `exists $meta`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
SearchParams: "",
RoundDecimal: 0,
})
assert.Error(t, err)
expr = `exists JSONField`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
@ -884,7 +916,16 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `JSONField > 0`
expr = `$meta > 0`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
SearchParams: "",
RoundDecimal: 0,
})
assert.Error(t, err)
expr = `$meta > 0`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -902,7 +943,7 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `JSONField < 100`
expr = `$meta < 100`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -911,7 +952,7 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `0 < JSONField < 100`
expr = `0 < $meta < 100`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -920,7 +961,7 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `20 > JSONField > 0`
expr = `20 > $meta > 0`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -929,7 +970,7 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `JSONField + 5 > 0`
expr = `$meta + 5 > 0`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -938,7 +979,7 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `JSONField > 2 + 5`
expr = `$meta > 2 + 5`
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",
@ -947,7 +988,7 @@ func Test_InvalidExprOnJSONField(t *testing.T) {
})
assert.Error(t, err)
expr = `exists JSONField["A"] > 10 `
expr = `exists $meta["A"] > 10 `
_, err = CreateSearchPlan(schema, expr, "FloatVectorField", &planpb.QueryInfo{
Topk: 0,
MetricType: "",

View File

@ -466,10 +466,11 @@ func (m *MetaCache) describeCollection(ctx context.Context, collectionName strin
resp := &milvuspb.DescribeCollectionResponse{
Status: coll.Status,
Schema: &schemapb.CollectionSchema{
Name: coll.Schema.Name,
Description: coll.Schema.Description,
AutoID: coll.Schema.AutoID,
Fields: make([]*schemapb.FieldSchema, 0),
Name: coll.Schema.Name,
Description: coll.Schema.Description,
AutoID: coll.Schema.AutoID,
Fields: make([]*schemapb.FieldSchema, 0),
EnableDynamicField: coll.Schema.EnableDynamicField,
},
CollectionID: coll.CollectionID,
VirtualChannelNames: coll.VirtualChannelNames,

View File

@ -50,10 +50,11 @@ func newTestSchema() *schemapb.CollectionSchema {
}
return &schemapb.CollectionSchema{
Name: "test",
Description: "schema for test used",
AutoID: true,
Fields: fields,
Name: "test",
Description: "schema for test used",
AutoID: true,
Fields: fields,
EnableDynamicField: true,
}
}

View File

@ -192,6 +192,11 @@ func (cct *createCollectionTask) PreExecute(ctx context.Context) error {
return err
}
// validate dynamic field
if err := validateDynamicField(cct.schema); err != nil {
return err
}
// validate auto id definition
if err := ValidateFieldAutoID(cct.schema); err != nil {
return err
@ -473,6 +478,7 @@ func (dct *describeCollectionTask) Execute(ctx context.Context) error {
dct.result.Schema.Name = result.Schema.Name
dct.result.Schema.Description = result.Schema.Description
dct.result.Schema.AutoID = result.Schema.AutoID
dct.result.Schema.EnableDynamicField = result.Schema.EnableDynamicField
dct.result.CollectionID = result.CollectionID
dct.result.VirtualChannelNames = result.VirtualChannelNames
dct.result.PhysicalChannelNames = result.PhysicalChannelNames

View File

@ -114,6 +114,9 @@ func (cit *createIndexTask) parseIndexParams() error {
indexParamsMap[common.IndexTypeKey] = DefaultIndexType
}
}
if cit.fieldSchema.DataType == schemapb.DataType_JSON {
return fmt.Errorf("create index on json field is not supported")
}
for _, kv := range cit.req.GetExtraParams() {
if kv.Key == common.IndexParamsKey {

View File

@ -457,4 +457,51 @@ func Test_parseIndexParams(t *testing.T) {
},
}, cit2.newTypeParams)
})
t.Run("create index on json field", func(t *testing.T) {
cit3 := &createIndexTask{
Condition: nil,
req: &milvuspb.CreateIndexRequest{
Base: nil,
DbName: "",
CollectionName: "",
FieldName: "",
ExtraParams: []*commonpb.KeyValuePair{
{
Key: common.IndexTypeKey,
Value: "HNSW",
},
{
Key: MetricTypeKey,
Value: "IP",
},
{
Key: common.IndexParamsKey,
Value: "{\"M\": 48, \"efConstruction\": 64}",
},
{
Key: DimKey,
Value: "128",
},
},
IndexName: "",
},
ctx: nil,
rootCoord: nil,
queryCoord: nil,
result: nil,
isAutoIndex: false,
newIndexParams: nil,
newTypeParams: nil,
collectionID: 0,
fieldSchema: &schemapb.FieldSchema{
FieldID: 101,
Name: "FieldID",
IsPrimaryKey: false,
Description: "field no.1",
DataType: schemapb.DataType_JSON,
},
}
err := cit3.parseIndexParams()
assert.Error(t, err)
})
}

View File

@ -2,6 +2,7 @@ package proxy
import (
"context"
"encoding/json"
"fmt"
"strconv"
@ -12,6 +13,7 @@ import (
"github.com/milvus-io/milvus-proto/go-api/milvuspb"
"github.com/milvus-io/milvus-proto/go-api/schemapb"
"github.com/milvus-io/milvus/internal/allocator"
"github.com/milvus-io/milvus/pkg/common"
"github.com/milvus-io/milvus/pkg/log"
"github.com/milvus-io/milvus/pkg/metrics"
"github.com/milvus-io/milvus/pkg/mq/msgstream"
@ -150,6 +152,13 @@ func (it *insertTask) PreExecute(ctx context.Context) error {
}
it.result.SuccIndex = sliceIndex
if it.schema.EnableDynamicField {
err = it.checkDynamicFieldData()
if err != nil {
return err
}
}
// check primaryFieldData whether autoID is true or not
// set rowIDs as primary data if autoID == true
// TODO(dragondriver): in fact, NumRows is not trustable, we should check all input fields
@ -268,3 +277,45 @@ func (it *insertTask) Execute(ctx context.Context) error {
func (it *insertTask) PostExecute(ctx context.Context) error {
return nil
}
func (it *insertTask) verifyDynamicFieldData() error {
for _, field := range it.insertMsg.FieldsData {
if field.GetFieldName() == common.MetaFieldName {
if !it.schema.EnableDynamicField {
return fmt.Errorf("without dynamic schema enabled, the field name cannot be set to %s", common.MetaFieldName)
}
for _, rowData := range field.GetScalars().GetJsonData().GetData() {
jsonData := make(map[string]interface{})
if err := json.Unmarshal(rowData, &jsonData); err != nil {
return err
}
if _, ok := jsonData[common.MetaFieldName]; ok {
return fmt.Errorf("cannot set json key to: %s", common.MetaFieldName)
}
}
}
}
return nil
}
func (it *insertTask) checkDynamicFieldData() error {
var dataNameSet = typeutil.NewSet[string]()
for _, data := range it.insertMsg.FieldsData {
dataNameSet.Insert(data.GetFieldName())
}
if _, ok := dataNameSet[common.MetaFieldName]; ok {
return it.verifyDynamicFieldData()
}
defaultData := make([][]byte, it.insertMsg.NRows())
for i := range defaultData {
defaultData[i] = []byte("{}")
}
dynamicData, err := autoGenDynamicFieldData(defaultData)
if err != nil {
return err
}
it.insertMsg.FieldsData = append(it.insertMsg.FieldsData, dynamicData)
return nil
}

View File

@ -2,6 +2,7 @@ package proxy
import (
"context"
"encoding/json"
"fmt"
"testing"
@ -261,3 +262,129 @@ func TestInsertTask(t *testing.T) {
assert.ElementsMatch(t, channels, resChannels)
})
}
func TestInsertTask_checkDynamicFieldData(t *testing.T) {
t.Run("normal case", func(t *testing.T) {
jsonData := make([][]byte, 0)
data := map[string]interface{}{
"bool": true,
"int": 100,
"float": 1.2,
"string": "abc",
"json": map[string]interface{}{
"int": 20,
"array": []int{1, 2, 3},
},
}
jsonBytes, err := json.MarshalIndent(data, "", " ")
assert.NoError(t, err)
jsonData = append(jsonData, jsonBytes)
jsonFieldData, err := autoGenDynamicFieldData(jsonData)
assert.NoError(t, err)
it := insertTask{
ctx: context.Background(),
insertMsg: &msgstream.InsertMsg{
InsertRequest: msgpb.InsertRequest{
CollectionName: "collectionName",
FieldsData: []*schemapb.FieldData{jsonFieldData},
},
},
schema: newTestSchema(),
}
err = it.checkDynamicFieldData()
assert.NoError(t, err)
})
t.Run("key has $meta", func(t *testing.T) {
jsonData := make([][]byte, 0)
data := map[string]interface{}{
"bool": true,
"int": 100,
"float": 1.2,
"string": "abc",
"json": map[string]interface{}{
"int": 20,
"array": []int{1, 2, 3},
},
"$meta": "error key",
}
jsonBytes, err := json.MarshalIndent(data, "", " ")
assert.NoError(t, err)
jsonData = append(jsonData, jsonBytes)
jsonFieldData, err := autoGenDynamicFieldData(jsonData)
assert.NoError(t, err)
it := insertTask{
ctx: context.Background(),
insertMsg: &msgstream.InsertMsg{
InsertRequest: msgpb.InsertRequest{
CollectionName: "collectionName",
FieldsData: []*schemapb.FieldData{jsonFieldData},
},
},
schema: newTestSchema(),
}
err = it.checkDynamicFieldData()
assert.Error(t, err)
})
t.Run("disable dynamic schema", func(t *testing.T) {
jsonData := make([][]byte, 0)
data := map[string]interface{}{
"bool": true,
"int": 100,
"float": 1.2,
"string": "abc",
"json": map[string]interface{}{
"int": 20,
"array": []int{1, 2, 3},
},
}
jsonBytes, err := json.MarshalIndent(data, "", " ")
assert.NoError(t, err)
jsonData = append(jsonData, jsonBytes)
jsonFieldData, err := autoGenDynamicFieldData(jsonData)
assert.NoError(t, err)
it := insertTask{
ctx: context.Background(),
insertMsg: &msgstream.InsertMsg{
InsertRequest: msgpb.InsertRequest{
CollectionName: "collectionName",
FieldsData: []*schemapb.FieldData{jsonFieldData},
},
},
schema: newTestSchema(),
}
it.schema.EnableDynamicField = false
err = it.checkDynamicFieldData()
assert.Error(t, err)
})
t.Run("json data is string", func(t *testing.T) {
data := "abcdefg"
jsonFieldData, err := autoGenDynamicFieldData([][]byte{[]byte(data)})
assert.NoError(t, err)
it := insertTask{
ctx: context.Background(),
insertMsg: &msgstream.InsertMsg{
InsertRequest: msgpb.InsertRequest{
CollectionName: "collectionName",
FieldsData: []*schemapb.FieldData{jsonFieldData},
},
},
schema: newTestSchema(),
}
err = it.checkDynamicFieldData()
assert.Error(t, err)
})
t.Run("no json data", func(t *testing.T) {
it := insertTask{
ctx: context.Background(),
insertMsg: &msgstream.InsertMsg{
InsertRequest: msgpb.InsertRequest{
CollectionName: "collectionName",
FieldsData: []*schemapb.FieldData{},
},
},
schema: newTestSchema(),
}
err := it.checkDynamicFieldData()
assert.NoError(t, err)
})
}

View File

@ -712,6 +712,41 @@ func TestCreateCollectionTask(t *testing.T) {
assert.Error(t, err)
}
})
t.Run("specify dynamic field", func(t *testing.T) {
dynamicField := &schemapb.FieldSchema{
Name: "json",
IsDynamic: true,
}
var marshaledSchema []byte
schema2 := &schemapb.CollectionSchema{
Name: collectionName,
Fields: append(schema.Fields, dynamicField),
}
marshaledSchema, err := proto.Marshal(schema2)
assert.NoError(t, err)
task2 := &createCollectionTask{
Condition: NewTaskCondition(ctx),
CreateCollectionRequest: &milvuspb.CreateCollectionRequest{
Base: nil,
DbName: dbName,
CollectionName: collectionName,
Schema: marshaledSchema,
ShardsNum: shardsNum,
},
ctx: ctx,
rootCoord: rc,
result: nil,
schema: nil,
}
err = task2.OnEnqueue()
assert.NoError(t, err)
err = task2.PreExecute(ctx)
assert.Error(t, err)
})
}
func TestHasCollectionTask(t *testing.T) {

View File

@ -344,6 +344,15 @@ func validatePrimaryKey(coll *schemapb.CollectionSchema) error {
return nil
}
func validateDynamicField(coll *schemapb.CollectionSchema) error {
for _, field := range coll.Fields {
if field.IsDynamic {
return fmt.Errorf("cannot explicitly set a field as a dynamic field")
}
}
return nil
}
// RepeatedKeyValToMap transfer the kv pairs to map.
func RepeatedKeyValToMap(kvPairs []*commonpb.KeyValuePair) (map[string]string, error) {
resMap := make(map[string]string)
@ -549,6 +558,23 @@ func autoGenPrimaryFieldData(fieldSchema *schemapb.FieldSchema, data interface{}
return &fieldData, nil
}
func autoGenDynamicFieldData(data [][]byte) (*schemapb.FieldData, error) {
fieldData := &schemapb.FieldData{
FieldName: common.MetaFieldName,
Type: schemapb.DataType_JSON,
Field: &schemapb.FieldData_Scalars{
Scalars: &schemapb.ScalarField{
Data: &schemapb.ScalarField_JsonData{
JsonData: &schemapb.JSONArray{
Data: data,
},
},
},
},
}
return fieldData, nil
}
// fillFieldIDBySchema set fieldID to fieldData according FieldSchemas
func fillFieldIDBySchema(columns []*schemapb.FieldData, schema *schemapb.CollectionSchema) error {
if len(columns) != len(schema.GetFields()) {

View File

@ -151,9 +151,12 @@ func (t *createCollectionTask) validateSchema(schema *schemapb.CollectionSchema)
return err
}
if hasSystemFields(schema, []string{RowIDFieldName, TimeStampFieldName}) {
log.Error("schema contains system field", zap.String("RowIDFieldName", RowIDFieldName), zap.String("TimeStampFieldName", TimeStampFieldName))
msg := fmt.Sprintf("schema contains system field: %s, %s", RowIDFieldName, TimeStampFieldName)
if hasSystemFields(schema, []string{RowIDFieldName, TimeStampFieldName, MetaFieldName}) {
log.Error("schema contains system field",
zap.String("RowIDFieldName", RowIDFieldName),
zap.String("TimeStampFieldName", TimeStampFieldName),
zap.String("MetaFieldName", MetaFieldName))
msg := fmt.Sprintf("schema contains system field: %s, %s, %s", RowIDFieldName, TimeStampFieldName, MetaFieldName)
return merr.WrapErrParameterInvalid("schema don't contains system field", "contains", msg)
}
return nil
@ -165,6 +168,17 @@ func (t *createCollectionTask) assignFieldID(schema *schemapb.CollectionSchema)
}
}
func (t *createCollectionTask) appendDynamicField(schema *schemapb.CollectionSchema) {
if schema.EnableDynamicField {
schema.Fields = append(schema.Fields, &schemapb.FieldSchema{
Name: MetaFieldName,
Description: "dynamic schema",
DataType: schemapb.DataType_JSON,
IsDynamic: true,
})
}
}
func (t *createCollectionTask) appendSysFields(schema *schemapb.CollectionSchema) {
schema.Fields = append(schema.Fields, &schemapb.FieldSchema{
FieldID: int64(RowIDField),
@ -190,6 +204,7 @@ func (t *createCollectionTask) prepareSchema() error {
if err := t.validateSchema(&schema); err != nil {
return err
}
t.appendDynamicField(&schema)
t.assignFieldID(&schema)
t.appendSysFields(&schema)
t.schema = &schema
@ -332,7 +347,8 @@ func (t *createCollectionTask) Execute(ctx context.Context) error {
State: pb.PartitionState_PartitionCreated,
},
},
Properties: t.Req.Properties,
Properties: t.Req.Properties,
EnableDynamicField: t.schema.EnableDynamicField,
}
// We cannot check the idempotency inside meta table when adding collection, since we'll execute duplicate steps

View File

@ -40,4 +40,7 @@ const (
// TimeStampFieldName name of the timestamp field
TimeStampFieldName = common.TimeStampFieldName
// MetaFieldName name of the dynamic schema field
MetaFieldName = common.MetaFieldName
)

View File

@ -905,10 +905,11 @@ func convertModelToDesc(collInfo *model.Collection, aliases []string) *milvuspb.
resp := &milvuspb.DescribeCollectionResponse{Status: merr.Status(nil)}
resp.Schema = &schemapb.CollectionSchema{
Name: collInfo.Name,
Description: collInfo.Description,
AutoID: collInfo.AutoID,
Fields: model.MarshalFieldModels(collInfo.Fields),
Name: collInfo.Name,
Description: collInfo.Description,
AutoID: collInfo.AutoID,
Fields: model.MarshalFieldModels(collInfo.Fields),
EnableDynamicField: collInfo.EnableDynamicField,
}
resp.CollectionID = collInfo.CollectionID
resp.VirtualChannelNames = collInfo.VirtualChannelNames

View File

@ -41,6 +41,9 @@ const (
// TimeStampFieldName defines the name of the Timestamp field
TimeStampFieldName = "Timestamp"
// MetaFieldName is the field name of dynamic schema
MetaFieldName = "$meta"
// DefaultShardsNum defines the default number of shards when creating a collection
DefaultShardsNum = int32(1)

View File

@ -12,7 +12,7 @@ require (
github.com/grpc-ecosystem/go-grpc-middleware v1.3.0
github.com/klauspost/compress v1.14.4
github.com/lingdor/stackerror v0.0.0-20191119040541-976d8885ed76
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230416064425-aec3e83865b2
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230515081521-d963c95b041f
github.com/panjf2000/ants/v2 v2.4.8
github.com/prometheus/client_golang v1.11.1
github.com/samber/lo v1.27.0

View File

@ -467,6 +467,8 @@ github.com/microcosm-cc/bluemonday v1.0.2/go.mod h1:iVP4YcDBq+n/5fb23BhYFvIMq/le
github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230416064425-aec3e83865b2 h1:G5uN68X/7eoCfHUkNvkbNueFhHuohCZG94te+ApLAOY=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230416064425-aec3e83865b2/go.mod h1:148qnlmZ0Fdm1Fq+Mj/OW2uDoEP25g3mjh0vMGtkgmk=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230515081521-d963c95b041f h1:uZzVaSbUtxMdEix9By6z+M/H/XNkXRQJdZQ9HP/wHtc=
github.com/milvus-io/milvus-proto/go-api v0.0.0-20230515081521-d963c95b041f/go.mod h1:148qnlmZ0Fdm1Fq+Mj/OW2uDoEP25g3mjh0vMGtkgmk=
github.com/milvus-io/pulsar-client-go v0.6.10 h1:eqpJjU+/QX0iIhEo3nhOqMNXL+TyInAs1IAHZCrCM/A=
github.com/milvus-io/pulsar-client-go v0.6.10/go.mod h1:lQqCkgwDF8YFYjKA+zOheTk1tev2B+bKj5j7+nm8M1w=
github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc=

View File

@ -248,16 +248,8 @@ func (helper *SchemaHelper) GetFieldFromNameDefaultJSON(fieldName string) (*sche
func (helper *SchemaHelper) getDefaultJSONField() (*schemapb.FieldSchema, error) {
var field *schemapb.FieldSchema
for _, f := range helper.schema.GetFields() {
// TODO @xiaocai2333: get $SYS_META json field
//if f.DataType == schemapb.DataType_JSON && f.GetIsDynamic() {
if f.DataType == schemapb.DataType_JSON {
if field != nil {
// TODO @xiaocai2333: will not return error after support $SYS_META
errMsg := "there is multi json field in schema, need to specified field name"
log.Warn(errMsg)
return nil, fmt.Errorf(errMsg)
}
field = f
if f.DataType == schemapb.DataType_JSON && f.IsDynamic {
return f, nil
}
}
if field == nil {

View File

@ -38,7 +38,7 @@ import (
"go.uber.org/zap"
)
func TestJsonExpr(t *testing.T) {
func TestJson_EnableDynamicSchema(t *testing.T) {
ctx := context.Background()
c, err := StartMiniCluster(ctx)
assert.NoError(t, err)
@ -50,7 +50,6 @@ func TestJsonExpr(t *testing.T) {
prefix := "TestHelloMilvus"
dbName := ""
collectionName := prefix + funcutil.GenRandomStr()
jsonField := "json"
dim := 128
rowNum := 100
@ -80,20 +79,14 @@ func TestJsonExpr(t *testing.T) {
IndexParams: nil,
AutoID: false,
}
jsonF := &schemapb.FieldSchema{
Name: jsonField,
Description: "this is a json field",
DataType: schemapb.DataType_JSON,
//IsDynamic: true,
}
return &schemapb.CollectionSchema{
Name: collectionName,
Description: "",
AutoID: false,
Name: collectionName,
Description: "",
AutoID: false,
EnableDynamicField: true,
Fields: []*schemapb.FieldSchema{
pk,
fVec,
jsonF,
},
}
}
@ -119,13 +112,323 @@ func TestJsonExpr(t *testing.T) {
assert.Equal(t, showCollectionsResp.GetStatus().GetErrorCode(), commonpb.ErrorCode_Success)
log.Info("ShowCollections result", zap.Any("showCollectionsResp", showCollectionsResp))
describeCollectionResp, err := c.proxy.DescribeCollection(ctx, &milvuspb.DescribeCollectionRequest{CollectionName: collectionName})
assert.NoError(t, err)
assert.True(t, describeCollectionResp.Schema.EnableDynamicField)
assert.Equal(t, 3, len(describeCollectionResp.GetSchema().GetFields()))
fVecColumn := newFloatVectorFieldData(floatVecField, rowNum, dim)
jsonData := newJSONData(jsonField, rowNum)
jsonData := newJSONData(common.MetaFieldName, rowNum)
insertFlushIndexLoad(ctx, t, c, dbName, collectionName, rowNum, dim, []*schemapb.FieldData{fVecColumn, jsonData})
checkSearch(t, c, collectionName, common.MetaFieldName, dim)
}
func checkSearch(t *testing.T, c *MiniCluster, collectionName, fieldName string, dim int) {
expr := ""
// search
expr = `$meta["A"] > 90`
checkFunc := func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("GT expression run successfully")
expr = `$meta["A"] < 10`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("LT expression run successfully")
expr = `$meta["A"] <= 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("LE expression run successfully")
expr = `A >= 95`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("GE expression run successfully")
expr = `$meta["A"] == 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("EQ expression run successfully")
expr = `A != 95`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NE expression run successfully")
expr = `not (A != 95)`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NOT NE expression run successfully")
expr = `A > 90 && B < 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 2, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NE expression run successfully")
expr = `A > 95 || 5 > B`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NE expression run successfully")
expr = `not (A == 95)`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NOT expression run successfully")
expr = `A in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("IN expression run successfully")
expr = `A not in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NIN expression run successfully")
expr = `C[0] in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("IN expression run successfully")
expr = `C[0] not in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NIN expression run successfully")
expr = `0 <= A < 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 2, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("BinaryRange expression run successfully")
expr = `100 > A >= 90`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("BinaryRange expression run successfully")
expr = `1+5 <= A < 5+10`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("BinaryRange expression run successfully")
expr = `A + 5 == 10`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("Arithmetic expression run successfully")
expr = `exists A`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("EXISTS expression run successfully")
expr = `exists AAA`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("EXISTS expression run successfully")
expr = `not exists A`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("NOT EXISTS expression run successfully")
expr = `E["G"] > 100`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 9, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("nested path expression run successfully")
expr = `D like "name-%"`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("like expression run successfully")
expr = `D like "name-11"`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("like expression run successfully")
expr = `A like "10"`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("like expression run successfully")
expr = `A in []`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("term empty expression run successfully")
expr = `A not in []`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, fieldName, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{fieldName}, expr, dim, t, checkFunc)
log.Info("term empty expression run successfully")
// invalid expr
expr = `E[F] > 100`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `A >> 10`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `not A > 5`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `not A == 5`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `A > B`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `A > Int64Field`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `A like abc`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `D like "%name-%"`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `D like "na%me"`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `1+5 <= A+1 < 5+10`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
expr = `$meta == ""`
doSearchWithInvalidExpr(c, collectionName, []string{fieldName}, expr, dim, t)
}
func insertFlushIndexLoad(ctx context.Context, t *testing.T, c *MiniCluster, dbName, collectionName string, rowNum int, dim int, fieldData []*schemapb.FieldData) {
hashKeys := generateHashKeys(rowNum)
insertResult, err := c.proxy.Insert(ctx, &milvuspb.InsertRequest{
DbName: dbName,
CollectionName: collectionName,
FieldsData: []*schemapb.FieldData{fVecColumn, jsonData},
FieldsData: fieldData,
HashKeys: hashKeys,
NumRows: uint32(rowNum),
})
@ -224,303 +527,6 @@ func TestJsonExpr(t *testing.T) {
}
time.Sleep(500 * time.Millisecond)
}
expr := ""
// search
expr = `json["A"] > 90`
checkFunc := func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("GT expression run successfully")
expr = `json["A"] < 10`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("LT expression run successfully")
expr = `json["A"] <= 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("LE expression run successfully")
expr = `A >= 95`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("GE expression run successfully")
expr = `json["A"] == 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("EQ expression run successfully")
expr = `A != 95`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NE expression run successfully")
expr = `not (A != 95)`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NOT NE expression run successfully")
expr = `A > 90 && B < 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 2, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NE expression run successfully")
expr = `A > 95 || 5 > B`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NE expression run successfully")
expr = `not (A == 95)`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NOT expression run successfully")
expr = `A in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("IN expression run successfully")
expr = `A not in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NIN expression run successfully")
expr = `C[0] in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("IN expression run successfully")
expr = `C[0] not in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NIN expression run successfully")
expr = `0 <= A < 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 2, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("BinaryRange expression run successfully")
expr = `100 > A >= 90`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("BinaryRange expression run successfully")
expr = `1+5 <= A < 5+10`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("BinaryRange expression run successfully")
expr = `A + 5 == 10`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("Arithmetic expression run successfully")
expr = `exists A`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("EXISTS expression run successfully")
expr = `exists AAA`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("EXISTS expression run successfully")
expr = `not exists A`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NOT EXISTS expression run successfully")
expr = `E["G"] > 100`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 9, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("nested path expression run successfully")
expr = `D like "name-%"`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("like expression run successfully")
expr = `D like "name-11"`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("like expression run successfully")
expr = `A like "10"`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("like expression run successfully")
expr = `A in []`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("term empty expression run successfully")
expr = `A not in []`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("term empty expression run successfully")
// invalid expr
expr = `E[F] > 100`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `A >> 10`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `not A > 5`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `not A == 5`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `A > B`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `A > Int64Field`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `A like abc`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `D like "%name-%"`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `D like "na%me"`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `1+5 <= A+1 < 5+10`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
expr = `json == ""`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
}
func doSearch(cluster *MiniCluster, collectionName string, outputField []string, expr string, dim int, t *testing.T, checkFunc func(results *milvuspb.SearchResults)) {
@ -613,3 +619,253 @@ func doSearchWithInvalidExpr(cluster *MiniCluster, collectionName string, output
assert.NoError(t, err)
assert.NotEqual(t, commonpb.ErrorCode_Success, searchResult.GetStatus().GetErrorCode())
}
func TestJSON_InsertWithoutDynamicData(t *testing.T) {
ctx := context.Background()
c, err := StartMiniCluster(ctx)
assert.NoError(t, err)
err = c.Start()
assert.NoError(t, err)
defer c.Stop()
assert.NoError(t, err)
prefix := "TestHelloMilvus"
dbName := ""
collectionName := prefix + funcutil.GenRandomStr()
dim := 128
rowNum := 100
constructCollectionSchema := func() *schemapb.CollectionSchema {
pk := &schemapb.FieldSchema{
FieldID: 0,
Name: int64Field,
IsPrimaryKey: true,
Description: "",
DataType: schemapb.DataType_Int64,
TypeParams: nil,
IndexParams: nil,
AutoID: true,
}
fVec := &schemapb.FieldSchema{
FieldID: 0,
Name: floatVecField,
IsPrimaryKey: false,
Description: "",
DataType: schemapb.DataType_FloatVector,
TypeParams: []*commonpb.KeyValuePair{
{
Key: common.DimKey,
Value: strconv.Itoa(dim),
},
},
IndexParams: nil,
AutoID: false,
}
return &schemapb.CollectionSchema{
Name: collectionName,
Description: "",
AutoID: false,
EnableDynamicField: true,
Fields: []*schemapb.FieldSchema{
pk,
fVec,
},
}
}
schema := constructCollectionSchema()
marshaledSchema, err := proto.Marshal(schema)
assert.NoError(t, err)
createCollectionStatus, err := c.proxy.CreateCollection(ctx, &milvuspb.CreateCollectionRequest{
DbName: dbName,
CollectionName: collectionName,
Schema: marshaledSchema,
ShardsNum: 2,
})
assert.NoError(t, err)
if createCollectionStatus.GetErrorCode() != commonpb.ErrorCode_Success {
log.Warn("createCollectionStatus fail reason", zap.String("reason", createCollectionStatus.GetReason()))
}
assert.Equal(t, createCollectionStatus.GetErrorCode(), commonpb.ErrorCode_Success)
log.Info("CreateCollection result", zap.Any("createCollectionStatus", createCollectionStatus))
showCollectionsResp, err := c.proxy.ShowCollections(ctx, &milvuspb.ShowCollectionsRequest{})
assert.NoError(t, err)
assert.Equal(t, showCollectionsResp.GetStatus().GetErrorCode(), commonpb.ErrorCode_Success)
log.Info("ShowCollections result", zap.Any("showCollectionsResp", showCollectionsResp))
describeCollectionResp, err := c.proxy.DescribeCollection(ctx, &milvuspb.DescribeCollectionRequest{CollectionName: collectionName})
assert.NoError(t, err)
assert.True(t, describeCollectionResp.Schema.EnableDynamicField)
assert.Equal(t, 3, len(describeCollectionResp.GetSchema().GetFields()))
fVecColumn := newFloatVectorFieldData(floatVecField, rowNum, dim)
insertFlushIndexLoad(ctx, t, c, dbName, collectionName, rowNum, dim, []*schemapb.FieldData{fVecColumn})
expr := ""
// search
expr = `$meta["A"] > 90`
checkFunc := func(result *milvuspb.SearchResults) {
assert.Equal(t, 0, len(result.Results.FieldsData))
}
doSearch(c, collectionName, []string{common.MetaFieldName}, expr, dim, t, checkFunc)
log.Info("GT expression run successfully")
}
func TestJSON_DynamicSchemaWithJSON(t *testing.T) {
ctx := context.Background()
c, err := StartMiniCluster(ctx)
assert.NoError(t, err)
err = c.Start()
assert.NoError(t, err)
defer c.Stop()
assert.NoError(t, err)
prefix := "TestHelloMilvus"
dbName := ""
collectionName := prefix + funcutil.GenRandomStr()
dim := 128
rowNum := 100
constructCollectionSchema := func() *schemapb.CollectionSchema {
pk := &schemapb.FieldSchema{
FieldID: 0,
Name: int64Field,
IsPrimaryKey: true,
Description: "",
DataType: schemapb.DataType_Int64,
TypeParams: nil,
IndexParams: nil,
AutoID: true,
}
fVec := &schemapb.FieldSchema{
FieldID: 0,
Name: floatVecField,
IsPrimaryKey: false,
Description: "",
DataType: schemapb.DataType_FloatVector,
TypeParams: []*commonpb.KeyValuePair{
{
Key: common.DimKey,
Value: strconv.Itoa(dim),
},
},
IndexParams: nil,
AutoID: false,
}
j := &schemapb.FieldSchema{
Name: jsonField,
Description: "json field",
DataType: schemapb.DataType_JSON,
}
return &schemapb.CollectionSchema{
Name: collectionName,
Description: "",
AutoID: false,
EnableDynamicField: true,
Fields: []*schemapb.FieldSchema{
pk,
fVec,
j,
},
}
}
schema := constructCollectionSchema()
marshaledSchema, err := proto.Marshal(schema)
assert.NoError(t, err)
createCollectionStatus, err := c.proxy.CreateCollection(ctx, &milvuspb.CreateCollectionRequest{
DbName: dbName,
CollectionName: collectionName,
Schema: marshaledSchema,
ShardsNum: 2,
})
assert.NoError(t, err)
if createCollectionStatus.GetErrorCode() != commonpb.ErrorCode_Success {
log.Warn("createCollectionStatus fail reason", zap.String("reason", createCollectionStatus.GetReason()))
}
assert.Equal(t, createCollectionStatus.GetErrorCode(), commonpb.ErrorCode_Success)
log.Info("CreateCollection result", zap.Any("createCollectionStatus", createCollectionStatus))
showCollectionsResp, err := c.proxy.ShowCollections(ctx, &milvuspb.ShowCollectionsRequest{})
assert.NoError(t, err)
assert.Equal(t, showCollectionsResp.GetStatus().GetErrorCode(), commonpb.ErrorCode_Success)
log.Info("ShowCollections result", zap.Any("showCollectionsResp", showCollectionsResp))
describeCollectionResp, err := c.proxy.DescribeCollection(ctx, &milvuspb.DescribeCollectionRequest{CollectionName: collectionName})
assert.NoError(t, err)
assert.True(t, describeCollectionResp.Schema.EnableDynamicField)
assert.Equal(t, 4, len(describeCollectionResp.GetSchema().GetFields()))
fVecColumn := newFloatVectorFieldData(floatVecField, rowNum, dim)
jsonData := newJSONData(jsonField, rowNum)
dynamicData := newJSONData(common.MetaFieldName, rowNum)
insertFlushIndexLoad(ctx, t, c, dbName, collectionName, rowNum, dim, []*schemapb.FieldData{fVecColumn, jsonData, dynamicData})
checkSearch(t, c, collectionName, common.MetaFieldName, dim)
expr := ""
// search
expr = `jsonField["A"] < 10`
checkFunc := func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 5, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("LT expression run successfully")
expr = `jsonField["A"] <= 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 3, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("LE expression run successfully")
expr = `jsonField["A"] == 5`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 1, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("EQ expression run successfully")
expr = `jsonField["C"][0] in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 4, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("IN expression run successfully")
expr = `jsonField["C"][0] not in [90, 91, 95, 97]`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 10, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("NIN expression run successfully")
expr = `jsonField["E"]["G"] > 100`
checkFunc = func(result *milvuspb.SearchResults) {
assert.Equal(t, 1, len(result.Results.FieldsData))
assert.Equal(t, jsonField, result.Results.FieldsData[0].GetFieldName())
assert.Equal(t, schemapb.DataType_JSON, result.Results.FieldsData[0].GetType())
assert.Equal(t, 9, len(result.Results.FieldsData[0].GetScalars().GetJsonData().GetData()))
}
doSearch(c, collectionName, []string{jsonField}, expr, dim, t, checkFunc)
log.Info("nested path expression run successfully")
expr = `jsonField == ""`
doSearchWithInvalidExpr(c, collectionName, []string{jsonField}, expr, dim, t)
}

View File

@ -33,6 +33,7 @@ const (
floatField = "floatField"
doubleField = "doubleField"
varCharField = "varCharField"
jsonField = "jsonField"
floatVecField = "floatVecField"
binVecField = "binVecField"
)