Docs Menu

Docs HomeDevelop ApplicationsPython DriversPyMongo

Customize Server Selection

On this page

  • Overview
  • Customized Selection Algorithm
  • Example: Select Servers on localhost
  • API Documentation

All MongoDB drivers follow a defined algorithm when selecting a server to read or write from. By using the server_selector property of MongoClient, you can customize this algorithm to choose the server that works best for your application.

Important

Customizing the server-selection algorithm can have unintended consequences, such as degraded read or write performance.

When PyMongo executes a read operation, it performs the following steps, in order, to select a MongoDB deployment:

  1. From the list of known servers, PyMongo selects all servers that match the active read preference.

  2. If at least one readable server exists, PyMongo calls the user-defined server-selector function and passes in the list from the previous step.

  3. PyMongo applies the localThresholdMS connection setting to the list of servers returned from the function.

  4. PyMongo selects a server at random from the servers still on the list and executes the operation against this server.

When PyMongo executes a write operation, it begins by selecting all writeable servers, not just those that match the active read preference. The remaining steps are identical.

To learn more about the default server-selection algorithm, which the driver follows when you don't use the server_selector argument, see Server Selection Algorithm in the MongoDB Server manual.

When using a sharded cluster with multiple mongos servers, you might want to prefer deployments running on localhost. Operations against these deployments usually have lower latency and higher throughput. This example shows how to customize the server-selection algorithm to favor servers running on localhost.

First, write a Python function to select your preferred servers. The server-selection function must meet the following criteria:

  • Accepts a list of ServerDescription objects as a parameter

  • Returns the list of ServerDescription objects suitable for the read or write operation

  • Doesn't create or modify any ServerDescription objects

The following example defines a function named prefer_local that accepts and returns a list of ServerDescription objects:

def prefer_local(server_descriptions):
...
return servers # list containing preferred servers

Next, implement your server-selection logic in the function body. You can use any property defined in the ServerDescription class to select your preferred servers. To return only MongoDB deployments running on localhost, this example loops on the servers in server_descriptions and checks the address property of each server for the value "localhost":

def prefer_local(server_descriptions):
servers = [
server for server in server_descriptions if server.address[0] == "localhost"
]
return servers

Next, consider the case when your algorithm finds no matching servers. If your function returns an empty list, your application can't communicate with MongoDB. Therefore, return a list containing at least one ServerDescription object from your function.

In this example, if no matching server is found, the prefer_local function returns the list of servers originally passed as an argument:

def prefer_local(server_descriptions):
servers = [
server for server in server_descriptions if server.address[0] == "localhost"
]
if not servers:
return server_descriptions
return servers

Finally, instruct PyMongo to use your function. To do so, call the MongoClient constructor and pass the server_selector argument with your function name as the value:

client = pymongo.MongoClient("mongodb://<username>:<password>@<hostname>:<port>",
server_selector=prefer_local)

For more information about customizing PyMongo's server-selection algorithm, see the following API documentation:

← Compress Network Traffic