B ˝`W @sUdZddlZddlZddlmZddlmZddlmZddlm Z ddlm Z ej rlddl Z dd lmZed ejejZed ejejZed d ddddddddddg ZeddddddgZejejejejejejdZ ej!e"ej#ej$fe%d<Gd d!d!Z&dS)"z8Parse tokens from the lexer into nodes for the compiler.N)nodes)TemplateAssertionError)TemplateSyntaxError)describe_token)describe_token_expr) Environment_ImportInclude _MacroCallforifblockZextendsprintZmacroZincludefromimportsetwith autoescapeeqneltZlteqgtZgteq)addsubmuldivfloordivmod _math_nodesc @s eZdZdZddeejeejeejeddddZdefeeje ej eddd d Z ejeej ej ed feje dd d dZdeeje ddddZdejej ed feje ddddZdejej ed fedddZdeje ejdddZejejej ejfdddZdej ed feej ejdd d!Zejejejfdd"d#Zejdd$d%Zejdd&d'Z ej!dd(d)Z"ej#dd*d+Z$ej%dd,d-Z&ej'dd.d/Z(e)ee)d0d1d2Z*ej+dd3d4Z,ej-dd5d6Z.ej/dd7d8Z0e1dd9d:d;Z2ej3ddd?Z6ej7dd@dAZ8ej9ddBdCZ:e;je;jdeeejej ed feejej?ej=ej fdIdKdGZ>deej@dLdMdNZAej@ddOdPZBej@ddQdRZCej@ddSdTZDej@ddUdVZEej@ddWdXZFej@ddYdZZGej@dd[d\ZHej@dd]d^ZIej@dd_d`ZJdeej@dadbdcZKej@ddddeZLdeeejej ed feejej ej@fdfdgdhZMej ddidjZNejOddkdlZPej@ej@d9dmdnZQej@ej@d9dodpZRej@ejejSejTfd9dqdrZUej@ddsdtZVej ddudvZWej@ejXd9dwdxZYdejej@eejej@dydzd{ZZej@ej@d9d|d}Z[dejej ed fej ejd~ddZ\ej]dddZ^dS)ParserzThis is the central parsing class Jinja uses. It's passed to extensions and can be used to parse expressions or statements. Nr) environmentsourcenamefilenamestatereturncCst||_||||||_||_||_d|_i|_x,|D] }x|jD]}|j |j|<qFWq:Wd|_ g|_ g|_ dS)NFr) r _tokenizestreamr"r#closed extensionsZiter_extensionsZtagsparse_last_identifier _tag_stack_end_token_stack)selfr r!r"r#r$ extensiontagr1>/opt/alt/python37/lib/python3.7/site-packages/jinja2/parser.py__init__3s zParser.__init__z te.NoReturn)msglinenoexcr%cCs(|dkr|jjj}||||j|jdS)zConvenience method that raises `exc` with the message, passed line number or last line number as well as the current name and filename. N)r'currentr5r"r#)r.r4r5r6r1r1r2failJs  z Parser.fail.)r"end_token_stackr5r%cCst}x|D]}|tt|q W|rDdtttt|d}nd}|dkrXdg}nd|dg}|r|dk r||kr|d|dn|d|d|jr|d|jdd|d ||dS) Nz or zUnexpected end of template.zEncountered unknown tag .z\You probably made a nesting mistake. Jinja is expecting this tag, but currently looking for z*Jinja was looking for the following tags: z/The innermost block that needs to be closed is  ) rupdatemaprjoinreprappendr,r8)r.r"r9r5ZexpectedZexprsZcurrently_lookingmessager1r1r2 _fail_ut_eofXs( zParser._fail_ut_eof)r"r5r%cCs|||j|dS)zCalled if the parser encounters an unknown tag. Tries to fail with a human readable error message that could help to identify the problem. N)rCr-)r.r"r5r1r1r2fail_unknown_tagszParser.fail_unknown_tag) end_tokensr5r%cCs.t|j}|dk r|||d||dS)z9Like fail_unknown_tag but for end of template situations.N)listr-rArC)r.rEr5stackr1r1r2fail_eofs  zParser.fail_eof)extra_end_rulesr%cCs,|jjjdkrdS|dk r(|jj|SdS)zAre we at the end of a tuple?) variable_end block_endrparenTNF)r'r7typetest_any)r.rIr1r1r2 is_tuple_ends zParser.is_tuple_end)r5r%cCs8|jd7_ttj}tjj|d|j|d|S)zDReturn a new free identifier as :class:`~jinja2.nodes.InternalName`.rZfi)r5)r+object__new__r InternalNameNoder3)r.r5rvr1r1r2free_identifiers zParser.free_identifier)r%cCs|jj}|jdkr |d|j|j|jd}z|jtkrZt |d|jjj}|S|jdkrl| S|jdkr~| S|j |j}|dk r||S|jd}||j|jWd|r|jXdS) zParse a single statement.r"ztag name expectedTZparse_callfilterNF)r'r7rMr8r5r,rAvalue_statement_keywordsgetattrparse_call_blockparse_filter_blockr)getpoprD)r.tokenZpop_tagfextr1r1r2parse_statements*     zParser.parse_statementF)rE drop_needler%cCsL|jd|jd||}|jjjdkr:|||rHt|j|S)aRParse multiple statements into a list until one of the end tokens is reached. This is used to parse the body of statements as it also parses template data if appropriate. The parser checks first if the current token is a colon and skips it if there is one. Then it checks for the block end and parses until if one of the `end_tokens` is reached. Per default the active token in the stream at the end of the call is the matched end token. If this is not wanted `drop_needle` can be set to `True` and the end token is removed. colonrKeof)r'skip_ifexpectsubparser7rMrHnext)r.rErcresultr1r1r2parse_statementss     zParser.parse_statementscCsft|jj}|jdd}|jdr<|}tj|||dS|d}|j ddd}tj ||||dS)zParse an assign statement.T)with_namespaceassign)r5N)z name:endset)rc) rir'r5parse_assign_targetrf parse_tuplerAssign parse_filterrk AssignBlock)r.r5targetexprZ filter_nodebodyr1r1r2 parse_sets    zParser.parse_setc Cs|jdj}|jdd}|jd|jddd}d}|jd rL|}|jd }|d }t|jj d krxg}n|jd dd}t j |||||||dS)zParse a for loop.zname:for)zname:in)rIzname:inF)zname:recursive) with_condexprrINzname:ifzname:recursive)z name:endforz name:elseZendfor)z name:endforT)rc)r5) r'rgr5rnrorfparse_expressionrkrirXrFor)r.r5rsitertest recursiveruelse_r1r1r2 parse_fors      zParser.parse_forcCstj|jdjd}}x||jdd|_|d|_g|_ g|_ t |j}|drxtj|jj jd}|j |qn|dr|jdd d |_ PqW|S) zParse an if construct.zname:if)r5F)rw)z name:elifz name:elsez name:endifz name:elifz name:else)z name:endifT)rc)rIfr'rgr5ror{rkruZelif_r}rir7rA)r.noderjr_r1r1r2parse_ifs     zParser.parse_ifcCstjt|jjd}g}g}xX|jjjdkrt|r<|jd|}| d| ||jd| | qW||_ ||_ |jddd|_|S) N)r5rKcommaparamrm)z name:endwithT)rc)rWithrir'r5r7rMrgrnset_ctxrArxtargetsvaluesrkru)r.rrrrsr1r1r2 parse_withs    zParser.parse_withcCsDtjt|jjd}td|g|_|jddd|_ t |gS)N)r5r)zname:endautoescapeT)rc) rZScopedEvalContextModifierrir'r5KeywordrxoptionsrkruScope)r.rr1r1r2parse_autoescape szParser.parse_autoescapecCstjt|jjd}|jdj|_|jd|_ |jd|_ |jj j dkrX| d|jddd |_|j rtd d |jDs| d |jd |j|S)N)r5r"z name:scopedz name:requiredrzpBlock names in Jinja have to be valid Python identifiers and may not contain hyphens, use an underscore instead.)z name:endblockT)rccss0|](}|jD]}t|tjo$|jVq qdS)N)r isinstance TemplateDatadataisspace).0ruZchildr1r1r2 ;sz%Parser.parse_block..z7Required blocks can only contain comments or whitespacezname:)rBlockrir'r5rgrXr"rfZscopedZrequiredr7rMr8rkruall)r.rr1r1r2 parse_block&s  zParser.parse_blockcCs"tjt|jjd}||_|S)N)r5)rExtendsrir'r5rxtemplate)r.rr1r1r2 parse_extendsDs zParser.parse_extends)rdefaultr%cCsH|jjddr>|jdr>t|jjdk|_|jn||_|S)Nz name:withz name:withoutz name:contextr) r'r7rNlookr{rirX with_contextskip)r.rrr1r1r2parse_import_contextIs zParser.parse_import_contextcCsbtjt|jjd}||_|jjdrP|j drPd|_ |j dnd|_ | |dS)N)r5z name:ignorez name:missingTF) rIncluderir'r5rxrr7r{rZignore_missingrr)r.rr1r1r2 parse_includeUs zParser.parse_includecCsFtjt|jjd}||_|jd|jddj |_ | |dS)N)r5zname:asT) name_onlyF) rImportrir'r5rxrrgrnr"rsr)r.rr1r1r2 parse_importas   zParser.parse_importcstjtjjd_jdg_t dfdd }xjrXjdjj j dkr|rnPj dd }|j d rjd |jtd jd rƈj dd }j|j |j fnj|j |sjj j dkrPqFjdqFWtdsd_S)N)r5z name:import)r%csBjjjdkr>jdr>tjjdk_jdSdS)N>withoutrz name:contextrTF)r'r7rXrr{rirrr1)rr.r1r2 parse_contextns z(Parser.parse_from..parse_contextrr"T)r_z4names starting with an underline can not be imported)r6zname:asrF)r FromImportrir'r5rxrrgnamesboolr7rMrnr" startswithr8rrfrAhasattrr)r.rrsaliasr1)rr.r2 parse_fromhs6        zParser.parse_from)rr%cCsg}|_g}|_|jdxl|jjjdkr|r@|jd|jdd}|d|jdrr| | n|r| d| |q"W|jddS) NlparenrLrT)rrrmz-non-default argument follows default argument) argsdefaultsr'rgr7rMrnrrfrArxr8)r.rrrargr1r1r2parse_signatures        zParser.parse_signaturecCsvtjt|jjd}|jjjdkr.||n g|_g|_ | }t |tj s\| d|j||_|jddd|_|S)N)r5rz expected call)z name:endcallT)rc)r CallBlockrir'r5r7rMrrrrxrCallr8rVrkru)r.rZ call_noder1r1r2r[s  zParser.parse_call_blockcCs8tjt|jjd}|jddd|_|jddd|_|S)N)r5T) start_inline)zname:endfilter)rc) r FilterBlockrir'r5rqrWrkru)r.rr1r1r2r\szParser.parse_filter_blockcCsBtjt|jjd}|jddj|_|||jddd|_ |S)N)r5T)r)z name:endmacro)rc) rMacrorir'r5rnr"rrkru)r.rr1r1r2 parse_macros  zParser.parse_macrocCsTtjt|jjd}g|_x4|jjjdkrN|jr<|jd|j| qW|S)N)r5rKr) rOutputrir'r5r7rMrgrArx)r.rr1r1r2 parse_prints zParser.parse_printzte.Literal[True]) with_tuplerr%cCsdS)Nr1)r.rrr1r1r2rnszParser.parse_assign_targetT)rrrIrlr%cCsdS)Nr1)r.rrrIrlr1r1r2rnscCs|rN|jjdkrN|jd}t|j|jd}tj|j|j|jd}nL|rt|jd}tj |jd|jd}n&|r|j d|d}n| }| d| s|dt|j|j|S)aParse an assignment target. As Jinja allows assignments to tuples, this function can parse all allowed assignment targets. Per default assignments to tuples are parsed, that can be disable however by setting `with_tuple` to `False`. If only assignments to names are wanted `name_only` can be set to `True`. The `extra_end_rules` parameter is forwarded to the tuple parsing function. If `with_namespace` is enabled, a namespace assignment may be parsed. dotr")r5ZstoreT) simplifiedrIzcan't assign to )r'rrMrgrirNSRefrXr5Namero parse_primaryrZ can_assignr8__name__lower)r.rrrIrlr_attrrsr1r1r2rns"      )rwr%cCs|r |S|S)zParse an expression. Per default all expressions are parsed, if the optional `with_condexpr` parameter is set to `False` conditional expressions are not parsed. )parse_condexprparse_or)r.rwr1r1r2rxszParser.parse_expressioncCsf|jjj}|}xN|jdr`|}|jdr>|}nd}tj||||d}|jjj}qW|S)Nzname:ifz name:else)r5)r'r7r5rrfrrZCondExpr)r.r5Zexpr1Zexpr2Zexpr3r1r1r2rs   zParser.parse_condexprcCsJ|jjj}|}x2|jdrD|}tj|||d}|jjj}qW|S)Nzname:or)r5)r'r7r5 parse_andrfrZOr)r.r5leftrightr1r1r2rs zParser.parse_orcCsJ|jjj}|}x2|jdrD|}tj|||d}|jjj}qW|S)Nzname:and)r5)r'r7r5 parse_notrfrZAnd)r.r5rrr1r1r2r&s zParser.parse_andcCs4|jjdr,t|jj}tj||dS|S)Nzname:not)r5) r'r7r{rir5rNotr parse_compare)r.r5r1r1r2r/s zParser.parse_notcCs|jjj}|}g}x|jjj}|tkrLt|j|t ||nh|j drp|t d|nD|jj dr|j dr|j d|t d|nP|jjj}qW|s|Stj|||dS)Nzname:ininzname:notrZnotin)r5)r'r7r5 parse_math1rM_compare_operatorsrirArZOperandrfr{rrZCompare)r.r5rtZops token_typer1r1r2r5s&     zParser.parse_comparecCsb|jjj}|}xJ|jjjdkr\t|jjj}t|j|}||||d}|jjj}qW|S)N)rr)r5)r'r7r5 parse_concatrMrri)r.r5rclsrr1r1r2rLs  zParser.parse_math1cCsb|jjj}|g}x*|jjjdkr>t|j||qWt|dkrT|dStj ||dS)Ntilderr)r5) r'r7r5 parse_math2rMrirAlenrZConcat)r.r5rr1r1r2rWs    zParser.parse_concatcCsb|jjj}|}xJ|jjjdkr\t|jjj}t|j|}||||d}|jjj}qW|S)N)rrrr)r5)r'r7r5 parse_powrMrri)r.r5rrrr1r1r2ras  zParser.parse_math2cCsV|jjj}|}x>|jjjdkrPt|j|}tj|||d}|jjj}qW|S)Npow)r5)r'r7r5 parse_unaryrMrirZPow)r.r5rrr1r1r2rls  zParser.parse_pow) with_filterr%cCs|jjj}|jjj}|dkr.parseFrTrzExpected an expression, got r)r5)r'r7r5rrxrExprrgrOrArMr8rTuple) r.rrwrIrr5r*rZis_tupler1)r.r2ros2    zParser.parse_tuplecCsn|jd}g}x@|jjjdkrP|r0|jd|jjjdkr@P||qW|jdtj||jdS)Nrrbracketr)r5) r'rgr7rMrArxrListr5)r.r_itemsr1r1r2rs   zParser.parse_listcCs|jd}g}xf|jjjdkrv|r0|jd|jjjdkr@P|}|jd|}|tj|||jdqW|jdtj ||jdS)NrZrbracerrd)r5) r'rgr7rMrxrArZPairr5Dict)r.r_rkeyrXr1r1r2rs    zParser.parse_dictcCsFx@|jjj}|dks|dkr(||}q|dkr<||}qPqW|S)Nrrr)r'r7rMparse_subscript parse_call)r.rrr1r1r2rs   zParser.parse_postfixcCs`xZ|jjj}|dkr ||}q|dkrB|jjjdkrB||}q|dkrV||}qPqW|S)Npiper"isr)r'r7rMrqrX parse_testr)r.rrr1r1r2rs    zParser.parse_filter_exprcCs t|j}|jdkr|jj}t|j|jdkrFtj||jd|jdS|jdkr^|d|jtj |j|jd}tj ||d|jdS|jdkrg}x0|jjjdkr|r|j d | | qW|j dt|d kr|d }ntj|d|jd}tj ||d|jdS|d |jdS) Nrr"r)r5rzexpected name or numberrrrrrzexpected subscript expression)rir'rMr7rGetattrrXr5r8rGetitemrgrAparse_subscribedrr)r.rr_Z attr_tokenrrr1r1r2r#s.          zParser.parse_subscriptcCs|jjj}|jjjdkr*t|jdg}n*|}|jjjdkrD|St|j|g}|jjjdkrn|dn(|jjjdkr||n |d|jjjdkrt|j|jjjdkr||q|dn |dtj|d|iS)Nrd)rrr5) r'r7r5rMrirxrArZSlice)r.r5rrr1r1r2rBs*        zParser.parse_subscribedc sjdg}g}d}d}d}tddfdd }x.jjjdkrf|rjjdjjjdkrjPjjjdkr||dko|dktj}njjjd kr||dktj}njjjd kr4jjd kr4||dkjjj}j d }| t j |||j d n,||dkoN|dkoN| | d}q:Wjd||||fS)NrF)rtr%cs|sdjdS)Nz+invalid syntax for function call expression)r8r5)rt)r.r_r1r2ensurejsz&Parser.parse_call_args..ensurerLrrrr"rmr)r5T)r'rgrr7rMrirxrrXrrArrr5) r.rkwargsdyn_args dyn_kwargsZ require_commarrrXr1)r.r_r2parse_call_argsbs@           zParser.parse_call_argscCs0|jj}|\}}}}tj||||||jdS)N)r5)r'r7rrrr5)r.rr_rrrrr1r1r2rszParser.parse_call)rrr%c Csx|jjjdks|r|s"t|j|jd}|j}x2|jjjdkrft|j|d|jdj7}q6W|jjjdkr|\}}}}ng}g}d}}tj|||||||j d}d}qW|S)Nrr"rr;r)r5F) r'r7rMrirgrXrrZFilterr5) r.rrr_r"rrrrr1r1r2rqs"   zParser.parse_filterc Cs$t|j}|jjdr(t|jd}nd}|jdj}x2|jjjdkrlt|j|d|jdj7}qrrrrr"rrz name:elsezname:orzname:andzname:isz'You cannot chain multiple tests with is)r5)rir'r7r{rgrXrMrrNr8rrrZTestr5r) r.rr_Znegatedr"rrrrZarg_noder1r1r2rs6      zParser.parse_test)rEr%csLggj}|dk r"|j|ddfdd }zx|jr&|jj}|jdkr||jrp|tj|j|jdt |jq:|jdkrt |j||j dd|j d q:|jd kr|t |j|dk r|jjj |rS| }t|tr|n ||j d q:td q:W|Wd|dk rF|jXS) N)r%cs8r4dj}tjdd|ddd=dS)Nr)r5)r5rArr)r5)ru data_bufferr1r2 flush_datas z#Parser.subparse..flush_datar)r5Zvariable_beginT)rwrJZ block_beginrKzinternal parsing error)rAr-r'r7rMrXrrr5rirorgrNrbrrFextendAssertionErrorr^)r.rEZadd_datarr_rTr1)rurr2rhsB               zParser.subparsecCs"tj|dd}||j|S)z0Parse the whole template into a `Template` node.r)r5)rTemplaterhZset_environmentr )r.rjr1r1r2r* s z Parser.parse)NNN)N)NN)N)N)F)..)TFNF)TFNF)T)T)FTNF)F)N)_r __module__ __qualname____doc__strtZOptionalr3rintTyper8rrrCrDrHrrOrrRrUZUnionrSrbrkrprrrvryr~rrrrrrrrrrr rrrrrrrr rrr[rr\rrrrtypingZoverloadrrnrrrxrrrrrrrrrrrrorrrrrrrrrrrrrqrrhrr*r1r1r1r2r.s $  "   . " $       $<   1+/r)'rr rrr exceptionsrrZlexerrrZ TYPE_CHECKINGZtyping_extensionsZter rZTypeVarrrr rrr frozensetrYrZAddZSubZMulZDivZFloorDivZModrrrr r__annotations__rr1r1r1r2sB      $