innerHTML Application

innerHTML Application

Blank's blog: http://www.planabc.net/
The use of the innerHTML property is very popular because it provides an easy way to completely replace the contents of an HTML element. Another approach is to use the DOM Level 2 API (removeChild, createElement, appendChild). But it is obvious that using innerHTML to modify the DOM tree is a very easy and effective method. However, you need to be aware that innerHTML has some issues of its own:
    When an HTML string contains a script tag marked as defer (<script defer>…</script>), a script injection attack can occur on Internet Explorer if the innerHTML attribute is not handled properly. Setting innerHTML will destroy existing HTML elements that have event handlers registered, potentially causing memory leaks on some browsers.

There are a few other minor drawbacks that are worth mentioning:
    You can't get references to elements you've just created, you need to manually add code to get those references (using DOM APIs). You cannot set the innerHTML property on all HTML elements in all browsers (for example, Internet Explorer does not allow you to set the innerHTML property on table row elements).

I am more concerned about the security and memory issues associated with using the innerHTML property. Obviously, these are not new problems, and there are already smart people who have figured out ways around some of these issues.
Douglas Crockford wrote a cleanup function that is responsible for breaking some circular references caused by event handlers registered with HTML elements and allowing the garbage collector to free the memory associated with these HTML elements.
Removing script tags from an HTML string is not as easy as it seems. A regular expression may do what you expect, although it is hard to know whether all possibilities are covered. Here is my solution:
/<script[^>]*>[\S\s]*?<\/script[^>]*>/ig
Now, let's combine these two techniques into a single setInnerHTML function and bind the setInnerHTML function to YUI's YAHOO.util.Dom:
YAHOO.util.Dom.setInnerHTML = function (el, html) {
el = YAHOO.util.Dom.get(el);
if (!el || typeof html !== 'string') {
return null;
}
// Break the circular reference
(function (o) {
var a = o.attributes, i, l, n, c;
if (a) {
l = a.length;
for (i = 0; i < l; i = 1) {
n = a[i].name;
if (typeof o[n] === 'function') {
o[n] = null;
}
}
}
a = o.childNodes;
if (a) {
l = a.length;
for (i = 0; i < l; i = 1) {
c = o.childNodes[i];
// Clear child nodes
arguments.callee(c);
// Remove all listeners registered on the element through YUI's addListener
YAHOO.util.Event.purgeElement(c);
}
}
})(el);
// Remove the script from the HTML string and set the innerHTML property
el.innerHTML = html.replace(/<script[^>]*>[\S\s]*?<\/script[^>]*>/ig, "");
// Return a reference to the first child node
return el.firstChild;
};
If there is anything else this function should have or if I'm missing something in the regex, please let me know.
Obviously, there are many other ways to inject malicious code on a web page. The setInnerHTML function normalizes the execution behavior of <script> tags on all A-grade browsers only. If you plan to inject untrusted HTML code, make sure to filter it on the server first. There are many libraries that can do this.
Original article: The Problem With innerHTML by Julien Lecomte

<<:  How MySQL handles implicit default values

>>:  Dockerfile implementation code when starting two processes in a docker container

Recommend

10 Website Usability Tips Everyone Should Know

Let’s not waste any more time and get straight to...

Browser compatibility summary of common CSS properties (recommended)

Why do we need to summarize the browser compatibi...

CSS animation property usage and example code (transition/transform/animation)

During development, a good user interface will al...

Detailed introduction to deploying k8s cluster on centos7 system

Table of contents 1 Version and planning 1.1 Vers...

Nginx reverse proxy to go-fastdfs case explanation

background go-fastdfs is a distributed file syste...

Testing of hyperlink opening target

The target attribute of a link determines where th...

Vue implements Tab tab switching

This article example shares the specific code of ...

An example of refactoring a jigsaw puzzle game using vue3

Preface It took two days to reconstruct a puzzle ...

In-depth study of MySQL multi-version concurrency control MVCC

MVCC MVCC (Multi-Version Concurrency Control) is ...

React Diff Principle In-depth Analysis

Table of contents Diffing Algorithm Layer-by-laye...

Detailed explanation of using JavaScript WeakMap

A WeakMap object is a collection of key/value pai...

Meta declaration annotation steps

Meta declaration annotation steps: 1. Sort out all...