Your IP : 216.73.216.213


Current Path : /opt/alt/python37/lib/python3.7/site-packages/redis/__pycache__/
Upload File :
Current File : //opt/alt/python37/lib/python3.7/site-packages/redis/__pycache__/connection.cpython-37.pyc

B

�aG��	@s�ddlmZddlmZddlmZddlmZmZmZddl	m
Z
mZmZddl
Z
ddlZddlZddlZddlZddlZddlmZmZmZmZmZmZmZmZmZmZmZmZm Z m!Z!m"Z"ddl#m$Z$m%Z%yddl&Z&d	Z'Wne(k
r�d
Z'YnXe)e
j*iZ+e'�r6e,e&d��r,de+e&j-<de+e&j.<n
de+e&j/<e0e+�1��Z2e$�r�ddl3Z3ee3j4�Z5e5ed
�kZ6e5ed�kZ7e5ed�kZ8e7�s�de3j4Z9e�:e9�d	Z;e7�s�d
Z;dZ<dZ=dZ>dZ?dZ@eA�ZBdZCdZDdZEdZFGdd�d�ZGGdd�d�ZHGdd�d�ZIGd d!�d!eH�ZJGd"d#�d#eH�ZKe$�r&eKZLneJZLGd$d%�d%�ZMGd&d'�d'eM�ZNGd(d)�d)eM�ZOd*ZPd+d,�ZQeReSeSeQeQeReReQd-�ZTd.d/�ZUGd0d1�d1�ZVGd2d3�d3eV�ZWdS)4�)�
StrictVersion)�chain)�time)�	LifoQueue�Empty�Full)�parse_qs�unquote�urlparseN)�AuthenticationError�$AuthenticationWrongNumberOfArgsError�BusyLoadingError�ChildDeadlockedError�ConnectionError�	DataError�ExecAbortError�InvalidResponse�NoPermissionError�
NoScriptError�
ReadOnlyError�
RedisError�
ResponseError�TimeoutError�ModuleError)�HIREDIS_AVAILABLE�str_if_bytesTF�SSLWantReadError�z0.1.3z0.1.4z1.0.0z`redis-py works best with hiredis >= 0.1.4. You're running hiredis %s. Please consider upgrading.�*�$s
�zConnection closed by server.z:Error loading the extension. Please check the server logs.z5Error unloading module: no such module with that namez/Error unloading module: operation not possible.z[Error unloading module: the module exports one or more module-side data types, can't unloadc@s*eZdZdZdd�Zdd�Zd
dd�Zd	S)�Encoderz=Encode strings to bytes-like and decode bytes-like to stringscCs||_||_||_dS)N)�encoding�encoding_errors�decode_responses)�selfr"r#r$�r&�A/opt/alt/python37/lib/python3.7/site-packages/redis/connection.py�__init__]szEncoder.__init__cCs�t|ttf�r|St|t�r&td��n<t|ttf�rBt|���}n t|t	�sbt
|�j}td|��t|t	�r||�|j|j
�}|S)z=Return a bytestring or bytes-like representation of the valuezNInvalid input of type: 'bool'. Convert to a bytes, string, int or float first.zLInvalid input of type: '%s'. Convert to a bytes, string, int or float first.)�
isinstance�bytes�
memoryview�boolr�int�float�repr�encode�str�type�__name__r"r#)r%�value�typenamer&r&r'r0bs




zEncoder.encodeFcCs:|js
|r6t|t�r|��}t|t�r6|�|j|j�}|S)z:Return a unicode string from the bytes-like representation)r$r)r+�tobytesr*�decoder"r#)r%r4�forcer&r&r'r7us


zEncoder.decodeN)F)r3�
__module__�__qualname__�__doc__r(r0r7r&r&r&r'r!Zsr!c@sLeZdZdededededeeeeee	ee
ei	eee
eeed�Zdd�Zd	S)
�
BaseParserzmax number of clients reachedz(Client sent AUTH, but no password is setzinvalid passwordz,wrong number of arguments for 'auth' commandz,wrong number of arguments for 'AUTH' command)�ERR�	EXECABORT�LOADING�NOSCRIPT�READONLY�NOAUTH�NOPERMcCs\|�d�d}||jkrT|t|�dd�}|j|}t|t�rL|�|t�}||�St|�S)zParse an error response� r�N)�split�EXCEPTION_CLASSES�lenr)�dict�getr)r%�response�
error_code�exception_classr&r&r'�parse_error�s


zBaseParser.parse_errorN)r3r9r:rrr�MODULE_LOAD_ERRORr�MODULE_EXPORTS_DATA_TYPES_ERROR�NO_SUCH_MODULE_ERROR� MODULE_UNLOAD_NOT_POSSIBLE_ERRORrr
rrrrGrNr&r&r&r'r<s$r<c@sXeZdZdd�Zedd��Zdedfdd�Zd	d
�Zdd�Z	d
d�Z
dd�Zdd�ZdS)�SocketBuffercCs,||_||_||_t��|_d|_d|_dS)Nr)�_sock�socket_read_size�socket_timeout�io�BytesIO�_buffer�
bytes_written�
bytes_read)r%�socketrUrVr&r&r'r(�s
zSocketBuffer.__init__cCs|j|jS)N)rZr[)r%r&r&r'�length�szSocketBuffer.lengthNTc

Cs@|j}|j}|j}|�|j�d}|tk	}�z�y||r>|�|�xh|j�|�}	t|	t	�rjt
|	�dkrjtt��|�
|	�t
|	�}
|j|
7_||
7}|dk	r�||kr�q@dSWnxtjk
r�|r�td��dStk
�r"}z8t�|jd�}|�s|j|k�rdStd|jf��Wdd}~XYnXWd|�r:|�|j�XdS)NrTzTimeout reading from socketF���z#Error while reading from socket: %s)rTrUrY�seekrZ�SENTINEL�
settimeout�recvr)r*rHr�SERVER_CLOSED_CONNECTION_ERROR�writer\�timeoutr�NONBLOCKING_EXCEPTIONS�#NONBLOCKING_EXCEPTION_ERROR_NUMBERSrJ�	__class__�errno�argsrV)
r%r]re�raise_on_timeout�sockrU�buf�marker�custom_timeout�data�data_length�ex�allowedr&r&r'�_read_from_socket�s@

"zSocketBuffer._read_from_socketcCst|j�p|j|dd�S)NF)rerk)r,r]rt)r%rer&r&r'�can_read�s
zSocketBuffer.can_readcCsn|d}||jkr"|�||j�|j�|j�|j�|�}|jt|�7_|j|jkrb|��|dd�S)Nr���)	r]rtrYr_r[�readrHrZ�purge)r%r]rpr&r&r'rw�s
zSocketBuffer.readcCsx|j}|�|j�|��}x*|�t�sD|��|�|j�|��}qW|jt|�7_|j|jkrl|�	�|dd�S)Nrv)
rYr_r[�readline�endswith�SYM_CRLFrtrHrZrx)r%rmrpr&r&r'ry�szSocketBuffer.readlinecCs&|j�d�|j��d|_d|_dS)Nr)rYr_�truncaterZr[)r%r&r&r'rx	s
zSocketBuffer.purgecCs<y|��|j��Wntk
r*YnXd|_d|_dS)N)rxrY�close�	ExceptionrT)r%r&r&r'r}szSocketBuffer.close)
r3r9r:r(�propertyr]r`rtrurwryrxr}r&r&r&r'rS�s
*rSc@s@eZdZdZdd�Zdd�Zdd�Zdd	�Zd
d�Zdd
�Z	dS)�PythonParserzPlain Python parsing classcCs||_d|_d|_d|_dS)N)rU�encoderrTrY)r%rUr&r&r'r( szPythonParser.__init__cCs&y|��Wntk
r YnXdS)N)�
on_disconnectr~)r%r&r&r'�__del__&szPythonParser.__del__cCs(|j|_t|j|j|j�|_|j|_dS)zCalled when the socket connectsN)rTrSrUrVrYr�)r%�
connectionr&r&r'�
on_connect,s

