This commit is contained in:
Russell Bicknell committed 2022-04-27 15:06:46 -07:00
1 parent 067dd30208
commit 8582dd6449
1 file changed
+49 -2
+49 -2
View File
@@ -69,6 +69,52 @@ function fixPlaceholder(node) {
}
}
/**
* Copies an attribute from one element to another, converting the value to a
* `TrustedScript` if it is named like a Polymer template event listener.
*
* @param {!Element} dest The element to set the attribute on
* @param {!Element} src The element to read the attribute from
* @param {string} name The name of the attribute
*/
const copyAttributeWithTemplateEventPolicy = (() => {
/**
* This `TrustedTypePolicy` is used to work around a Chrome bug in the Trusted
* Types API where any attribute that starts with `on` may only be set to a
* `TrustedScript` value, even if that attribute would not cause an event
* listener to be created. (See https://crbug.com/993268 for details.)
*
* Polymer's template system allows `<dom-if>` and `<dom-repeat>` to be
* written using the `<template is="...">` syntax, even if there is no UA
* support for custom element extensions of built-in elements. In doing so, it
* copies attributes from the original `<template>` to a newly created
* `<dom-if>` or `<dom-repeat>`, which can trigger the bug mentioned above if
* any of those attributes uses Polymer's `on-` syntax for event listeners.
* (Note, the value of these `on-` listeners is not evaluated as script: it is
* the name of a member function of a component that will be used as the event
* listener.)
*
* @type {!TrustedTypePolicy|undefined}
*/
const polymerTemplateEventAttributePolicy = window.trustedTypes &&
window.trustedTypes.createPolicy(
'polymer-template-event-attribute-policy', {
createScript: x => x,
});
return (dest, src, name) => {
const value = src.getAttribute(name);
if (polymerTemplateEventAttributePolicy && name.startsWith('on-')) {
dest.setAttribute(
name, polymerTemplateEventAttributePolicy.createScript(value, name));
return;
}
dest.setAttribute(name, value);
};
})();
function wrapTemplateExtension(node) {
let is = node.getAttribute('is');
if (is && templateExtensions[is]) {
@@ -78,8 +124,9 @@ function wrapTemplateExtension(node) {
t.parentNode.replaceChild(node, t);
node.appendChild(t);
while(t.attributes.length) {
node.setAttribute(t.attributes[0].name, t.attributes[0].value);
t.removeAttribute(t.attributes[0].name);
const {name} = t.attributes[0];
copyAttributeWithTemplateEventPolicy(node, t, name);
t.removeAttribute(name);
}
}
return node;