Skip to content

Commit 6b064c5

Browse files
committed
doc: update doc on tal:replace and tal:content
Describe use of tal:replace for XSS and how to execute a replaced tag with <tal:x> and tal:content.
1 parent 8e002b0 commit 6b064c5

File tree

1 file changed

+48
-7
lines changed

1 file changed

+48
-7
lines changed

doc/reference.txt

Lines changed: 48 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2480,23 +2480,60 @@ The basic TAL commands are:
24802480
**tal:replace="expression"**
24812481
Replace this tag with the result of the expression. For example::
24822482

2483-
<span tal:replace="request/user/realname" />
2483+
<span tal:replace="request/user/id" />
24842484

24852485
The example would replace the <span> tag and its contents with the
2486-
user's realname. If the user's realname was "Bruce", then the
2487-
resultant output would be "Bruce".
2486+
user's id. If the user's id was "3" the resulting output would be
2487+
"3".
2488+
2489+
You need to be a little careful with ``tal:replace``. Unlike
2490+
``tal:content``, it doesn't always escape the output. For example
2491+
if you used::
2492+
2493+
<tal:x tal:replace="request/user/realname" />
2494+
2495+
it would replace the contents with the value of the user's
2496+
realname. The realname is something the user can control. The user
2497+
could include something like::
2498+
2499+
Bruce<script>alert("hello there");</script>
2500+
2501+
This would result in an alert box popping up when the page was
2502+
loaded. Attackers could use this `XSS exploit`_ for malicious
2503+
purposes.
2504+
2505+
Generally you would use tal:replace when calling a utility function
2506+
using a :ref:`Python expression <python expression>` that generates
2507+
trusted HTML.
2508+
2509+
If you are inserting untrusted content, it is better to use
2510+
``tal:content`` with tags that disappear as described below.
2511+
2512+
.. _`XSS exploit`: https://owasp.org/www-community/attacks/xss/
24882513

24892514
**tal:content="expression"**
2490-
Replace the contents of this tag with the result of the expression.
2491-
For example::
2515+
Replace the contents of this tag (but not the tag itself) with the
2516+
result of the expression. For example::
24922517

2493-
<span tal:content="request/user/realname">user's name appears here
2494-
</span>
2518+
<span tal:content="request/user/realname">user's name appears here
2519+
</span>
24952520

24962521
This example would replace the contents of the ``<span>`` tag with the
24972522
user's realname. If the user's realname was "Bruce" then the
24982523
output will be ``<span>Bruce</span>``.
24992524

2525+
``tal:content`` replaces special HTML claracters like ``<`` with an
2526+
HTML entitity ``&lt;``. This makes it safer to use when inserting
2527+
untrusted data. To have ``tal:content`` insert unescaped HTML, you
2528+
need to use the `structure modifier`_.
2529+
2530+
If the tag is an unknown ``tal:`` tag, TAL removes the tag. So
2531+
evaulating:
2532+
2533+
<tal:x tal:replace="request/user/realname" />
2534+
2535+
results in ``Bruce``.
2536+
25002537
**tal:attributes="attribute expression; attribute expression; ..."**
25012538
Set attributes on this tag to the results of expressions. For
25022539
example::
@@ -2574,6 +2611,8 @@ attribute values may be one of the following forms:
25742611
expression in the interpolation decorator ``${ ... }`` is a
25752612
path expression as above.
25762613

2614+
.. _`python expression`:
2615+
25772616
**Python Expressions** - e.g. ``python: 1+1``
25782617
These expressions give the full power of Python. All the "root level"
25792618
variables are available, so ``python:item.status.checklist()`` is
@@ -2582,6 +2621,8 @@ attribute values may be one of the following forms:
25822621

25832622
Modifiers:
25842623

2624+
.. _`structure modifier`:
2625+
25852626
**structure** - e.g. ``structure python:msg.content.plain(hyperlink=1)``
25862627
The result of expressions are *escaped* to be safe for HTML
25872628
display (all "<", ">" and "&" are replaced with entities

0 commit comments

Comments
 (0)