o
    'hK                     @  s  U d Z ddlmZ ddlZddlZddlZddlZddlZddlZddl	m
Z
mZmZmZmZmZmZmZmZmZmZ ddlmZmZmZmZ ddlmZ ddlmZmZ ddlm Z m!Z!m"Z"m#Z#m$Z$ dd	l%m&Z& dd
l'm(Z( ddl)m*Z* ddl+m,Z, ddl-m.Z. ddl/m0Z0 ddl1m2Z2 ddl3m4Z4 ddl5m6Z6 ddl7m8Z8 ej9ej:ej;ej<ej=ej>dZ?G dd dZ@G dd dZAe
reeeBef  ZCneZCdZDG dd deCZEeEeAjFdZGdeHd< 	 eEeAjIdZJdeHd< 	 eEeAjKdZLdeHd< 	 eLZMdeHd< 	 dd&d'ZNdd*d+ZOeMfdd-d.ZPeMfdd1d2ZQeMfdd5d6ZRdd9d:ZSdd<d=ZTddAdBZUddCdDZVddEdFZWddHdIZXddKdLZYddMdNZZddPdQZ[ddSdTZ\ddUdVZ]ddWdXZ^ddYdZZ_dd\d]Z`dd_d`ZaddbdcZbddedfZcddhdiZdddjdkZeddmdnZfi doeYdpe]dqeXdreSdsecdteddueedve[dweTdxdydz d{e`d|efd}ebd~e^de\deZde_deaiZgdeHd< ehegZidddZjdddZkdddZldddZmdddZndddZodddZpdddZqdddZrdddZsdddZtdddZudddZvdddZwdddZxdddZydddZzdddZ{i e|ene}esejere"eke~eqeepeBenedenejeueete*emeele&eye,e{e.eze0eve2eoe4eoe6ewe(exiZdeHd< i ZdeHd< eD ]Zeedrwee eej< qhedd eD ZeMfdddZdddZdddZdddZdddZe0dede*de(de6de.de,diZdeHd< eBee}eejee2ee&eiZdeHd< dddd̈́ZdddфZdddԄZdS (   a\  Tools for using Python's :mod:`json` module with BSON documents.

This module provides two helper methods `dumps` and `loads` that wrap the
native :mod:`json` methods and provide explicit BSON conversion to and from
JSON. :class:`~bson.json_util.JSONOptions` provides a way to control how JSON
is emitted and parsed, with the default being the Relaxed Extended JSON format.
:mod:`~bson.json_util` can also generate Canonical or legacy `Extended JSON`_
when :const:`CANONICAL_JSON_OPTIONS` or :const:`LEGACY_JSON_OPTIONS` is
provided, respectively.

.. _Extended JSON: https://github.com/mongodb/specifications/blob/master/source/extended-json/extended-json.md

Example usage (deserialization):

.. doctest::

   >>> from bson.json_util import loads
   >>> loads(
   ...     '[{"foo": [1, 2]}, {"bar": {"hello": "world"}}, {"code": {"$scope": {}, "$code": "function x() { return 1; }"}}, {"bin": {"$type": "80", "$binary": "AQIDBA=="}}]'
   ... )
   [{'foo': [1, 2]}, {'bar': {'hello': 'world'}}, {'code': Code('function x() { return 1; }', {})}, {'bin': Binary(b'...', 128)}]

Example usage with :const:`RELAXED_JSON_OPTIONS` (the default):

.. doctest::

   >>> from bson import Binary, Code
   >>> from bson.json_util import dumps
   >>> dumps(
   ...     [
   ...         {"foo": [1, 2]},
   ...         {"bar": {"hello": "world"}},
   ...         {"code": Code("function x() { return 1; }")},
   ...         {"bin": Binary(b"")},
   ...     ]
   ... )
   '[{"foo": [1, 2]}, {"bar": {"hello": "world"}}, {"code": {"$code": "function x() { return 1; }"}}, {"bin": {"$binary": {"base64": "AQIDBA==", "subType": "00"}}}]'

Example usage (with :const:`CANONICAL_JSON_OPTIONS`):

