o
    'hذ                     @  s  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	Z	ddl
Z
ddlZddlmZ ddl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mZmZmZmZm Z m!Z!m"Z"m#Z# ddl$m%Z% dd	l&m'Z'm(Z(m)Z) dd
l*m+Z+m,Z,m-Z-m.Z.m/Z/ ddl0m1Z1 ddl2m3Z3 ddl4m5Z5m6Z6m7Z7m8Z8m9Z9 ddl:m;Z;m<Z< ddl=m>Z>m?Z? ddl@mAZA ddlBmCZC ddlDmEZEmFZFmGZGmHZHmIZI erddlJmKZK ddlLmMZM ddlNmOZOmPZP dZQeReeSjTZUd1ddZVG dd dZWG dd  d ZXd2d$d%ZYd3d)d*ZZ	d4d5d/d0Z[dS )6z<Internal class to monitor a topology of one or more servers.    )annotationsN)Path)TYPE_CHECKINGAnyCallableMappingOptionalcast)_csotcommonhelpers_sharedperiodic_executor)	ConnectionFailureInvalidOperationNetworkTimeoutNotPrimaryErrorOperationFailurePyMongoErrorServerSelectionTimeoutErrorWaitQueueTimeoutError
WriteError)Hello)
_cond_wait_create_condition_create_lock)_SDAM_LOGGER_SERVER_SELECTION_LOGGER
_debug_log_SDAMStatusMessage_ServerSelectionStatusMessage)PoolOptions)ServerDescription)	Selectionany_server_selectorarbiter_server_selectorsecondary_server_selectorwritable_server_selector)_ServerSession_ServerSessionPool)MonitorBase
SrvMonitor)Pool)Server)SRV_POLLING_TOPOLOGIESTOPOLOGY_TYPETopologyDescription)_updated_topology_description_srv_pollingupdated_topology_description)ObjectId)TopologySettings)ClusterTime_AddressT	queue_ref"weakref.ReferenceType[queue.Queue]returnboolc                 C  sF   |  }|sdS 	 z|  }W n tjy   Y dS w |\}}||  q)NFT)
get_nowaitqueueEmpty)r6   qeventfnargs rA   X/var/www/html/olx_land/venv/lib/python3.10/site-packages/pymongo/synchronous/topology.pyprocess_events_queueW   s   rC   c                   @  s  e Zd ZdZdddZddd	ZdddZ			ddddZdddZ				ddd"d#Z					ddd$d%Z
		ddd'd(Z	)	)ddd/d0Z	)	)ddd1d2Zdd5d6Zdd7d8Zdd:d;Zdd<d=Zdd>d?ZddAdBZddCdDZddEdFZddHdIZddLdMZddNdOZdddSdTZddUdVZddWdXZddYdZZedd\d]Zdd_d`ZddcddZ ddfdgZ!ddidjZ"ddkdlZ#ddodpZ$ddqdrZ%ddsdtZ&ddudvZ'ddwdxZ(ddzd{Z)dd|d}Z*dd~dZ+dddZ,dddZ-dddZ.dddZ/dddZ0dS )Topologyz*Monitor a topology of one or more servers.topology_settingsr3   c                   s  |j | _ |jj| _| jd uo| jj| _| jd uo| jj| _d | _d | _	| js)| jr0t
