
    i`                        d 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 ddlmZ dZdZ	 ddlZddlmZ ddlmZ dd	lmZ d
Zn## e$ r ddlZddlmZ ddlmZ dd	lmZ d
ZY nw xY wddlmZ ddlmZ ddl 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*m+Z+m,Z, ddl m-Z- ddl.m/Z/ ddl0m1Z1m2Z2 ddl3m4Z4 ddl5m6Z6 ddl7m8Z8 ddl9m:Z: ddl;m<Z<  ej=        d          Z>ej?        dk     rddl@mAZA nddlmAZA e	r
ddlBmCZCmDZDmEZE 	 ddl.mFZG 	 	 	 	 	 d+d ZH G d! d"e<          ZI G d# d$e$          ZJd%eKd&         fd'Z%d,d)ZLd%ed$         fd*Z'dS )-z
Sync CalDAV client using niquests or requests library.

This module provides the traditional synchronous API with protocol layer
for XML building and response parsing.

For async code, use: from caldav import aio
    N)TracebackType)TYPE_CHECKINGAnyOptional)unquoteF)AuthBase)Response)CaseInsensitiveDictT)Mapping)etree)__version__)BaseDAVClient)get_calendars)get_davclient)CalendarCalendarSet	Principal)
FeatureSet)CONNKEYS)cdavdav)error)to_wire)URL)HTTPBearerAuth)BaseDAVResponsecaldav)      )Self)CalendarObjectResourceEventTodo)resolve_features
   c                    t          |t                    rt          |          }| rdt          |           v r| dfS | s4|r2dt          |          v r!|rt                              d|            |} |r| rddlm}m} 	  || |t          |t                    r|nd|          }	|	rbt          
                    d	|	j         d
|	j         d           |	j        r"t                              d|	j                    |	j        |	j        fS n^# |$ r'}
t                              d|
            Y d}
~
n7d}
~
wt          $ r'}
t                              d|
            Y d}
~
nd}
~
ww xY w|                    dt                    }| r| rdt          |           v rd|v r|d         } |                    dd           d|  |                    dd           } | dfS )a  
    Auto-construct URL from domain and features, with optional RFC6764 discovery.

    Args:
        url: User-provided URL, domain, or email address
        features: FeatureSet object or dict
        timeout: Timeout for RFC6764 well-known URI lookups
        ssl_verify_cert: SSL verification setting
        enable_rfc6764: Whether to attempt RFC6764 discovery
        username: Username to use for discovery if URL is not provided
        require_tls: Only accept TLS connections during discovery (default: True)

    Returns:
        A tuple of (url_string, discovered_username_or_None)
        The discovered_username will be extracted from email addresses like user@example.com
    /N@z7No URL provided, using username for RFC6764 discovery: r   )DiscoveryErrordiscover_caldavT)
identifiertimeoutssl_verify_certrequire_tlszRFC6764 discovered service: z
 (source: )z Username discovered from email: zRFC6764 discovery failed: zRFC6764 discovery error: zauto-connect.urldomainschemehttps://basepath )
isinstancedictr   strlogdebugcaldav.discoveryr)   r*   boolinfourlsourceusername	Exceptionis_supportedget)r>   featuresr,   r-   enable_rfc6764r@   r.   r)   r*   service_infoe	url_hintss               K/root/projects/butler/venv/lib/python3.11/site-packages/caldav/davclient.py	_auto_urlrJ   ]   s   2 (D!! (h''  sc#hhT{  8 s8}} 4 4 4		VHVVWWW  7# 7DDDDDDDD	7*?3=ot3T3T ^Z^'	  L  Ae<3Cee|Obeee    ( ZIIXAVXXYYY$(,*?@@A  	8 	8 	8II616677777777 	7 	7 	7II5!5566666666	7 %%&8$??I  "C "C3s88OO(i2G2G!]]8W--
V
V#
Vy}}ZQS7T7T
V
VC;s%   ?B	D
 
E%D11E%>E  E%c                   `    e Zd ZU dZdZedz  ed<   dZedz  ed<   	 d
de	de
d         ddfd	ZdS )DAVResponsea  
    This class is a response from a DAV request.  It is instantiated from
    the DAVClient class.  End users of the library should not need to
    know anything about this class.  Since we often get XML responses,
    it tries to parse it into `self.tree`
    Nresults
