To remove a shard you must ensure the shard's data is migrated to the remaining shards in the cluster. This procedure describes how to safely migrate data and remove a shard.
About this Task
Creating, sharding, or moving collections while performing this procedure may cause interruptions and lead to unexpected results.
Do not use this procedure to migrate an entire cluster to new hardware. To migrate, see Migrate a Self-Managed Sharded Cluster to Different Hardware.
When you remove a shard in a cluster with an uneven chunk distribution, the balancer first removes the chunks from the draining shard and then balances the remaining uneven chunk distribution.
Removing a shard may cause an open change stream cursor to close, and the closed change stream cursor may not be fully resumable.
You can safely restart a cluster during a shard removal process. If you restart a cluster during an ongoing draining process, draining continues automatically after the cluster components restart. MongoDB records the shard draining status in the
config.shardscollection.
Before you Begin
This procedure uses the
sh.moveCollection()method to move collections off of the removed shard. Before you begin this procedure, review themoveCollectionconsiderations and requirements to understand the command behavior.To remove a shard, first connect to one of the cluster's
mongosinstances usingmongosh.
Note
When removing multiple shards, remove them simultaneously rather than one at a time. Removing one shard at a time causes the balancer to drain data into other remaining shards. A shard can only participate in one chunk migration at a time, so removing one shard limits the throughput of data migration.
Steps
Ensure the balancer is enabled.
To migrate data from a shard, the balancer process must
be enabled. To check the balancer state, use the
sh.getBalancerState() method:
sh.getBalancerState()
If the operation returns true, the balancer is enabled.
If the operation returns false, see
Enable the Balancer.
Determine the name of the shard to remove.
To find the name of the shard, run the listShards command:
db.adminCommand( { listShards: 1 } )
The shards._id field contains the shard name.
Start draining the shard.
Run the startShardDraining command to start
moving chunks from the sharded collections to the other shards
in the cluster:
db.adminCommand( { startShardDraining: "shard04" } )
If you need to remove multiple shards, you can start the draining processes to run in parallel.
Move collections.
When you create a collection on mongos and
don't call shardCollection, that collection
remains unsharded and MongoDB stores it in full on a
particular shard in the cluster. Databases that use the
shard as a primary, also store their collections on the
shard.
If the shard you want to remove contains an unsharded collection or a primary database, you need to move the collection to another shard.
To identify whether the shard you want to remove contains
these collection and to see the draining status, run the
shardDrainingStatus command and check the
array for the collectionsToMove output field:
db.adminCommand( { shardDrainingStatus: "shard04" } )
{ msg: "draining ongoing", state: "ongoing", remaining: { chunks: Long(2), dbs: Long(2), jumboChunks: Long(0), collectionsToMove: Long(2) }, shard: "shard04", note: "you need to call moveCollection for collectionsToMove and afterwards movePrimary for the dbsToMove", dbsToMove: [ "accounts", ], collectionsToMove: [ "accounts.us-east", "accounts.us-west", "locations.us", ], ok: 1, operationTime: Timestamp(1575399086, 1655), $clusterTime: { clusterTime: Timestamp(1575399086, 1655), signature: { hash: BinData(0,"XBrTmjMMe82fUtVLRm13GBVtRE8="), keyId: Long("6766255701040824328") } } }
Any collection found in the collectionsToMove field is
a collection stored on this shard. Before you can remove
the shard, you must first move these collections to
another shard.
To move a collection to another shard, use the
moveCollection command:
db.adminCommand( { moveCollection: "accounts.us-east", toShard: "shard05" } )
Move primaries.
Sharded clusters designate a specific shard to serve as the primary shard for a database. If the shard you want to remove is a primary, you need to move it to a different shard.
To identify primaries, run the
shardDrainingStatus command and check the
array on the dbsToMove output field.
db.adminCommand( { shardDrainingStatus: "shard04" } )
{ msg: "draining ongoing", state: "ongoing", remaining: { chunks: Long(2), dbs: Long(2), jumboChunks: Long(0), collectionsToMove: Long(2) }, shard: "shard04", note: "you need to call moveCollection for collectionsToMove and afterwards movePrimary for the dbsToMove", dbsToMove: [ "accounts", ], collectionsToMove: [ ], ok: 1, operationTime: Timestamp(1575399086, 1655), $clusterTime: { clusterTime: Timestamp(1575399086, 1655), signature: { hash: BinData(0,"XBrTmjMMe82fUtVLRm13GBVtRE8="), keyId: Long("6766255701040824328") } } }
Each database shown in the dbsToMove field is a
database you need to move onto a different shard.
To move the database, use the movePrimary
command:
db.adminCommand( { movePrimary: "accounts", to: "shard05" })
Remove the shard.
Before you remove the shard, check that the draining operation is complete.
To check the status of the draining operation, run the
shardDrainingStatus command:
db.adminCommand( { shardDrainingStatus: "shard04" } )
{ "msg" : "draining completed successfully", "state" : "drainingComplete", "ok" : 1, "$clusterTime" : { "clusterTime" : Timestamp(1771839836, 139), "signature" : { "hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="), "keyId" : NumberLong(0) } }, "operationTime" : Timestamp(1771839836, 139) }
When the state field returns drainingComplete for
the shard you want to remove, the draining process is
complete. You can now remove the shard.
To remove the shard, run the
commitShardRemoval command:
db.adminCommand( { commitShardRemoval: "shard04" } )
{ "ok" : 1, "$clusterTime" : { "clusterTime" : Timestamp(1771840037, 12), "signature" : { "hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="), "keyId" : NumberLong(0) } }, "operationTime" : Timestamp(1771840037, 12) }
If the shard is not completely drained, the command returns an error.