zPythonParser.on_connectcCs*d|_|jdk	r |j��d|_d|_dS)z"Called when the socket disconnectsN)rTrYr}r�)r%r&r&r'r�4s


zPythonParser.on_disconnectcCs|jo|j�|�S)N)rYru)r%rer&r&r'ru<szPythonParser.can_readcs
�j��}|stt��|dd�|dd�}}|dkrDtd|��|dkrv|jddd�}��|�}t|t�rr|�|S|dkr�nn|d	kr�t|�}n\|d
kr�t|�}|dkr�dS�j�	|�}n2|dkr�t|�}|dkr�dS�fd
d�t
|�D�}t|t��r�j�|�}|S)NrE)�-�+�:rrzProtocol Error: %rr�zutf-8�replace)�errorsr�r�rr^rcsg|]}����qSr&)�
read_response)�.0�i)r%r&r'�
<listcomp>gsz.PythonParser.read_response.<locals>.<listcomp>)
rYryrrcrr7rNr)r-rw�ranger*r�)r%�raw�byterK�errorr]r&)r%r'r�?s:



zPythonParser.read_responseN)
r3r9r:r;r(r�r�r�rur�r&r&r&r'r�sr�c@sNeZdZdZdd�Zdd�Zdd�Zdd	�Zd
d�Ze	dfd
d�Z
dd�ZdS)�
HiredisParserz*Parser class for connections using HirediscCs$tstd��||_tr t|�|_dS)NzHiredis is not installed)rrrU�HIREDIS_USE_BYTE_BUFFER�	bytearrayrY)r%rUr&r&r'r(os
zHiredisParser.__init__cCs&y|��Wntk
r YnXdS)N)r�r~)r%r&r&r'r�wszHiredisParser.__del__cCsd|j|_|j|_t|jd�}ts(t|d<|jjr<|jj	|d<t
rL|jj|d<tj
f|�|_d|_dS)N)�
protocolError�
replyErrorr�r"r�F)rTrV�_socket_timeoutrrN� HIREDIS_SUPPORTS_CALLABLE_ERRORSrr�r$r"� HIREDIS_SUPPORTS_ENCODING_ERRORSr#�hiredis�Reader�_reader�_next_response)r%r��kwargsr&r&r'r�}s
zHiredisParser.on_connectcCsd|_d|_d|_dS)NF)rTr�r�)r%r&r&r'r��szHiredisParser.on_disconnectcCs@|jstt��|jdkr<|j��|_|jdkr<|j|dd�SdS)NF)rerkT)r�rrcr��gets�read_from_socket)r%rer&r&r'ru�s

