2023-02-22 03:37:45 +00:00
// Licensed to the LF AI & Data foundation under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
2022-09-05 05:29:11 +00:00
package rootcoord
import (
"context"
"fmt"
2023-02-26 03:31:49 +00:00
"github.com/cockroachdb/errors"
2023-01-11 06:35:40 +00:00
"go.uber.org/zap"
2022-09-05 05:29:11 +00:00
2023-06-08 17:28:37 +00:00
"github.com/milvus-io/milvus-proto/go-api/v2/commonpb"
"github.com/milvus-io/milvus-proto/go-api/v2/milvuspb"
"github.com/milvus-io/milvus-proto/go-api/v2/schemapb"
2023-01-11 06:35:40 +00:00
"github.com/milvus-io/milvus/internal/metastore/model"
"github.com/milvus-io/milvus/internal/proto/datapb"
"github.com/milvus-io/milvus/internal/proto/indexpb"
2022-09-05 05:29:11 +00:00
"github.com/milvus-io/milvus/internal/proto/querypb"
2023-04-06 11:14:32 +00:00
"github.com/milvus-io/milvus/pkg/log"
"github.com/milvus-io/milvus/pkg/util/commonpbutil"
"github.com/milvus-io/milvus/pkg/util/typeutil"
2022-09-05 05:29:11 +00:00
)
type watchInfo struct {
ts Timestamp
collectionID UniqueID
partitionID UniqueID
vChannels [ ] string
startPositions [ ] * commonpb . KeyDataPair
2022-10-09 17:37:21 +00:00
schema * schemapb . CollectionSchema
2022-09-05 05:29:11 +00:00
}
// Broker communicates with other components.
type Broker interface {
ReleaseCollection ( ctx context . Context , collectionID UniqueID ) error
2023-03-20 06:55:57 +00:00
ReleasePartitions ( ctx context . Context , collectionID UniqueID , partitionIDs ... UniqueID ) error
SyncNewCreatedPartition ( ctx context . Context , collectionID UniqueID , partitionID UniqueID ) error
2022-09-05 05:29:11 +00:00
GetQuerySegmentInfo ( ctx context . Context , collectionID int64 , segIDs [ ] int64 ) ( retResp * querypb . GetSegmentInfoResponse , retErr error )
WatchChannels ( ctx context . Context , info * watchInfo ) error
UnwatchChannels ( ctx context . Context , info * watchInfo ) error
Flush ( ctx context . Context , cID int64 , segIDs [ ] int64 ) error
Import ( ctx context . Context , req * datapb . ImportTaskRequest ) ( * datapb . ImportTaskResponse , error )
2022-09-26 10:06:54 +00:00
UnsetIsImportingState ( context . Context , * datapb . UnsetIsImportingStateRequest ) ( * commonpb . Status , error )
2022-12-28 03:11:30 +00:00
GetSegmentStates ( context . Context , * datapb . GetSegmentStatesRequest ) ( * datapb . GetSegmentStatesResponse , error )
2023-01-12 01:55:42 +00:00
GcConfirm ( ctx context . Context , collectionID , partitionID UniqueID ) bool
2022-09-05 05:29:11 +00:00
2022-09-23 01:36:51 +00:00
DropCollectionIndex ( ctx context . Context , collID UniqueID , partIDs [ ] UniqueID ) error
2023-01-11 06:35:40 +00:00
GetSegmentIndexState ( ctx context . Context , collID UniqueID , indexName string , segIDs [ ] UniqueID ) ( [ ] * indexpb . SegmentIndexState , error )
DescribeIndex ( ctx context . Context , colID UniqueID ) ( * indexpb . DescribeIndexResponse , error )
2022-10-10 12:31:22 +00:00
2022-10-11 13:07:23 +00:00
BroadcastAlteredCollection ( ctx context . Context , req * milvuspb . AlterCollectionRequest ) error
2022-09-05 05:29:11 +00:00
}
type ServerBroker struct {
s * Core
}
func newServerBroker ( s * Core ) * ServerBroker {
return & ServerBroker { s : s }
}
func ( b * ServerBroker ) ReleaseCollection ( ctx context . Context , collectionID UniqueID ) error {
2023-04-17 03:00:30 +00:00
log . Ctx ( ctx ) . Info ( "releasing collection" , zap . Int64 ( "collection" , collectionID ) )
2022-09-05 05:29:11 +00:00
resp , err := b . s . queryCoord . ReleaseCollection ( ctx , & querypb . ReleaseCollectionRequest {
2022-10-21 07:57:28 +00:00
Base : commonpbutil . NewMsgBase ( commonpbutil . WithMsgType ( commonpb . MsgType_ReleaseCollection ) ) ,
2022-09-05 05:29:11 +00:00
CollectionID : collectionID ,
NodeID : b . s . session . ServerID ,
} )
if err != nil {
return err
}
if resp . GetErrorCode ( ) != commonpb . ErrorCode_Success {
return fmt . Errorf ( "failed to release collection, code: %s, reason: %s" , resp . GetErrorCode ( ) , resp . GetReason ( ) )
}
2023-04-17 03:00:30 +00:00
log . Ctx ( ctx ) . Info ( "done to release collection" , zap . Int64 ( "collection" , collectionID ) )
2022-09-05 05:29:11 +00:00
return nil
}
2023-03-20 06:55:57 +00:00
func ( b * ServerBroker ) ReleasePartitions ( ctx context . Context , collectionID UniqueID , partitionIDs ... UniqueID ) error {
if len ( partitionIDs ) == 0 {
return nil
}
log := log . Ctx ( ctx ) . With ( zap . Int64 ( "collection" , collectionID ) , zap . Int64s ( "partitionIDs" , partitionIDs ) )
log . Info ( "releasing partitions" )
resp , err := b . s . queryCoord . ReleasePartitions ( ctx , & querypb . ReleasePartitionsRequest {
Base : commonpbutil . NewMsgBase ( commonpbutil . WithMsgType ( commonpb . MsgType_ReleasePartitions ) ) ,
CollectionID : collectionID ,
PartitionIDs : partitionIDs ,
} )
if err != nil {
return err
}
if resp . GetErrorCode ( ) != commonpb . ErrorCode_Success {
return fmt . Errorf ( "release partition failed, reason: %s" , resp . GetReason ( ) )
}
log . Info ( "release partitions done" )
return nil
}
func ( b * ServerBroker ) SyncNewCreatedPartition ( ctx context . Context , collectionID UniqueID , partitionID UniqueID ) error {
log := log . Ctx ( ctx ) . With ( zap . Int64 ( "collection" , collectionID ) , zap . Int64 ( "partitionID" , partitionID ) )
log . Info ( "begin to sync new partition" )
resp , err := b . s . queryCoord . SyncNewCreatedPartition ( ctx , & querypb . SyncNewCreatedPartitionRequest {
Base : commonpbutil . NewMsgBase ( commonpbutil . WithMsgType ( commonpb . MsgType_ReleasePartitions ) ) ,
CollectionID : collectionID ,
PartitionID : partitionID ,
} )
if err != nil {
return err
}
if resp . GetErrorCode ( ) != commonpb . ErrorCode_Success {
return fmt . Errorf ( "sync new partition failed, reason: %s" , resp . GetReason ( ) )
}
log . Info ( "sync new partition done" )
return nil
}
2022-09-05 05:29:11 +00:00
func ( b * ServerBroker ) GetQuerySegmentInfo ( ctx context . Context , collectionID int64 , segIDs [ ] int64 ) ( retResp * querypb . GetSegmentInfoResponse , retErr error ) {
resp , err := b . s . queryCoord . GetSegmentInfo ( ctx , & querypb . GetSegmentInfoRequest {
2022-10-21 07:57:28 +00:00
Base : commonpbutil . NewMsgBase (
commonpbutil . WithMsgType ( commonpb . MsgType_GetSegmentState ) ,
commonpbutil . WithSourceID ( b . s . session . ServerID ) ,
) ,
2022-09-05 05:29:11 +00:00
CollectionID : collectionID ,
SegmentIDs : segIDs ,
} )
return resp , err
}
func toKeyDataPairs ( m map [ string ] [ ] byte ) [ ] * commonpb . KeyDataPair {
ret := make ( [ ] * commonpb . KeyDataPair , 0 , len ( m ) )
for k , data := range m {
ret = append ( ret , & commonpb . KeyDataPair {
Key : k ,
Data : data ,
} )
}
return ret
}
func ( b * ServerBroker ) WatchChannels ( ctx context . Context , info * watchInfo ) error {
2023-04-17 03:00:30 +00:00
log . Ctx ( ctx ) . Info ( "watching channels" , zap . Uint64 ( "ts" , info . ts ) , zap . Int64 ( "collection" , info . collectionID ) , zap . Strings ( "vChannels" , info . vChannels ) )
2022-09-05 05:29:11 +00:00
resp , err := b . s . dataCoord . WatchChannels ( ctx , & datapb . WatchChannelsRequest {
CollectionID : info . collectionID ,
ChannelNames : info . vChannels ,
StartPositions : info . startPositions ,
2022-10-09 17:37:21 +00:00
Schema : info . schema ,
2022-09-05 05:29:11 +00:00
} )
if err != nil {
return err
}
if resp . GetStatus ( ) . GetErrorCode ( ) != commonpb . ErrorCode_Success {
return fmt . Errorf ( "failed to watch channels, code: %s, reason: %s" , resp . GetStatus ( ) . GetErrorCode ( ) , resp . GetStatus ( ) . GetReason ( ) )
}
2023-04-17 03:00:30 +00:00
log . Ctx ( ctx ) . Info ( "done to watch channels" , zap . Uint64 ( "ts" , info . ts ) , zap . Int64 ( "collection" , info . collectionID ) , zap . Strings ( "vChannels" , info . vChannels ) )
2022-09-05 05:29:11 +00:00
return nil
}
func ( b * ServerBroker ) UnwatchChannels ( ctx context . Context , info * watchInfo ) error {
// TODO: release flowgraph on datanodes.
return nil
}
func ( b * ServerBroker ) Flush ( ctx context . Context , cID int64 , segIDs [ ] int64 ) error {
resp , err := b . s . dataCoord . Flush ( ctx , & datapb . FlushRequest {
2022-10-21 07:57:28 +00:00
Base : commonpbutil . NewMsgBase (
commonpbutil . WithMsgType ( commonpb . MsgType_Flush ) ,
commonpbutil . WithSourceID ( b . s . session . ServerID ) ,
) ,
2022-09-05 05:29:11 +00:00
DbID : 0 ,
SegmentIDs : segIDs ,
CollectionID : cID ,
2023-01-31 04:41:53 +00:00
IsImport : true ,
2022-09-05 05:29:11 +00:00
} )
if err != nil {
return errors . New ( "failed to call flush to data coordinator: " + err . Error ( ) )
}
2022-09-26 10:06:54 +00:00
if resp . GetStatus ( ) . GetErrorCode ( ) != commonpb . ErrorCode_Success {
2022-09-05 05:29:11 +00:00
return errors . New ( resp . Status . Reason )
}
log . Info ( "flush on collection succeed" , zap . Int64 ( "collection ID" , cID ) )
return nil
}
func ( b * ServerBroker ) Import ( ctx context . Context , req * datapb . ImportTaskRequest ) ( * datapb . ImportTaskResponse , error ) {
return b . s . dataCoord . Import ( ctx , req )
}
2022-09-26 10:06:54 +00:00
func ( b * ServerBroker ) UnsetIsImportingState ( ctx context . Context , req * datapb . UnsetIsImportingStateRequest ) ( * commonpb . Status , error ) {
return b . s . dataCoord . UnsetIsImportingState ( ctx , req )
}
2022-12-28 03:11:30 +00:00
func ( b * ServerBroker ) GetSegmentStates ( ctx context . Context , req * datapb . GetSegmentStatesRequest ) ( * datapb . GetSegmentStatesResponse , error ) {
return b . s . dataCoord . GetSegmentStates ( ctx , req )
}
2022-09-23 01:36:51 +00:00
func ( b * ServerBroker ) DropCollectionIndex ( ctx context . Context , collID UniqueID , partIDs [ ] UniqueID ) error {
2023-04-17 03:00:30 +00:00
log . Ctx ( ctx ) . Info ( "dropping collection index" , zap . Int64 ( "collection" , collID ) , zap . Int64s ( "partitions" , partIDs ) )
2023-01-11 06:35:40 +00:00
rsp , err := b . s . dataCoord . DropIndex ( ctx , & indexpb . DropIndexRequest {
2022-09-05 05:29:11 +00:00
CollectionID : collID ,
2022-09-23 01:36:51 +00:00
PartitionIDs : partIDs ,
2022-09-05 05:29:11 +00:00
IndexName : "" ,
2022-10-31 03:39:33 +00:00
DropAll : true ,
2022-09-05 05:29:11 +00:00
} )
if err != nil {
return err
}
if rsp . ErrorCode != commonpb . ErrorCode_Success {
return fmt . Errorf ( rsp . Reason )
}
2023-04-17 03:00:30 +00:00
log . Ctx ( ctx ) . Info ( "done to drop collection index" , zap . Int64 ( "collection" , collID ) , zap . Int64s ( "partitions" , partIDs ) )
2022-09-05 05:29:11 +00:00
return nil
}
2023-01-11 06:35:40 +00:00
func ( b * ServerBroker ) GetSegmentIndexState ( ctx context . Context , collID UniqueID , indexName string , segIDs [ ] UniqueID ) ( [ ] * indexpb . SegmentIndexState , error ) {
resp , err := b . s . dataCoord . GetSegmentIndexState ( ctx , & indexpb . GetSegmentIndexStateRequest {
2022-09-05 05:29:11 +00:00
CollectionID : collID ,
IndexName : indexName ,
SegmentIDs : segIDs ,
} )
if err != nil {
return nil , err
}
if resp . Status . ErrorCode != commonpb . ErrorCode_Success {
return nil , errors . New ( resp . Status . Reason )
}
return resp . GetStates ( ) , nil
}
2022-09-26 10:06:54 +00:00
2022-10-11 13:07:23 +00:00
func ( b * ServerBroker ) BroadcastAlteredCollection ( ctx context . Context , req * milvuspb . AlterCollectionRequest ) error {
2022-11-08 14:51:03 +00:00
log . Info ( "broadcasting request to alter collection" , zap . String ( "collection name" , req . GetCollectionName ( ) ) , zap . Int64 ( "collection id" , req . GetCollectionID ( ) ) )
2022-11-21 02:09:10 +00:00
2023-06-25 09:20:43 +00:00
colMeta , err := b . s . meta . GetCollectionByID ( ctx , req . GetDbName ( ) , req . GetCollectionID ( ) , typeutil . MaxTimestamp , false )
2022-11-21 02:09:10 +00:00
if err != nil {
return err
}
partitionIDs := make ( [ ] int64 , len ( colMeta . Partitions ) )
for _ , p := range colMeta . Partitions {
partitionIDs = append ( partitionIDs , p . PartitionID )
}
dcReq := & datapb . AlterCollectionRequest {
CollectionID : req . GetCollectionID ( ) ,
Schema : & schemapb . CollectionSchema {
Name : colMeta . Name ,
Description : colMeta . Description ,
AutoID : colMeta . AutoID ,
Fields : model . MarshalFieldModels ( colMeta . Fields ) ,
} ,
PartitionIDs : partitionIDs ,
StartPositions : colMeta . StartPositions ,
Properties : req . GetProperties ( ) ,
}
resp , err := b . s . dataCoord . BroadcastAlteredCollection ( ctx , dcReq )
2022-10-10 12:31:22 +00:00
if err != nil {
return err
}
if resp . ErrorCode != commonpb . ErrorCode_Success {
return errors . New ( resp . Reason )
}
2022-11-08 14:51:03 +00:00
log . Info ( "done to broadcast request to alter collection" , zap . String ( "collection name" , req . GetCollectionName ( ) ) , zap . Int64 ( "collection id" , req . GetCollectionID ( ) ) )
2022-10-10 12:31:22 +00:00
return nil
}
2023-01-11 06:35:40 +00:00
func ( b * ServerBroker ) DescribeIndex ( ctx context . Context , colID UniqueID ) ( * indexpb . DescribeIndexResponse , error ) {
return b . s . dataCoord . DescribeIndex ( ctx , & indexpb . DescribeIndexRequest {
2022-09-26 10:06:54 +00:00
CollectionID : colID ,
} )
}
2023-01-12 01:55:42 +00:00
func ( b * ServerBroker ) GcConfirm ( ctx context . Context , collectionID , partitionID UniqueID ) bool {
2023-06-19 02:52:41 +00:00
log := log . Ctx ( ctx ) . With ( zap . Int64 ( "collection" , collectionID ) , zap . Int64 ( "partition" , partitionID ) )
log . Info ( "confirming if gc is finished" )
2023-01-12 01:55:42 +00:00
req := & datapb . GcConfirmRequest { CollectionId : collectionID , PartitionId : partitionID }
resp , err := b . s . dataCoord . GcConfirm ( ctx , req )
2023-06-19 02:52:41 +00:00
2023-01-12 01:55:42 +00:00
if err != nil {
2023-06-19 02:52:41 +00:00
log . Warn ( "gc is not finished" , zap . Error ( err ) )
2023-01-12 01:55:42 +00:00
return false
}
2023-06-19 02:52:41 +00:00
2023-01-12 01:55:42 +00:00
if resp . GetStatus ( ) . GetErrorCode ( ) != commonpb . ErrorCode_Success {
2023-06-19 02:52:41 +00:00
log . Warn ( "gc is not finished" , zap . String ( "code" , resp . GetStatus ( ) . GetErrorCode ( ) . String ( ) ) ,
zap . String ( "reason" , resp . GetStatus ( ) . GetReason ( ) ) )
2023-01-12 01:55:42 +00:00
return false
}
2023-06-19 02:52:41 +00:00
log . Info ( "received gc_confirm response" , zap . Bool ( "finished" , resp . GetGcFinished ( ) ) )
2023-01-12 01:55:42 +00:00
return resp . GetGcFinished ( )
}