
    Ii}                         S SK r S SKJr  S SKJr  S SKJr  S SKrS SKJr  SSK	J
r
Jr  SSKJrJr  SS	KJr  SS
KJr  SSKJr  SSKJrJrJrJr  SSKJr  SSKJrJrJr   " S S\ 5      r!g)    N)deque)contextmanager)time)urlparse   )errorsdefines)ColumnOrientedBlockRowOrientedBlock)
Connection)	log_block)ServerPacketTypes)IterQueryResultProgressQueryResultQueryResult	QueryInfo)escape_params)column_chunkschunks	parse_urlc                   f  ^  \ rS rSrSrSrU 4S jrS rS rS r	S r
S	 rS
 r  S%S jrS&S jrS rS rS rS rS r\S 5       r   S'S jr   S'S jr   S(S jr  S)S jr  S*S jr   S+S jr   S+S jr   S,S jr  S-S jrS rS.S jr S r!S r"S  r#S&S! jr$S" r%\&S# 5       r'S$r(U =r)$ )/Client   a
  
Client for communication with the ClickHouse server.
Single connection is established per each connected instance of the client.

:param settings: Dictionary of settings that passed to every query (except
                 for the client settings, see below). Defaults to ``None``
                 (no additional settings). See all available settings in
                 `ClickHouse docs
                 <https://clickhouse.com/docs/en/operations/settings/settings/>`_.
:param \**kwargs: All other args are passed to the
                   :py:class:`~clickhouse_driver.connection.Connection`
                   constructor.

The following keys when passed in ``settings`` are used for configuring the
client itself:

    * ``insert_block_size`` -- chunk size to split rows for ``INSERT``.
      Defaults to ``1048576``.
    * ``strings_as_bytes`` -- turns off string column encoding/decoding.
    * ``strings_encoding`` -- specifies string encoding. UTF-8 by default.
    * ``use_numpy`` -- Use NumPy for columns reading. New in version
                       *0.2.0*.
    * ``opentelemetry_traceparent`` -- OpenTelemetry traceparent header as
                       described by W3C Trace Context recommendation.
                       New in version *0.2.2*.
    * ``opentelemetry_tracestate`` -- OpenTelemetry tracestate header as
                       described by W3C Trace Context recommendation.
                       New in version *0.2.2*.
    * ``quota_key`` -- A string to differentiate quotas when the user have
                       keyed quotas configured on server.
                       New in version *0.2.3*.
    * ``input_format_null_as_default`` -- Initialize null fields with
                       default values if data type of this field is not
                       nullable. Does not work for NumPy. Default: False.
                       New in version *0.2.4*.
    * ``round_robin`` -- If ``alt_hosts`` are provided the query will be
                       executed on host picked with round-robin algorithm.
                       New in version *0.2.5*.
    * ``namedtuple_as_json`` -- Controls named tuple and nested types
                       deserialization. To interpret these column alongside
                       with ``allow_experimental_object_type=1`` as Python
                       tuple set ``namedtuple_as_json`` to ``False``.
                       Default: True.
                       New in version *0.2.6*.
    * ``server_side_params`` -- Species on which side query parameters
                       should be rendered into placeholders.
                       Default: False. Means that parameters are rendered
                       on driver's side.
                       New in version *0.2.7*.