jdd| _ttjr?tttj| j d | jrU| jd usIJ | j| jj| j ff || _t| | |jd d |}|| _ttji d d d | j}| jr| jd us~J | j| jj|| j| j ff ttjrtttj| j || jd |jD ].}| jr| jd usJ | j| jj || j ff ttjrtttj!| j |d |d d qt"|# | _$d| _%d| _&t' | _(t)| j(t*r| jj+nd | _,i | _-d | _.d | _/t0 | _1| js| jr-| jd usJ d fdd}t2j3t4j5t4j6|dd}t78| j|j9 || _	|:  d | _;| jj<d urC| jj=sCt>| | j| _;g | _?d S )Nd   )maxsizemessage
topologyIdrI   rJ   previousDescriptionnewDescriptionr      )rI   rJ   
serverHost
serverPortFr8   r9   c                     s   t  S N)rC   rA   weakrA   rB   target   s   z!Topology.__init__.<locals>.targetpymongo_events_thread)intervalmin_intervalrT   name)r8   r9   )@_topology_id_pool_options_event_listeners
_listenersenabled_for_server_publish_serverenabled_for_topology_publish_tp_events_Topology__events_executorr;   Queuer   isEnabledForloggingDEBUGr   r   START_TOPOLOGYputpublish_topology_opened	_settingsr/   get_topology_typeget_server_descriptionsreplica_set_name_descriptionr.   Unknown$publish_topology_description_changedTOPOLOGY_CHANGEseedspublish_server_openedSTART_SERVERlistserver_descriptions_seed_addresses_opened_closedr   _lockr   _IS_SYNCcondition_class
_condition_servers_pid_max_cluster_timer(   _session_poolr   PeriodicExecutorr   EVENTS_QUEUE_FREQUENCYMIN_HEARTBEAT_INTERVALweakrefrefcloseopen_srv_monitorfqdnload_balancedr*   _monitor_tasks)selfrE   topology_description
initial_tdseedrT   executorrA   rR   rB   __init__k   s   
	
	

zTopology.__init__r8   Nonec                 C  s   t  }| jdu r|| _nH|| jkrU|| _tjdd dkr$dtfi}nddi}tj	di | | j | j	
 D ]}|  q:| j  W d   n1 sPw   Y  | j |   W d   dS 1 shw   Y  dS )	a  Start monitoring, or restart after a fork.

        No effect if called multiple times.

        .. warning:: Topology is shared among multiple threads and is protected
          by mutual exclusion. Using Topology from a process other than the one
          that initialized it will emit a warning and may result in deadlock. To
          prevent this from happening, MongoClient must be created after any
          forking.

        N   )      skip_file_prefixes
stacklevel   MongoClient opened before fork. May not be entirely fork-safe, proceed with caution. See PyMongo's documentation for details: https://dochub.mongodb.org/core/pymongo-fork-deadlock)r   )osgetpidr   sysversion_info_pymongo_dirwarningswarnrz   r~   valuesr   r   reset_ensure_opened)r   pidkwargsserverrA   rA   rB   r      s*   



"zTopology.openfloatc                 C  s   t  }|d u r| jjS |S rQ   )r
   	remainingrj   server_selection_timeout)r   timeoutrA   rA   rB   get_server_selection_timeout   s   z%Topology.get_server_selection_timeoutNselector Callable[[Selection], Selection]	operationstrr   Optional[float]addressOptional[_Address]operation_idOptional[int]list[Server]c                   sv   |du r	   }n|}ts jr    j  |||||} fdd|D W  d   S 1 s4w   Y  dS )a  Return a list of Servers matching selector, or time out.

        :param selector: function that takes a list of Servers and returns
            a subset of them.
        :param operation: The name of the operation that the server is being selected for.
        :param server_selection_timeout: maximum seconds to wait.
            If not provided, the default value common.SERVER_SELECTION_TIMEOUT
            is used.
        :param address: optional server address to select.

        Calls self.open() if needed.

        Raises exc:`ServerSelectionTimeoutError` after
        `server_selection_timeout` if no matching servers are found.
        Nc                   s   g | ]}t t |jqS rA   )r	   r,   get_server_by_addressr   .0sdr   rA   rB   
<listcomp>*  s    z+Topology.select_servers.<locals>.<listcomp>)r   r{   r   cleanup_monitorsrz   _select_servers_loop)r   r   r   r   r   r   server_timeoutrv   rA   r   rB   select_servers  s   



$zTopology.select_serversr   list[ServerDescription]c           
      C  sP  t  }|| }d}ttjr tttj|||| j	| j	j