sync_tokenresponse	davclient	DAVClientreturnc                 2    |                      ||           d S N)_init_from_response)selfrO   rP   s      rI   __init__zDAVResponse.__init__   s     
 	  955555    rT   )__name__
__module____qualname____doc__rM   list__annotations__rN   r8   r	   r   rW    rX   rI   rL   rL      s            GTD[!Jd
!!!
 ,06 66 K(6 
	6 6 6 6 6 6rX   rL   c            %          e Zd ZU dZdZedz  ed<   dZeed<   dZ	e
ed<   	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 dKdedz  dedz  d	edz  d
edz  dedz  dedz  dedz  de
ez  deeeef         z  dz  deeef         de
deez  ez  de
de
dee
         dee         dee         ddf$dZdefdZ	 	 	 dLdedz  dedz  dedz  ddfdZdMdZdNdZdNd Zd! Zd" Zdefd#ZdNd$edz  dee          fd%Z!	 	 	 	 	 	 	 dOd&e d'e
d(e
d)e
d*e"dz  d+e"dz  d,e
dz  d-e
d.e"ded/         fd0Z#dedz  fd1Z$de
fd2Z%de
fd3Z&dedz  fd4Z'de
fd5Z(de
fd6Z)	 	 	 dPdedz  d8ede*fd9Z+dNded:ed;dde*fd<Z,dQded=ed8edz  de*fd>Z-dNded:ed;dde*fd?Z.dRded:ed;dde*fd@Z/dNded:edeeef         de*fdAZ0dNded:edeeef         de*fdBZ1dede*fdCZ2dede*fdDZ3dNdEee         dz  ddfdFZ4	 	 	 	 dSdedHed:edeeef         de*f
dIZ5	 	 	 dTdedHed:edeeef         de*f
dJZ6dS )UrQ   a  
    Basic client for webdav, uses the niquests lib; gives access to
    low-level operations towards the caldav server.

    Unless you have special needs, you should probably care most about
    the constructor (__init__), the principal method and the calendar method.
    Nproxyr>   F	huge_treer5   Tr@   passwordauth	auth_typer,   r-   ssl_certheadersrD   rE   r.   rate_limit_handlerate_limit_default_sleeprate_limit_max_sleeprR   c           	         |
pi }
t          |          }t          |          | _        || _        	 | j                            d          }t          j        |          | _        n(# t          $ r t          j                    | _        Y nw xY wt          || j        |pd||||          \  }}t                              dt          |          z              t          j        |          | _        |i|}d|vr| j        j        dz   |z   }|                    d          }t%          |          d	k    r|d
z  }t                              d|z             || _        t)          dt*          z   ddd          | _        | j                            |
pi            | j        j        2t3          | j        j                  }t3          | j        j                  }|!||}t                              d|            || _        || _        || _        || _        t;          | j        t                    r| j                            d          | _        |r| j        rt?          j         d           n| j        r| !                                 || _"        || _#        |	| _$        | j        %                                | _        t                              dt          |          z              d| _&        | j                            dtN                    }|4|r0|(                    d          rd}d|v r|d         }d|v r|d         }nd}|| _)        || _*        || _+        dS )a  
        Sets up a HTTPConnection object towards the server in the url.

        Args:
          url: A fully qualified url, domain name, or email address. Can be omitted if username
               is an email address (RFC6764 discovery will use the username).
               Examples:
               - Full URL: `https://caldav.example.com/dav/`
               - Domain: `example.com` (will attempt RFC6764 discovery if enable_rfc6764=True)
               - Email: `user@example.com` (will attempt RFC6764 discovery if enable_rfc6764=True)
               - URL with auth: `scheme://user:pass@hostname:port`
               - Omit URL: Use `username='user@example.com'` for discovery
          username: Username for authentication. If url is omitted and username contains @,
                    RFC6764 discovery will be attempted using the username as email address.
          proxy: A string defining a proxy server: `scheme://hostname:port`. Scheme defaults to http, port defaults to 8080.
          auth: A niquests.auth.AuthBase or requests.auth.AuthBase object, may be passed instead of username/password.  username and password should be passed as arguments or in the URL
          timeout and ssl_verify_cert are passed to niquests.request.
          if auth_type is given, the auth-object will be auto-created. Auth_type can be ``bearer``, ``digest`` or ``basic``. Things are likely to work without ``auth_type`` set, but if nothing else the number of requests to the server will be reduced, and some servers may require this to squelch warnings of unexpected HTML delivered from the
           server etc.
          ssl_verify_cert can be the path of a CA-bundle or False.
          huge_tree: boolean, enable XMLParser huge_tree to handle big events, beware of security issues, see : https://lxml.de/api/lxml.etree.XMLParser-class.html
          features: The default, None, will in version 2.x enable all existing workarounds in the code for backward compability.  Otherwise it will expect a FeatureSet or a dict as defined in `caldav.compatibility_hints` and use that to figure out what workarounds are needed.
          enable_rfc6764: boolean, enable RFC6764 DNS-based service discovery for CalDAV/CardDAV.
                          Default: True. When enabled and a domain or email address is provided as url,
                          the library will attempt to discover the CalDAV service using:
                          1. DNS SRV records (_caldavs._tcp / _caldav._tcp)
                          2. DNS TXT records for path information
                          3. Well-Known URIs (/.well-known/caldav)
                          Set to False to disable automatic discovery and rely only on feature hints.
                          SECURITY: See require_tls parameter for security considerations.
          require_tls: boolean, require TLS (HTTPS) for discovered services. Default: True.
                       When True, RFC6764 discovery will ONLY accept HTTPS connections,
                       preventing DNS-based downgrade attacks where malicious DNS could
                       redirect to unencrypted HTTP. Set to False ONLY if you need to
                       support non-TLS servers and trust your DNS infrastructure.
                       This parameter has no effect if enable_rfc6764=False.
          rate_limit_handle: boolean, whether to automatically sleep and retry when the server
                             responds with 429 Too Many Requests or 503 Service Unavailable.
                             Default: False (raise RateLimitError immediately).
          rate_limit_default_sleep: int or None, fallback sleep duration in seconds when the
                                    server's 429 response does not include a parseable Retry-After
                                    header. None (default) means raise RateLimitError rather than
                                    sleeping when no Retry-After is provided.
          rate_limit_max_sleep: int or None, maximum number of seconds to sleep when rate limited,
                                regardless of the server's Retry-After value. None (default) means
                                there is no cap and the server-requested delay is respected as-is.

        The niquests library will honor a .netrc-file, if such a file exists
        username and password may be omitted.

        THe niquest library will honor standard proxy environmental variables like
        HTTP_PROXY, HTTPS_PROXY and ALL_PROXY.  See https://niquests.readthedocs.io/en/latest/user/advanced.html#proxies

        If the caldav server is behind a proxy or replies with html instead of xml
        when returning 401, warnings will be printed which might be unwanted.
        Check auth parameter for details.
        zhttp.multiplexing)multiplexedr%   )r,   r-   rE   r@   r.   zurl: Nr3   :   z:8080zinit - proxy: %szpython-caldav/ztext/xmlztext/xml, text/calendar)z
