PYTHON-1839 Deprecate waitQueueMultiple option

This commit is contained in:
Prashant Mital 2019-08-09 13:51:14 -07:00
parent 62400e548d
commit 4800512c36
No known key found for this signature in database
GPG Key ID: 3D2DAA9E483ABE51
5 changed files with 58 additions and 34 deletions

View File

@ -32,6 +32,9 @@ Version 3.9 adds support for MongoDB 4.2. Highlights include:
- ``ssl_ca_certs`` has been deprecated in favor of ``tlsCAFile``.
- ``ssl_certfile`` has been deprecated in favor of ``tlsCertificateKeyFile``.
- ``ssl_pem_passphrase`` has been deprecated in favor of ``tlsCertificateKeyFilePassword``.
- ``waitQueueMultiple`` has been deprecated without replacement. This option
was a poor solution for putting an upper bound on queuing since it didn't
affect queuing in other parts of the driver.
- The ``retryWrites`` URI option now defaults to ``True``. Supported write
operations that fail with a retryable error will automatically be retried one
time, with at-most-once semantics.

View File

@ -98,21 +98,12 @@ process, increase ``maxPoolSize``::
client = MongoClient(host, port, maxPoolSize=None)
By default, any number of threads are allowed to wait for sockets to become
available, and they can wait any length of time. Override ``waitQueueMultiple``
to cap the number of waiting threads. E.g., to keep the number of waiters less
than or equal to 500::
client = MongoClient(host, port, maxPoolSize=50, waitQueueMultiple=10)
When 500 threads are waiting for a socket, the 501st that needs a socket
raises :exc:`~pymongo.errors.ExceededMaxWaiters`. Use this option to
bound the amount of queueing in your application during a load spike, at the
cost of additional exceptions.
Once the pool reaches its max size, additional threads are allowed to wait
indefinitely for sockets to become available, unless you set
``waitQueueTimeoutMS``::
Once the pool reaches its maximum size, additional threads have to wait for
sockets to become available. PyMongo does not limit the number of threads
that can wait for sockets to become available and it is the application's
responsibility to limit the size of its thread pool to bound queuing during a
load spike. Threads are allowed to wait for any length of time unless
``waitQueueTimeoutMS`` is defined::
client = MongoClient(host, port, waitQueueTimeoutMS=100)

View File

@ -658,16 +658,26 @@ INTERNAL_URI_OPTION_NAME_MAP = {
'tlscertificatekeyfilepassword': 'ssl_pem_passphrase',
}
# Map from deprecated URI option names to the updated option names.
# Case is preserved for updated option names as they are part of user warnings.
# Map from deprecated URI option names to a tuple indicating the method of
# their deprecation and any additional information that may be needed to
# construct the warning message.
URI_OPTIONS_DEPRECATION_MAP = {
'j': 'journal',
'wtimeout': 'wTimeoutMS',
'ssl_cert_reqs': 'tlsAllowInvalidCertificates',
'ssl_match_hostname': 'tlsAllowInvalidHostnames',
'ssl_crlfile': 'tlsCRLFile',
'ssl_ca_certs': 'tlsCAFile',
'ssl_pem_passphrase': 'tlsCertificateKeyFilePassword',
# format: <deprecated option name>: (<mode>, <message>),
# Supported <mode> values:
# - 'renamed': <message> should be the new option name. Note that case is
# preserved for renamed options as they are part of user warnings.
# - 'removed': <message> may suggest the rationale for deprecating the
# option and/or recommend remedial action.
'j': ('renamed', 'journal'),
'wtimeout': ('renamed', 'wTimeoutMS'),
'ssl_cert_reqs': ('renamed', 'tlsAllowInvalidCertificates'),
'ssl_match_hostname': ('renamed', 'tlsAllowInvalidHostnames'),
'ssl_crlfile': ('renamed', 'tlsCRLFile'),
'ssl_ca_certs': ('renamed', 'tlsCAFile'),
'ssl_pem_passphrase': ('renamed', 'tlsCertificateKeyFilePassword'),
'waitqueuemultiple': ('removed', (
'Instead of using waitQueueMultiple to bound queuing, limit the size '
'of the thread pool in your application server'))
}
# Augment the option validator map with pymongo-specific option information.

View File

@ -195,16 +195,27 @@ def _handle_option_deprecations(options):
"""
for optname in list(options):
if optname in URI_OPTIONS_DEPRECATION_MAP:
newoptname = URI_OPTIONS_DEPRECATION_MAP[optname]
if newoptname in options:
warn_msg = "Deprecated option '%s' ignored in favor of '%s'."
warnings.warn(warn_msg % (options.cased_key(optname),
options.cased_key(newoptname)))
options.pop(optname)
continue
warn_msg = "Option '%s' is deprecated, use '%s' instead."
warnings.warn(warn_msg % (options.cased_key(optname),
newoptname))
mode, message = URI_OPTIONS_DEPRECATION_MAP[optname]
if mode == 'renamed':
newoptname = message
if newoptname in options:
warn_msg = ("Deprecated option '%s' ignored in favor of "
"'%s'.")
warnings.warn(
warn_msg % (options.cased_key(optname),
options.cased_key(newoptname)),
DeprecationWarning, stacklevel=2)
options.pop(optname)
continue
warn_msg = "Option '%s' is deprecated, use '%s' instead."
warnings.warn(
warn_msg % (options.cased_key(optname), newoptname),
DeprecationWarning, stacklevel=2)
elif mode == 'removed':
warn_msg = "Option '%s' is deprecated. %s."
warnings.warn(
warn_msg % (options.cased_key(optname), message),
DeprecationWarning, stacklevel=2)
return options

View File

@ -485,6 +485,15 @@ class TestURI(unittest.TestCase):
"fsync": True, "wtimeoutms": 10}
self.assertEqual(res, parse_uri(uri)["options"])
def test_waitQueueMultiple_deprecated(self):
uri = "mongodb://example.com/?waitQueueMultiple=5"
with warnings.catch_warnings(record=True) as ctx:
warnings.simplefilter('always')
parse_uri(uri)
self.assertEqual(len(ctx), 1)
self.assertTrue(issubclass(ctx[0].category, DeprecationWarning))
if __name__ == "__main__":
unittest.main()