jd | jj||| jjd}	|	s|dks5||kr_ttjrOtttj|||| j	| j	j
j| |d t| | d| d| j	|s|tttj|||| j	| j	j
jtd|t    d	 d
}|   |   t| jtj | j  t  }| jj||| jjd}	|	r-| j  |	S )z7select_servers() guts. Hold the lock when calling this.F)rI   r   r   operationIdtopologyDescriptionclientId)custom_selectorr   )rI   r   r   r   r   r   failurez, Timeout: zs, Topology Description: i  )rI   r   r   r   r   r   remainingTimeMST)time	monotonicr   rd   re   rf   r   r   STARTEDdescription_topology_settingsrY   rn   apply_selectorrj   server_selectorFAILED_error_messager   WAITINGintr   _request_check_allr   r}   r   r   check_compatible)
r   r   r   r   r   r   nowend_timelogged_waitingrv   rA   rA   rB   r   .  sn   	






-zTopology._select_servers_loopdeprioritized_serversOptional[list[Server]]r,   c           
      C  sX   |  |||||}t||}t|dkr|d S t|d\}}	|jj|	jjkr*|S |	S )NrN   r   r   )r   _filter_serverslenrandomsamplepooloperation_count)
r   r   r   r   r   r   r   serversserver1server2rA   rA   rB   _select_serverz  s   	

zTopology._select_serverc                 C  sp   | j ||||||d}t rt|jj ttj	r6t
ttj|||| j| jjj|jjd |jjd d	 |S )zALike select_servers, but choose a random server if several match.r   r   rN   )rI   r   r   r   r   r   rO   rP   )r   r
   get_timeoutset_rttr   min_round_trip_timer   rd   re   rf   r   r   	SUCCEEDEDr   rY   r   )r   r   r   r   r   r   r   r   rA   rA   rB   select_server  s.   


zTopology.select_serverr5   c                 C  s   | j t||||dS )a=  Return a Server for "address", reconnecting if necessary.

        If the server's type is not known, request an immediate check of all
        servers. Time out after "server_selection_timeout" if the server
        cannot be reached.

        :param address: A (host, port) pair.
        :param operation: The name of the operation that the server is being selected for.
        :param server_selection_timeout: maximum seconds to wait.
            If not provided, the default value
            common.SERVER_SELECTION_TIMEOUT is used.
        :param operation_id: The unique id of the current operation being performed. Defaults to None if not provided.

        Calls self.open() if needed.

        Raises exc:`ServerSelectionTimeoutError` after
        `server_selection_timeout` if no matching servers are found.
        r   )r   r#   )r   r   r   r   r   rA   rA   rB   select_server_by_address  s   z!Topology.select_server_by_addressFserver_descriptionr!   
reset_poolr9   interrupt_connectionsc           	      C  sT  | j }|j|j }t||rdS t| j |}|js"|jr0|jtj	kr0| j
|j}|r0|j  ||k}| jrP|sP| jdus@J | j| jj|||j| jff || _ |   | jrr|sr| jduscJ | j| jj|| j | jff ttjr|stttj| j|| j d | jr|jtjkr| j jt vr| j!  t"s| j#$| j | j%&  dS )ziProcess a new ServerDescription on an opened topology.

        Hold the lock when calling this.
        NrK   )'rn   _server_descriptionsr   _is_stale_server_descriptionr1   is_readableis_server_type_knowntopology_typer.   Singler~   getr   readyr^   ra   rh   r\   "publish_server_description_changedrY   _update_serversr`   rp   r   rd   re   rf   r   r   rq   r   ro   r-   r   r{   r   appendr}   
notify_all)	r   r   r   r   td_oldsd_oldnew_tdr   suppress_eventrA   rA   rB   _process_change  sX   





