
    _dR                         d Z ddlZddlZddlmZ ddlmZ ddlmZm	Z	m
Z
mZmZmZmZmZmZ ddlmZmZ ddlmZmZmZmZ  G d	 d
e      Z G d de      Z G d de      Z G d de      Z G d de      Zy)z/A base class for objects that are configurable.    N)deepcopy)dedent)	Any	ContainerDict	HasTraitsInstancedefaultobserveobserve_compatvalidate)indentwrap_paragraphs   )ConfigDeferredConfigLazyConfigValue_is_section_keyc                       e Zd Zy)ConfigurableErrorN__name__
__module____qualname__     ?/usr/lib/python3/dist-packages/traitlets/config/configurable.pyr   r           r   r   c                       e Zd Zy)MultipleInstanceErrorNr   r   r   r   r    r    $   r   r   r    c                        e Zd Z eedi       Z edd      Z fdZed        Z	d Z
ddZ ed	      ed
               Zd Zedd       Zedd       Zedd       Zed        Zedd       Zed        Z xZS )Configurabler   z*traitlets.config.configurable.ConfigurableT)
allow_nonec                    j                  dd      }|(j                  dd      |j                  d<   || _        j                  dd      }t	        |   di  t               fd}| j                  |       ||| _        n| j                  | j                         | j                  |       D ]  }t        | ||           y)a  Create a configurable given a config config.

        Parameters
        ----------
        config : Config
            If this is empty, default values are used. If config is a
            :class:`Config` instance, it will be used to configure the
            instance.
        parent : Configurable instance, optional
            The parent Configurable instance of this object.

        Notes
        -----
        Subclasses of Configurable must call the :meth:`__init__` method of
        :class:`Configurable` *before* doing anything else and using
        :func:`super`::

            class MyConfigurable(Configurable):
                def __init__(self, config=None):
                    super(MyConfigurable, self).__init__(config=config)
                    # Then any other code you need to finish initialization.

        This ensures that instances will be configured properly.
        parentNconfigc                 Z    | j                   v rj                  | j                          yy)zRecord traits set by both config and kwargs.

            They will need to be overridden again after loading config.
            N)nameadd)changeconfig_override_nameskwargss    r   notice_config_overridez5Configurable.__init__.<locals>.notice_config_overrideZ   s(    
 {{f$%))&++6 %r   r   )popgetr&   r%   super__init__setr   _load_config	unobservesetattr)selfr,   r%   r&   r-   r(   r+   	__class__s    `    @r   r1   zConfigurable.__init__2   s    2 Hd+zz(D)1#)==x  DKHd+ 	"6" !$	7 	+,  !DK dkk*-.) 	.DD$t-	.r   c                     t        | j                        D cg c]*  }t        |t              rt        | |      r|j                  , c}S c c}w )zreturn section names as a list)reversed__mro__
issubclassr"   r   )clscs     r   section_nameszConfigurable.section_namesz   sD    
 ckk*
!\*z#q/A JJ
 	
 
s   /A
c                    |g}| j                   r*|j                  | j                   j                  |             t               }|D ]=  }| j	                         D ](  }|j                  |      s|j                  ||          * ? |S )a  extract my config from a global Config object

        will construct a Config object of only the config values that apply to me
        based on my mro(), as well as those of my parent(s) if they exist.

        If I am Bar and my parent is Foo, and their parent is Tim,
        this will return merge following config sections, in this order::

            [Bar, Foo.Bar, Tim.Foo.Bar]

        With the last item being the highest priority.
        )r%   append_find_my_configr   r>   _has_sectionmerge)r6   cfgcfgs	my_configr=   snames         r   rA   zConfigurable._find_my_config   s     u;;KK33C89H	 	.A++- . >>%(OOAeH-	.	. r   c           
         || j                  d      }|| j                         }| j                  |      }| j                         5  |j	                         D ]N  \  }}||v rit        |t              rt        | |      }|j                  |      }n$t        |t              r|j                  ||         }t        | |t        |             tt        |      rt        |t              rddlm} t        | t               r| j"                  j$                  }	nd }	 |||      }
dj'                  || j(                  j*                        }t-        |
      d	k(  r|d
|
d    dz  }n;t-        |
      d	k\  r-|dj'                  dj/                  t1        |
                  z  } |	|       Q 	 ddd       y# 1 sw Y   yxY w)z load traits from a Config objectNTr&   r   )get_close_matchesc                 0    t        j                  | d      S )N	   )
stacklevel)warningswarn)msgs    r   <lambda>z+Configurable._load_config.<locals>.<lambda>   s    8==+K r   z5Config option `{option}` not recognized by `{klass}`.)optionklassr   z  Did you mean `z`?z#  Did you mean one of: `{matches}`?, )matches)traitsr>   rA   hold_trait_notificationsitems
isinstancer   getattr	get_valuer   r5   r   r   r   difflibrJ   LoggingConfigurablelogwarningformatr7   r   lenjoinsorted)r6   rD   r>   rV   rF   r(   config_valueinitialrJ   rO   rU   rP   s               r   r3   zConfigurable._load_config   s    >[[[-F  ..0M((-	 **, !	&/oo&7  "l6>!,@ #*$"5'3'='=g'F#L.A'3'='=fTl'K D$(>?(.z,PV7W9!$(;<#xx//K/f=GQXX#4>>+B+B Y C 7|q(!1'!*R@@W*DKK$(IIfWo$>  L    IA !	 !	 !	s   BF5F5*CF55F>r&   c                     | j                  d      }| j                         }| j                  |j                  ||       y)zUpdate all the class traits having ``config=True`` in metadata.

        For any class trait with a ``config`` metadata attribute that is
        ``True``, we update the trait with the value of the corresponding
        config entry.
        TrI   )rV   r>   N)rV   r>   r3   new)r6   r*   rV   r>   s       r   _config_changedzConfigurable._config_changed   s=     D)
 **,&**V=Qr   c                     t        | j                        | _        | j                  |       | j                  j                  |       y)z%Update config and load the new valuesN)r   r&   r3   rC   )r6   r&   s     r   update_configzConfigurable.update_config   s4     t{{+&!&!r   c                    |t        ||       sJ g }dj                  d | j                  D              }|j                  | j                   d| d       |j                  t        |d         dz         t        | j                  d      j                               D ](  \  }}| j                  ||      }|j                  |       * d	j                  |      S )
zGet the help string for this class in ReST format.

        If `inst` is given, its current trait values will be used in place of
        class defaults.
        rT   c              3   4   K   | ]  }|j                     y wN)r   .0ps     r   	<genexpr>z.Configurable.class_get_help.<locals>.<genexpr>   s      C Cs   (z	) optionsr   -TrI   
)
rY   rb   	__bases__r@   r   ra   rc   class_traitsrX   class_get_trait_help)r<   inst
final_helpbase_classes_vhelps          r   class_get_helpzConfigurable.class_get_help   s     |z$444
yy CS]] CCS\\N!L>CD#jm,s233++4+8>>@A 	$DAq++At4Dd#	$ yy$$r   c           	         |t        ||       sJ g }d| j                   d|j                   }t        |t        t        f      rm|j
                  j                  dd      }t        |t              rd}n'd|j                  j                  j                         z  }|dk(  r	| d| d	}n%| d
| d	}n| d|j                  j                   d}|j                  |       ||j                  }|dk7  r5dj                  t        |d            }|j                  t        |             d|j                  j                  v r+|j                  t        d|j                         z               |2|j                  t        dt        ||j                                     nF	 |j!                         }|3t%        |      dkD  r|dd d	z   }|j                  t        d|z               dj                  |      S # t"        $ r d}Y Sw xY w)a  Get the helptext string for a single trait.

        :param inst:
            If given, its current trait values will be used in place of
            the class default.
        :param helptext:
            If not given, uses the `help` attribute of the current trait.
        Nz--.multiplicityr@   z<key-1>=<value-1>z<%s-item-1>=... z=<> rt   L   EnumzChoices: %sz	Current: @   =   zDefault: %s)rY   r   r(   r   r   metadatar/   r7   lowerr@   r}   rb   r   r   inforZ   default_value_repr	Exceptionra   )	r<   traitrx   helptextlinesheaderr   sample_valuedvrs	            r   rw   z!Configurable.class_get_trait_help   s    |z$444cll^1UZZL1ei./ >>--nhGL%&2,u/G/G/M/M/OOx'"81\N#6"81\N#6xr%//":":!;1=FVzzHr>yy2!>?HLL)*U__---LL

 <=>LL)GD%**,E+H IJK..0 s8b=cr(U*CVMC$789yy  s   G5 5HHc                 8    t        | j                  |             y)z4Get the help string for a single trait and print it.N)printr~   )r<   rx   s     r   class_print_helpzConfigurable.class_print_help1  s     	c  &'r   c                     | }| j                         D ]I  }t        |t              s||v s|j                  d      j	                  |j
                  d      |u sH|}K |S )a7  Get the class that defines a trait

        For reducing redundant help output in config files.
        Returns the current class if:
        - the trait is defined on this class, or
        - the class where it is defined would not be in the config file

        Parameters
        ----------
        trait : Trait
            The trait to look for
        classes : list
            The list of other classes to consider for redundancy.
            Will return `cls` even if it is not defined on `cls`
            if the defining class is not in `classes`.
        TrI   N)mror;   r"   class_own_traitsr/   r(   )r<   r   classesdefining_clsr%   s        r   _defining_classzConfigurable._defining_class6  se    $ ggi 	&F6<0g%++4+8<<UZZNRWW%	& r   c           	      L   d }d}dj                  d | j                  D              }d| j                   d| d}|||g}| j                         j	                  d      }|r|j
                  }|st        | d	d
      }|r(|j                   ||             |j                  d
       t        | j                  d      j                               D ]B  \  }}	|	j                         }
|r| j                  |	|      }n| }|| u r{|	j                  r!|j                   ||	j                               dt        |	      j                  v r"|j                  d|	j                         z         |j                  d|
z         na|	j                  r4|j                   ||	j                  j                  dd      d                |j                  d|j                   d|        |j                  d| j                   d| d|
        |j                  d
       E dj                  |      S )zGet the config section for this class.

        Parameters
        ----------
        classes : list, optional
            The list of other classes in the config file.
            Used to reduce redundant information.
        c                 b    dj                  t        | d            } d| j                  dd      z   S )z"return a commented, wrapped block.z

N   z## rt   z
#  )rb   r   replace)ss    r   r=   z,Configurable.class_config_section.<locals>.c]  s-    OAr23A199T7333r   zO#------------------------------------------------------------------------------rT   c              3   V   K   | ]!  }t        |t              s|j                   # y wrm   )r;   r"   r   rn   s     r   rq   z4Configurable.class_config_section.<locals>.<genexpr>e  s     "d!
STVbHc1::"ds   ))z# rr   z) configurationdescription__doc__r   TrI   r   z#  Choices: %sz#  Default: %srt   r   r   z#  See also: r   z# c.z = )rb   ru   r   rv   r/   default_valuerZ   r@   rc   rX   r   r   r}   typer   split)r<   r   r=   breakerparent_classesr   r   descr(   r   default_reprdefining_classs               r   class_config_sectionz!Configurable.class_config_sectionR  s   	4 !"ds}}"dda/?!W%!%%m4%%D3	2.DLL4!LL!#"2"2$"2"?"E"E"GH 	KD% 335L!$!4!4UG!D!$$::LL5::/T%[111LL!1EJJL!@A-<= ::LL5::#3#3D!#<Q#?!@A}^-D-D,EQtfMNLL4~QtfC~FGLL/	0 yyr   c                    g }| j                   }t        | j                  d      j                               D ]  \  }}|j                  j                   }|dz   |j
                  z   }d|v r|d|j                         z   z  }n|d|z   z  }|j                  |       	 |j                         }|Vt        |      dkD  r|dd d	z   }|j                  d
d      }|j                  t        d|z               |j                  d       |j                  xs d}|j                  t        t        |                   |j                  d        dj                  |      S # t        $ r d}Y w xY w)zwGenerate rST documentation for this class' config options.

        Excludes traits defined on parent classes.
        TrI   r   r   z : Nr   r   r   z\nz\\nzDefault: ``%s``r   zNo descriptionrt   )r   rc   rv   rX   r7   r(   info_rstr@   r   r   ra   r   r   r}   r   rb   )	r<   r   	classnamer{   r   ttypetermliner   r}   s	            r   class_config_rst_docz!Configurable.class_config_rst_doc  s]    LL	s//t/<BBDE 	HAuOO,,E 33H EENN$444EEM)LL"..0 s8b=cr(U*Ckk%1V$5$;<=R ::1!1DLLt-. LL=	@ yy!  s   EE*)E*)NNrm   )r   r   r   r	   r   r&   r%   r1   classmethodr>   rA   r3   r   r   rh   rj   r~   rw   r   r   r   r   __classcell__)r7   s   @r   r"   r"   -   s    fb"%FBtTFB.P 
 
2,\ XR  R "  % %  1  1 f ( (  6 9  9 v '  ' r   r"   c                   `    e Zd ZdZ ed      Z ed      d        Z ed      d        Z	d Z
y)	r]   zA parent class for Configurables that log.

    Subclasses have a log trait, and the default behavior
    is to get the logger from the currently running Application.
    z Logger or LoggerAdapter instance)r}   r^   c                     t        |j                  t        j                  t        j                  f      s9t        j                  | j                  j                   d|j                   d       |j                  S )Nz..log should be a Logger or LoggerAdapter, got r   )	rY   valueloggingLoggerLoggerAdapterrN   rO   r7   r   )r6   proposals     r   _validate_logz!LoggingConfigurable._validate_log  s]    (..7>>7;P;P*QRMM>>**+ , 'q* ~~r   c                     t        | j                  t              r| j                  j                  S ddlm} |j                         S )Nr   )r^   )rY   r%   r]   r^   	traitlets
get_logger)r6   r^   s     r   _log_defaultz LoggingConfigurable._log_default  s/    dkk#67;;??"!~~r   c                     | j                   }t        |t        j                        r|j                  }t        |dd      sy|j                  d   S )zReturn the default Handler

        Returns None if none can be found

        Deprecated, this now returns the first log handler which may or may
        not be the default one.
        handlersNr   )r^   rY   r   r   loggerrZ   r   )r6   r   s     r   _get_log_handlerz$LoggingConfigurable._get_log_handler  sD     fg334]]Fvz40q!!r   N)r   r   r   r   r   r^   r   r   r
   r   r   r   r   r   r]   r]     sG     5
