U
    f&                     @   s   d 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 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
ZedZdd Zdd ZG dd dejZG dd dejeZG dd dejZG dd dejZdddefddZdS )a0  
HTTP server that implements the Python WSGI protocol (PEP 333, rev 1.21).

Based on wsgiref.simple_server which is part of the standard library since 2.5.

This is a simple server for use in testing or debugging Django apps. It hasn't
been reviewed for security issues. DON'T USE IT FOR PRODUCTION USE!
    N)deque)simple_server)ImproperlyConfigured)LimitedStream)get_wsgi_application)connections)import_string)
WSGIServerWSGIRequestHandlerzdjango.serverc               
   C   sd   ddl m}  t| d}|dkr$t S z
t|W S  tk
r^ } ztd| |W 5 d}~X Y nX dS )aK  
    Load and return the WSGI application as configured by the user in
    ``settings.WSGI_APPLICATION``. With the default ``startproject`` layout,
    this will be the ``application`` object in ``projectname/wsgi.py``.

    This function, and the ``WSGI_APPLICATION`` setting itself, are only useful
    for Django's internal server (runserver); external WSGI servers should just
    be configured to point to the correct application object directly.

    If settings.WSGI_APPLICATION is not set (is ``None``), return
    whatever ``django.core.wsgi.get_wsgi_application`` returns.
    r   )settingsZWSGI_APPLICATIONNzBWSGI application '%s' could not be loaded; Error importing module.)Zdjango.confr   getattrr   r   ImportErrorr   )r   Zapp_patherr r   @/tmp/pip-unpacked-wheel-_jot26k8/django/core/servers/basehttp.pyget_internal_wsgi_application   s    

r   c                  C   s   t  \} }}t| tttfS N)sysexc_info
issubclassBrokenPipeErrorConnectionAbortedErrorConnectionResetError)exc_type_r   r   r   is_broken_pipe_error8   s    r   c                       s8   e Zd ZdZdZddd fdd
Z fdd	Z  ZS )
r	   z7BaseHTTPServer that implements the Python WSGI protocol
   FT)ipv6allow_reuse_addressc                   s$   |rt j| _|| _t j|| d S r   )socketAF_INET6address_familyr   super__init__)selfr   r   argskwargs	__class__r   r   r#   I   s    zWSGIServer.__init__c                    s&   t  rtd| nt || d S )Nz- Broken pipe from %s)r   loggerinfor"   handle_error)r$   requestclient_addressr'   r   r   r+   O   s    zWSGIServer.handle_error)__name__
__module____qualname____doc__request_queue_sizer#   r+   __classcell__r   r   r'   r   r	   D   s   r	   c                       sJ   e Zd ZdZdZdd fdd
Z fddZd	d
 Z fddZ  Z	S )ThreadedWSGIServerz$A threaded version of the WSGIServerTN)connections_overridec                   s   t  j|| || _d S r   )r"   r#   r5   )r$   r5   r%   r&   r'   r   r   r#   [   s    zThreadedWSGIServer.__init__c                    s4   | j r"| j  D ]\}}|t|< qt || d S r   )r5   itemsr   r"   process_request_thread)r$   r,   r-   aliasconnr'   r   r   r7   a   s    
z)ThreadedWSGIServer.process_request_threadc                 C   s   t   d S r   )r   Z	close_allr$   r   r   r   _close_connectionsi   s    z%ThreadedWSGIServer._close_connectionsc                    s   |    t | d S r   )r;   r"   close_request)r$   r,   r'   r   r   r<   m   s    z ThreadedWSGIServer.close_request)
r.   r/   r0   r1   daemon_threadsr#   r7   r;   r<   r3   r   r   r'   r   r4   V   s   r4   c                       sD   e Zd ZdZ fddZ fddZ fddZ fdd	Z  ZS )
ServerHandlerz1.1c              	      sP   zt |d}W n ttfk
r.   d}Y nX t jt|||||f| dS )a#  
        Use a LimitedStream so that unread request data will be ignored at
        the end of the request. WSGIRequest uses a LimitedStream but it
        shouldn't discard the data since the upstream servers usually do this.
        This fix applies only for testserver/runserver.
        CONTENT_LENGTHr   N)intget
