+
    *:gK                       a  0 t $ R t^ RIHt ^ RIHt ^ RIHtHtH	t	H
t
 0 RmRR00 Rm.tR R ltR R	 ltR
 R ltR R lt]! 4       tR]R&   R# )z
babel.messages.checkers
~~~~~~~~~~~~~~~~~~~~~~~

Various routines that help with validation of translations.

:since: version 0.9

:copyright: (c) 2013-2025 by the Babel Team.
:license: BSD, see LICENSE for more details.
)annotations)Callable)PYTHON_FORMATCatalogMessageTranslationErrorxXc               $    V ^8  d   QhRRRRRR/#    catalogzCatalog | Nonemessager   returnNone )formats   "9/usr/lib/python3/dist-packages/babel/messages/checkers.py__annotate__r      s!     4 4 4' 4d 4    c                R   VP                   '       g.   \        VP                  \        4      '       g   \	        R4      hR# V f   R# VP                  p\        V\
        \        34      '       g   V3p\        V4      V P                  8w  d   \	        RV P                  ,          4      hR# )z0Verify the number of plurals in the translation.z/Found plural forms for non-pluralizable messageNz*Wrong number of plural forms (expected %d))	pluralizable
isinstancestringstrr   listtuplelennum_plurals)r   r   msgstrss   && r   r   r      s    '..#.." $- . . 
nnGge}--*
7|w***K&22 3 4 	4 +r   c               $    V ^8  d   QhRRRRRR/# r   r   )r   s   "r   r   r   .   s!     , ,> ,G , ,r   c                *   RVP                   9  d   R# VP                  p\        V\        \        34      '       g   V3pVP
                  p\        V\        \        34      '       g   V3p\        W#4       F  w  rEV'       g   K  \        WE4       K  	  R# )z9Verify the format string placeholders in the translation.zpython-formatN)flagsidr   r   r   r   zip_validate_format)r   r   msgidsr   msgidmsgstrs   &&    r   python_formatr)   .   sq    gmm+ZZFftUm,,nnGge}--*V-6U+ .r   c               $    V ^8  d   QhRRRRRR/# )r   r   r   alternativer   r   r   )r   s   "r   r   r   >   s&     \ \S \s \t \r   c           
        R R lpR R lpR R lp\        W V34      w  rVV'       g   R# \        WEV34      w  rxV'       d   V'       g   V'       g   \        R4      hWx8w  d   \        R	4      hV'       du   \        V4      \        V4      8w  d   \        R
4      h\        \	        WV4      4       F6  w  p	w  w  rw  rV! W4      '       d   K  \        RV	^,           W3,          4      h	  R# \        V4      pV FM  w  rW9  d   \        RV: 24      hV! WV,          4      '       d   K1  \        RV: RV: RW,          : R24      h	  R# )a  Test format string `alternative` against `format`.  `format` can be the
msgid of a message and `alternative` one of the `msgstr`\s.  The two
arguments are not interchangeable as `alternative` may contain less
placeholders if `format` uses named placeholders.

If the string formatting of `alternative` is compatible to `format` the
function returns `None`, otherwise a `TranslationError` is raised.

Examples for compatible format strings:

>>> _validate_format('Hello %s!', 'Hallo %s!')
>>> _validate_format('Hello %i!', 'Hallo %d!')

Example for an incompatible format strings:

>>> _validate_format('Hello %(name)s!', 'Hallo %s!')
Traceback (most recent call last):
  ...
TranslationError: the format strings are of different kinds

This function is used by the `python_format` checker.

:param format: The original format string
:param alternative: The alternative format string that should be checked
                    against format
:raises TranslationError: on formatting errors
c                    V ^8  d   QhRRRR/# )r   r   r   r   list[tuple[str, str]]r   )r   s   "r   r   &_validate_format.<locals>.__annotate__[   s      s 4 r   c                    . p\         P                  ! V 4       F?  pVP                  4       w  r4pVR 8X  d   Vf   K#  VP                  V\	        V4      34       KA  	  V# )%)r   finditergroupsappendr   )r   resultmatchnamer   typechars   &     r   _parse _validate_format.<locals>._parse[   sV    (*"++F3E%*\\^"D(34<MM4X/0	 4
 r   c               $    V ^8  d   QhRRRRRR/# )r   ar   br   boolr   )r   s   "r   r   r/   d   s!      s s t r   c                R    W8X  d   R # \          F  pW9   g   K  W9   g   K   R # 	  R# )TF)_string_format_compatibilities)r<   r=   sets   && r   _compatible%_validate_format.<locals>._compatibled   s%    61CxAH 2 r   c                    V ^8  d   QhRRRR/# )r   resultsr.   r   r>   r   )r   s   "r   r   r/   l   s     	  	 #8 	 T 	 r   c                n    R pV  F#  w  r#Vf   VR J pK  VR J V8w  g   K  \        R4      h	  \        V4      # )Nz5format string mixes positional and named placeholders)r   r>   )rE   
positionalr7   _chars   &   r   _check_positional+_validate_format.<locals>._check_positionall   sP    
"KD!!T\
DLZ/* ,D E E # Jr   Nzplaceholders are incompatiblez)the format strings are of different kindsz-positional format placeholders are unbalancedzDincompatible format for placeholder %d: %r and %r are not compatiblezunknown named placeholder z$incompatible format for placeholder z: z and z are not compatible)mapr   r   	enumerater$   dict)r   r+   r9   rB   rI   r<   r=   a_positionalb_positionalidx_firstsecondtype_mapr7   r8   s   &&              r   r%   r%   >   sJ   :	  v,-DA "%%6A!?LL>??		%JKK q6SV" $0 1 1.7A	.B*C**1kqu--& (J(+a'?(@ A A /C 7ND#&)CD8'LMM D>::&:4("l%'99LN 	  r   c                   V ^8  d   QhRR/# )r   r   1list[Callable[[Catalog | None, Message], object]]r   )r   s   "r   r   r      s      I r   c                     ^ RI Hp  . pVP                  R V ! R4       4       4       \        V4      ^ 8X  d   \        \
        .# V# )    )find_entrypointsc              3  4   "   T F  w  rV! 4       x  K  	  R # 5i)Nr   ).0r7   loads   &  r   	<genexpr>!_find_checkers.<locals>.<genexpr>   s     R/Q|DFF/Qs   zbabel.checkers)babel.messages._compatrY   extendr   r   r)   )rY   checkerss     r   _find_checkersrb      sA    7BDHOOR/?@P/QRR
8} ]++Or   rV   ra   N>   diu>   FGfg)__conditional_annotations____doc__
__future__r   collections.abcr   babel.messages.catalogr   r   r   r   r@   r   r)   r%   rb   ra   __annotations__)rj   s   @r   <module>rp      sW   
 # $ T T #J" 4(, \~ ?M>N
; Nr   