@@ -29,26 +29,54 @@ the driver doesn't understand. For example, the
2929BSON library's ``Decimal128`` type is distinct
3030from Python's built-in ``Decimal`` type. Attempting
3131to save an instance of ``Decimal`` with {+driver-short+} results in an
32- ``InvalidDocument`` exception, as shown in the following code example:
32+ ``InvalidDocument`` exception, as shown in the following code example. Select the
33+ :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the corresponding code.
3334
34- .. io-code-block::
35- :copyable: true
35+ .. tabs::
36+
37+ .. tab:: Synchronous
38+ :tabid: sync
39+
40+ .. io-code-block::
41+ :copyable: true
42+
43+ .. input::
44+ :language: python
45+
46+ from decimal import Decimal
47+
48+ num = Decimal("45.321")
49+ db["coll"].insert_one({"num": num})
50+
51+ .. output::
52+ :language: shell
53+
54+ Traceback (most recent call last):
55+ ...
56+ bson.errors.InvalidDocument: cannot encode object: Decimal('45.321'), of
57+ type: <class 'decimal.Decimal'>
58+
59+ .. tab:: Asynchronous
60+ :tabid: async
61+
62+ .. io-code-block::
63+ :copyable: true
3664
37- .. input::
38- :language: python
65+ .. input::
66+ :language: python
3967
40- from decimal import Decimal
68+ from decimal import Decimal
4169
42- num = Decimal("45.321")
43- db["coll"].insert_one({"num": num})
70+ num = Decimal("45.321")
71+ await db["coll"].insert_one({"num": num})
4472
45- .. output::
46- :language: shell
73+ .. output::
74+ :language: shell
4775
48- Traceback (most recent call last):
49- ...
50- bson.errors.InvalidDocument: cannot encode object: Decimal('45.321'), of
51- type: <class 'decimal.Decimal'>
76+ Traceback (most recent call last):
77+ ...
78+ bson.errors.InvalidDocument: cannot encode object: Decimal('45.321'), of
79+ type: <class 'decimal.Decimal'>
5280
5381The following sections show how to define a custom type for this ``Decimal`` type.
5482
@@ -154,46 +182,97 @@ object as a keyword argument. Pass your ``CodecOptions`` object to the
154182 codec_options = CodecOptions(type_registry=type_registry)
155183 collection = db.get_collection("test", codec_options=codec_options)
156184
157- You can then encode and decode instances of the ``Decimal`` class:
185+ You can then encode and decode instances of the ``Decimal`` class. Select the
186+ :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the corresponding code.
158187
159- .. io-code-block::
160- :copyable: true
188+ .. tabs::
189+
190+ .. tab:: Synchronous
191+ :tabid: sync
161192
162- .. input ::
163- :language: python
193+ .. io-code-block ::
194+ :copyable: true
164195
165- import pprint
166-
167- collection.insert_one({"num": Decimal("45.321")})
168- my_doc = collection.find_one()
169- pprint.pprint(my_doc)
196+ .. input::
197+ :language: python
170198
171- .. output::
172- :language: shell
173-
174- {'_id': ObjectId('...'), 'num': Decimal('45.321')}
199+ import pprint
200+
201+ collection.insert_one({"num": Decimal("45.321")})
202+ my_doc = collection.find_one()
203+ pprint.pprint(my_doc)
204+
205+ .. output::
206+ :language: shell
207+
208+ {'_id': ObjectId('...'), 'num': Decimal('45.321')}
209+
210+ .. tab:: Asynchronous
211+ :tabid: async
212+
213+ .. io-code-block::
214+ :copyable: true
215+
216+ .. input::
217+ :language: python
218+
219+ import pprint
220+
221+ await collection.insert_one({"num": Decimal("45.321")})
222+ my_doc = await collection.find_one()
223+ pprint.pprint(my_doc)
224+
225+ .. output::
226+ :language: shell
227+
228+ {'_id': ObjectId('...'), 'num': Decimal('45.321')}
175229
176230To see how MongoDB stores an instance of the custom type,
177231create a new collection object without the customized codec options, then use it
178232to retrieve the document containing the custom type. The following example shows
179233that {+driver-short+} stores an instance of the ``Decimal`` class as a ``Decimal128``
180- value:
234+ value. Select the :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the
235+ corresponding code.
236+
237+ .. tabs::
238+
239+ .. tab:: Synchronous
240+ :tabid: sync
181241
182- .. io-code-block::
183- :copyable: true
242+ .. io-code-block::
243+ :copyable: true
184244
185- .. input::
186- :language: python
245+ .. input::
246+ :language: python
187247
188- import pprint
248+ import pprint
189249
190- new_collection = db.get_collection("test")
191- pprint.pprint(new_collection.find_one())
250+ new_collection = db.get_collection("test")
251+ pprint.pprint(new_collection.find_one())
192252
193- .. output::
194- :language: shell
253+ .. output::
254+ :language: shell
195255
196- {'_id': ObjectId('...'), 'num': Decimal128('45.321')}
256+ {'_id': ObjectId('...'), 'num': Decimal128('45.321')}
257+
258+ .. tab:: Asynchronous
259+ :tabid: async
260+
261+ .. io-code-block::
262+ :copyable: true
263+
264+ .. input::
265+ :language: python
266+
267+ import pprint
268+
269+ new_collection = db.get_collection("test")
270+ pprint.pprint(await new_collection.find_one())
271+
272+ .. output::
273+ :language: shell
274+
275+ {'_id': ObjectId('...'), 'num': Decimal128('45.321')}
197276
198277Encode a Subtype
199278----------------
@@ -209,23 +288,48 @@ return its value as an integer:
209288 return int(self)
210289
211290If you try to save an instance of the ``DecimalInt`` class without first registering a type
212- codec for it, {+driver-short+} raises an error:
291+ codec for it, {+driver-short+} raises an error. Select the
292+ :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the corresponding code.
293+
294+ .. tabs::
295+
296+ .. tab:: Synchronous
297+ :tabid: sync
213298
214- .. io-code-block::
215- :copyable: true
299+ .. io-code-block::
300+ :copyable: true
301+
302+ .. input::
303+ :language: python
304+
305+ collection.insert_one({"num": DecimalInt("45.321")})
306+
307+ .. output::
308+ :language: shell
309+
310+ Traceback (most recent call last):
311+ ...
312+ bson.errors.InvalidDocument: cannot encode object: Decimal('45.321'),
313+ of type: <class 'decimal.Decimal'>
216314
217- .. input::
218- :language: python
315+ .. tab:: Asynchronous
316+ :tabid: async
317+
318+ .. io-code-block::
319+ :copyable: true
219320
220- collection.insert_one({"num": DecimalInt("45.321")})
321+ .. input::
322+ :language: python
323+
324+ await collection.insert_one({"num": DecimalInt("45.321")})
221325
222- .. output::
223- :language: shell
326+ .. output::
327+ :language: shell
224328
225- Traceback (most recent call last):
226- ...
227- bson.errors.InvalidDocument: cannot encode object: Decimal('45.321'),
228- of type: <class 'decimal.Decimal'>
329+ Traceback (most recent call last):
330+ ...
331+ bson.errors.InvalidDocument: cannot encode object: Decimal('45.321'),
332+ of type: <class 'decimal.Decimal'>
229333
230334To encode an instance of the ``DecimalInt`` class, you must define a type codec for
231335the class. This type codec must inherit from the parent class's codec, ``DecimalCodec``,
@@ -240,31 +344,64 @@ as shown in the following example:
240344 return DecimalInt
241345
242346You can then add the sublcass's type codec to the type registry and encode instances
243- of the custom type:
347+ of the custom type. Select the
348+ :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the corresponding code.
244349
245- .. io-code-block::
246- :copyable: true
350+ .. tabs::
247351
248- .. input::
249- :language: python
352+ .. tab:: Synchronous
353+ :tabid: sync
354+
355+ .. io-code-block::
356+ :copyable: true
250357
251- import pprint
252- from bson.codec_options import CodecOptions
358+ .. input::
359+ :language: python
253360
254- decimal_int_codec = DecimalIntCodec()
255- type_registry = TypeRegistry([decimal_codec, decimal_int_codec])
256- codec_options = CodecOptions(type_registry=type_registry)
361+ import pprint
362+ from bson.codec_options import CodecOptions
257363
258- collection = db.get_collection("test", codec_options=codec_options)
259- collection.insert_one({"num": DecimalInt("45.321")})
260-
261- my_doc = collection.find_one()
262- pprint.pprint(my_doc)
364+ decimal_int_codec = DecimalIntCodec()
365+ type_registry = TypeRegistry([decimal_codec, decimal_int_codec])
366+ codec_options = CodecOptions(type_registry=type_registry)
263367
264- .. output::
265- :language: shell
368+ collection = db.get_collection("test", codec_options=codec_options)
369+ collection.insert_one({"num": DecimalInt("45.321")})
370+
371+ my_doc = collection.find_one()
372+ pprint.pprint(my_doc)
373+
374+ .. output::
375+ :language: shell
376+
377+ {'_id': ObjectId('...'), 'num': Decimal('45.321')}
266378
267- {'_id': ObjectId('...'), 'num': Decimal('45.321')}
379+ .. tab:: Asynchronous
380+ :tabid: async
381+
382+ .. io-code-block::
383+ :copyable: true
384+
385+ .. input::
386+ :language: python
387+
388+ import pprint
389+ from bson.codec_options import CodecOptions
390+
391+ decimal_int_codec = DecimalIntCodec()
392+ type_registry = TypeRegistry([decimal_codec, decimal_int_codec])
393+ codec_options = CodecOptions(type_registry=type_registry)
394+
395+ collection = db.get_collection("test", codec_options=codec_options)
396+ await collection.insert_one({"num": DecimalInt("45.321")})
397+
398+ my_doc = collection.find_one()
399+ pprint.pprint(my_doc)
400+
401+ .. output::
402+ :language: shell
403+
404+ {'_id': ObjectId('...'), 'num': Decimal('45.321')}
268405
269406.. note::
270407
@@ -306,8 +443,8 @@ The following code example shows this process:
306443 collection = db.get_collection("test", codec_options=codec_options)
307444
308445You can then use this reference to a collection to store instances of the ``Decimal``
309- class. Select the :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the
310- corresponding code.
446+ class. Select the
447+ :guilabel:`Synchronous` or :guilabel:`Asynchronous` tab to see the corresponding code.
311448
312449.. tabs::
313450
@@ -409,8 +546,8 @@ back into Python objects:
409546 return value
410547
411548You can then add the ``PickledBinaryDecoder`` to the codec options for a collection
412- and use it to encode and decode your custom types. Select the :guilabel:`Synchronous` or
413- :guilabel:`Asynchronous` tab to see the corresponding code.
549+ and use it to encode and decode your custom types. Select the
550+ :guilabel:`Synchronous` or :guilabel:` Asynchronous` tab to see the corresponding code.
414551
415552.. tabs::
416553
0 commit comments