.. doctest::

   >>> from bson import Binary, Code
   >>> from bson.json_util import dumps, CANONICAL_JSON_OPTIONS
   >>> dumps(
   ...     [
   ...         {"foo": [1, 2]},
   ...         {"bar": {"hello": "world"}},
   ...         {"code": Code("function x() { return 1; }")},
   ...         {"bin": Binary(b"")},
   ...     ],
   ...     json_options=CANONICAL_JSON_OPTIONS,
   ... )
   '[{"foo": [{"$numberInt": "1"}, {"$numberInt": "2"}]}, {"bar": {"hello": "world"}}, {"code": {"$code": "function x() { return 1; }"}}, {"bin": {"$binary": {"base64": "AQIDBA==", "subType": "00"}}}]'

Example usage (with :const:`LEGACY_JSON_OPTIONS`):

.. doctest::

   >>> from bson import Binary, Code
   >>> from bson.json_util import dumps, LEGACY_JSON_OPTIONS
   >>> dumps(
   ...     [
   ...         {"foo": [1, 2]},
   ...         {"bar": {"hello": "world"}},
   ...         {"code": Code("function x() { return 1; }", {})},
   ...         {"bin": Binary(b"")},
   ...     ],
   ...     json_options=LEGACY_JSON_OPTIONS,
   ... )
   '[{"foo": [1, 2]}, {"bar": {"hello": "world"}}, {"code": {"$code": "function x() { return 1; }", "$scope": {}}}, {"bin": {"$binary": "AQIDBA==", "$type": "00"}}]'

Alternatively, you can manually pass the `default` to :func:`json.dumps`.
It won't handle :class:`~bson.binary.Binary` and :class:`~bson.code.Code`
instances (as they are extended strings you can't provide custom defaults),
but it will be faster as there is less recursion.

.. note::
   If your application does not need the flexibility offered by
   :class:`JSONOptions` and spends a large amount of time in the `json_util`
   module, look to
   `python-bsonjs <https://pypi.python.org/pypi/python-bsonjs>`_ for a nice
   performance improvement. `python-bsonjs` is a fast BSON to MongoDB
   Extended JSON converter for Python built on top of
   `libbson <https://github.com/mongodb/libbson>`_. `python-bsonjs` works best
   with PyMongo when using :class:`~bson.raw_bson.RawBSONDocument`.
    )annotationsN)TYPE_CHECKINGAnyCallableMappingMutableMappingOptionalSequenceTupleTypeUnioncast)ALL_UUID_SUBTYPESUUID_SUBTYPEBinaryUuidRepresentation)Code)CodecOptionsDatetimeConversion)_MAX_UTC_MSEPOCH_AWARE
DatetimeMS_datetime_to_millis_millis_to_datetime)DBRef)
Decimal128)Int64)MaxKey)MinKey)ObjectId)Regex)RE_TYPE	Timestamp)utc)ilmsuxc                   @     e Zd ZdZ	 dZ	 dZdS )DatetimeRepresentationr         N)__name__
__module____qualname__LEGACY
NUMBERLONGISO8601 r5   r5   J/var/www/html/olx_land/venv/lib/python3.10/site-packages/bson/json_util.pyr,      s    

