
    fd@                        d 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d	lmZ dd
lmZ  e       Z ee	       G d de             Z ee       G d de             Zd Z ee
       G d de             Z G d de      Z ee       G d de             Zdad Zd Zd Z	 ddlmZ  ee       [y# e$ r Y yw xY w)zVocabulary support for schema.
    )OrderedDict)directlyProvides)implementer)
providedBy)ITitledTokenizedTerm)ITokenizedTerm)ITreeVocabulary)IVocabularyRegistry)IVocabularyTokenizedc                   *    e Zd ZdZddZd Zd Zd Zy)
SimpleTermz
    Simple tokenized term used by SimpleVocabulary.

    .. versionchanged:: 4.6.0
       Implement equality and hashing based on the value, token and title.
    Nc                    || _         ||}t        |t              r|j                  d      }nt        |t              st	        |      }|j                  dd      j                  d      }|| _        || _        |t        | t               yy)a
  Create a term for *value* and *token*. If *token* is
        omitted, str(value) is used for the token, escaping any
        non-ASCII characters.

        If *title* is provided, term implements
        :class:`zope.schema.interfaces.ITitledTokenizedTerm`.
        Nraw_unicode_escapeasciibackslashreplace)
value
isinstancebytesdecodestrencodetokentitler   r   )selfr   r   r   s       n/var/dept/share/cheung/public_html/OutSchool/python/env/lib/python3.12/site-packages/zope/schema/vocabulary.py__init__zSimpleTerm.__init__*   s     
=E
 eU#LL!56EE3' JEW&89@@I

T#78     c                     || u ryt        |t              sy| j                  |j                  k(  xr4 | j                  |j                  k(  xr | j                  |j                  k(  S NTF)r   r   r   r   r   r   others     r   __eq__zSimpleTerm.__eq__F   sZ    D=%, JJ%++% *

ekk)*

ekk)	
r   c                 &    | j                  |       S Nr"   r    s     r   __ne__zSimpleTerm.__ne__S       ;;u%%%r   c                 Z    t        | j                  | j                  | j                  f      S r$   )hashr   r   r   r   s    r   __hash__zSimpleTerm.__hash__V   s     TZZTZZ899r   )NN)__name__
__module____qualname____doc__r   r"   r&   r+    r   r   r   r   !   s    98
&:r   r   c                   v    e Zd ZdZd Zed        Zed        Zed        Zd Z	d Z
d Zd	 Zd
 Zd Zd Zd Zy)SimpleVocabularyz
    Vocabulary that works from a sequence of terms.

    .. versionchanged:: 4.6.0
       Implement equality and hashing based on the terms list
       and interfaces implemented by this object.
    c                    i | _         i | _        || _        |j                  dd      }| j                  D ]  }|sr|j                  | j                   v r!t        dt        |j                        z        |j                  | j                  v r!t        dt        |j                        z        || j                   |j                  <   || j                  |j                  <    |rt        | g|  yy)a0  Initialize the vocabulary given a list of terms.

        The vocabulary keeps a reference to the list of terms passed
        in; it should never be modified while the vocabulary is used.

        One or more interfaces may also be provided so that alternate
        widgets may be bound without subclassing.

        By default, ValueErrors are thrown if duplicate values or tokens
        are passed in. If you want to swallow these exceptions, pass
        in ``swallow_duplicates=True``. In this case, the values will
        override themselves.
        swallow_duplicatesFzterm values must be unique: %szterm tokens must be unique: %sN)	by_valueby_token_termsgetr   
ValueErrorreprr   r   )r   terms
interfaceskwargsswallow_dupesterms         r   r   zSimpleVocabulary.__init__d   s     

#7?KK 		-D ::.$84

;KKM M::.$84

