From a6b99de571f351d83b62bbb53907057069e16c9c Mon Sep 17 00:00:00 2001 From: Joseph Dougherty Date: Wed, 5 May 2021 13:37:37 -0400 Subject: [PATCH] DOCSP-15027 Introduces Versioned API in 5.0 --- source/reference.txt | 5 +- source/reference/versioned-api.txt | 333 +++++++++++++++++++++++++++++ 2 files changed, 337 insertions(+), 1 deletion(-) create mode 100644 source/reference/versioned-api.txt diff --git a/source/reference.txt b/source/reference.txt index dea3f8dbcdd..bbe69934567 100644 --- a/source/reference.txt +++ b/source/reference.txt @@ -75,7 +75,9 @@ Reference :doc:`/reference/server-sessions` Describes server sessions. - +:doc:`/reference/versioned-api` + Describes server sessions. + .. seealso:: The @@ -105,3 +107,4 @@ Reference /reference/default-mongodb-port /reference/mongodb-defaults /reference/server-sessions + /reference/versioned-api diff --git a/source/reference/versioned-api.txt b/source/reference/versioned-api.txt new file mode 100644 index 00000000000..142002c99ae --- /dev/null +++ b/source/reference/versioned-api.txt @@ -0,0 +1,333 @@ +============= +Versioned API +============= + +.. default-domain:: mongodb + +.. contents:: On this page + :local: + :backlinks: none + :depth: 1 + :class: singlecol + +What is the Versioned API, and Should You Use It? +------------------------------------------------- + +The MongoDB Versioned API lets you upgrade your MongoDB server at will, +and ensure that behavior changes between MongoDB versions do not break +your application. + +MongoDB 5.0 introduces the Versioned API for applications +communicating with MongoDB server products. The Versioned API allows +you to specify which version of the MongoDB API your application +runs against. + +The Versioned API provides long-term API stability for applications +and supports more frequent releases and automatic server upgrades. This +allows your applications to take advantage of rapidly released +features without risking backwards-breaking changes. + +The default behavior for your driver connection will continue to +function as expected, even if you do not explicitly specify +an :ref:`apiVersion `. + +The Versioned API encompasses the +:ref:`subset of MongoDB commands ` that +applications use to read and write data, create collections +and indexes, and perform other common tasks. + +Backward Compatibility Guarantee +-------------------------------- + +Your application will not experience significant behavior changes +resulting from server upgrades. This guarantee holds as long as the +new server supports your specified API version. + +To guarantee backward compatibility, your application must: + +- Declare an API version +- Only use commands and features supported in your specified API version +- Deploy with a supported version of an official driver + +Declare the API Version +----------------------- + +To use the Versioned API, upgrade to the latest driver and create your +application's MongoClient: + +.. code-block:: none + + client = MongoClient( + , + api={"version": "1", "strict": True} + ) + +Alternatively, if you are using running the :binary:`~bin.mongo` shell, +you can specify the ``--apiVersion`` and ``--apiStrict`` connection +options: + +.. code-block:: shell + + mongo --apiVersion 1 --apiStrict + +``"1"`` is currently the only API version available. + +Setting ``{ "strict" : True }`` or ``--apiStrict`` means the +server will reject all commands outside of the Versioned API. + +Migrate To Versioned API Commands +--------------------------------- + +To migrate your application to use the Versioned API, you must: + +#. Run your application's test suite with the new MongoClient options. +#. Determine which commands and features you're using that are outside + of the Versioned API. +#. Migrate to alternative commands and features in the Versioned API. + +Once your application uses only commands and features defined in the +Versioned API, you can redeploy it with the new MongoClient options +and be confident that future server upgrades won't negatively +impact your application. + +Example: :dbcommand:`count` Migration +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +This example shows how to migrate an application that implements the +:dbcommand:`count` command to an alternative method of counting +documents. Since the :dbcommand:`count` command does not belong to the +Versioned API, this application cannot use the Versioned API until the +:dbcommand:`count` command is removed from the code. + +You can use the sample code below to create a ``sales`` collection to +follow along: + +.. code-block:: javascript + + db.sales.insertMany([ + { "_id" : 1, "item" : "abc", "price" : 10, "quantity" : 2, "date" : ISODate("2021-01-01T08:00:00Z") }, + { "_id" : 2, "item" : "jkl", "price" : 20, "quantity" : 1, "date" : ISODate("2021-02-03T09:00:00Z") }, + { "_id" : 3, "item" : "xyz", "price" : 5, "quantity" : 5, "date" : ISODate("2021-02-03T09:05:00Z") }, + { "_id" : 4, "item" : "abc", "price" : 10, "quantity" : 10, "date" : ISODate("2021-02-15T08:00:00Z") }, + { "_id" : 5, "item" : "xyz", "price" : 5, "quantity" : 10, "date" : ISODate("2021-02-15T09:05:00Z") }, + { "_id" : 6, "item" : "xyz", "price" : 5, "quantity" : 5, "date" : ISODate("2021-02-15T12:05:10Z") }, + { "_id" : 7, "item" : "xyz", "price" : 5, "quantity" : 10, "date" : ISODate("2021-02-15T14:12:12Z") }, + { "_id" : 8, "item" : "abc", "price" : 10, "quantity" : 5, "date" : ISODate("2021-03-16T20:20:13Z") } + ]) + +Versioned API Error Response +~~~~~~~~~~~~~~~~~~~~~~~~ + +For example, issuing ``db.sales.count()`` results in this error: + +.. code-block:: javascript + :copyable: false + + { + "ok" : 0, + "errmsg" : "Provided apiStrict:true, but the command count is not in API Version 1", + "code" : 323, + "codeName" : "APIStrictError" + } + +However, the :dbcommand:`aggregate` command is +:ref:`in the Versioned API ` and can be used to +obtain a count in the following way: + +.. code-block:: javascript + + db.sales.aggregate([ + { + $group: { + _id: null, + count: { $count: { } } + } + } + ]) + +This results in a document where the ``count`` field contains the +number of documents in the collection: + +.. code-block:: javascript + + { "_id" : null, "count" : 8 } + +How To Use Commands and Features Outside of the Versioned API +------------------------------------------------------------- + +To use commands and features outside of the Versioned API, you can +connect to your deployment with a *non-strict* client. By default, +clients are *non-strict* unless specified otherwise in the connection. + +.. code-block:: none + + # Non-strict client + client = MongoClient( + , + api={"version": "1", "strict": False} + ) + +If you are running the :binary:`~bin.mongo` shell, you can create a +non-strict client by specifying ``--apiVersion`` but omitting the +``--apiStrict`` option. + +.. code-block:: shell + + mongo --apiVersion 1 + +Using this non-strict client allows you to run commands outside of the +Versioned API. For example, this non-strict client now allows you to +use the :dbcommand:`count` command once again. + +.. important:: + + Commands and features outside of the Versioned API do not have the same + backward compatibility guarantees as versioned alternatives. + +.. _api-v1-command-list: + +API V1 Commands +--------------- + +API V1 protects you from API-breaking changes +for the following commands: + +- :dbcommand:`abortTransaction` +- :dbcommand:`aggregate` +- :dbcommand:`authenticate` +- :dbcommand:`collMod` +- :dbcommand:`commitTransaction` +- :dbcommand:`create` +- :dbcommand:`createIndexes` +- :dbcommand:`delete` +- :dbcommand:`drop` +- :dbcommand:`dropDatabase` +- :dbcommand:`dropIndexes` +- :dbcommand:`endSessions` +- :dbcommand:`explain` +- :dbcommand:`find` +- :dbcommand:`findAndModify` +- :dbcommand:`getMore` +- :dbcommand:`insert` +- :dbcommand:`hello` +- :dbcommand:`killCursors` +- :dbcommand:`listCollections` +- :dbcommand:`listDatabases` +- :dbcommand:`listIndexes` +- :dbcommand:`ping` +- :dbcommand:`refreshSessions` +- :dbcommand:`update` + + +Parameters +---------- + +You can specify the following optional parameters for Versioned API in +your application's MongoDB driver connection code. Check the MongoDB +driver documentation for the driver you use in your application for +more information: + +.. list-table:: + :widths: 30,30,40 + :header-rows: 1 + + * - Parameter + + - Type + + - Description + + * - :ref:`apiVersion ` + + - string + + - .. _api-version-desc: + + API Version. ``"1"`` is currently the only supported API Version. + + See :ref:`APIVersionError `. + + * - :ref:`apiStrict ` + + - boolean + + - .. _api-strict-desc: + + If ``true``, your application can only use commands defined for + your specified :ref:`apiVersion `. + + If not specified, defaults to ``false``. + + See :ref:`APIStrictError `. + + * - :ref:`apiDeprecationErrors ` + + - boolean + + - .. _api-depr-desc: + + If ``true``, your application errors if it invokes a command or + behavior that is deprecated in the specified + :ref:`apiVersion `. + + If not specified, defaults to ``false``. + + See :ref:`APIDeprecationError `. + + +Behavior +-------- + +Parameter Validation +~~~~~~~~~~~~~~~~~~~~ + +Starting in MongoDB 5.0, API V1 database commands raise an error if +passed a parameter not explicitly accepted by the command. + +In MongoDB 4.4 and earlier, unrecognized parameters are silently +ignored. + +.. _api-error-responses: + +API Error Responses +~~~~~~~~~~~~~~~~~~~ + +This table shows error responses for problematic Versioned API requests. + +.. list-table:: + :widths: 25,75 + :header-rows: 1 + + * - Server Response + + - Request + + * - :ref:`APIDeprecationError ` + + - .. _api-deprecation-resp: + + Specifies ``{ apiDeprecationErrors: true }`` with + API version ``V`` and uses a behavior deprecated in ``V``. + + * - :ref:`APIStrictError ` + + - .. _api-strict-resp: + + Specifies ``{ apiStrict: true }`` with API version ``V``, + but uses a behavior not in version ``V``. + + * - :ref:`APIVersionError ` + + - .. _api-vers-resp: + + Specifies an :ref:`apiVersion ` that the server + does not support. + + * - :ref:`InvalidOptions ` + + - .. _api-invalid-opts-resp: + + Specifies ``{ apiStrict: true }`` or + ``{ apiDeprecationErrors: true }`` but omits + :ref:`apiVersion `. +