~f&8 ddlZddlZddlmZddlmZddlmZddlm Z m Z m Z ddl m Z mZmZmZddlmZGdd e ZGd d e ZGd d e ZGddee ZGddZGdde ZGddeZy)N)Optional)Redis)SentinelCommands) ConnectionConnectionPool SSLConnection)ConnectionError ReadOnlyError ResponseError TimeoutError) str_if_bytesc eZdZy)MasterNotFoundErrorN__name__ __module__ __qualname__W/var/lib/jenkins/workspace/mettalog/venv/lib/python3.12/site-packages/redis/sentinel.pyrr rrc eZdZy)SlaveNotFoundErrorNrrrrrrrrrcfeZdZfdZdZfdZdZdZ d ddddee d ee ffd Z xZ S) SentinelManagedConnectionc P|jd|_t| di|y)Nconnection_poolr)poprsuper__init__)selfkwargs __class__s rr z"SentinelManagedConnection.__init__s%%zz*;< "6"rc|j}dt|jdt|jd|jd}|j r!d|j d|j }||z}|S)N<. (service=z%s)>z,host=z,port=)rtyperr service_namehostport)r!pools host_infos r__repr__z"SentinelManagedConnection.__repr__s{##T %%&aT (;(;'<))*$ 0  99  6$))=II Arc|\|_|_t| |jj r9|j dt|jdk7r tdyy)NPINGPONGz PING failed) r*r+rconnectrcheck_connection send_commandr read_responser )r!addressr#s r connect_toz$SentinelManagedConnection.connect_to$sc& 49     0 0   f %D..01V;%m44< 1rc*|jry|jjr*|j|jj y|jj D]} |j|cSt#t $rY)wxYwN)_sockr is_masterr8get_master_address rotate_slavesr r)r!slaves r_connect_retryz(SentinelManagedConnection._connect_retry,s ::     ) ) OOD00CCE F--;;=??511> % $'s,B BBcP|jj|jdS)Ncyr:r)errors rz3SentinelManagedConnection.connect..:sTr)retrycall_with_retryr@r!s rr3z!SentinelManagedConnection.connect9s zz))$*=*=?QRRrF)disconnect_on_error push_requestrHrIc t||||S#t$r3|jjr|j t dwxYw)N)disable_decodingrHrIz"The previous master is now a slave)rr6r rr< disconnectr )r!rKrHrIr#s rr6z'SentinelManagedConnection.read_response<sc 7(!1$7))   ##-- !%&JKK  s >t?P?PQ >>d11^C"0D #668O***U*Crc#K|jj|j}|r|j't j dt |dz |_tt |D]5}|jdzt |z|_||j}|7 |jtd|j#t$rY#wxYww)NrzNo slave found for ) rXdiscover_slavesr)r\randomrandintlenranger=rr)r!slaves_r?s rr>z)SentinelConnectionPoolProxy.rotate_slavesxs&&66t7H7HI $$,(.q#f+/(J%3v;')-)>)>)Bc&k(Q%t445 (  ))+ +!#6t7H7H6K!LMM#   s*B'C#*C<C# C C#C  C#N)rrrr rYr=r>rrrrSrSYs % NrrScXeZdZdZfdZdZfdZedZfdZ dZ dZ xZ S) SentinelConnectionPoolz Sentinel backed connection pool. If ``check_connection`` flag is set to True, SentinelManagedConnection sends a PING command right after establishing the connection. c |jd|jddrtnt|d<|jdd|_|jdd|_t ||j|j |||_t|$d i||j|jd<||_ ||_ y) Nconnection_classsslFr<Tr4)rr<r4r)rXrr) getrrQrr<r4rSproxyrr connection_kwargsr)rX)r!r)rXr"r#s rr zSentinelConnectionPool.__init__s%+ZZ zz%' )* & !"  K6 & +=u E0 nn!22%-    "6"48JJ01( 0rc |jrdnd}dt|jdt|jd|jd|d S)Nmasterr?r%r&r'(z))>)r<r(rrr))r!roles rr/zSentinelConnectionPool.__repr__sR>>xwT %%&aT (;(;'<))*!D6 6 rcVt||jjyr:)rrYro)r!r#s rrYzSentinelConnectionPool.resets   rc.|jjSr:)ror[rGs rr[z%SentinelConnectionPool.master_addressszz(((rc|j xs3|jxr%|j|j|jfk(}t }|xr|j |Sr:)r<r[r*r+rowns_connection)r! connectioncheckparentr#s rrxz&SentinelConnectionPool.owns_connectionsZNN" NN Xt22z 6XX ;// ;;rc6|jjSr:)ror=rGs rr=z)SentinelConnectionPool.get_master_addressszz,,..rc6|jjS)zRound-robin slave balancer)ror>rGs rr>z$SentinelConnectionPool.rotate_slavesszz''))r) rrr__doc__r r/rYpropertyr[rxr=r>rNrOs@rrjrjs:1* ))</*rrjcXeZdZdZ d dZdZdZdZdZdZ d Z e e fd Z e e fd Zy) Sentinelar Redis Sentinel cluster client >>> from redis.sentinel import Sentinel >>> sentinel = Sentinel([('localhost', 26379)], socket_timeout=0.1) >>> master = sentinel.master_for('mymaster', socket_timeout=0.1) >>> master.set('foo', 'bar') >>> slave = sentinel.slave_for('mymaster', socket_timeout=0.1) >>> slave.get('foo') b'bar' ``sentinels`` is a list of sentinel nodes. Each node is represented by a pair (hostname, port). ``min_other_sentinels`` defined a minimum number of peers for a sentinel. When querying a sentinel, if it doesn't meet this threshold, responses from that sentinel won't be considered valid. ``sentinel_kwargs`` is a dictionary of connection arguments used when connecting to sentinel instances. Any argument that can be passed to a normal Redis connection can be specified here. If ``sentinel_kwargs`` is not specified, any socket_timeout and socket_keepalive options specified in ``connection_kwargs`` will be used. ``connection_kwargs`` are keyword arguments that will be used when establishing a connection to a Redis server. Nc |5|jDcic]\}}|jds||}}}||_|Dcgc]\}}t||fi|jc}}|_||_||_ycc}}wcc}}w)Nsocket_)items startswithsentinel_kwargsr sentinelsmin_other_sentinelsrp) r!rrrrpkvhostnamer+s rr zSentinel.__init__s  "!2!8!8!:Aall9>U1O /#, $ (D 9D$8$8 9 $7 !2  sA=A=!Bc*t|jdd}d|jvr|jd|r0t j |j j|i|y|j D]}|j|i|y)z Execute Sentinel command in sentinel nodes. once - If set to True, then execute the resulting command on a single node at random, rather than across the entire sentinel cluster. onceFT)rMrnkeysrrcchoicerexecute_command)r!argsr"rsentinels rrzSentinel.execute_commands FJJvu-. V[[] " JJv   9FMM$.. ) 9 94 J6 J!NN((($9&9+rcg}|jD]6}|jdj|jj8dt |j dt |jddj|dS)Nz {host}:{port}r%r&z (sentinels=[,z])>) rappend format_maprrpr(rrjoin)r!sentinel_addressesrs rr/zSentinel.__repr__sH  % %**8+C+C+U+UV ' T %%&aT (;(;'<388$678 = rcJ|dr |ds|dry|d|jkryy)Nr<is_sdownis_odownFznum-other-sentinelsT)r)r!stater)s rcheck_master_statezSentinel.check_master_states5[!U:%6% :K & '$*B*B Brct}t|jD]t\}} |j}|j|}|s+|j||s>||jdc|jd<|j|<|d|dfcSd}t|dkDrddj|}td ||#tt f$r }|j |d|Yd}~d}~wwxYw) z Asks sentinel servers for the Redis master's address corresponding to the service labeled ``service_name``. Returns a pair (address, port) or raises MasterNotFoundError if no master is found. z - Nripr+z : z, zNo master found for ) list enumeratersentinel_mastersr r rrnrrerr) r!r)collected_errors sentinel_normasterser error_infos rr_zSentinel.discover_masters 6%.t~~%> !K "335KK -E00 ENN1%?q!4>>+#>T{E&M11&?  1 $tyy)9:; sC  C:C55C:c`g}|D]&}|ds|dr|j|d|df(|S)z1Remove slaves that are in an ODOWN or SDOWN staterrrr+)r)r!rg slaves_aliver?s r filter_slaveszSentinel.filter_slaves8sF EZ E*$5   teFm < =rc|jD]+} |j|}|j |}|s)|cSgS#tttf$rYFwxYw)z;Returns a list of alive slaves for service ``service_name``)rsentinel_slavesr r r r)r!r)rrgs rrbzSentinel.discover_slavesAsaH !11,?''/F ' $]LA  s=AAc d|d<t|j}|j||j|||fi|S)a Returns a redis client instance for the ``service_name`` master. A :py:class:`~redis.sentinel.SentinelConnectionPool` class is used to retrieve the master's address before establishing a new connection. NOTE: If the master's address has changed, any cached connections to the old master are closed. By default clients will be a :py:class:`~redis.Redis` instance. Specify a different class to the ``redis_class`` argument if you desire something different. The ``connection_pool_class`` specifies the connection pool to use. The :py:class:`~redis.sentinel.SentinelConnectionPool` will be used by default. All other keyword arguments are merged with any connection_kwargs passed to this class and passed to the connection pool as keyword arguments to be used to initialize Redis connections. Tr<dictrpupdate from_poolr!r) redis_classconnection_pool_classr"rps r master_forzSentinel.master_forMsP:#{ !7!78  ($$ !, J8I J  rc d|d<t|j}|j||j|||fi|S)a Returns redis client instance for the ``service_name`` slave(s). A SentinelConnectionPool class is used to retrieve the slave's address before establishing a new connection. By default clients will be a :py:class:`~redis.Redis` instance. Specify a different class to the ``redis_class`` argument if you desire something different. The ``connection_pool_class`` specifies the connection pool to use. The SentinelConnectionPool will be used by default. All other keyword arguments are merged with any connection_kwargs passed to this class and passed to the connection pool as keyword arguments to be used to initialize Redis connections. Fr<rrs r slave_forzSentinel.slave_forqsP0${ !7!78  ($$ !, J8I J  r)rN)rrrr~r rr/rr_rrbrrjrrrrrrrsN> 3,"  W: 4 " N4  rr)rcrUtypingr redis.clientrredis.commandsrredis.connectionrrrredis.exceptionsr r r r redis.utilsr rrrrQrSrjrrrrrs +FFXX$ /   > >B #