zTopology._process_changec                 C  sx   | j  | jr| j|jr| ||| W d   n1 sw   Y  |r8| j|j}|r:|jj	|d dS dS dS )z>Process a new ServerDescription after an hello call completes.N)r   )
rz   rx   rn   
has_serverr   r   r~   r   r   r   )r   r   r   r   r   rA   rA   rB   	on_change  s   	zTopology.on_changeseedlistlist[tuple[str, Any]]c                 C  s   | j }|jtvr
dS t| j || _ |   | jr.| jdusJ | j| jj	|| j | j
ff ttjrBtttj| j
|| j d dS dS )z_Process a new seedlist on an opened topology.
        Hold the lock when calling this.
        NrK   )rn   r   r-   r0   r   r`   ra   rh   r\   rp   rY   r   rd   re   rf   r   r   rq   )r   r  r   rA   rA   rB   _process_srv_update0  s*   

zTopology._process_srv_updatec                 C  sL   | j  | jr| | W d   dS W d   dS 1 sw   Y  dS )z?Process a new list of nodes obtained from scanning SRV records.N)rz   rx   r  )r   r  rA   rA   rB   on_srv_updateL  s   "zTopology.on_srv_updateOptional[Server]c                 C     | j |S )aJ  Get a Server or None.

        Returns the current version of the server immediately, even if it's
        Unknown or absent from the topology. Only use this in unittests.
        In driver code, use select_server_by_address, since then you're
        assured a recent view of the server's type and wire protocol version.
        )r~   r   r   r   rA   rA   rB   r   S  s   zTopology.get_server_by_addressc                 C  s
   || j v S rQ   )r~   r  rA   rA   rB   r   ]  s   
zTopology.has_serverc                 C  s`   | j # | jj}|tjkr	 W d   dS t|  d jW  d   S 1 s)w   Y  dS )z!Return primary's address or None.Nr   )rz   rn   r   r.   ReplicaSetWithPrimaryr&   _new_selectionr   )r   r   rA   rA   rB   get_primary`  s   
$zTopology.get_primaryset[_Address]c                 C  sp   | j + | jj}|tjtjfvrt W  d   S dd t||  D W  d   S 1 s1w   Y  dS )z+Return set of replica set member addresses.Nc                 S  s   h | ]}|j qS rA   )r   r   rA   rA   rB   	<setcomp>u  s    z4Topology._get_replica_set_members.<locals>.<setcomp>)	rz   rn   r   r.   r  ReplicaSetNoPrimarysetiterr	  )r   r   r   rA   rA   rB   _get_replica_set_membersj  s   $z!Topology._get_replica_set_membersc                 C  
   |  tS )z"Return set of secondary addresses.)r  r%   r   rA   rA   rB   get_secondariesw     
zTopology.get_secondariesc                 C  r  )z Return set of arbiter addresses.)r  r$   r   rA   rA   rB   get_arbiters{  r  zTopology.get_arbitersOptional[ClusterTime]c                 C     | j S )z1Return a document, the highest seen $clusterTime.r   r   rA   rA   rB   max_cluster_time     zTopology.max_cluster_timecluster_timeOptional[Mapping[str, Any]]c                 C  s.   |r| j r|d | j d kr|| _ d S d S d S )NclusterTimer  r   r  rA   rA   rB   _receive_cluster_time_no_lock  s   
z&Topology._receive_cluster_time_no_lockc                 C  s6   | j  | | W d    d S 1 sw   Y  d S rQ   )rz   r  r  rA   rA   rB   receive_cluster_time  s   "zTopology.receive_cluster_time   	wait_timer   c                 C  s@   | j  |   t| j| W d   dS 1 sw   Y  dS )z=Wake all monitors, wait for at least one to check its server.N)rz   r   r   r}   )r   r!  rA   rA   rB   request_check_all  s   "zTopology.request_check_allc                 C  s   | j jtjkr| j jS | j jS )z~Return a list of all data-bearing servers.

        This includes any server that might be selected for an operation.
        )rn   r   r.   r   known_serversreadable_serversr   rA   rA   rB   data_bearing_servers  s   zTopology.data_bearing_serversc                 C  s   g }| j   |  D ]}| j|j }|||jj f q