;KKM M(,DMM$**%(,DMM$**%		- T/J/ r   c           	      r    |D cg c]  } | j                   |d   |d   g|dd  ! }} | |g| S c c}w )aB  
        Construct a vocabulary from a list of (token, value) pairs or
        (token, value, title) triples. The list does not have to be
        homogeneous.

        The order of the items is preserved as the order of the terms
        in the vocabulary. Terms are created by calling the class
        method :meth:`createTerm`` with the pair or triple.

        One or more interfaces may also be provided so that alternate
        widgets may be bound without subclassing.

        .. versionchanged:: 4.6.0
            Allow passing in triples to set item titles.
           r      N
createTerm)clsitemsr<   itemr;   s        r   	fromItemszSimpleVocabulary.fromItems   sV    $ #$  Qa<48< $ $5&:&&$s   $4c                 Z    |D cg c]  }| j                  |       }} | |g| S c c}w )a  Construct a vocabulary from a simple list.

        Values of the list become both the tokens and values of the
        terms in the vocabulary. The order of the values is preserved
        as the order of the terms in the vocabulary. Tokens are
        created by calling the class method :meth:`createTerm()` with
        the value as the only parameter.

        One or more interfaces may also be provided so that alternate
        widgets may be bound without subclassing.
        rC   )rE   valuesr<   r   r;   s        r   
fromValueszSimpleVocabulary.fromValues   s5     5;;5&;;5&:&& <s   (c                     t        | S )zCreate a single term from data.

        Subclasses may override this with a class method that creates
        a term of the appropriate type from the arguments.
        )r   )rE   argss     r   rD   zSimpleVocabulary.createTerm   s     4  r   c                 >    	 || j                   v S # t        $ r Y yw xY w)*See zope.schema.interfaces.IBaseVocabularyF)r5   	TypeErrorr   r   s     r   __contains__zSimpleVocabulary.__contains__   s(    	DMM)) 		    	c                 R    	 | j                   |   S # t        $ r t        |      w xY wrO   )r5   KeyErrorLookupErrorrQ   s     r   getTermzSimpleVocabulary.getTerm   0    	%=='' 	%e$$	%    &c                 R    	 | j                   |   S # t        $ r t        |      w xY wz/See zope.schema.interfaces.IVocabularyTokenized)r6   rV   rW   r   r   s     r   getTermByTokenzSimpleVocabulary.getTermByToken   rY   rZ   c                 ,    t        | j                        S z.See zope.schema.interfaces.IIterableVocabulary)iterr7   r*   s    r   __iter__zSimpleVocabulary.__iter__   s    DKK  r   c                 ,    t        | j                        S r`   )lenr5   r*   s    r   __len__zSimpleVocabulary.__len__   s    4==!!r   c                     || u ryt        |t              sy| j                  |j                  k(  xr t        |       t        |      k(  S r   )r   r2   r7   r   r    s     r   r"   zSimpleVocabulary.__eq__   sH    D=%!12 KK5<<' 64 Ju$55	
r   c                 &    | j                  |       S r$   r%   r    s     r   r&   zSimpleVocabulary.__ne__   r'   r   c                 >    t        t        | j                              S r$   )r)   tupler7   r*   s    r   r+   zSimpleVocabulary.__hash__   s    E$++&''r   N)r,   r-   r.   r/   r   classmethodrH   rK   rD   rR   rX   r^   rb   re   r"   r&   r+   r0   r   r   r2   r2   Z   sp    0> ' '( ' ' ! !%%!"

&(r   r2   c                     t        |j                               D ]A  }t        |d   |d   g|dd  }t        j	                         | |<   t        | |   ||          C | S )z Helper method that creates a tree-like dict with ITokenizedTerm
    objects as keys from a similar tree with tuples as keys.

    See fromDict for more details.
    rA   r   rB   N)sortedkeysr   TreeVocabularyterms_factory_createTermTree)ttreedict_keyr?   s       r   rp   rp      sh     ejjl# 1#a&#a&33qr73$224ddU3Z01 Lr   c                   z    e Zd ZdZeZd Zd Zd Zd Z	d Z