r,   c                   @  r+   )JSONModer   r-   r.   N)r/   r0   r1   r2   RELAXED	CANONICALr5   r5   r5   r6   r7      s    
r7   l        c                      s   e Zd ZU ded< ded< ded< ded< ded< d fddZdddejfd fddZd  fddZd! fddZ	d"ddZ
  ZS )#JSONOptionsint	json_modeboolstrict_number_longdatetime_representationstrict_uuidzType[MutableMapping[str, Any]]document_classargsr   kwargsc                   s   t    dS )a  Encapsulates JSON options for :func:`dumps` and :func:`loads`.

        :param strict_number_long: If ``True``, :class:`~bson.int64.Int64` objects
            are encoded to MongoDB Extended JSON's *Strict mode* type
            `NumberLong`, ie ``'{"$numberLong": "<number>" }'``. Otherwise they
            will be encoded as an `int`. Defaults to ``False``.
        :param datetime_representation: The representation to use when encoding
            instances of :class:`datetime.datetime`. Defaults to
            :const:`~DatetimeRepresentation.LEGACY`.
        :param strict_uuid: If ``True``, :class:`uuid.UUID` object are encoded to
            MongoDB Extended JSON's *Strict mode* type `Binary`. Otherwise it
            will be encoded as ``'{"$uuid": "<hex>" }'``. Defaults to ``False``.
        :param json_mode: The :class:`JSONMode` to use when encoding BSON types to
            Extended JSON. Defaults to :const:`~JSONMode.LEGACY`.
        :param document_class: BSON documents returned by :func:`loads` will be
            decoded to an instance of this class. Must be a subclass of
            :class:`collections.MutableMapping`. Defaults to :class:`dict`.
        :param uuid_representation: The :class:`~bson.binary.UuidRepresentation`
            to use when encoding and decoding instances of :class:`uuid.UUID`.
            Defaults to :const:`~bson.binary.UuidRepresentation.UNSPECIFIED`.
        :param tz_aware: If ``True``, MongoDB Extended JSON's *Strict mode* type
            `Date` will be decoded to timezone aware instances of
            :class:`datetime.datetime`. Otherwise they will be naive. Defaults
            to ``False``.
        :param tzinfo: A :class:`datetime.tzinfo` subclass that specifies the
            timezone from which :class:`~datetime.datetime` objects should be
            decoded. Defaults to :const:`~bson.tz_util.utc`.
        :param datetime_conversion: Specifies how UTC datetimes should be decoded
            within BSON. Valid options include 'datetime_ms' to return as a
            DatetimeMS, 'datetime' to return as a datetime.datetime and
            raising a ValueError for out-of-range values, 'datetime_auto' to
            return DatetimeMS objects when the underlying datetime is
            out-of-range and 'datetime_clamp' to clamp to the minimum and
            maximum possible datetimes. Defaults to 'datetime'. See
            :ref:`handling-out-of-range-datetimes` for details.
        :param args: arguments to :class:`~bson.codec_options.CodecOptions`
        :param kwargs: arguments to :class:`~bson.codec_options.CodecOptions`

        .. seealso:: The specification for Relaxed and Canonical `Extended JSON`_.

        .. versionchanged:: 4.0
           The default for `json_mode` was changed from :const:`JSONMode.LEGACY`
           to :const:`JSONMode.RELAXED`.
           The default for `uuid_representation` was changed from
           :const:`~bson.binary.UuidRepresentation.PYTHON_LEGACY` to
           :const:`~bson.binary.UuidRepresentation.UNSPECIFIED`.

        .. versionchanged:: 3.5
           Accepts the optional parameter `json_mode`.

        .. versionchanged:: 4.0
           Changed default value of `tz_aware` to False.
        N)super__init__)selfrB   rC   	__class__r5   r6   rE      s   6zJSONOptions.__init__NclsType[JSONOptions]Optional[bool]Optional[int]returnc                   sz  | dd|d< |d r| dt|d< |tjtjtjd fvr#tdttt	 j
| g|R i |}|tjtjtjfvrAtd||_|jtjkro|rPtd|d tjfvr[td|dvrctd	d|_tj|_d
|_|S |jtjkr|dvr}td|d tjfvrtd|dvrtd	d
|_tj|_d
|_|S d|_tj|_d|_|d ur||_|d ur||_|d ur||_|S )Ntz_awareFtzinfoznJSONOptions.datetime_representation must be one of LEGACY, NUMBERLONG, or ISO8601 from DatetimeRepresentation.zQJSONOptions.json_mode must be one of LEGACY, RELAXED, or CANONICAL from JSONMode.z<Cannot specify strict_number_long=True with JSONMode.RELAXEDz_datetime_representation must be DatetimeRepresentation.ISO8601 or omitted with JSONMode.RELAXED)NTz6Cannot specify strict_uuid=False with JSONMode.RELAXEDTz=Cannot specify strict_number_long=False with JSONMode.RELAXEDzbdatetime_representation must be DatetimeRepresentation.NUMBERLONG or omitted with JSONMode.RELAXED)getr$   r,   r2   r3   r4   
ValueErrorr   r:   rD   __new__r7   r8   r9   r<   r>   r?   r@   )rI   r>   r?   r@   r<   rB   rC   rF   rG   r5   r6   rR   1  sl   	 zJSONOptions.__new__strc                   s    d | j| j| j| jt  S )Nz[strict_number_long={!r}, datetime_representation={!r}, strict_uuid={!r}, json_mode={!r}, {})formatr>   r?   r@   r<   rD   _arguments_repr)rF   rG   r5   r6   rU   t  s   zJSONOptions._arguments_reprdict[Any, Any]c                   s*   t   }|| j| j| j| jd |S )Nr>   r?   r@   r<   )rD   _options_dictupdater>   r?   r@   r<   )rF   options_dictrG   r5   r6   rX     s   
zJSONOptions._options_dictc                 K  s@   |   }dD ]}||t| |||< q|| tdi |S )a  
        Make a copy of this JSONOptions, overriding some options::

            >>> from bson.json_util import CANONICAL_JSON_OPTIONS
            >>> CANONICAL_JSON_OPTIONS.tz_aware
            True
            >>> json_options = CANONICAL_JSON_OPTIONS.with_options(tz_aware=False, tzinfo=None)
            >>> json_options.tz_aware
            False

        .. versionadded:: 3.12
        rW   Nr5   )rX   rP   getattrrY   r:   )rF   rC   optsoptr5   r5   r6   with_options  s
   