zHiredisParser.can_readTc	
Cs$|j}|tk	}�z�y�|r"|�|�trX|j�|j�}|dkrDtt��|j�	|jd|�n8|j�
|j�}t|t
�r|t|�dkr�tt��|j�	|�dStjk
r�|r�td��dStk
�r}z4t�|jd�}|s�|j|kr�dStd|jf��Wdd}~XYnXWd|�r|�|j�XdS)NrTzTimeout reading from socketFr^z#Error while reading from socket: %s)rTr`rar��	recv_intorYrrcr��feedrbrUr)r*rHr\rerrfrgrJrhrirjr�)	r%rerkrlro�bufflen�bufferrrrsr&r&r'r��s6
"zHiredisParser.read_from_socketcCs�|jstt��|jdk	r(|j}d|_|S|j��}x|dkrP|��|j��}q4Wts�t|t�rr|�	|j
d�}n4t|t�r�|r�t|dt�r�|�	|dj
d�|d<t|t�r�|�n$t|t�r�|r�t|dt�r�|d�|S)NFr)r�rrcr�r�r�r�r)rrNrj�list)r%rKr&r&r'r��s,




zHiredisParser.read_responseN)r3r9r:r;r(r�r�r�rur`r�r�r&r&r&r'r�ms&r�c@s�eZdZdZddddddddddddded	dddfd
d�Zdd
�Zdd�Zdd�Zdd�Z	dd�Z
dd�Zdd�Zdd�Z
dd�Zdd�Zd d!�Zd/d#d$�Zd%d&�Zd0d'd(�Zd)d*�Zd+d,�Zd-d.�ZdS)1�
Connectionz4Manages TCP communication to and from a Redis server�	localhosti�rNFzutf-8�stricticCs�t��|_||_t|�|_||_||_||_||_	||_
|p>||_||_|pNi|_
|	|_|
|_||_d|_t|||
�|_d|_||d�|_g|_d|_dS)Nr)rUip)�os�getpid�pid�hostr-�port�db�username�client_name�passwordrV�socket_connect_timeout�socket_keepalive�socket_keepalive_options�socket_type�retry_on_timeout�health_check_interval�next_health_checkr!r�rT�_parser�_connect_callbacks�_buffer_cutoff)r%r�r�r�r�rVr�r�r�r�r�r"r#r$�parser_classrUr�r�r�r&r&r'r(�s(



zConnection.__init__cCs(d�dd�|��D��}d|jj|fS)N�,cSsg|]\}}d||f�qS)z%s=%sr&)r��k�vr&r&r'r�
sz'Connection.__repr__.<locals>.<listcomp>z%s<%s>)�join�repr_piecesrhr3)r%�	repr_argsr&r&r'�__repr__szConnection.__repr__cCs6d|jfd|jfd|jfg}|jr2|�d|jf�|S)Nr�r�r�r�)r�r�r�r��append)r%�piecesr&r&r'r�szConnection.repr_piecescCs&y|��Wntk
r YnXdS)N)�
disconnectr~)r%r&r&r'r�szConnection.__del__cCs|j�|�dS)N)r�r�)r%�callbackr&r&r'�register_connect_callback sz$Connection.register_connect_callbackcCs
g|_dS)N)r�)r%r&r&r'�clear_connect_callbacks#sz"Connection.clear_connect_callbacksc
Cs�|jr
dSy|��}WnNtjk
r4td��Yn2tjk
rd}zt|�|���Wdd}~XYnX||_y|��Wnt	k
r�|�
��YnXx|jD]}||�q�WdS)z5Connects to the Redis server if not already connectedNzTimeout connecting to server)rT�_connectr\rerr�r�_error_messager�rr�r�)r%rl�er�r&r&r'�connect&s  zConnection.connectcCsd}x�t�|j|j|jtj�D]�}|\}}}}}d}y�t�|||�}|�tjtjd�|j	r�|�tj
tjd�x&|j�
�D]\}	}
|�tj|	|
�qzW|�|j�|�|�|�|j�|Stk
r�}z|}|dk	r�|��Wdd}~XYqXqW|dk	�r|�td��dS)zCreate a TCP socket connectionNrEz)socket.getaddrinfo returned an empty list)r\�getaddrinfor�r�r��SOCK_STREAM�
setsockopt�IPPROTO_TCP�TCP_NODELAYr��
SOL_SOCKET�SO_KEEPALIVEr��itemsrar�r�rV�OSErrorr})r%�err�res�family�socktype�proto�	canonname�socket_addressrlr�r��_r&r&r'r�>s.

zConnection._connectcCsJt|j�dkr&d|j|j|jdfSd|jd|j|j|jdfSdS)NrEzError connecting to %s:%s. %s.rz!Error %s connecting to %s:%s. %s.)rHrjr�r�)r%�	exceptionr&r&r'r�fs
zConnection._error_messagecCs�|j�|�|js|jr�|jr0|j|jp*df}n|jf}|jd|�ddi�y|��}Wn.tk
r�|jd|jdd�|��}YnXt|�dkr�td��|j	r�|�dd	|j	�t|���dkr�t
d
��|jr�|�d|j�t|���dkr�t
d��d
S)z=Initialize the connection, authenticate and select a database��AUTH�check_healthF)r��OKzInvalid Username or Password�CLIENT�SETNAMEzError setting client name�SELECTzInvalid DatabaseN)r�)r�r�r�r��send_commandr�rrrr�rr�)r%�	auth_args�
auth_responser&r&r'r�ps*zConnection.on_connectcCsb|j��|jdkrdSy*t��|jkr6|j�tj�|j�	�Wnt
k
rVYnXd|_dS)z!Disconnects from the Redis serverN)r�r�rTr�r�r��shutdownr\�	SHUT_RDWRr}r�)r%r&r&r'r��s

zConnection.disconnectc	Cs�|jr�t�|jkr�y*|jddd�t|���dkr:td��WnFttfk
r�|��|jddd�t|���dkr~td��YnXdS)z3Check the health of the connection with a PING/PONG�PINGF)r��PONGz#Bad response from PING health checkN)	r�rr�r�rr�rrr�)r%r&r&r'r��s
zConnection.check_healthTc
Cs�|js|��|r|��y.t|t�r,|g}x|D]}|j�|�q2WWn�tjk
rn|��t	d��Yn�tj
k
r�}zP|��t|j�dkr�d|jd}}n|jd}|jd}t
d||f��Wdd}~XYntk
r�|���YnXdS)z2Send an already packed command to the Redis serverzTimeout writing to socketrE�UNKNOWNrz%Error %s while writing to socket. %s.N)rTr�r�r)r1�sendallr\rer�rr�rHrjr�
BaseException)r%�commandr��itemr�ri�errmsgr&r&r'�send_packed_command�s.



zConnection.send_packed_commandcOs |j|j|�|�dd�d�dS)z+Pack and send a command to the Redis serverr�T)r�N)r��pack_commandrJ)r%rjr�r&r&r'r��szConnection.send_commandcCs$|j}|s|��|j}|j�|�S)z8Poll the socket to see if there's data that can be read.)rTr�r�ru)r%rerlr&r&r'ru�s
zConnection.can_readc
Cs�y|j��}Wn�tjk
r@|��td|j|jf��Yn`tjk
r�}z$|��t	d|j|j|j
f��Wdd}~XYntk
r�|���YnX|jr�t
�|j|_t|t�r�|�|S)z0Read the response from a previously sent commandzTimeout reading from %s:%sz#Error while reading from %s:%s : %sN)r�r�r\rer�rr�r�r�rrjr�r�rr�r)r)r%rKr�r&r&r'r��s$$
zConnection.read_responsec	Gsg}t|dt�r4t|d�����|dd�}n(d|dkr\t|d���|dd�}t�ttt|����t	f�}|j
}x�t|jj|�D]|}t|�}t|�|ks�||ks�t|t
�r�t�|tt|���t	f�}|�|�|�|�t	}q�t�|tt|���t	|t	f�}q�W|�|�|S)z2Pack a series of arguments into the Redis protocolrrEN� )r)r1�tupler0rF�	SYM_EMPTYr��SYM_STARrHr{r��mapr�r+�
SYM_DOLLARr�)r%rj�output�buff�
buffer_cutoff�arg�
arg_lengthr&r&r'r��s*"



