Devanshu
Devanshu

Reputation: 933

querySelector() return static node list or live node list

querySelectorALL() as specified by MDN donot support live nodes and return only static nodes.MDN querySelectorALL

Can querySelector() support live node MDN donot specified anything about itMDN querySelector

Upvotes: 5

Views: 5482

Answers (1)

T.J. Crowder
T.J. Crowder

Reputation: 1073978

querySelectorAll returns a static list (specifically, a static NodeList), whereas (say) getElementsByTagName returns a live list (specifically, a live HTMLCollection).¹ It's the list that's static or live, not the nodes/elements on the list.

An element returned by querySelector is the element in the DOM (as are the elements in the list from querySelectorAll). They're "live," not snapshots or clones — e.g., if they're changed, you can see those changes via the reference you have from querySelector/querySelectorAll.

Example:

const element = document.querySelector("input");
const staticList = document.querySelectorAll("input");
const liveList = document.getElementsByTagName("input");

element.addEventListener("input", () => {
  // Both of these are references to the live node in the DOM
  console.log(element.value);
  console.log(staticList[0].value);
});

document.getElementById("del").addEventListener("click", () => {
  // Removing the input
  document.body.removeChild(document.querySelector("input"));
  // It's still on the static list
  console.log("staticList.length = " + staticList.length); // 1
  // It's off the live list now
  console.log("liveList.length = " + liveList.length); // 0
  // Since we still have a reference to it, we can still see it's value
  console.log(element.value); // "what you typed"
});
Type something: <input type="text">
<br>then click this: <button id="del" type="button">Delete</button>


¹ HTMLCollection instances are always live.² NodeList instances may be either live or static (snapshots). The NodeList you get from querySelectorAll is static, but the NodeList you get from (say) the childNodes property of an Element is live. Here's an example of that:

const container = document.getElementById("container");

console.log(`Get a static list of the container's elements`);
const list = container.querySelectorAll("*");
console.log(`It's a NodeList:`);
console.log(list.constructor.name); // "NodeList"
console.log(`With one element in it:`);
console.log(list.length); // 1

console.log(`Get a live list of children`);
const children = container.childNodes;
console.log(`It's also a NodeList:`);
console.log(children.constructor.name); // "NodeList"
console.log(`With one element in it (so far):`);
console.log(children.length); // 1

console.log(`Add a new child`);
const p = document.createElement("p");
container.appendChild(p);

console.log(`The static list still has one element:`);
console.log(list.length); // 1
console.log(`But the live list has two:`);
console.log(children.length); // 2
.as-console-wrapper {
    max-height: 100% !important;
}
<div id="container"><p></p></div>

² "HTMLCollection instances are always live." - Actually, the specification doesn't say that. I base that statement on two things:

  1. MDN says that (but MDN, while very high-quality, isn't always 100% correct).
  2. All the current HTMLCollection instances the specification describes are live, and no new HTMLCollection instances will be added in the future; it's a legacy type. If any new collections are added, they'll be defined either as Sequence<T> instances or as NodeList instances.

Upvotes: 5

Related Questions