zJSONOptions.with_options)rB   r   rC   r   )rI   rJ   r>   rK   r?   rL   r@   rK   r<   r;   rB   r   rC   r   rM   r:   )rM   rS   )rM   rV   )rC   r   rM   r:   )r/   r0   r1   __annotations__rE   r7   r8   rR   rU   rX   r^   __classcell__r5   r5   rG   r6   r:      s   
 :Cr:   )r<   LEGACY_JSON_OPTIONSCANONICAL_JSON_OPTIONSRELAXED_JSON_OPTIONSDEFAULT_JSON_OPTIONSobjr   rB   rC   rM   rS   c                 O  s*   | dt}tjt| |g|R i |S )aQ  Helper function that wraps :func:`json.dumps`.

    Recursive function that handles all BSON types including
    :class:`~bson.binary.Binary` and :class:`~bson.code.Code`.

    :param json_options: A :class:`JSONOptions` instance used to modify the
        encoding of MongoDB Extended JSON types. Defaults to
        :const:`DEFAULT_JSON_OPTIONS`.

    .. versionchanged:: 4.0
       Now outputs MongoDB Relaxed Extended JSON by default (using
       :const:`DEFAULT_JSON_OPTIONS`).

    .. versionchanged:: 3.4
       Accepts optional parameter `json_options`. See :class:`JSONOptions`.
    json_options)poprd   jsondumps_json_convert)re   rB   rC   rf   r5   r5   r6   ri     s   ri   r(   Union[str, bytes, bytearray]c                   sP   | dt  jtu r fdd|d< n fdd|d< tj| g|R i |S )a  Helper function that wraps :func:`json.loads`.

    Automatically passes the object_hook for BSON type conversion.

    Raises ``TypeError``, ``ValueError``, ``KeyError``, or
    :exc:`~bson.errors.InvalidId` on invalid MongoDB Extended JSON.

    :param json_options: A :class:`JSONOptions` instance used to modify the
        decoding of MongoDB Extended JSON types. Defaults to
        :const:`DEFAULT_JSON_OPTIONS`.

    .. versionchanged:: 4.0
       Now loads :class:`datetime.datetime` instances as naive by default. To
       load timezone aware instances utilize the `json_options` parameter.
       See :ref:`tz_aware_default_change` for an example.

    .. versionchanged:: 3.5
       Parses Relaxed and Canonical Extended JSON as well as PyMongo's legacy
       format. Now raises ``TypeError`` or ``ValueError`` when parsing JSON
       type wrappers with values of the wrong type or any extra keys.

    .. versionchanged:: 3.4
       Accepts optional parameter `json_options`. See :class:`JSONOptions`.
    rf   c                   
   t |  S N)object_hookre   rf   r5   r6   <lambda>     
 zloads.<locals>.<lambda>rn   c                   rl   rm   )object_pairs_hook)pairsrp   r5   r6   rq     rr   rs   )rg   rd   rA   dictrh   loads)r(   rB   rC   r5   rp   r6   rv     s
   
rv   rf   c                   sn   t | dr fdd|  D S t | dr%t| ttfs% fdd| D S zt|  W S  ty6   |  Y S w )z]Recursive helper method that converts BSON types so they can be
    converted into json.
    itemsc                   s   i | ]