6Ce_  U^   "r   r]   c                   T    e Zd ZdZdZed        Zed        Zed        Zed        Z	y)SingletonConfigurablezA configurable that only allows one instance.

    This class is for classes that should only have one instance of itself
    or *any* subclass. To create and retrieve such a class use the
    :meth:`SingletonConfigurable.instance` method.
    Nc              #      K   | j                         D ].  }t        | |      st        |t              s!|t        k7  s+| 0 yw)zfWalk the cls.mro() for parent classes that are also singletons

        For use in instance()
        N)r   r;   r   r<   subclasss     r   	_walk_mrozSingletonConfigurable._walk_mro  s@      	 	H3)x)>? 55	s    AA	AAc                     | j                         sy| j                         D ]   }t        |j                  |       sd|_        " y)z5unset _instance for this class and singleton parents.N)initializedr   rY   	_instancer   s     r   clear_instancez$SingletonConfigurable.clear_instance  s@       	*H(,,c2 &*"		*r   c                    | j                   $ | |i |}| j                         D ]	  }||_          t        | j                   |       r| j                   S t        d| j                  dt        | j                         j                        )a  Returns a global instance of this class.

        This method create a new instance if none have previously been created
        and returns a previously created instance is one already exists.

        The arguments and keyword arguments passed to this method are passed
        on to the :meth:`__init__` method of the class upon instantiation.

        Examples
        --------
        Create a singleton class using instance, and retrieve it::

            >>> from traitlets.config.configurable import SingletonConfigurable
            >>> class Foo(SingletonConfigurable): pass
            >>> foo = Foo.instance()
            >>> foo == Foo.instance()
            True

        Create a subclass that is retrived using the base class instance::

            >>> class Bar(SingletonConfigurable): pass
            >>> class Bam(Bar): pass
            >>> bam = Bam.instance()
            >>> bam == Bar.instance()
            True
        zAn incompatible sibling of 'z(' is already instanciated as singleton: )r   r   rY   r    r   r   )r<   argsr,   rx   r   s        r   instancezSingletonConfigurable.instance	  s    : == ''D  MMO *%)"* cmmS)== ''*||T#--5H5Q5QS r   c                 :    t        | d      xr | j                  duS )zHas an instance been created?r   N)hasattrr   )r<   s    r   r   z!SingletonConfigurable.initialized5  s     sK(FS]]$-FFr   )
r   r   r   r   r   r   r   r   r   r   r   r   r   r   r     s_     I  * * ) )V G Gr   r   )r   r   rN   copyr   textwrapr   traitlets.traitletsr   r   r   r   r	   r
   r   r   r   traitlets.utils.textr   r   loaderr   r   r   r   r   r   r    r"   r]   r   r   r   r   <module>r      sv    5    
 
 
 9 L L		 		- 	I 9 I X)", )"XSG/ SGr   