
    j                       d dl mZ d dlZd dlZd dlZd dlmZm	Z	m
Z
mZ d dlZddlmZmZ ddlmZmZmZ dd	gZ	 d d
lmZ d dlmZmZ dddej        dddZn# e$ r dddej        dddZY nw xY w G d d	          ZdS )     )annotationsN)Any	AwaitableCallableLiteral   )RequestResponse   )ServerServerConnectionserverouteRouter)NotFound)MapRequestRedirect)server_namesslcreate_routertask_statusurl_mapr   argsr   r   
str | Noner   ,ssl_module.SSLContext | Literal[True] | Noner   type[Router] | Noner   trio.TaskStatus[Server]kwargsreturnNonec                  	
K   |dnd}|dur|||d<   |t           } || ||          
|                    dd          		
j        }nd	
fd}t          
j        g|R ||d| d{V S )a
  
        Create a WebSocket server dispatching connections to different handlers.

        This feature requires the third-party library `werkzeug`_:

        .. code-block:: console

            $ pip install werkzeug

        .. _werkzeug: https://werkzeug.palletsprojects.com/

        :func:`route` accepts the same arguments as
        :func:`~websockets.trio.server.serve`, except as described below.

        The first argument is a :class:`werkzeug.routing.Map` that maps URL patterns
        to connection handlers. In addition to the connection, handlers receive
        parameters captured in the URL as keyword arguments.

        Here's an example::

            from websockets.trio.router import route
            from werkzeug.routing import Map, Rule

            async def channel_handler(websocket, channel_id):
                ...

            url_map = Map([
                Rule("/channel/<uuid:channel_id>", endpoint=channel_handler),
                ...
            ])

            # set this event to exit the server
            stop = trio.Event()

            with trio.open_nursery() as nursery:
                server = await nursery.start(route, url_map, ...)
                async with server:
                    await stop.wait()

        Refer to the documentation of :mod:`werkzeug.routing` for details.

        If you define redirects with ``Rule(..., redirect_to=...)`` in the URL map,
        when the server runs behind a reverse proxy that modifies the ``Host``
        header or terminates TLS, you need additional configuration:

        * Set ``server_name`` to the name of the server as seen by clients. When
          not provided, websockets uses the value of the ``Host`` header.

        * Set ``ssl=True`` to generate ``wss://`` URIs without enabling TLS.
          Under the hood, this bind the URL map with a ``url_scheme`` of
          ``wss://`` instead of ``ws://``.

        There is no need to specify ``websocket=True`` in each rule. It is added
        automatically.

        Args:
            url_map: Mapping of URL patterns to connection handlers.
            server_name: Name of the server as seen by clients. If :obj:`None`,
                websockets uses the value of the ``Host`` header.
            ssl: Configuration for enabling TLS on the connection. Set it to
                :obj:`True` if a reverse proxy terminates TLS connections.
            create_router: Factory for the :class:`Router` dispatching requests to
                handlers. Set it to a wrapper or a subclass to customize routing.
            task_status: For compatibility with :meth:`nursery.start
                <trio.Nursery.start>`.

        NwswssTr   process_request
connectionr   requestr	   r   Response | Nonec                   K    | |          }t          |t                    r| d {V }||S                     | |          S )N)
isinstancer   route_request)r%   r&   response_process_requestrouters      `/workspace/show-city-briefing-agent/.venv/lib/python3.11/site-packages/websockets/trio/router.pyr$   zroute.<locals>.process_request   s_       ,+J@@h	22 .%-~~~~~~H'#O++J@@@    )r$   r   r%   r   r&   r	   r   r'   )r   popr*   r   handler)r   r   r   r   r   r   r   
url_schemer$   r,   r-   s            @@r.   r   r   $   s     X ![TTe
d??sF5M "MwZ@@ JJ($// 	 # $ O	A 	A 	A 	A 	A 	A 	A N

 
 ,#	
 

 
 
 
 
 
 
 
 
 	
r/   c               $   K   t          d          )Nzroute() requires werkzeug)ImportError)r   r   r   r   r   r   r   s          r.   r   r      s       5666r/   c                  H    e Zd ZdZ	 	 dddZddZddZddZddZddZ	dS ) r   z*WebSocket router supporting :func:`route`.Nr"   r   r   r   r   r3   strr   r    c                v    || _         || _        || _        | j                                         D ]	}d|_        
d S )NT)r   r   r3   
iter_rules	websocket)selfr   r   r3   rules        r.   __init__zRouter.__init__   sJ     &$L++-- 	" 	"D!DNN	" 	"r/   r%   r   r&   r	   c                8    | j         |j        d         S | j         S )NHost)r   headers)r;   r%   r&   s      r.   get_server_namezRouter.get_server_name   s!    #?6**##r/   urlr
   c                j    |                     t          j        j        d|           }||j        d<   |S )Nz	Found at Location)respondhttp
HTTPStatusFOUNDr@   )r;   r%   rB   r+   s       r.   redirectzRouter.redirect   s7    %%do&;=N=N=NOO'*$r/   c                L    |                     t          j        j        d          S )Nz	Not Found)rE   rF   rG   	NOT_FOUNDr;   r%   s     r.   	not_foundzRouter.not_found   s    !!$/";[IIIr/   r'   c                   | j                             |                     ||          | j                  }	 t          j                            |j                  }|                    |j        |j	                  \  }}nR# t          $ r%}|                     ||j                  cY d}~S d}~wt          $ r |                     |          cY S w xY w||c|_        |_        dS )zRoute incoming request.)r   r3   )	path_info
query_argsN)r   bindrA   r3   urllibparseurlparsepathmatchqueryr   rI   new_urlr   rM   r2   handler_kwargs)r;   r%   r&   url_map_adapterparsedr2   r   rI   s           r.   r*   zRouter.route_request   s    ,++,,ZAA , 
 
		.\**7<88F-33 +!< 4  OGVV  	? 	? 	?==X-=>>>>>>>> 	. 	. 	.>>*-----	.8?5
J5ts$   AB   
C
B*$C*"CCc                8   K    |j         |fi |j         d{V S )zHandle a connection.N)r2   rY   rL   s     r.   r2   zRouter.handler   s6      'Z'
PPj6OPPPPPPPPPr/   )Nr"   )r   r   r   r   r3   r7   r   r    )r%   r   r&   r	   r   r7   )r%   r   rB   r7   r   r
   )r%   r   r   r
   r0   )r%   r   r   r    )
__name__
__module____qualname____doc__r=   rA   rI   rM   r*   r2    r/   r.   r   r      s        44
 #'	
" 
" 
" 
" 
"$ $ $ $   
J J J J   *Q Q Q Q Q Qr/   )r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r    )
__future__r   rF   r   
ssl_moduleurllib.parserR   typingr   r   r   r   triohttp11r	   r
   serverr   r   r   __all__werkzeug.exceptionsr   werkzeug.routingr   r   TASK_STATUS_IGNOREDr   r5   r   ra   r/   r.   <module>rm      s   " " " " " "          4 4 4 4 4 4 4 4 4 4 4 4  & & & & & & & & 3 3 3 3 3 3 3 3 3 3 H
G
,,,,,,55555555( #'<@-1/3/Gt
 t
 t
 t
 t
 t
 t
  7 7 7
 #'<@-1/3/G	7 	7 	7 	7 	7 	7 	7 	77L4Q 4Q 4Q 4Q 4Q 4Q 4Q 4Q 4Q 4Qs   A A/.A/