\}}|t | qS r5   rj   ).0kvrp   r5   r6   
<dictcomp>  s    z!_json_convert.<locals>.<dictcomp>__iter__c                   s   g | ]}t | qS r5   rx   )ry   r{   rp   r5   r6   
<listcomp>  s    z!_json_convert.<locals>.<listcomp>)hasattrrw   
isinstancerS   bytesdefault	TypeErrorre   rf   r5   rp   r6   rj     s   
rj   rt   Sequence[Tuple[str, Any]]c                 C  s   t || |S rm   )rn   rA   )rt   rf   r5   r5   r6   rs     s   rs   dctMapping[str, Any]c                 C  s4   d }| D ]
}|t v r|} nq|rt| | |S | S rm   )_PARSERS_SET_PARSERS)r   rf   matchrz   r5   r5   r6   rn     s   rn   docdummy0c                 C  sJ   | d }t |ttfs| S d}| ddD ]
}|t|dO }qt||S )N$regexr   $options )r   rS   r   rP   _RE_OPT_TABLEr    )r   r   patternflagsr]   r5   r5   r6   _parse_legacy_regex  s   
r   Union[Binary, uuid.UUID]c                 C  sd   t | dkrtd|  t| d tstd|  |jtjkr+tt	
| d S t	
| d S )z*Decode a JSON legacy $uuid to Python UUID.r-   zBad $uuid, extra field(s): $uuidz$uuid must be a string: )lenr   r   rS   uuid_representationr   UNSPECIFIEDr   	from_uuiduuidUUIDr   rf   r5   r5   r6   _parse_legacy_uuid)  s   r   datasubtyper;   c                 C  sn   |t v r(|j}t| |}|tjkr|S |tkrtj}n|tjkr#tj}||S |dkr2t	t
j| S t| |S Nr   )r   r   r   r   r   r   STANDARDPYTHON_LEGACYas_uuidr   r   r   )r   r   rf   r   binary_valuer5   r5   r6   _binary_or_uuid5  s   




r   c                 C  sh   t | d trd| d  | d< t| d d}|dkr%t| d dd  d}t| d  }t|||S )N$type%02x   l       $binary)r   r;   base64	b64decodeencoder   )r   rf   r   r   r5   r5   r6   _parse_legacy_binaryJ  s   r   c                 C  s   | d }|d }|d }t |tstd|  t |tr#t|dkr*td|  t|dkr7td|  t| }t|t|d|S )	Nr   r   subTypez!$binary base64 must be a string: r.   z7$binary subType must be a string at most 2 characters: z=$binary must include only "base64" and "subType" components: r   )	r   rS   r   r   r   r   r   r   r;   )r   rf   binaryb64r   r   r5   r5   r6   _parse_canonical_binaryT  s   
r   $Union[datetime.datetime, DatetimeMS]c              
   C  s  | d }t | dkrtd|  t|tr<zT|d dkr'|dd }d}nC|d dv r@|d	 d
kr@|dd }|dd }n*|d dv rS|dd }|dd }n|d	 dv rf|dd	 }|d	d }n|}d}W n ty } z	td|d|d}~ww |d}d}|dkrtt||d d }|d| }t	j	
|dj|td}|r|dkrt |dkr|dd d
\}	}
t|	d t|
d  }n+t |dkrt|dd d t|dd d  }nt |dkrt|dd d }|d dkr|d9 }|t	j|d }|jr)|jr||j}|jtjkr't|S |S |jdd}|jtjkr:t|S |S tt|td|S )z3Decode a JSON datetime to python datetime.datetime.$dater-   zBad $date, extra field(s): ZNi)+-:r   z
time data z( does not match ISO-8601 datetime format.r   i@B %Y-%m-%dT%H:%M:%S)microsecondrO   r   i  <         r   )secondsrO   zCodecOptions[Any])r   r   r   rS   
IndexErrorrQ   rfindr;   floatdatetimestrptimereplacer$   split	timedeltarN   rO   
astimezonedatetime_conversionr   DATETIME_MSr   r   r   )r   rf   dtmdtoffsetexc	dot_indexr   awarehoursminutessecsaware_tzinfo_noner5   r5   r6   _parse_canonical_datetimec  sl   
*r   r   c                 C  s&   t | dkrtd|  t| d S )z1Decode a JSON ObjectId to bson.objectid.ObjectId.r-   zBad $oid, extra field(s): $oid)r   r   r   r   r   r5   r5   r6   _parse_canonical_oid  s   r   c                 C  *   | d }t | dkrtd|  t|S )z&Decode a JSON symbol to Python string.$symbolr-   zBad $symbol, extra field(s): )r   r   rS   )r   r   symbolr5   r5   r6   _parse_canonical_symbol     r   r   c                 C  s6   | D ]}|dvrt d|  qt| d | ddS )z%Decode a JSON code to bson.code.Code.$code$scopezBad $code, extra field(s): r   r   )scope)r   r   rP   )r   r   keyr5   r5   r6   _parse_canonical_code  s
   r   