W d    n1 s(w   Y  |D ])\}}z|j| W q/ t	yX } zt
|d|dd }| |jj|  d }~ww d S )Nr   F)rz   r%  r~   r   r   r   genget_overallremove_stale_socketsr   _ErrorContexthandle_errorr   )r   r   r   r   
generationexcctxrA   rA   rB   update_pool  s"   zTopology.update_poolc                 C  s  | j T | j}| j D ]}|  ts| j|j q| j	 | _| j
  D ]\}}|| jv r8|| j| _q)| jrJ| j  tsJ| j| j d| _d| _W d   n1 sZw   Y  | jr| jdusiJ ttji | jj| jj| jj| jj| _| j| jj|| j| jff | j| jj| jff tt j!rt"tt#j$| j|| jd t"tt#j%| jd | j&s| jr| j'  | j'(d t)t*+| j dS dS )zClear pools and terminate monitors. Topology does not reopen on
        demand. Any further operations will raise
        :exc:`~.errors.InvalidOperation`.
        FTNrK   rH   rN   ),rz   rn   r~   r   r   r{   r   r   _monitorr   rv   itemsr   r   rx   ry   r`   ra   r/   r.   ro   rm   max_set_versionmax_election_idr   rh   r\   rp   rY   publish_topology_closedr   rd   re   rf   r   r   rq   STOP_TOPOLOGYr^   rb   joinrC   r   r   )r   old_tdr   r   r   rA   rA   rB   r     sl   




zTopology.closer/   c                 C  r  rQ   )rn   r   rA   rA   rB   r     r  zTopology.descriptionlist[_ServerSession]c                 C  s
   | j  S )z"Pop all session ids from the pool.)r   pop_allr   rA   rA   rB   pop_all_sessions  r  zTopology.pop_all_sessionssession_timeout_minutesr'   c                 C  r  )z>Start or resume a server session, or raise ConfigurationError.)r   get_server_session)r   r:  rA   rA   rB   r;    s   zTopology.get_server_sessionserver_sessionc                 C  s   | j | d S rQ   )r   return_server_session)r   r<  rA   rA   rB   r=    s   zTopology.return_server_sessionr"   c                 C  s   t | jS )zmA Selection object, initially including all known servers.

        Hold the lock when calling this.
        )r"   from_topology_descriptionrn   r   rA   rA   rB   r	    s   zTopology._new_selectionc              	   C  s   | j rtd| js@d| _|   | js| jr| j  | jr*| j	j
tv r*| j  | jjr@| t| jd td| jdd | j D ]}|  qEdS )z[Start monitors, or restart after a fork.

        Hold the lock when calling this.
        z"Cannot use MongoClient after closeTr   rN      )ok	serviceIdmaxWireVersionN)ry   r   rx   r   r`   r^   rb   r   r   r   r   r-   rj   r   r   r!   rw   r   rY   r~   r   r   r   rA   rA   rB   r     s&   


zTopology._ensure_openederr_ctxr)  c                 C  sp   | j |}|d u rdS |j|j|jrdS |jj}|j}d }|r3t	|dr3t
|jtr3|jd}t||S )NTdetailstopologyVersion)r~   r   _poolstale_generationsock_generation
service_idr   topology_versionerrorhasattr
isinstancerE  dict _is_stale_error_topology_version)r   r   rD  r   cur_tvrL  error_tvrA   rA   rB   _is_stale_error0  s   
zTopology._is_stale_errorc           	      C  sp  |  ||rd S | j| }|j}|j}| jjr|s|jsd S t|tr(|jr(d S t|t	r/d S t|t
tfrt|dr?|j}nt|t
rFdnd }|jd|}|tjv rx|tjv }| jjsf| t||d |sm|jdkrr|| |  d S |js| jjs| t||d || d S d S t|trt|trd S | jjs| t||d || |j  d S d S )Ncodei{'  rL     )rS  r~   rL  rJ  rj   r   completed_handshakerN  r   r   r   r   rM  rT  rE  r   r   _NOT_PRIMARY_CODES_SHUTDOWN_CODESr   r!   max_wire_versionr   request_checkr   r   r/  cancel_check)	r   r   rD  r   rL  rJ  err_codedefaultis_shutting_downrA   rA   rB   _handle_errorD  sH   


	





zTopology._handle_errorc                 C  s8   | j  | || W d   dS 1 sw   Y  dS )zHandle an application error.

        May reset the server to Unknown, clear the pool, and request an
        immediate check depending on the error and the context.
        N)rz   r`  )r   r   rD  rA   rA   rB   r*    s   "zTopology.handle_errorc                 C  s   | j  D ]}|  qdS )z3Wake all monitors. Hold the lock when calling this.N)r~   r   r[  rC  rA   rA   rB   r     s   
zTopology._request_check_allc              	   C  s  | j   D ]\\}}|| jvrG| jj|| | || jd}d}| jr.| jdur.t	
| j}t|| ||| j| j|d}|| j|< |  q| j| jj}|| j| _||jkrc| j| j|j qt| j D ]\}}| j |s|  ts| j|j | j| qkdS )zrSync our Servers from TopologyDescription.server_descriptions.

        Hold the lock while calling this.
        )r   topologyr   rE   N)r   r   monitortopology_id	listenersevents)rn   rv   r0  r~   rj   monitor_class_create_pool_for_monitorr^   ra   r   r   r,   _create_pool_for_serverrY   r\   r   r   is_writabler   update_is_writableru   r   r   r{   r   r   r/  pop)r   r   r   rb  rS   r   was_writablerA   rA   rB   r     sD   

	

zTopology._update_serversr+   c                 C  s   | j j|| j j| jdS )N)	client_id)rj   
pool_classpool_optionsrY   r  rA   rA   rB   rh    s   z Topology._create_pool_for_serverc                 C  sH   | j j}t|j|j|j|j|j|j|jd|j	d	}| j j
||d| jdS )NF)	connect_timeoutsocket_timeoutssl_contexttls_allow_invalid_hostnamesevent_listenersappnamedriverpause_enabled
server_api)	handshakerm  )rj   ro  r    rp  _ssl_contextrs  r[   ru  rv  rx  rn  rY   )r   r   optionsmonitor_pool_optionsrA   rA   rB   rg    s   
z!Topology._create_pool_for_monitorc                   s  | j jtjtjfv }|rd}n| j jtjkrd}nd}| j jr4|tu r+|r'dS d| S d| d| dS t| j 	 }t| j 	 
 }|sT|rPd	|| jjS d
| S |d j t fdd|dd D }|r du rrd| S |rt|| jsd| S t S ddd |D S )zeFormat an error message if server selection fails.

        Hold the lock when calling this.
        zreplica set membersmongosesr   zNo primary available for writeszNo %s available for writeszNo z match selector ""z)No {} available for replica set name "{}"zNo %s availabler   c                 3  s    | ]}|j  kV  qd S rQ   rU  r   r   rU  rA   rB   	<genexpr>  s    z*Topology._error_message.<locals>.<genexpr>rN   NzNo %s found yetz\Could not reach any servers in %s. Replica set is configured with internal hostnames or IPs?,c                 s  s     | ]}|j rt|j V  qd S rQ   )rL  r   r  rA   rA   rB   r    s    )rn   r   r.   r  r  Shardedr#  r&   ru   rv   r   formatrj   rm   rL  allr  intersectionrw   r   r5  )r   r   is_replica_setserver_plural	addressesr   samerA   rU  rB   r     sH   
zTopology._error_messagec                 C  sV   g }z| j r|| j   | j sW n	 ty   Y nw tjdd |D ddi d S )Nc                 S  s   g | ]}|  qS rA   )r5  )r   trA   rA   rB   r     s    z-Topology.cleanup_monitors.<locals>.<listcomp>return_exceptionsT)r   r   rk  
IndexErrorasynciogather)r   tasksrA   rA   rB   r     s   zTopology.cleanup_monitorsc                 C  s*   d}| j sd}d| jj d| | jdS )N zCLOSED < >)rx   	__class____name__rn   )r   msgrA   rA   rB   __repr__   s   zTopology.__repr__>tuple[tuple[_Address, ...], Optional[str], Optional[str], str]c                 C  s"   | j }tt|j|j|j|jfS )z?The properties to use for MongoClient/Topology equality checks.)rj   tuplesortedrr   rm   r   srv_service_name)r   tsrA   rA   rB   eq_props&  s   zTopology.eq_propsotherobjectc                 C  s    t || jr|  | kS tS rQ   )rN  r  r  NotImplemented)r   r  rA   rA   rB   __eq__+  s   zTopology.__eq__c                 C  s   t |  S rQ   )hashr  r   rA   rA   rB   __hash__0  s   zTopology.__hash__)rE   r3   )r8   r   )r8   r   )NNN)r   r   r   r   r   r   r   r   r   r   r8   r   )r   r   r   r   r   r   r   r   r   r   r8   r   )NNNN)r   r   r   r   r   r   r   r   r   r   r   r   r8   r,   )NN)
r   r5   r   r   r   r   r   r   r8   r,   )FF)r   r!   r   r9   r   r9   r8   r   )r  r  r8   r   )r   r5   r8   r  )r   r5   r8   r9   )r8   r   )r   r   r8   r  )r8   r  )r8   r  )r  r  r8   r   )r   )r!  r   r8   r   )r8   r   )r8   r/   )r8   r7  )r:  r   r8   r'   )r<  r'   r8   r   )r8   r"   )r   r5   rD  r)  r8   r9   )r   r5   rD  r)  r8   r   )r   r5   r8   r+   )r   r   r8   r   )r8   r   )r8   r  )r  r  r8   r9   )r8   r   )1r  
__module____qualname____doc__r   r   r   r   r   r   r   r   r   r   r  r  r   r   r
  r  r  r  r  r  r  r"  r%  r.  r   propertyr   r9  r;  r=  r	  r   rS  r`  r*  r   r   rh  rg  r   r   r  r  r  r  rA   rA   rA   rB   rD   h   s    

