This is an automated email from the ASF dual-hosted git repository.

papegaaij pushed a commit to branch wicket-10.x
in repository https://gitbox.apache.org/repos/asf/wicket.git

commit 34b36f2bc3f76030c38cac48996f0d8b893edc68
Author: Emond Papegaaij <[email protected]>
AuthorDate: Wed Aug 19 22:24:56 2026 +0200

    Escape the attribute values of a MetaDataHeaderItem as markup
    
    generateString escaped attribute names with Strings.escapeMarkup but ran the
    values through Strings.replaceAll(value, "\"", "\\\""). A backslash before a
    double quote means nothing in HTML, so a value holding a double quote ended 
its
    own attribute and whatever followed was read as further attributes. Values 
may
    come from an IModel, so they are not necessarily literals. WICKET-6178 set 
out to
    escape these values and this is what it left behind.
    
    They now go through Strings.escapeMarkup, like the names beside them and 
like
    every attribute ComponentTag writes.
    
    Two tests asserted the old output. testEscapeOnlyDoubleQuotes was named 
after the
    behaviour that was the problem and is renamed. HtmlImportHeaderItemTest 
expects
    an escaped ampersand in the href of a link tag, which is what a url holding 
two
    parameters has to carry, and is what ComponentTag writes for every other
    attribute.
    
    Co-Authored-By: Claude Opus 5 (1M context) <[email protected]>
---
 .../markup/head/HtmlImportHeaderItemTest.java      |  7 +++--
 .../wicket/markup/head/MetaDataHeaderItemTest.java | 35 ++++++++++++++++++++--
 .../wicket/markup/head/MetaDataHeaderItem.java     |  2 +-
 3 files changed, 39 insertions(+), 5 deletions(-)

diff --git 
a/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/HtmlImportHeaderItemTest.java
 
b/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/HtmlImportHeaderItemTest.java
index 7d5eebfed3..1788a57406 100644
--- 
a/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/HtmlImportHeaderItemTest.java
+++ 
b/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/HtmlImportHeaderItemTest.java
@@ -20,6 +20,7 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
 
 import org.apache.wicket.markup.html.basic.SimplePage;
 import org.apache.wicket.request.mapper.parameter.PageParameters;
+import org.apache.wicket.util.string.Strings;
 import org.apache.wicket.util.tester.WicketTester;
 import org.junit.jupiter.api.Test;
 
@@ -54,7 +55,9 @@ class HtmlImportHeaderItemTest
                MetaDataHeaderItem importLink = 
HtmlImportHeaderItem.forImportLinkTag(SimplePage.class,
                        parameters, "monitor", true);
 
-               assertEquals("<link rel=\"import\" href=\"" + pageUrl + "\" 
media=\"monitor\" async />\n",
-                       importLink.generateString());
+               // the href is escaped as markup, like every other attribute 
Wicket writes. The url holds
+               // a literal & between its two parameters, which has to be 
written as an entity
+               assertEquals("<link rel=\"import\" href=\"" + 
Strings.escapeMarkup(pageUrl)
+                       + "\" media=\"monitor\" async />\n", 
importLink.generateString());
        }
 }
diff --git 
a/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/MetaDataHeaderItemTest.java
 
b/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/MetaDataHeaderItemTest.java
index fc2c93b5b6..df4997e779 100644
--- 
a/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/MetaDataHeaderItemTest.java
+++ 
b/wicket-core-tests/src/test/java/org/apache/wicket/markup/head/MetaDataHeaderItemTest.java
@@ -43,12 +43,43 @@ class MetaDataHeaderItemTest
                assertEquals(expectedString, metaTag.generateString());
        }
        
+       /**
+        * Attribute values are escaped as markup. A backslash before a double 
quote means nothing in
+        * HTML, so escaping that way left the value able to close its own 
attribute.
+        */
        @Test
-    void testEscapeOnlyDoubleQuotes() throws Exception
+    void testEscapesAttributeValuesAsMarkup() throws Exception
        {
-               String expectedString = "<link rel=\"single quote \' double 
quotes\\\"\" href=\"\" />\n";
+               String expectedString = "<link rel=\"single quote &#039; double 
quotes&quot;\" href=\"\" />\n";
                MetaDataHeaderItem metaTag = 
MetaDataHeaderItem.forLinkTag("single quote \' double quotes\"", "");
                
                assertEquals(expectedString, metaTag.generateString());
        }
+
+       /**
+        * A value cannot end its attribute and add another one.
+        */
+       @Test
+    void testAttributeValueCannotInjectAnotherAttribute() throws Exception
+       {
+               MetaDataHeaderItem metaTag = 
MetaDataHeaderItem.forMetaTag("description",
+                       "x\" onload=\"x=1");
+
+               assertEquals("<meta name=\"description\" content=\"x&quot; 
onload=&quot;x=1\" />\n",
+                       metaTag.generateString());
+       }
+
+       /**
+        * The same for a value taken from a model.
+        */
+       @Test
+    void testAttributeValueFromModelIsEscaped() throws Exception
+       {
+               MetaDataHeaderItem metaTag = 
MetaDataHeaderItem.forLinkTag("stylesheet", "");
+               metaTag.addTagAttribute("title", 
Model.of("<script>x=1</script>"));
+
+               assertEquals(
+                       "<link rel=\"stylesheet\" href=\"\" 
title=\"&lt;script&gt;x=1&lt;/script&gt;\" />\n",
+                       metaTag.generateString());
+       }
 }
diff --git 
a/wicket-core/src/main/java/org/apache/wicket/markup/head/MetaDataHeaderItem.java
 
b/wicket-core/src/main/java/org/apache/wicket/markup/head/MetaDataHeaderItem.java
index 6649ef2b66..05bfbfe211 100644
--- 
a/wicket-core/src/main/java/org/apache/wicket/markup/head/MetaDataHeaderItem.java
+++ 
b/wicket-core/src/main/java/org/apache/wicket/markup/head/MetaDataHeaderItem.java
@@ -131,7 +131,7 @@ public class MetaDataHeaderItem extends HeaderItem
                        {
                                buffer.append('=')
                                        .append('"')
-                                       
.append(Strings.replaceAll(value.toString(), "\"", "\\\""))
+                                       
.append(Strings.escapeMarkup(value.toString()))
                                        .append('"');
                        }
                }

Reply via email to