Regex[str]c                 C  sl   | d }t | dkrtd|  t |dkrtd|  |d }t|ts/tdt| t|d |S )	z(Decode a JSON regex to bson.regex.Regex.$regularExpressionr-   z(Bad $regularExpression, extra field(s): r.   zLBad $regularExpression must include only "pattern and "options" components: optionszCBad $regularExpression options, options must be string, was type %sr   )r   r   r   rS   typer    )r   r   regexr\   r5   r5   r6   _parse_canonical_regex  s   

r   c                 C  s^   t | dtr-d| v r-t | dttdfr-t| d| dfd| ddi| S | S )z(Decode a JSON DBRef to bson.dbref.DBRef.$refz$idz$dbNdatabase)r   rP   rS   r   r   rg   r   r5   r5   r6   _parse_canonical_dbref  s   *r   c                 C  s   | d }t | dkrtd|  t|trB| }|jdur&td| t|jts3td| t |dkr@td| |S td	|  )
z9Decode a JSON (deprecated) DBPointer to bson.dbref.DBRef.
$dbPointerr-   z Bad $dbPointer, extra field(s): Nz!Bad $dbPointer, extra field $db: z)Bad $dbPointer, $id must be an ObjectId: r.   z)Bad $dbPointer, extra field(s) in DBRef: z"Bad $dbPointer, expected a DBRef: )r   r   r   r   as_docr   idr   )r   r   dbref	dbref_docr5   r5   r6   _parse_canonical_dbpointer  s   

r   c                 C  B   | d }t | dkrtd|  t|tstd|  t|S )z"Decode a JSON int32 to python int.
$numberIntr-   z Bad $numberInt, extra field(s): z$numberInt must be string: )r   r   r   rS   r;   )r   r   i_strr5   r5   r6   _parse_canonical_int32     
r   r   c                 C  r   )z(Decode a JSON int64 to bson.int64.Int64.$numberLongr-   z!Bad $numberLong, extra field(s): )r   r   r   )r   r   l_strr5   r5   r6   _parse_canonical_int64  r   r   r   c                 C  r   )z%Decode a JSON double to python float.$numberDoubler-   z#Bad $numberDouble, extra field(s): z$numberDouble must be string: )r   r   r   rS   r   r   r   d_strr5   r5   r6   _parse_canonical_double   r   r  r   c                 C  r   )z7Decode a JSON decimal128 to bson.decimal128.Decimal128.$numberDecimalr-   z$Bad $numberDecimal, extra field(s): z$numberDecimal must be string: )r   r   r   rS   r   r   r5   r5   r6   _parse_canonical_decimal128
  r   r  r   c                 C  sJ   t | d tus| d dkrtd|  t| dkr"td|  t S )z,Decode a JSON MinKey to bson.min_key.MinKey.$minKeyr-   z$minKey value must be 1: Bad $minKey, extra field(s): )r   r;   r   r   r   r   r5   r5   r6   _parse_canonical_minkey  s
   r  r   c                 C  sH   t | d tus| d dkrtd| ft| dkr!td|  t S )z,Decode a JSON MaxKey to bson.max_key.MaxKey.$maxKeyr-   z$maxKey value must be 1: %sr  )r   r;   r   r   r   r   r5   r5   r6   _parse_canonical_maxkey  s
   r	  c                 C  s   d| v r	t | |S t| |S )Nr   )r   r   r   r5   r5   r6   _parse_binary&  s   

r
  r#   c                 C  s   | d }t |d |d S )N