l
'
)P&$H














	
C





!

D
	

,


:
	

rD   c                   @  s   e Zd ZdZdddZdS )r)  z.An error with context for SDAM error handling.rL  BaseExceptionrZ  r   rI  rW  r9   rJ  Optional[ObjectId]c                 C  s"   || _ || _|| _|| _|| _d S rQ   )rL  rZ  rI  rW  rJ  )r   rL  rZ  rI  rW  rJ  rA   rA   rB   r   7  s
   
z_ErrorContext.__init__N)
rL  r  rZ  r   rI  r   rW  r9   rJ  r  )r  r  r  r  r   rA   rA   rA   rB   r)  4  s    r)  
current_tvr  rR  c                 C  s8   | du s|du r
dS | d |d krdS | d |d kS )z9Return True if the error's topologyVersion is <= current.NF	processIdcounterrA   )r  rR  rA   rA   rB   rP  F  s
   rP  
current_sdr!   new_sdc                 C  sF   | j |j }}|du s|du rdS |d |d krdS |d |d kS )z4Return True if the new topologyVersion is < current.NFr  r  )rK  )r  r  r  new_tvrA   rA   rB   r   Q  s   r   
candidatesr   r   r   c                   s"    s| S  fdd| D }|p| S )zBFilter out deprioritized servers from a list of server candidates.c                   s   g | ]}| vr|qS rA   rA   r  r   rA   rB   r   b  s    z#_filter_servers.<locals>.<listcomp>rA   )r  r   filteredrA   r  rB   r   [  s   r   )r6   r7   r8   r9   )r  r  rR  r  r8   r9   )r  r!   r  r!   r8   r9   rQ   )r  r   r   r   r8   r   )\r  
__future__r   r  re   r   r;   r   r   r   r   r   pathlibr   typingr   r   r   r   r   r	   pymongor
   r   r   r   pymongo.errorsr   r   r   r   r   r   r   r   r   pymongo.hellor   pymongo.lockr   r   r   pymongo.loggerr   r   r   r   r   pymongo.pool_optionsr    pymongo.server_descriptionr!   pymongo.server_selectorsr"   r#   r$   r%   r&   "pymongo.synchronous.client_sessionr'   r(   pymongo.synchronous.monitorr)   r*   pymongo.synchronous.poolr+   pymongo.synchronous.serverr,   pymongo.topology_descriptionr-   r.   r/   r0   r1   bsonr2   pymongo.synchronous.settingsr3   pymongo.typingsr4   r5   r{   r   __file__parentr   rC   rD   r)  rP  r   r   rA   rA   rA   rB   <module>   s\    ,
       S