ddZd	 Zd
 Zd Zed        Zd Zd Zd Zd Zd Zy)rn   z> Vocabulary that relies on a tree (i.e nested) structure.
    c                     | j                         | _        | j                  j                  |       i | _        i | _        i | _        | j                  |       |rt        | g|  yy)a  Initialize the vocabulary given a recursive dict (i.e a tree) with
        ITokenizedTerm objects for keys and self-similar dicts representing the
        branches for values.

        Refer to the method fromDict for more details.

        Concerning the ITokenizedTerm keys, the 'value' and 'token' attributes
        of each key (including nested ones) must be unique.

        One or more interfaces may also be provided so that alternate
        widgets may be bound without subclassing.
        N)ro   r7   updatepath_by_valueterm_by_valueterm_by_token_populateIndexesr   )r   r;   r<   s      r   r   zTreeVocabulary.__init__   sa     ((*5!e$T/J/ r   c                 >    	 || j                   v S # t        $ r Y yw xY w)zt See zope.schema.interfaces.IBaseVocabulary

        D.__contains__(k) -> True if D has a key k, else False
        F)rx   rP   rQ   s     r   rR   zTreeVocabulary.__contains__  s*    
	D.... 		rS   c                 8    | j                   j                  |      S )z#x.__getitem__(y) <==> x[y]
        )r7   __getitem__)r   rs   s     r   r}   zTreeVocabulary.__getitem__  s     {{&&s++r   c                 6    | j                   j                         S )zZSee zope.schema.interfaces.IIterableVocabulary

        x.__iter__() <==> iter(x)
        )r7   rb   r*   s    r   rb   zTreeVocabulary.__iter__   s    
 {{##%%r   c                 6    | j                   j                         S )z x.__len__() <==> len(x)
        )r7   re   r*   s    r   re   zTreeVocabulary.__len__'  s     {{""$$r   Nc                 :    | j                   j                  ||      S )zaGet a value for a key

        The default is returned if there is no value for the key.
        )r7   r8   )r   rs   defaults      r   r8   zTreeVocabulary.get,  s    
 {{sG,,r   c                 6    | j                   j                         S )z/Return the keys of the mapping object.
        )r7   rm   r*   s    r   rm   zTreeVocabulary.keys3  s     {{!!r   c                 6    | j                   j                         S )z1Return the values of the mapping object.
        )r7   rJ   r*   s    r   rJ   zTreeVocabulary.values8  s     {{!!##r   c                 6    | j                   j                         S )z0Return the items of the mapping object.
        )r7   rF   r*   s    r   rF   zTreeVocabulary.items=  s     {{  ""r   c                 D     | t        | j                         |      g| S )a  Constructs a vocabulary from a dictionary-like object (like dict or
        OrderedDict), that has tuples for keys.

        The tuples should have either 2 or 3 values, i.e:
        (token, value, title) or (token, value). Only tuples that have
        three values will create a
        :class:`zope.schema.interfaces.ITitledTokenizedTerm`.

        For example, a dict with 2-valued tuples::

          dict_ = {
            ('exampleregions', 'Regions used in ATVocabExample'): {
                ('aut', 'Austria'): {
                    ('tyr', 'Tyrol'): {
                        ('auss', 'Ausserfern'): {},
                    }
                },
                ('ger', 'Germany'): {
                    ('bav', 'Bavaria'):{}
                },
            }
          }

        One or more interfaces may also be provided so that alternate
        widgets may be bound without subclassing.

        .. versionchanged:: 4.6.0
           Only create ``ITitledTokenizedTerm`` when a title is actually
           provided.
        )rp   ro   )rE   rr   r<   s      r   fromDictzTreeVocabulary.fromDictB  s%    @ ?3#4#4#6>LLLr   c                    |j                         D ]  }t        |d      }t        |d      }|| j                  v rt        d|z        || j                  v rt        d|z        || j                  |<   || j                  |<   || j
                  vr| j                  | |      | j
                  |<   | j                  ||           y)a   The TreeVocabulary contains three helper indexes for quick lookups.
        They are: term_by_value, term_by_token and path_by_value

        This method recurses through the tree and populates these indexes.

        tree:  The tree (a nested/recursive dictionary).
        r   r   z Term values must be unique: '%s'z Term tokens must be unique: '%s'N)rm   getattrrx   r9   ry   rw   _getPathToTreeNoderz   )r   treer?   r   r   s        r   rz   zTreeVocabulary._populateIndexesd  s     IIK 	.DD'*ED'*E*** 6>@ @ *** 6>@ @ )-Du%(,Du%D...,0,C,CDDI-K""5)!!$t*-%	.r   c                 R    	 | j                   |   S # t        $ r t        |      w xY wrU   )rx   rV   rW   rQ   s     r   rX   zTreeVocabulary.getTerm  2    	%%%e,, 	%e$$	%rZ   c                 R    	 | j                   |   S # t        $ r t        |      w xY wr\   )ry   rV   rW   r]   s     r   r^   zTreeVocabulary.getTermByToken  r   rZ   c                     g }|j                         D ]L  \  }}||j                  k(  r|gc S | j                  ||      }|s/|j                  d|j                          |S  |S )zHelper method that computes the path in the tree from the root
        to the given node.

        The tree must be a recursive IEnumerableMapping object.
        r   )rF   r   r   insert)r   r   nodepathparentchilds         r   r   z!TreeVocabulary._getPathToTreeNode  sk     !ZZ\ 	MFEv||#v**5$7DAv||,	 r   c                 :    | j                   j                  |g       S )zReturns a list of strings representing the path from the root node
        to the node with the given value in the tree.

        Returns an empty string if no node has that value.
        )rw   r8   rQ   s     r   getTermPathzTreeVocabulary.getTermPath  s     !!%%eR00r   r$   )r,   r-   r.   r/   r   ro   r   rR   r}   rb   re   r8   rm   rJ   rF   rj   r   rz   rX   r^   r   r   r0   r   r   rn   rn      sk    
  M00	,