$timestamptr%   r"   )r   r   tspr5   r5   r6   _parse_timestamp-  s   r  r   r   r   r   r  r  r   r   r   z
$undefinedc                 C  s   d S rm   r5   )__1r5   r5   r6   rq   <  s    rq   r   r  r  r   r   r   r   r   z,dict[str, Callable[[Any, JSONOptions], Any]]r   r   c                 C  s@   |j tjkrt|  d| dS dt|  d| diS )Nr   )r   r   r   )r   r   )r<   r7   r2   r   	b64encodedecode)r   r   rf   r5   r5   r6   _encode_binaryI  s   r  ru   c                 C  sb   |j tjkrdt|   krtkrn nt|  |S |j tjkr'dt| iS ddtt| iiS )Nr   r   r   )	r?   r,   r4   r;   r   _encode_datetimeas_datetimer2   rS   r   r5   r5   r6   _encode_datetimemsO  s   r  c                 C  s,   | j d u rdt| iS t| t| j |dS )Nr   r   )r   rS   rj   r   r5   r5   r6   _encode_codeZ  s   
r  c                 C  s   |j r	dt| iS t| S )Nr   )r>   rS   r;   r   r5   r5   r6   _encode_int64a  s   r  c                 C  s   | S rm   r5   re   r   r5   r5   r6   _encode_nooph  s   r  c                 C  s   d}| j tj@ r|d7 }| j tj@ r|d7 }| j tj@ r |d7 }| j tj@ r*|d7 }| j tj@ r4|d7 }| j tj@ r>|d7 }t| j	t
rH| j	}n| j	d}|jtjkrY||d	S d
||diS )Nr   r%   r&   r'   r(   r)   r*   zutf-8)r   r   r   )r   r   )r   re
IGNORECASELOCALE	MULTILINEDOTALLUNICODEVERBOSEr   r   rS   r  r<   r7   r2   )re   rf   r   r   r5   r5   r6   _encode_regexl  s&   
r"  c                 C  sB   |j tjkrt |   krtk rn ndt| iS dt| iS | S )Nr   r   )r<   r7   r9   
_INT32_MAXrS   r   r5   r5   r6   _encode_int  s
   r$  c                 C  s`   |j tjkr.t| rddiS t| r | dkrdnd}d|iS |j tjkr.dtt| iS | S )Nr   NaNr   Infinityz	-Infinity)	r<   r7   r2   mathisnanisinfr9   rS   repr)re   rf   representationr5   r5   r6   _encode_float  s   

r,  datetime.datetimec                 C  s   |j tjkrN| js| jtd} | jd usJ | tkrN| j| }|j|j	|j
fdkr-d}n| d}t| jd }|r@d|f nd}dd	| d
||iS t| }|j tjkr\d|iS ddt|iiS )Nr   )r   r   r   r   z%zi  z.%03dr   r   z{}{}{}r   r   )r?   r,   r4   rO   r   r$   r   	utcoffsetdaysr   microsecondsstrftimer;   r   rT   r   r2   rS   )re   rf   off	tz_stringmillisfracsecsr5   r5   r6   r    s"   
r  c                 C  s   t | d|S r   )r  r   r5   r5   r6   _encode_bytes     r6  r   c                 C  s   t | | j|S rm   )r  r   r   r5   r5   r6   _encode_binary_obj     r8  	uuid.UUIDc                 C  s.   |j rtj| |jd}t||j|S d| jiS )N)r   r   )r@   r   r   r   r  r   hex)re   rf   binvalr5   r5   r6   _encode_uuid  s   
r=  c                 C     dt | iS )Nr   rS   r  r5   r5   r6   _encode_objectid  r7  r@  c                 C  s   d| j | jdiS )Nr  )r  r%   )timeincr  r5   r5   r6   _encode_timestamp  s   rC  c                 C  r>  )Nr  r?  r  r5   r5   r6   _encode_decimal128  r7  rD  r   c                 C  s   t |  |dS )Nrp   )rj   r   r   r5   r5   r6   _encode_dbref  s   rE  dummy1c                 C     ddiS )Nr  r-   r5   r   rF  r5   r5   r6   _encode_minkey     rI  c                 C  rG  )Nr  r-   r5   rH  r5   r5   r6   _encode_maxkey  rJ  rK  z-dict[Type, Callable[[Any, JSONOptions], Any]]	_ENCODERSz,dict[int, Callable[[Any, JSONOptions], Any]]_MARKERS_type_markerc                 c  s    | ]}|V  qd S rm   r5   )ry   r  r5   r5   r6   	<genexpr>  s    rO  c                 C  s   z
t t|  | |W S  ty   Y nw t| dr/| j}|tv r/t| }|t t| < || |S tD ]}t| |rIt | }|t t| < || |  S q1td|  )NrN  z%r is not JSON serializable)	rL  r   KeyErrorr   rN  rM  _BUILT_IN_TYPESr   r   )re   rf   markerfuncbaser5   r5   r6   r     s$   


r   c                 C  s   t | S rm   )r   ro   r5   r5   r6   _get_str_size  rJ  rU  c                 C  s   dt t|   S )Nr   )r   rS   rA  ro   r5   r5   r6   _get_datetime_size  s   rV  r    c                 C     dt | j S )N   )r   r   ro   r5   r5   r6   _get_regex_size#  r9  rY  c                 C  rW  )N"   )r   
collectionro   r5   r5   r6   _get_dbref_size'  r9  r\              zdict[Any, int]_CONSTANT_SIZE_TABLEzdict[Any, Callable[[Any], int]]_VARIABLE_SIZE_TABLEmax_sizecurrent_sizec                 C  s(  ||kr|S t | }zt| W S  ty   Y nw zt| | W S  ty)   Y nw |tkrQ| jrG|dt| j|| t|  t| j 7 }|S |dt|  7 }|S |tkrx| 	 D ]\}}|t|||7 }|t|||7 }||kru|  S qY|S t
| dr| D ]}|t|||7 }||kr|  S q|S )z!Recursively finds size of objectsr   r}   )r   ra  rP  rb  r   r   get_sizer   ru   rw   r   )re   rc  rd  obj_typerz   r{   r%   r5   r5   r6   re  >  sH   
"
re  
max_lengthTuple[Any, int]c                 C  s   |dkrdS |}t | dr2i }|  D ]\}}t||\}}|r$|||< |dkr- ||fS q||fS t | dr`t| ttfs`g }| D ]}t||\}}|rR|| |dkr[ ||fS qB||fS t| |S )zMRecursively truncate documents as needed to fit inside max_length characters.r   r   rw   r}   )r   rw   _truncate_documentsr   rS   r   append	_truncate)re   rg  	remaining	truncatedrz   r{   truncated_vr5   r5   r6   ri  g  s4   


ri  rl  c                 C  sR   t | |}||kr| || fS z| d | }W n ty"   | }Y nw ||| fS rm   )re  r   )re   rl  sizerm  r5   r5   r6   rk    s   
rk  )re   r   rB   r   rC   r   rM   rS   )r(   rk   rB   r   rC   r   rM   r   )re   r   rf   r:   rM   r   )rt   r   rf   r:   rM   r   )r   r   rf   r:   rM   r   )r   r   r   r   rM   r   )r   r   rf   r:   rM   r   )r   r   r   r;   rf   r:   rM   r   )r   r   rf   r:   rM   r   )r   r   r   r   rM   r   )r   r   r   r   rM   rS   )r   r   r   r   rM   r   )r   r   r   r   rM   r   )r   r   r   r   rM   r;   )r   r   r   r   rM   r   )r   r   r   r   rM   r   )r   r   r   r   rM   r   )r   r   r   r   rM   r   )r   r   r   r   rM   r   )r   r   r   r   rM   r#   )r   r   r   r;   rf   r:   rM   r   )re   r   rf   r:   rM   ru   )re   r   rf   r:   rM   ru   )re   r   rf   r:   rM   r   )re   r   r   r   rM   r   )re   r;   rf   r:   rM   r   )re   r   rf   r:   rM   r   )re   r-  rf   r:   rM   ru   )re   r   rf   r:   rM   ru   )re   r   rf   r:   rM   ru   )re   r:  rf   r:   rM   ru   )re   r   r   r   rM   ru   )re   r#   r   r   rM   ru   )re   r   rf   r:   rM   ru   )r   r   rF  r   rM   ru   )re   r   rM   r;   )re   r-  rM   r;   )re   r    rM   r;   )re   r   rM   r;   )r   )re   r   rc  r;   rd  r;   rM   r;   )re   r   rg  r;   rM   rh  )re   r   rl  r;   rM   rh  )__doc__
__future__r   r   r   rh   r'  r  r   typingr   r   r   r   r   r   r	   r
   r   r   r   bson.binaryr   r   r   r   	bson.coder   bson.codec_optionsr   r   bson.datetime_msr   r   r   r   r   
bson.dbrefr   bson.decimal128r   
bson.int64r   bson.max_keyr   bson.min_keyr   bson.objectidr   
bson.regexr    bson.sonr!   bson.timestampr#   bson.tz_utilr$   ILMSUXr   r,   r7   rS   _BASE_CLASSr#  r:   r2   ra   r_   r9   rb   r8   rc   rd   ri   rv   rj   rs   rn   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r  r  r  r	  r
  r  r   setr   r  r  r  r  r  r"  r$  r,  r  r6  r8  r=  r@  rC  rD  rE  rI  rK  r=   r   r   r;   r   r   rL  rM  _typr   rN  tuplerQ  r   rU  rV  rY  r\  ra  rb  re  ri  rk  r5   r5   r5   r6   <module>   s  W4
$+ 1

"







E













	
	
	


















	




	
)