Esempio n. 1
0
        void _delete( Request& r , DbMessage& d, ShardManager* manager ){

            int flags = d.pullInt();
            bool justOne = flags & 1;
            
            uassert( "bad delete message" , d.moreJSObjs() );
            BSONObj pattern = d.nextJsObj();
            
            if ( manager->hasShardKey( pattern ) ){
                Shard& s = manager->findShard( pattern );
                doWrite( dbDelete , r , s.getServer() );
                return;
            }
            
            if ( ! justOne && ! pattern.hasField( "_id" ) )
                throw UserException( "can only delete with a non-shard key pattern if can delete as many as we find" );
            
            vector<Shard*> shards;
            manager->getShardsForQuery( shards , pattern );
            
            set<string> seen;
            for ( vector<Shard*>::iterator i=shards.begin(); i!=shards.end(); i++){
                Shard * s = *i;
                if ( seen.count( s->getServer() ) )
                    continue;
                seen.insert( s->getServer() );
                doWrite( dbDelete , r , s->getServer() );
            }
        }
Esempio n. 2
0
 void ShardManager::ensureIndex(){
     set<string> seen;
     
     for ( vector<Shard*>::const_iterator i=_shards.begin(); i!=_shards.end(); i++ ){
         Shard* s = *i;
         if ( seen.count( s->getServer() ) )
             continue;
         seen.insert( s->getServer() );
         s->ensureIndex();
     }
 }
Esempio n. 3
0
    Shard* ShardManager::findShardOnServer( const string& server ) const {

        for ( vector<Shard*>::const_iterator i=_shards.begin(); i!=_shards.end(); i++ ){
            Shard* s = *i;
            if ( s->getServer() == server )
                return s;
        }

        return 0;
    }
Esempio n. 4
0
    ServerShardVersion ShardManager::getVersion( const string& server ) const{
        // TODO: cache or something?
        
        ServerShardVersion max = 0;

        for ( vector<Shard*>::const_iterator i=_shards.begin(); i!=_shards.end(); i++ ){
            Shard* s = *i;
            if ( s->getServer() != server )
                continue;
            
            if ( s->_lastmod > max )
                max = s->_lastmod;
        }        

        return max;
    }
Esempio n. 5
0
        virtual void queryOp( Request& r ){
            QueryMessage q( r.d() );
            
            log(3) << "shard query: " << q.ns << "  " << q.query << endl;
            
            if ( q.ntoreturn == 1 && strstr(q.ns, ".$cmd") )
                throw UserException( "something is wrong, shouldn't see a command here" );

            ShardManager * info = r.getShardManager();
            assert( info );
            
            Query query( q.query );

            vector<Shard*> shards;
            info->getShardsForQuery( shards , query.getFilter()  );
            
            set<ServerAndQuery> servers;
            map<string,int> serverCounts;
            for ( vector<Shard*>::iterator i = shards.begin(); i != shards.end(); i++ ){
                servers.insert( (*i)->getServer() );
                int& num = serverCounts[(*i)->getServer()];
                num++;
            }
            
            ShardedCursor * cursor = 0;
            
            BSONObj sort = query.getSort();
            
            if ( sort.isEmpty() ){
                // 1. no sort, can just hit them in serial
                cursor = new SerialServerShardedCursor( servers , q );
            }
            else {
                int shardKeyOrder = info->getShardKey().canOrder( sort );
                if ( shardKeyOrder ){
                    // 2. sort on shard key, can do in serial intelligently
                    set<ServerAndQuery> buckets;
                    for ( vector<Shard*>::iterator i = shards.begin(); i != shards.end(); i++ ){
                        Shard * s = *i;
                        BSONObj extra = BSONObj();
                        if ( serverCounts[s->getServer()] > 1 ){
                            BSONObjBuilder b;
                            s->getFilter( b );
                            extra = b.obj();
                        }
                        buckets.insert( ServerAndQuery( s->getServer() , extra , s->getMin() ) );
                    }
                    cursor = new SerialServerShardedCursor( buckets , q , shardKeyOrder );
                }
                else {
                    // 3. sort on non-sharded key, pull back a portion from each server and iterate slowly
                    cursor = new ParallelSortShardedCursor( servers , q , sort );
                }
            }

            assert( cursor );
            if ( ! cursor->sendNextBatch( r ) ){
                delete( cursor );
                return;
            }
            log(6) << "storing cursor : " << cursor->getId() << endl;
            cursorCache.store( cursor );
        }