&%
-"
$
#
 M MB.8%% 1r   rn   c                   (     e Zd ZdZ fdZd Z xZS )VocabularyRegistryErrorz
    A specialized subclass of `LookupError` raised for unknown
    (unregistered) vocabularies.

    .. seealso:: `VocabularyRegistry`
    c                 L    || _         t        t        |   t	        |              y r$   )namesuperr   r   r   )r   r   	__class__s     r   r   z VocabularyRegistryError.__init__  s    	%t5c$i@r   c                      d| j                   z  S )Nzunknown vocabulary: %r)r   r*   s    r   __str__zVocabularyRegistryError.__str__  s    '$))33r   )r,   r-   r.   r/   r   r   __classcell__)r   s   @r   r   r     s    A4r   r   c                   &    e Zd ZdZdZd Zd Zd Zy)VocabularyRegistryaR  
    Default implementation of
    :class:`zope.schema.interfaces.IVocabularyRegistry`.

    An instance of this class is used by default by
    :func:`getVocabularyRegistry`, which in turn is used by
    :class:`~.Choice` fields.

    Named vocabularies must be manually registered with this object
    using :meth:`register`. This associates a vocabulary name with a
    :class:`zope.schema.interfaces.IVocabularyFactory`.

    An alternative to this is to use the :mod:`zope.component` registry via
    `zope.vocabularyregistry
    <https://pypi.org/project/zope.vocabularyregistry/>`_.
    _mapc                     i | _         y r$   r   r*   s    r   r   zVocabularyRegistry.__init__  s	    	r   c                 b    	 | j                   |   } ||      S # t        $ r t        |      w xY w)z.See zope.schema.interfaces.IVocabularyRegistry)r   rV   r   )r   contextr   vtypes       r   r8   zVocabularyRegistry.get  s<    	0IIdOE W~  	0)$//	0s    .c                 "    || j                   |<   y)z>Register a *factory* for the vocabulary with the given *name*.Nr   )r   r   factorys      r   registerzVocabularyRegistry.register  s    !		$r   N)r,   r-   r.   r/   	__slots__r   r8   r   r0   r   r   r   r     s      I"r   r   Nc                  @    t         t        t                      t         S )zReturn the vocabulary registry.

    If the registry has not been created yet, an instance of
    VocabularyRegistry will be installed and used.
    )_vocabulariessetVocabularyRegistryr   r0   r   r   getVocabularyRegistryr     s     023r   c                     | a y)zSet the vocabulary registry.Nr   )registrys    r   r   r     s	     Mr   c                      da y)z)Remove the registries (for use by tests).Nr   r0   r   r   _clearr     s	     Mr   )
addCleanUp)r/   collectionsr   zope.interfacer   r   r   zope.schema.interfacesr   r   r	   r
   r   object_markerr   r2   rp   rn   rW   r   r   r   r   r   r   zope.testing.cleanupr   ImportErrorr0   r   r   <module>r      s
   # + & % 7 1 2 6 7 ( ^5: 5: 5:p !"D(v D( #D(N
 _t1V t1 t1p4k 4  ! "  " " "F /
 v  		s   2C C
	C