zConnection.pack_commandc	Cs�g}g}d}|j}x�|D]�}x||j|�D]n}t|�}||ksN||ksNt|t�rf|�t�|��d}g}||ksxt|t�r�|�|�q(|�|�||7}q(WqW|r�|�t�|��|S)z.Pack multiple commands into the Redis protocolr)r�r�rHr)r+r�r�r�)	r%�commandsr�r��
buffer_lengthr��cmd�chunk�chunklenr&r&r'�
pack_commandss&


zConnection.pack_commands)T)r)r3r9r:r;�
DefaultParserr(r�r�r�r�r�r�r�r�r�r�r�r�r�rur�r�rr&r&r&r'r��s2
(
'


"r�cs*eZdZd�fdd�	Z�fdd�Z�ZS)	�
SSLConnectionN�requiredFcs�tstd��t�jf|�||_||_|dkr6tj}n8t|t	�rntjtj
tjd�}||krftd|��||}||_||_
||_dS)Nz$Python wasn't built with SSL support)�none�optionalr
z-Invalid SSL Certificate Requirements Flag: %s)�
ssl_availabler�superr(�keyfile�certfile�ssl�	CERT_NONEr)r1�
CERT_OPTIONAL�
CERT_REQUIRED�	cert_reqs�ca_certs�check_hostname)r%�ssl_keyfile�ssl_certfile�
ssl_cert_reqs�ssl_ca_certs�ssl_check_hostnamer��	CERT_REQS)rhr&r'r(2s&