User-AgentzContent-TypeAcceptz(Using discovered username from RFC6764: utf-8zNboth auth object and auth_type sent to DAVClient.  The latter will be ignored.z
self.url: z
rate-limitenableTdefault_sleep	max_sleepF),_resolve_featuresr   rD   rb   rB   requestsSessionsession	TypeErrorrJ   r9   r:   r8   r   	objectifyr>   r1   splitlenra   r
   r   rg   updater@   r   rc   rd   re   r6   encodeloggingr   build_auth_objectr,   r-   rf   unauth
_principalr7   rC   rh   ri   rj   )rV   r>   ra   r@   rc   rd   re   r,   r-   rf   rg   rb   rD   rE   r.   rh   ri   rj   rl   discovered_username_proxyp
rate_limits                          rI   rW   zDAVClient.__init__   s   Z -R %X.."8,,"	.-445HIIK#+DDDDLL 	. 	. 	.#+--DLLL	. $-MMr+)#$
 $
 $
   			'CHH$%%%=%%FE!!5058
 S!!A1vv{{'!II(F3444DJ +.< *3 
 
 	GMr***8(tx011Htx011H  3 ?*HIIKKKLLL  	" dmS)) 	: M0099DM 	%DN 	%M`    ^ 	%""$$$ . 8??$$		,S)***]//dCC
$ *jnnX66 *$(!"j00/9//J,*,,+5k+B($)!!2(@%$8!!!s   4A% %"B
	B
c                     t          | d          r;	 |                                  n%# t          $ r |                     |            Y nw xY w| S )Nsetup)hasattrr   rx   rV   s    rI   	__enter__zDAVClient.__enter__w  s`    4!! 	!!

 ! ! !

4     !s   ' A	A	exc_type	exc_value	tracebackc                     |                                   t          | d          r=	 |                                  d S # t          $ r |                     |            Y d S w xY wd S )Nteardown)closer   r   rx   )rV   r   r   r   s       rI   __exit__zDAVClient.__exit__  sy     	

4$$ 	$$ $ $ $d######$	$ 	$s   < AAc                 8    | j                                          dS )z8
        Closes the DAVClient's session object.
        N)rw   r   r   s    rI   r   zDAVClient.close  s     	rX   c                    |                      |          }|                     | j        |          }|j        dk    r+t	          j        |j         d|j         d|j                   |                     |	                                          S )a=  
        Search for principals on the server.

        Instead of returning the current logged-in principal, this method
        attempts to query for all principals (or principals matching a name).
        This may or may not work depending on the permissions and
        implementation of the calendar server.

        Args:
            name: Optional name filter to search for specific principals

        Returns:
            List of Principal objects found on the server

        Raises:
            ReportError: If the server doesn't support principal search
        i,   z - )