insert_block_sizestrings_as_bytesstrings_encoding	use_numpyopentelemetry_traceparentopentelemetry_tracestate	quota_keyinput_format_null_as_defaultnamedtuple_as_jsonserver_side_paramsc                 l  > UR                  SS 5      =(       d    0 R                  5       U l        [        U R                  R                  S[        R
                  5      5      U R                  R                  SS5      U R                  R                  S[        R                  5      U R                  R                  SS5      U R                  R                  SS 5      U R                  R                  SS	5      U R                  R                  S
S	5      U R                  R                  SS5      U R                  R                  SS5      U R                  R                  SS5      S.
U l        U R                  S   (       a   SSKJ	nJ
nJn  XPl        X0l        X@l        O!["        U l        [$        U l        [&        U l        UR                  SS5      n[)        [+        U0 UD6/5      U l        U(       a  SU;   a  UR                  S5      nUR/                  S5       H  n[1        SU-   5      n	UR                  5       n
[3        U5      nUS:  a  U	R4                  U	R6                  4USS  -   nOQUS:  a#  U	R4                  4USS  -   nU	R6                  U
S'   O([9        5       nU	R4                  U
S'   U	R6                  U
S'   [+        U0 U
D6nU R,                  R;                  U5        M     U R=                  5       U l        U RA                  5         [B        [D        U ]  5         g ! [         a    [!        S5      ef = f)Nsettingsr   r   Fr   r   r   r     r!   r"   r#   Tr$   r   r   )NumpyIterQueryResultNumpyProgressQueryResultNumpyQueryResult"Extras for NumPy must be installedround_robin	alt_hosts,zclickhouse://   porthost)$popcopyr&   intr	   DEFAULT_INSERT_BLOCK_SIZESTRINGS_ENCODINGclient_settingsnumpy.resultr(   r)   r*   query_result_clsiter_query_result_clsprogress_query_result_clsImportErrorRuntimeErrorr   r   r   r   r   connectionssplitr   lenhostnamer0   tupleappendget_connection
connectionreset_last_querysuperr   __init__)selfargskwargsr(   r)   r*   r,   r-   r1   urlconnection_kwargsnum_argsconnection_argsrE   	__class__s                 >/venv/lib/python3.13/site-packages/clickhouse_driver/client.pyrH   Client.__init__U   s   J5;AAC "%T]]%6%6#W%F%F& " !% 1 1"E! !% 1 1"G$<$<! **U *.):):+T* )-(9(9*B) **R -1MM,=,=.- #'--"3"3$d# #'--"3"3$e#9 
B ,	I  )9%-A*1I. %0D!)8D&-@D*jj6 *d"=f"=!>?;&0

;/I!,56$*KKM!t9q='*||SXX&>ab&IO]'*||&6ab&AO03%f- ',gO03%f-03%f-'N<MN
  ''
3' -* --/fd$&G  I"#GHHIs    L L3c                     U $ N rI   s    rQ   	__enter__Client.__enter__   s        c                 $    U R                  5         g rT   )
disconnect)rI   exc_typeexc_valexc_tbs       rQ   __exit__Client.__exit__   s    rY   c                    [        U S5      (       a%  U R                  R                  U R                  5        U R                  R	                  5       nU R
                  UR                  l        U R                  UR                  l        U$ )NrE   )hasattrr>   rC   rE   popleftr&   contextr7   rI   rE   s     rQ   rD   Client.get_connection   sg    4&&##DOO4%%--/
&*mm
#-1-A-A
*rY   c                 j    U R                  5         U R                   H  nUR                  5         M     g rT   )disconnect_connectionr>   r[   re   s     rQ   r[   Client.disconnect   s*    ""$**J!!# +rY   c                 X    U R                   R                  5         U R                  5         g)z
Disconnects from the server.
N)rE   r[   rF   rV   s    rQ   rh   Client.disconnect_connection   s      	""$rY   c                     S U l         g rT   )
last_queryrV   s    rQ   rF   Client.reset_last_query   s	    rY   c                     U R                  5       nU(       a  U R                  XAUS9$ U R                  XAUS9nUR                  5       $ )Nwith_column_typescolumnar)packet_generatorr;   r9   
get_result)rI   rq   progressrr   genresults         rQ   receive_resultClient.receive_result   s_     ##%118 2  
 **8 + F $$&&rY   c              #   v   #    U R                  5       nU R                  X!S9nU H  nU H  nUv   M	     M     g 7fNrq   )rs   r:   )rI   rq   rv   rw   rowsrows         rQ   iter_receive_resultClient.iter_receive_result   sF     ##%++ , 
 D	  s   79c              #      #      U R                  5       nU(       d  g USL a  M!  Uv   M&  ! [        [        4 a    U R                  5         e f = f7f)NT)receive_packet	ExceptionKeyboardInterruptr[   rI   packets     rQ   rs   Client.packet_generator   sX     ,,.T>  01 !s+   A* A* A* A"AAc                    U R                   R                  5       nUR                  [        R                  :X  a  UR
                  eUR                  [        R                  :X  a'  U R                  R                  UR                  5        U$ UR                  [        R                  :X  a  gUR                  [        R                  :X  a  U$ UR                  [        R                  :X  a  U$ UR                  [        R                  :X  a  U$ UR                  [        R                  :X  a&  U R                  R                  UR                   5        gg)NFT)rE   r   typer   	EXCEPTION	exceptionPROGRESSrm   store_progressru   END_OF_STREAMDATATOTALSEXTREMESPROFILE_INFOstore_profileprofile_infor   s     rQ   r   Client.receive_packet   s    //1;;+555"""[[-666OO**6??;M[[-;;;[[-222M[[-444M[[-666M[[-:::OO))&*=*=> rY   c                 x   [        U=(       d    0 5      nU R                  R                  5       nU R                   H  nX1;   d  M
  UR	                  U5      X#'   M     X R
                  R                  l        U R                  R                  5       nUR                  U5        X@R
                  R                  l        g rT   )	dictr7   r3   available_client_settingsr2   rE   rd   r&   update)rI   r&   r7   keyquery_settingss        rQ   make_query_settingsClient.make_query_settings  s    B' ..33511C'/||C'8$ 2 3B/ ++-h'+9(rY   c                     UR                  S5      nUR                  5       R                  S5      (       a#  USS  R                  5       U R                  l        g g )Nz; zuse    )striplower
startswithrE   database)rI   querys     rQ   track_current_databaseClient.track_current_database  sE    D!;;=##F++',QRy'8DOO$ ,rY   c                    [        U R                  5      n[        U S5      (       a  US-  n[        U5       HS  n U R	                  5       U l        U R                  U5        U R
                  R                  5         [        5       U l	          g    g ! [        R                  [        R                  4 a    X2S-
  :  a   M  e f = f)NrE   r   )r@   r>   rb   rangerD   rE   r   force_connectr   rm   r   SocketTimeoutErrorNetworkError)rI   r&   num_connectionsis       rQ   establish_connectionClient.establish_connection#  s    d../4&&q O'A	"&"5"5"7((2--/"++  ( --v/B/BC **s   AB,C >C c              #      #     U R                  U5        S U R                  R                  l        S v   U R	                  U5        g ! [
        [        4 a    U R                  5         e f = f7frT   )r   rE   server_infosession_timezoner   r   r   r[   )rI   r   r&   s      rQ   disconnect_on_errorClient.disconnect_on_error6  s\     
	%%h/;?DOO''8''.,- 	OO	s   A+AA A+"A((A+c	                 b   [        5       n	U R                  X5         [        U[        [        [
        R                  45      n
U
(       a  U R                  XUXWUS9nOU R                  XUUXWUS9nU R                  R                  [        5       U	-
  5        UsSSS5        $ ! , (       d  f       g= f)az  
Executes query.

Establishes new connection if it wasn't established yet.
After query execution connection remains intact for next queries.
If connection can't be reused it will be closed and new connection will
be created.

:param query: query that will be send to server.
:param params: substitution parameters for SELECT queries and data for
               INSERT queries. Data for INSERT can be `list`, `tuple`
               or :data:`~types.GeneratorType`.
               Defaults to ``None`` (no parameters  or data).
:param with_column_types: if specified column names and types will be
                          returned alongside with result.
                          Defaults to ``False``.
:param external_tables: external tables to send.
                        Defaults to ``None`` (no external tables).
:param query_id: the query identifier. If no query id specified
                 ClickHouse server will generate it.
:param settings: dictionary of query settings.
                 Defaults to ``None`` (no additional settings).
:param types_check: enables type checking of data for INSERT queries.
                    Causes additional overhead. Defaults to ``False``.
:param columnar: if specified the result of the SELECT query will be
                 returned in column-oriented form.
                 It also allows to INSERT data in columnar form.
                 Defaults to ``False`` (row-like form).

:return: * number of inserted rows for INSERT queries with data.
           Returning rows count from INSERT FROM SELECT is not
           supported.
         * if `with_column_types=False`: `list` of `tuples` with
           rows/columns.
         * if `with_column_types=True`: `tuple` of 2 elements:
            * The first element is `list` of `tuples` with
              rows/columns.
            * The second element information is about columns: names
              and types.
)external_tablesquery_idtypes_checkrr   paramsrq   r   r   r   rr   N)r   r   
isinstancelistrB   typesGeneratorTypeprocess_insert_queryprocess_ordinary_queryrm   store_elapsed)rI   r   r   rq   r   r   r&   r   rr   
start_time	is_insertrvs               rQ   executeClient.executeD  s    X V
%%e6 #6D%9L9L+MNI..?%% /  00<M$3%%	 1  OO))$&:*=>' 766s   A:B  
B.c	                 ~    U R                  X5         U R                  XUXEXxS9sSSS5        $ ! , (       d  f       g= f)a  
Executes SELECT query with progress information.
See, :ref:`execute-with-progress`.