zSSLConnection.__init__csbt���}t��}|j|_|j|_|jr@|jr@|j	|j|jd�|j
rR|�|j
�|j||j
d�S)z Wrap the socket with SSL support)rr)�server_hostname)rr�r�create_default_contextrr�verify_moderr�load_cert_chainr�load_verify_locations�wrap_socketr�)r%rl�context)rhr&r'r�Ms

zSSLConnection._connect)NNr
NF)r3r9r:r(r��
__classcell__r&r&)rhr'r	0sr	c
@sHeZdZdddddddddedddf
dd	�Zd
d�Zdd
�Zdd�ZdS)�UnixDomainSocketConnectionr�rNzutf-8r�FicCspt��|_||_||_||_|
|_||_||_|	|_	||_
d|_t|||�|_
d|_|
|d�|_g|_d|_dS)Nr)rUip)r�r�r��pathr�r�r�r�rVr�r�r�r!r�rTr�r�r�)r%r'r�r�r�rVr"r#r$r�r�rUr�r�r&r&r'r(]s
z#UnixDomainSocketConnection.__init__cCs.d|jfd|jfg}|jr*|�d|jf�|S)Nr'r�r�)r'r�r�r�)r%r�r&r&r'r�ss
z&UnixDomainSocketConnection.repr_piecescCs,t�tjtj�}|�|j�|�|j�|S)z&Create a Unix domain socket connection)r\�AF_UNIXr�rarVr�r')r%rlr&r&r'r�|sz#UnixDomainSocketConnection._connectcCsBt|j�dkr"d|j|jdfSd|jd|j|jdfSdS)NrEz(Error connecting to unix socket: %s. %s.rz+Error %s connecting to unix socket: %s. %s.)rHrjr')r%r�r&r&r'r��s
z)UnixDomainSocketConnection._error_message)r3r9r:rr(r�r�r�r&r&r&r'r&[s	r&)�0�F�FALSE�N�NOcCs6|dks|dkrdSt|t�r.|��tkr.dSt|�S)Nr�F)r)r1�upper�
FALSE_STRINGSr,)r4r&r&r'�to_bool�s
r0)r�rVr�r�r��max_connectionsr�rc
Cs�t|�}i}x�t|j���D]r\}}|rt|�dkrt|d�}t�|�}|r�y||�||<Wq�tt	fk
r�t	d|��Yq�Xq|||<qW|j
r�t|j
�|d<|jr�t|j�|d<|jdkr�|j
r�t|j
�|d<t|d<n�|jdk�r||j�rt|j�|d	<|j�rt|j�|d
<|j
�rfd|k�rfytt|j
��dd
��|d<Wntt	fk
�rdYnX|jdk�r�t|d<nd}t	d|��|S)Nrz)Invalid value for `%s` in connection URL.r�r��unixr'�connection_class)�redis�redissr�r�r��/r�r5zredis://, rediss://, unix://z8Redis URL must specify one of the following schemes (%s))r
r�queryr�rHr	�URL_QUERY_ARGUMENT_PARSERSrJ�	TypeError�
ValueErrorr�r��schemer'r&�hostnamer�r-r��AttributeErrorr	)�urlr��namer4�parser�
valid_schemesr&r&r'�	parse_url�sJ