ValueError	TypeErrorr"   r#   r   )r$   stdinstdoutstderrenvironr&   content_lengthr'   r   r   r#   u   s    
   zServerHandler.__init__c                    s   t    | jd dkr*d| jkr*| jd= | jd dkrNd| jkrNd| jd< nt| jjtjshd| jd< | j	ddkrd| j_
d S )NREQUEST_METHODHEADzContent-Lengthclose
ConnectionT)r"   cleanup_headersrG   headers
isinstancerequest_handlerserversocketserverThreadingMixInrA   close_connectionr:   r'   r   r   rM      s    

zServerHandler.cleanup_headersc                    s   |     t   d S r   )Z	get_stdinreadr"   rK   r:   r'   r   r   rK      s    zServerHandler.closec                    sJ   | j d dkr<z t| jdd | js,|   W 5 |   X n
t   d S )NrI   rJ   r   )maxlen)rG   rK   r   resultZheaders_sentsend_headersr"   finish_responser:   r'   r   r   rY      s    zServerHandler.finish_response)	r.   r/   r0   http_versionr#   rM   rK   rY   r3   r   r   r'   r   r>   r   s
   r>   c                       s@   e Zd ZdZdd Zdd Z fddZdd	 Zd
d Z  Z	S )r
   zHTTP/1.1c                 C   s
   | j d S )Nr   )r-   r:   r   r   r   address_string   s    z!WSGIRequestHandler.address_stringc                 G   s   | j |  d}|d d dkrH|d drHd|d< tjd|d	 d S |d  rt|d d
krt|d }||d< |dkrtj}q|dkrtj}qtj	}ntj	}||f|d|i d S )N)r,   Zserver_time   r   4zi  status_codezNYou're accessing the development server over HTTPS, but it only supports HTTP.)extra   i  r_   )
r,   Zlog_date_time_string
startswithr)   errorisdigitlenr@   warningr*   )r$   formatr%   r_   r^   levelr   r   r   log_message   s*    zWSGIRequestHandler.log_messagec                    s&   | j D ]}d|kr| j |= qt  S )Nr   )rN   r"   get_environ)r$   kr'   r   r   ri      s    

zWSGIRequestHandler.get_environc              	   C   sN   d| _ |   | j s|   qz| jtj W n ttfk
rH   Y nX d S )NT)rT   handle_one_request
connectionshutdownr   SHUT_WRAttributeErrorOSErrorr:   r   r   r   handle   s    
zWSGIRequestHandler.handlec                 C   s|   | j d| _t| jdkr<d| _d| _d| _| d dS |  sHdS t	| j | j
|  |  }| |_|| j  dS )zDCopy of WSGIRequestHandler.handle() but with different ServerHandleri  i    i  N)rfilereadlineZraw_requestlinerd   ZrequestlineZrequest_versioncommandZ
send_errorZparse_requestr>   wfileZ
get_stderrri   rP   runrQ   Zget_app)r$   handlerr   r   r   rk      s"    
   z%WSGIRequestHandler.handle_one_request)
r.   r/   r0   Zprotocol_versionr[   rh   ri   rq   rk   r3   r   r   r'   r   r
      s   
r
   Fc           
      C   sj   | |f}|r t dtj|fi }n|}||t|d}	|d k	rJ|t|	d| |rTd|	_|	| |	  d S )Nr	   )r   Zserver_portT)typerR   rS   r
   r   r=   Zset_appserve_forever)
addrportZwsgi_handlerr   	threadingZon_bindZ
server_clsserver_addressZ	httpd_clsZhttpdr   r   r   rw      s    	
rw   )r1   loggingr   rR   r   collectionsr   wsgirefr   Zdjango.core.exceptionsr   Zdjango.core.handlers.wsgir   Zdjango.core.wsgir   Z	django.dbr   Zdjango.utils.module_loadingr   __all__	getLoggerr)   r   r   r	   rS   r4   r>   r
   rw   r   r   r   r   <module>   s0   	
>S