:param query: query that will be send to server.
:param params: substitution parameters for SELECT queries and data for
               INSERT queries. Data for INSERT can be `list`, `tuple`
               or :data:`~types.GeneratorType`.
               Defaults to ``None`` (no parameters  or data).
:param with_column_types: if specified column names and types will be
                          returned alongside with result.
                          Defaults to ``False``.
:param external_tables: external tables to send.
                        Defaults to ``None`` (no external tables).
:param query_id: the query identifier. If no query id specified
                 ClickHouse server will generate it.
:param settings: dictionary of query settings.
                 Defaults to ``None`` (no additional settings).
:param types_check: enables type checking of data for INSERT queries.
                    Causes additional overhead. Defaults to ``False``.
:param columnar: if specified the result will be returned in
                 column-oriented form.
                 Defaults to ``False`` (row-like form).
:return: :ref:`progress-query-result` proxy.
r   N)r   $process_ordinary_query_with_progress)	rI   r   r   rq   r   r   r&   r   rr   s	            rQ   execute_with_progressClient.execute_with_progress  s=    < %%e6<<8I /' =  766s   .
<c	           
          U R                  X5         U R                  XUUXWS9n	US:  a  [        X5      OU	sSSS5        $ ! , (       d  f       g= f)aw  
*New in version 0.0.14.*

Executes SELECT query with results streaming. See, :ref:`execute-iter`.

:param query: query that will be send to server.
:param params: substitution parameters for SELECT queries and data for
               INSERT queries. Data for INSERT can be `list`, `tuple`
               or :data:`~types.GeneratorType`.
               Defaults to ``None`` (no parameters  or data).
:param with_column_types: if specified column names and types will be
                          returned alongside with result.
                          Defaults to ``False``.
:param external_tables: external tables to send.
                        Defaults to ``None`` (no external tables).
:param query_id: the query identifier. If no query id specified
                 ClickHouse server will generate it.
:param settings: dictionary of query settings.
                 Defaults to ``None`` (no additional settings).
:param types_check: enables type checking of data for INSERT queries.
                    Causes additional overhead. Defaults to ``False``.
:param chunk_size: chunk query results.
:return: :ref:`iter-query-result` proxy.
)r   rq   r   r   r   r   N)r   iter_process_ordinary_queryr   )
rI   r   r   rq   r   r   r&   r   
chunk_sizer   s
             rQ   execute_iterClient.execute_iter  sQ    8 %%e6118I /! 2 B
 .8!^6") 766s   %A