rBc@steZdZdZedd��Zedfdd�Zdd�Zd	d
�Z	dd�Z
d
d�Zdd�Zdd�Z
dd�Zdd�Zddd�ZdS)�ConnectionPoola�
    Create a connection pool. ``If max_connections`` is set, then this
    object raises :py:class:`~redis.ConnectionError` when the pool's
    limit is reached.

    By default, TCP connections are created unless ``connection_class``
    is specified. Use :py:class:`~redis.UnixDomainSocketConnection` for
    unix sockets.

    Any additional keyword arguments are passed to the constructor of
    ``connection_class``.
    cKst|�}|�|�|f|�S)a
        Return a connection pool configured from the given URL.

        For example::

            redis://[[username]:[password]]@localhost:6379/0
            rediss://[[username]:[password]]@localhost:6379/0
            unix://[[username]:[password]]@/path/to/socket.sock?db=0

        Three URL schemes are supported:

        - `redis://` creates a TCP socket connection. See more at:
          <https://www.iana.org/assignments/uri-schemes/prov/redis>
        - `rediss://` creates a SSL wrapped TCP socket connection. See more at:
          <https://www.iana.org/assignments/uri-schemes/prov/rediss>
        - ``unix://``: creates a Unix Domain Socket connection.

        The username, password, hostname, path and all querystring values
        are passed through urllib.parse.unquote in order to replace any
        percent-encoded values with their corresponding characters.

        There are several ways to specify a database number. The first value
        found will be used:
            1. A ``db`` querystring option, e.g. redis://localhost?db=0
            2. If using the redis:// or rediss:// schemes, the path argument
               of the url, e.g. redis://localhost/0
            3. A ``db`` keyword argument to this function.

        If none of these options are specified, the default db=0 is used.

        All querystring options are cast to their appropriate Python types.
        Boolean arguments can be specified with string values "True"/"False"
        or "Yes"/"No". Values that cannot be properly cast cause a
        ``ValueError`` to be raised. Once parsed, the querystring arguments
        and keyword arguments are passed to the ``ConnectionPool``'s
        class initializer. In the case of conflicting arguments, querystring
        arguments always win.
        )rB�update)�clsr>r��url_optionsr&r&r'�from_url�s(