_build_principal_search_queryreportr>   statusr   ReportErrorreasonraw _parse_principal_search_response_find_objects_and_props)rV   namebodyrO   s       rI   search_principalszDAVClient.search_principals  s    $ 11$77;;tx.. ?c!!#x$[$[$[$[X\$[$[\\\44X5U5U5W5WXXXrX   c                 f    t          j        dt          d           |                     |          S )z
        Deprecated. Use :meth:`search_principals` instead.

        This method searches for principals on the server.
        z;principals() is deprecated, use search_principals() insteadrn   )
stacklevel)r   )warningswarnDeprecationWarningr   )rV   r   s     rI   
principalszDAVClient.principals  s?     	I	
 	
 	
 	

 %%4%000rX   c                 D    | j         st          |d| i|| _         | j         S )a`  
        Legacy method. Use :meth:`get_principal` for new code.

        Convenience method, it gives a bit more object-oriented feel to
        write client.principal() than Principal(client).

        This method returns a :class:`caldav.Principal` object, with
        higher-level methods for dealing with the principals
        calendars.
        client)r   r   )rV   largskwargss      rI   	principalzDAVClient.principal  s0      	G'eFtFvFFDOrX   c                     t          dd| i|S )a>  Returns a calendar object.

        Typically, a URL should be given as a named parameter (url)

        No network traffic will be initiated by this method.

        If you don't know the URL of the calendar, use
        client.principal().calendar(...) instead, or
        client.principal().get_calendars()
        r   r_   )r   )rV   r   s     rI   calendarzDAVClient.calendar  s     ..t.v...rX   c                 *    |                                  S )aw  Get the principal (user) for this CalDAV connection.

        This is the recommended method for new code. It provides API
        consistency between sync and async clients.

        Returns:
            Principal object for the authenticated user.

        Example::

            principal = client.get_principal()
            calendars = principal.get_calendars()
        )r   r   s    rI   get_principalzDAVClient.get_principal  s     ~~rX   r   c                     ddl m} ddlm} |                                 }                     t          |j                   j        d          } ||j	                  }|st          |j                  } 
                    |          }                     | j        d          } ||j	                  } fd|D             S )a  Get all calendars for the given principal.

        This method fetches calendars from the principal's calendar-home-set
        and returns a list of Calendar objects.

        Args:
            principal: Principal object (if None, fetches principal first)

        Returns:
            List of Calendar objects.

        Example:
            principal = client.get_principal()
            calendars = client.get_calendars(principal)
            for cal in calendars:
                print(f"Calendar: {cal.get_display_name()}")
        r   )(_extract_calendars_from_propfind_results)'_extract_calendar_home_set_from_resultsN)propsdepth   c                 T    g | ]$}t          |j        |j        |j                   %S ))r   r>   r   id)r   r>   r   cal_id).0r=   rV   s     rI   
<listcomp>z+DAVClient.get_calendars.<locals>.<listcomp>!  s@     
 
 
 DdhTY4;OOO
 
 
rX   )!caldav.operations.calendarset_opsr   caldav.operations.principal_opsr   r   propfindr8   r>   CALENDAR_HOME_SET_PROPSrM   _make_absolute_urlCALENDAR_LIST_PROPS)rV   r   extract_calendarsextract_home_setrO   calendar_home_urlcalendar_infoss   `      rI   r   zDAVClient.get_calendars  s3   $	
 	
 	
 	
 	
 	
	
 	
 	
 	
 	
 	
 ((I ==	. ! 
 

 -,X-=>>  	3 !$IM 2 2 !334EFF ==* ! 
 
 +*8+;<<
 
 
 
&
 
 
 	
rX   r   eventtodojournalstartendinclude_completedexpandr   r!   c	                 ,     |j         d|||||||d|	S )a  Search a calendar for events, todos, or journals.

        This method provides a clean interface to calendar search.

        Args:
            calendar: Calendar to search
            event: Search for events (VEVENT)
            todo: Search for todos (VTODO)
            journal: Search for journals (VJOURNAL)
            start: Start of date range
            end: End of date range
            include_completed: Include completed todos (default: False for todos)
            expand: Expand recurring events
            **kwargs: Additional search parameters

        Returns:
            List of Event/Todo/Journal objects.

        Example:
            # Get all events in January 2024
            events = client.search_calendar(
                calendar,
                event=True,
                start=datetime(2024, 1, 1),
                end=datetime(2024, 1, 31),
            )
        )r   r   r   r   r   r   r   r_   )search)