Ac           
      r    SSK nU R                  USSUX4US9u  pU	 V
Vs/ s H  u  pU
PM	     n	n
nU(       a(  U	 Vs/ s H  n[        R
                  " SSU5      PM     n	nUR                  [        X5       VVs0 s H  u  pX_M	     snnU	S9$ ! [         a    [        S5      ef = fs  snn
f s  snf s  snnf )	a  
*New in version 0.2.0.*

Queries DataFrame with specified SELECT query.

:param query: query that will be send to server.
:param params: substitution parameters.
               Defaults to ``None`` (no parameters  or data).
:param external_tables: external tables to send.
                        Defaults to ``None`` (no external tables).
:param query_id: the query identifier. If no query id specified
                 ClickHouse server will generate it.
:param settings: dictionary of query settings.
                 Defaults to ``None`` (no additional settings).
:param replace_nonwords: boolean to replace non-words in column names
                         to underscores. Defaults to ``True``.
:return: pandas DataFrame.
r   Nr+   T)rr   rq   r   r   r   r&   z\W_)columns)pandasr<   r=   r   resub	DataFramezip)rI   r   r   r   r   r&   replace_nonwordspddatar   nametype_xdcols                  rQ   query_dataframeClient.query_dataframe  s    ,	E DD+ % 
 ,337KD4736=>grvveS!,gG>||"%d"45"4SV"45w  
 	
  	ECDD	E 4> 6s   B B("B.:B3
B%c                     SSK n[        5       nU R	                  X5         U R
                  R                  XS9  U R
                  R                  U5        U R                  5       nSn	U(       a  UR                   V
s/ s H  oS   PM	     nn
[        U5      [        UR                  5      -
  n[        U5      (       a%  Sn[        UR                  [        U5      5      5      eU Vs/ s H  oU   R                   PM     nnU R#                  XSS9n	U R%                  5         U R&                  R)                  [        5       U-
  5        U	sSSS5        $ ! [         a    [        S5      ef = fs  sn
f s  snf ! , (       d  f       g= f)a  
*New in version 0.2.0.*

Inserts pandas DataFrame with specified query.

:param query: query that will be send to server.
:param dataframe: pandas DataFrame.
:param external_tables: external tables to send.
                        Defaults to ``None`` (no external tables).
:param query_id: the query identifier. If no query id specified
                 ClickHouse server will generate it.
:param settings: dictionary of query settings.
                 Defaults to ``None`` (no additional settings).
:return: number of inserted rows.
r   Nr+   r   z&DataFrame missing required columns: {}T)rr   )r   r<   r=   r   r   rE   
send_querysend_external_tablesreceive_sample_blockcolumns_with_typessetr   r@   
ValueErrorformatr   values	send_datareceive_end_of_queryrm   r   )rI   r   	dataframer   r   r&   r   r   sample_blockr   r   r   diffmsgcolumnr   s                   rQ   insert_dataframeClient.insert_dataframe  sN   &	E V
%%e6OO&&u&@OO00A446LB)5)H)HI)HAQ4)HI7|c)*;*;&<<t99BC$SZZT
%;<<?FGwV&)00wG^^L^F))+OO))$&:*=>' 76  	ECDD	E J H 76s7   E AE5=E+AE5'E0?A	E5E(+
E55
Fc                     Ub&  U R                  XU R                  R                  5      nU R                  R                  XUS9  U R                  R	                  UUS9  U R                  USUS9$ )Nr   r   r   T)rq   ru   rr   substitute_paramsrE   rd   r   r   rx   rI   r   r   rq   r   r   r   rr   s           rQ   r   +Client.process_ordinary_query_with_progress(  s    
 **t66E 	""5F"K,,_9D 	- 	F""5F,08 # E 	ErY   c                     Ub&  U R                  XU R                  R                  5      nU R                  R                  XUS9  U R                  R	                  UUS9  U R                  UUS9$ )Nr   r   rp   r   r   s           rQ   r   Client.process_ordinary_query8  s}    
 **t66E 	""5F"K,,_9D 	- 	F""5F,4 # 6 	6rY   c                     Ub&  U R                  XU R                  R                  5      nU R                  R                  XUS9  U R                  R	                  UUS9  U R                  US9$ )Nr   r   r|   )r   rE   rd   r   r   r   )rI   r   r   rq   r   r   r   s          rQ   r   "Client.iter_process_ordinary_queryG  st    
 **t66E 	""5F"K,,_9D 	- 	F'':K'LLrY   c                     U R                   R                  XS9  U R                   R                  UUS9  U R                  5       nU(       a"  U R	                  XrXVS9nU R                  5         U$ g )Nr   r   )r   rr   )rE   r   r   r   r   receive_end_of_insert_query)	rI   query_without_datar   r   r   r   rr   r   r   s	            rQ   r   Client.process_insert_queryV  sw     	""#5"I,,_9D 	- 	F002,7   LB,,.I	 rY   c                     U R                   R                  5       nUR                  [        R                  :X  a  UR
                  $ UR                  [        R                  :X  a  UR                  eUR                  [        R                  :X  a  [        UR
                  5        O[UR                  [        R                  :X  a  O<U R                   R                  SUR                  5      n[        R                  " U5      eM  )Nz$Data, Exception, Log or TableColumns)rE   r   r   r   r   blockr   r   LOGr   TABLE_COLUMNSunexpected_packet_messager   UnexpectedPacketFromServerErrorrI   r   messages      rQ   r   Client.receive_sample_blockd  s    __335F{{/444||# 1 ; ;;&&& 1 5 55&,,' 1 ? ?? //CC:FKK <<WEE' rY   c                 .   SnU R                   R                  R                  nU(       a  [        O[        nUS   (       a   SSKJn  U(       a  Un	O[        S5      eU(       a  [        O[        n	U	" X&S   5       HN  n
U" UR                  U
US9nU R                   R                  U5        X[R                  -  nU R                  5         MP     U R                   R                  U" 5       5        U R                  5         U$ ! [         a    [        S5      ef = f)	Nr   r   r   )r   z0NumPy inserts is only allowed with columnar=Truer+   r   r   )rE   rd   r7   r
   r   numpy.helpersr   r   r<   r=   r   r   r   num_rowsreceive_profile_events)rI   r   r   r   rr   inserted_rowsr7   	block_clsnumpy_column_chunksslicerchunkr  s               rQ   r   Client.send_dataz  s    //11AA+3'9I	;'IO0F$J  '/]FFD2E"FGEl==u*57EOO%%e,^^+M '') H 	!!)+.##%+  I"#GHHIs   C> C> >Dc                     U R                   R                  5       nUR                  [        R                  :X  a  g UR                  [        R
                  :X  a&  U R                  R                  UR                  5        OUR                  [        R                  :X  a  UR                  eUR                  [        R                  :X  a  [        UR                  5        OUR                  [        R                  :X  a  OUR                  [        R                  :X  a&  U R                  R!                  UR"                  5        O<U R                   R%                  SUR                  5      n[&        R(                  " U5      eGM}  )NzDException, EndOfStream, Progress, TableColumns, ProfileEvents or Log)rE   r   r   r   r   r   rm   r   ru   r   r   r  r   r  r  PROFILE_EVENTSr   r   r  r   r	  r
  s      rQ   r   Client.receive_end_of_query  s   __335F{{/=== 1 : ::..v? 1 ; ;;&&& 1 5 55&,,' 1 ? ?? 1 @ @@--f.A.AB //CC+,2KK <<WEE5 rY   c                 8    U R                   R                  5       nUR                  [        R                  :X  a  g UR                  [        R
                  :X  a  [        UR                  5        OUR                  [        R                  :X  a&  U R                  R                  UR                  5        OfUR                  [        R                  :X  a  UR                  eU R                   R                  SUR                  5      n[        R                   " U5      eGM  )Nz'EndOfStream, Log, Progress or Exception)rE   r   r   r   r   r  r   r  r   rm   r   ru   r   r   r  r   r	  r
  s      rQ   r  "Client.receive_end_of_insert_query  s    __335F{{/=== 1 5 55&,,' 1 : ::..v? 1 ; ;;&&& //CC=v{{ <<WEE' rY   c                 *   U R                   R                  R                  nU[        R                  :  a  g  U R                   R                  5       nUR                  [        R                  :X  a&  U R                  R                  UR                  5        g UR                  [        R                  :X  a&  U R                  R                  UR                  5        OUR                  [        R                  :X  a  [!        UR"                  5        OUR                  [        R$                  :X  a  UR&                  eUR                  [        R(                  :X  a  O<U R                   R+                  SUR                  5      n[,        R.                  " U5      eGM^  )Nz9ProfileEvents, Progress, Log, Exception or TimezoneUpdate)rE   r   used_revisionr	   7DBMS_MIN_PROTOCOL_VERSION_WITH_PROFILE_EVENTS_IN_INSERTr   r   r   r  rm   r   r   r   r   ru   r  r   r  r   r   TIMEZONE_UPDATEr  r   r	  )rI   revisionr   r  s       rQ   r  Client.receive_profile_events  s(   ??..<<KKL __335F{{/>>>--f.A.AB 1 : ::..v? 1 5 55&,,' 1 ; ;;&&& 1 A AA //CC%&,kk <<WEE1 rY   c                 T    U R                   R                  5         U R                  US9$ r{   )rE   send_cancelrx   )rI   rq   s     rQ   cancelClient.cancel  s'    ##%""5F"GGrY   c                     U R                   R                  R                  S   (       a  U$ [        U[        5      (       d  [        S5      e[        X#5      nX-  $ )a?  
Substitutes parameters into a provided query.

For example::

    client = Client(...)

    substituted_query = client.substitute_params(
        query='SELECT 1234, %(foo)s',
        params={'foo': 'bar'},
        context=client.connection.context
    )

    # prints: SELECT 1234, 'bar'
    print(substituted_query)
r$   z$Parameters are expected in dict form)rE   rd   r7   r   r   r   r   )rI   r   r   rd   escapeds        rQ   r   Client.substitute_params  sM    $ ??""223GHL&$''CDD0rY   c                 .    [        U5      u  p#U " U40 UD6$ )a  
Return a client configured from the given URL.

For example::

    clickhouse://[user:password]@localhost:9000/default
    clickhouses://[user:password]@localhost:9440/default

Three URL schemes are supported:

    * clickhouse:// creates a normal TCP socket connection
    * clickhouses:// creates a SSL wrapped TCP socket connection

Any additional querystring arguments will be passed along to
the Connection class's initializer.
)r   )clsrL   r1   rK   s       rQ   from_urlClient.from_url  s    $ !~4"6""rY   )r7   rE   r>   r:   rm   r;   r9   r&   )FFF)F)NFNNNFF)NFNNNFr   )NNNNT)NNN)NFNNFF)NFNNF)NNFF)FF)*__name__
__module____qualname____firstlineno____doc__r   rH   rW   r_   rD   r[   rh   rF   rx   r   rs   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r  r  r$  r   classmethodr+  __static_attributes____classcell__)rP   s   @rQ   r   r      sK   1f!P'd$
  @E %' 	 :: 9
&   =B>B,1AH 9>:>(-#L 9>:>*+"DJ FJ,0'
T DH-` 9>+/(-E" 9>+/(-6  9>+/M  =A9>F,&PF:F, FDH6 # #rY   r   )"r   collectionsr   
contextlibr   r   r   urllib.parser   r'   r   r	   r  r
   r   rE   r   logr   protocolr   rw   r   r   r   r   util.escaper   util.helpersr   r   r   objectr   rU   rY   rQ   <module>r=     sI    	  %   !  8 "  '  ' : :X#V X#rY   