zConnectionPool.from_urlNcKsJ|pd}t|t�r|dkr"td��||_||_||_t��|_|�	�dS)Nlrz,"max_connections" must be a positive integer)
r)r-r:r3�connection_kwargsr1�	threading�Lock�
_fork_lock�reset)r%r3r1rHr&r&r'r(s

zConnectionPool.__init__cCs dt|�jt|jf|j��fS)Nz%s<%s>)r2r3r/r3rH)r%r&r&r'r�(szConnectionPool.__repr__cCs,t��|_d|_g|_t�|_t��|_	dS)Nr)
rIrJ�_lock�_created_connections�_available_connections�set�_in_use_connectionsr�r�r�)r%r&r&r'rL.s

zConnectionPool.resetcCsP|jt��krL|jjdd�}|s$t�z|jt��kr<|��Wd|j��XdS)N�)re)r�r�r�rK�acquirerrL�release)r%�acquiredr&r&r'�	_checkpid?s#zConnectionPool._checkpidc	Os�|��|j�>y|j��}Wntk
r:|��}YnX|j�|�WdQRXyV|��y|�	�rnt
d��Wn4t
k
r�|��|��|�	�r�t
d��YnXWn tk
r�|�
|��YnX|S)zGet a connection from the poolNzConnection has datazConnection not ready)rVrMrO�pop�
IndexError�make_connectionrQ�addr�rurr�r�rT)r%�command_name�keys�optionsr�r&r&r'�get_connectionns*
zConnectionPool.get_connectioncCs,|j}t|�dd�|�dd�|�dd�d�S)z,Return an encoder based on encoding settingsr"zutf-8r#r�r$F)r"r#r$)rHr!rJ)r%r�r&r&r'�get_encoder�s


zConnectionPool.get_encodercCs0|j|jkrtd��|jd7_|jf|j�S)zCreate a new connectionzToo many connectionsrE)rNr1rr3rH)r%r&r&r'rY�szConnectionPool.make_connectionc	Csv|��|j�^y|j�|�Wntk
r4YnX|�|�rN|j�|�n|jd8_|�	�dSWdQRXdS)z(Releases the connection back to the poolrEN)
rVrMrQ�remove�KeyError�owns_connectionrOr�rNr�)r%r�r&r&r'rT�s
zConnectionPool.releasecCs|j|jkS)N)r�)r%r�r&r&r'rb�szConnectionPool.owns_connectionTc	CsN|��|j�6|r$t|j|j�}n|j}x|D]}|��q0WWdQRXdS)z�
        Disconnects connections in the pool

        If ``inuse_connections`` is True, disconnect connections that are
        current in use, potentially by other threads. Otherwise only disconnect
        connections that are idle in the pool.
        N)rVrMrrOrQr�)r%�inuse_connections�connectionsr�r&r&r'r��s