rV   r   r   r   r   r   r   r   r   r   s
             rI   search_calendarzDAVClient.search_calendar&  sD    N x 	
/	
 	
 	
 	
 		
rX   c                    	 |                      |                                 j                  }n7# t          $ r* |                      t	          | j                            }Y nw xY w|j                            dd          S )z
        Legacy method. Use :meth:`supports_dav` for new code.

        Does a probe towards the server and returns the DAV header if it
        says it supports RFC4918 / DAV, or None otherwise.
        DAVN)optionsr   r>   rA   r8   rg   rC   )rV   rO   s     rI   check_dav_supportzDAVClient.check_dav_supportX  sz    	3 ||DNN$4$4$899HH 	3 	3 	3||CMM22HHH	3##E4000s   ,/ 1A#"A#c                 :    |                                  }|duod|v S )z
        Legacy method. Use :meth:`supports_caldav` for new code.

        Does a probe towards the server and returns True if it says it
        supports RFC4791 / CalDAV.
        Nzcalendar-accessr   rV   support_lists     rI   check_cdav_supportzDAVClient.check_cdav_supportj  s+     --//4'M,=,MMrX   c                 :    |                                  }|duod|v S )z
        Legacy method. Use :meth:`supports_scheduling` for new code.

        Does a probe towards the server and returns True if it says it
        supports RFC6638 / CalDAV Scheduling.
        Nzcalendar-auto-scheduler   r   s     rI   check_scheduling_supportz"DAVClient.check_scheduling_supportt  s+     --//4'T,D,TTrX   c                 *    |                                  S )al  Check if the server supports WebDAV (RFC4918).

        This is the recommended method for new code. It provides API
        consistency between sync and async clients.

        Returns:
            The DAV header value if supported, None otherwise.

        Example::

            if client.supports_dav():
                print("Server supports WebDAV")
        r   r   s    rI   supports_davzDAVClient.supports_dav  s     %%'''rX   c                 *    |                                  S )at  Check if the server supports CalDAV (RFC4791).

        This is the recommended method for new code. It provides API
        consistency between sync and async clients.

        Returns:
            True if the server supports CalDAV, False otherwise.

        Example::

            if client.supports_caldav():
                calendars = client.get_calendars()
        )r   r   s    rI   supports_caldavzDAVClient.supports_caldav  s     &&(((rX   c                 *    |                                  S )a  Check if the server supports CalDAV Scheduling (RFC6638).

        This is the recommended method for new code. It provides API
        consistency between sync and async clients.

        Returns:
            True if the server supports CalDAV Scheduling, False otherwise.

        Example::

            if client.supports_scheduling():
                # Server supports free-busy lookups and scheduling
                pass
        )r   r   s    rI   supports_schedulingzDAVClient.supports_scheduling  s     ,,...rX   r   r   c                    ddl m} d}|6t          |t                    r ||                              d          }n|}dt          |          i}|                     |pt          | j                  d||          }|j        dv rd|j	        r]dd	l
m} t          |j	        t                    r|j	        n|j	                            d          }	 ||	|j        |j                  |_        |S )
av  
        Send a propfind request.

        Parameters
        ----------
        url : URL
            url for the root of the propfind.
        props : str or List[str]
            XML body string (old interface) or list of property names (new interface).
        depth : int
            maximum recursion depth

        Returns
        -------
        DAVResponse
        r   )_build_propfind_bodyr5   Nrp   DepthPROPFIND)      )_parse_propfind_response)caldav.protocol.xml_buildersr   r6   r]   decoder8   requestr>   r   _rawcaldav.protocol.xml_parsersr   bytesr}   rb   rM   )
rV   r>   r   r   r   r   rg   rO   r   	raw_bytess
             rI   r   zDAVClient.propfind  s   , 	FEEEEE %&& ++E2299'BB CJJ'<< 4s48}}j$PP ?j((X](LLLLLL ",HM5!A!Adx}G[G[\cGdGd   878?H,>   H rX   r   dummyc                 0    |                      |d|          S )z
        Send a proppatch request.

        Args:
            url: url for the root of the propfind.
            body: XML propertyupdate request
            dummy: compatibility parameter

        Returns:
            DAVResponse
        	PROPPATCHr   rV   r>   r   r   s       rI   	proppatchzDAVClient.proppatch  s     ||Cd333rX   queryc                 \    |dt          |          ini }|                     |d||          S )aL  
        Send a report request.

        Args:
            url: url for the root of the propfind.
            query: XML request
            depth: maximum recursion depth. None means don't send Depth header
                (required for calendar-multiget per RFC 4791 section 7.9).

        Returns
            DAVResponse
        Nr   REPORT)r8   r   )rV   r>   r   r   rg   s        rI   r   zDAVClient.report  s6     ,1+<7CJJ''"||C5':::rX   c                 0    |                      |d|          S )a  
        Send a MKCOL request.

        MKCOL is basically not used with caldav, one should use
        MKCALENDAR instead.  However, some calendar servers MAY allow
        "subcollections" to be made in a calendar, by using the MKCOL
        query.  As for 2020-05, this method is not exercised by test
        code or referenced anywhere else in the caldav library, it's
        included just for the sake of completeness.  And, perhaps this
        DAVClient class can be used for vCards and other WebDAV
        purposes.

        Args:
            url: url for the root of the mkcol
            body: XML request
            dummy: compatibility parameter

        Returns:
            DAVResponse
        MKCOLr   r   s       rI   mkcolzDAVClient.mkcol  s    * ||C$///rX   c                 0    |                      |d|          S )z
        Send a mkcalendar request.

        Args:
            url: url for the root of the mkcalendar
            body: XML request
            dummy: compatibility parameter

        Returns:
            DAVResponse
        
MKCALENDARr   r   s       rI   
mkcalendarzDAVClient.mkcalendar  s     ||Ct444rX   c                 2    |                      |d||          S )z%
        Send a put request.
        PUTr   rV   r>   r   rg   s       rI   putzDAVClient.put$  s     ||Cg666rX   c                 2    |                      |d||          S )z&
        Send a POST request.
        POSTr   r   s       rI   postzDAVClient.post*  s     ||Cw777rX   c                 0    |                      |dd          S )z(
        Send a delete request.
        DELETEr5   r   rV   r>   s     rI   deletezDAVClient.delete0  s     ||C2...rX   c                 0    |                      |dd          S )z*
        Send an options request.
        OPTIONSr5   r   r  s     rI   r   zDAVClient.options6  s     ||CB///rX   
auth_typesc                    |                      |          }| j        }t          |t                    r|                    d          }|dk    r,t
          j                            | j        |          | _        dS |dk    r,t
          j        	                    | j        |          | _        dS |dk    rt          |          | _        dS dS )a$  Build authentication object for the requests/niquests library.

        Uses shared auth type selection logic from BaseDAVClient, then
        creates the appropriate auth object for this HTTP library.

        Args:
            auth_types: List of acceptable auth types from server.
        rp   digestbasicbearerN)_select_auth_typerc   r6   r   r   ru   rd   HTTPDigestAuthr@   HTTPBasicAuthr   )rV   r	  re   rc   s       rI   r   zDAVClient.build_auth_object<  s     **:66	 =h&& 	0w//H    44T]HMMDIII'!! 33DM8LLDIII(""&x00DIII #"rX   GETmethodc           	      d   	 |                      ||||          S # t          j        $ r}| j        s t          j        |j        | j        | j                  }|r||dz  z  }|| j        || j        k    r t          j	        |           | 
                    ||||||z             cY d}~S d}~ww xY w)aJ  
        Send a generic HTTP request.

        Uses the sync session directly for all operations.

        Args:
            url: The URL to request
            method: HTTP method (GET, PUT, DELETE, etc.)
            body: Request body
            headers: Optional headers dict

        Returns:
            DAVResponse
        rn   N)_sync_requestr   RateLimitErrorrh   compute_sleep_secondsretry_after_secondsri   rj   timesleepr   )rV   r>   r  r   rg   rate_limit_time_sleptrG   sleep_secondss           rI   r   zDAVClient.requestU  s    ,	c%%c64AAA# 	c 	c 	c) !7%-) M
 % ;!6!::$)5)D,EEEJ}%%%<<VT7<QTa<abbbbbbbb!	cs    B/A;B*$B/*B/c                    |                      ||||          \  }}d}| j        +|j        | j        i}t                              d|z             | j                            |t          |          t          |          ||| j	        | j
        | j        | j        	  	        }t          |j                  }	t          j        |j        t          |          |	                    d                     |                     |j        |	          r3|                     |	d                    |                     ||||          S |j        dv r#|                     t          |          |           t/          ||           }
|
S )zI
        Sync HTTP request implementation with auth negotiation.
        Nzusing proxy - %s)datarg   proxiesrd   r,   verifycertzRetry-AfterzWWW-Authenticate)i  i  )_prepare_requestra   r1   r9   r:   rw   r   r8   r   rd   r,   r-   rf   r
   rg   r   raise_if_rate_limitedstatus_coderC   _should_negotiate_auth_build_auth_from_401r  _raise_authorization_errorrL   )rV   r>   r  r   rg   url_objcombined_headersr  r	r_headersrO   s              rI   r  zDAVClient._sync_request  sn    %)$9$9#vtW$U$U!!:!~tz2GII(G4555L  LL$L' ! 

 

 (	22	 	#AM3w<<}A]A]^^^ &&q}i@@ 	B%%i0B&CDDD%%c64AAA =J&&++CLL!<<<q$''rX   )r5   NNNNNNTNNFNTTNNN)NNN)rR   NrT   )FFFNNNF)NNr   )r5   r   )r5   N)r  r5   Nr   )r  r5   N)7rY   rZ   r[   r\   ra   r8   r^   r>   r   rb   r<   r   inttupler   r   r7   r   rW   r    r   BaseExceptionr   r   r   r   r   r   r   r   r   r]   r   r   r   r   r   r   r   r   r   r   rL   r   r   r   r   r   r   r  r  r   r   r   r  r_   rX   rI   rQ   rQ      s          E3:COOOIt  ## $ $"&*15%),0# ,026.2%o9 o94Zo9 Tzo9 *	o9
 *o9 oo9 :o9 to9 o9 c3h'$.o9 c"o9 o9 t#c)o9 o9 o9  $D>!o9" #+3-#o9$ 'sm%o9& 
'o9 o9 o9 o9b4     *.*.*.	$ $$&$ !4'$ !4'	$
 
$ $ $ $   Y Y Y Y61 1 1 1  / / /  y         9
 9
y4'7 9
4> 9
 9
 9
 9
|  )-0
 0
0
 0
 	0

 0
 Tz0
 4Z0
  $;0
 0
 0
 
&	'0
 0
 0
 0
d13: 1 1 1 1$ND N N N NU$ U U U U(cDj ( ( ( ( ) ) ) ) ) /T / / / /& 	. .4Z. 	.
 
. . . .`4 4S 4 4D 4K 4 4 4 4; ;# ;c ;sTz ;+ ; ; ; ; 0 0 0C 0 0 0 0 0 0.5 5c 5 5$ 5+ 5 5 5 57 7s 7# 7S0A 7[ 7 7 7 78 8 83 8c1B 8k 8 8 8 8/# /+ / / / /03 0; 0 0 0 01 1DI,< 1 1 1 1 18 %)(c (c(c (c 	(c
 c"(c 
(c (c (c (cZ %), ,, , 	,
 c", 
, , , , , ,rX   rQ   rR   r   c                  &    t          t          fi | S )a  
    Get calendars from a CalDAV server with configuration from multiple sources.

    This is a convenience wrapper around :func:`caldav.base_client.get_calendars`
    that uses DAVClient.

    Args:
        calendar_url: URL(s) or ID(s) of specific calendars to fetch.
        calendar_name: Name(s) of specific calendars to fetch by display name.
        check_config_file: Whether to look for config files (default: True).
        config_file: Explicit path to config file.
        config_section: Section name in config file.
        testconfig: Whether to use test server configuration.
        environment: Whether to read from environment variables (default: True).
        name: Name of test server to use (for testconfig).
        raise_errors: If True, raise exceptions on errors; if False, log and skip.
        **config_data: Connection parameters (url, username, password, etc.)

    Returns:
        List of Calendar objects matching the criteria.

    Example::

        from caldav import get_calendars

        # Get all calendars
        calendars = get_calendars(url="https://...", username="...", password="...")

        # Get specific calendar by name
        calendars = get_calendars(calendar_name="Work", url="...", ...)
    )_base_get_calendarsrQ   r   s    rI   r   r     s    @ y33F333rX   CalendarResultc                  n    ddl m} t          t          fi | }|r|d         nd} |||j                  S )a  
    Get a single calendar from a CalDAV server.

    This is a convenience function for the common case where only one
    calendar is needed. Returns a CalendarResult that can be used as a
    context manager.

    Args:
        Same as :func:`get_calendars`.

    Returns:
        CalendarResult wrapping a Calendar object (or None if not found).
        Use as context manager to auto-close the connection.

    Example::

        from caldav import get_calendar

        with get_calendar(calendar_name="Work", url="...", ...) as calendar:
            if calendar:
                events = calendar.date_search(start=..., end=...)
    r   )r1  N)r   )caldav.base_clientr1  r/  rQ   r   )r   r1  	calendarsr   s       rI   get_calendarr5    sU    . 211111#I8888I(2y||dH>(9+;<<<<rX   c                  &    t          t          fi | S )z
    Get a DAVClient instance with configuration from multiple sources.

    See :func:`caldav.base_client.get_davclient` for full documentation.

    Returns:
        DAVClient instance, or None if no configuration is found.
    )_base_get_davclientrQ   r0  s    rI   r   r     s     y33F333rX   )r%   TTNT)rR   r1  )Mr\   copyr~   sysr  r   typesr   typingr   r   r   urllib.parser   _USE_NIQUESTS_USE_REQUESTSniquestsru   niquests.authr   niquests.modelsr	   niquests.structuresr
   ImportErrorrequests.authrequests.modelsrequests.structurescollections.abcr   lxmlr   caldav.compatibility_hintsr   r   r3  r   r   r/  r   r7  caldav.collectionr   r   r   r   caldav.configr   caldav.elementsr   r   
caldav.libr   caldav.lib.python_utilitiesr   caldav.lib.urlr   caldav.requestsr   caldav.responser   	getLoggerr9   version_infotyping_extensionsr    caldav.calendarobjectresourcer!   r"   r#   r$   rt   rJ   rL   rQ   r]   r5  r_   rX   rI   <module>rV     s      



         / / / / / / / / / /             &&&&&&((((((777777MM   OOO&&&&&&((((((777777MMM $ # # # # #       ! ! ! !       , , , , , , C C C C C C C C C C C C > > > > > > > > > > 1 1 1 1 1 1 # " " " " " % % % % % % % %       / / / / / /       * * * * * * + + + + + +g!!g&&&&&&& RQQQQQQQQQQ& @ ? ? ? ? ? C C C CL6 6 6 6 6/ 6 6 6,r r r r r r r rj 4tJ/  4  4  4  4F= = = =<	4x4 	4 	4 	4 	4 	4 	4s   A A+*A+