zConnectionPool.disconnect)T)r3r9r:r;�classmethodrGr�r(r�rLrVr^r_rYrTrbr�r&r&r&r'rC�s,/!	rCcsReZdZdZddeef�fdd�	Zdd�Zdd	�Zd
d�Z	dd
�Z
dd�Z�ZS)�BlockingConnectionPoola
    Thread-safe blocking connection pool::

        >>> from redis.client import Redis
        >>> client = Redis(connection_pool=BlockingConnectionPool())

    It performs the same function as the default
    :py:class:`~redis.ConnectionPool` implementation, in that,
    it maintains a pool of reusable connections that can be shared by
    multiple redis clients (safely across threads if required).

    The difference is that, in the event that a client tries to get a
    connection from the pool when all of connections are in use, rather than
    raising a :py:class:`~redis.ConnectionError` (as the default
    :py:class:`~redis.ConnectionPool` implementation does), it
    makes the client wait ("blocks") for a specified number of seconds until
    a connection becomes available.

    Use ``max_connections`` to increase / decrease the pool size::

        >>> pool = BlockingConnectionPool(max_connections=10)

    Use ``timeout`` to tell it either how many seconds to wait for a connection
    to become available, or to block forever:

        >>> # Block forever.
        >>> pool = BlockingConnectionPool(timeout=None)

        >>> # Raise a ``ConnectionError`` after five seconds if a connection is
        >>> # not available.
        >>> pool = BlockingConnectionPool(timeout=5)
    �2�cs(||_||_t�jf||d�|��dS)N)r3r1)�queue_classrerr()r%r1rer3rirH)rhr&r'r(�szBlockingConnectionPool.__init__cCsP|�|j�|_x,y|j�d�Wqtk
r6PYqXqWg|_t��|_dS)N)	rir1�pool�
put_nowaitr�_connectionsr�r�r�)r%r&r&r'rL�szBlockingConnectionPool.resetcCs|jf|j�}|j�|�|S)zMake a fresh connection.)r3rHrlr�)r%r�r&r&r'rYsz&BlockingConnectionPool.make_connectioncOs�|��d}y|jjd|jd�}Wntk
r>td��YnX|dkrP|��}yV|��y|��rltd��Wn4tk
r�|�	�|��|��r�td��YnXWn t
k
r�|�|��YnX|S)a7
        Get a connection, blocking for ``self.timeout`` until a connection
        is available from the pool.

        If the connection returned is ``None`` then creates a new connection.
        Because we use a last-in first-out queue, the existing connections
        (having been returned to the pool after the initial ``None`` values
        were added) will be returned before ``None`` values. This means we only
        create new connections when we need to, i.e.: the actual number of
        connections will only increase in response to demand.
        NT)�blockrezNo connection available.zConnection has datazConnection not ready)rVrjrJrerrrYr�rur�r�rT)r%r[r\r]r�r&r&r'r^s,

z%BlockingConnectionPool.get_connectioncCsT|��|�|�s*|��|j�d�dSy|j�|�Wntk
rNYnXdS)z)Releases the connection back to the pool.N)rVrbr�rjrkr)r%r�r&r&r'rTIs
zBlockingConnectionPool.releasecCs$|��x|jD]}|��qWdS)z(Disconnects all connections in the pool.N)rVrlr�)r%r�r&r&r'r�^sz!BlockingConnectionPool.disconnect)
r3r9r:r;r�rr(rLrYr^rTr�r%r&r&)rhr'rf�s 
4rf)X�distutils.versionr�	itertoolsrr�queuerrr�urllib.parserr	r
rirWr�r\rI�warnings�redis.exceptionsrrr
rrrrrrrrrrrr�redis.utilsrrrr
�ImportError�BlockingIOError�EWOULDBLOCKrg�hasattrr�SSLWantWriteError�SSLErrorr�r\rfr��__version__Zhiredis_versionr�ZHIREDIS_SUPPORTS_BYTE_BUFFERr��msg�warnr�r�r�r{r�rc�objectr`rOrQrRrPr!r<rSr�r�rr�r	r&r/r0r-r.r8rBrCrfr&r&r&r'�<module>s�D





%'xOzE+3	5r