The getElementsByTagName() method is a high-performance DOM selection interface that retrieves a collection of all elements in the document, or within a specific parent element, that possess a given HTML tag name. It is one of the oldest and most reliable methods in the Web API, providing a direct “hook” into the document’s structure based on element types like div, p, li, or script.
1. Syntax and Operation
The method can be called on the global document object to search the entire page, or on an individual element to search only within its descendants.
const collection = rootElement.getElementsByTagName(tagName);
Parameters
tagName (Required): A string representing the name of the elements to be matched.
- Using the special string “*” will return every single element within the search scope.
- In HTML documents, the search is case-insensitive (e.g., “div” and “DIV” are identical).
Return Value
- HTMLCollection: A live, ordered collection of elements. Because it is “live,” any changes made to the DOM (adding or removing tags of that type) are reflected in the collection automatically without needing to re-call the method.
2. Practical Examples
A. Global Selection (All Images)
This is a classic way to perform “audits” on a page, such as ensuring all images have alt text.
const allImages = document.getElementsByTagName('img');
for (let i = 0; i < allImages.length; i++) {
if (!allImages[i].hasAttribute('alt')) {
console.warn(`Image ${i} is missing an alt attribute!`);
allImages[i].style.border = "5px solid red";
}
}
B. Scoped Selection (List Items within a specific Nav)
Unlike getElementById, you can limit the scope of getElementsByTagName to a specific branch of the DOM tree.
const navMenu = document.getElementById('main-nav');
const navLinks = navMenu.getElementsByTagName('li');
console.log(`There are ${navLinks.length} items in the navigation.`);
3. The “Live” Collection Trap
One of the most significant architectural differences between getElementsByTagName and querySelectorAll is the “live” nature of the HTMLCollection.
If you are looping through a collection and adding or removing elements of the same tag type, you can accidentally create an infinite loop or skip elements because the collection’s length and indices change in real-time.
const paragraphs = document.getElementsByTagName('p');
// ❌ DANGEROUS: This loop will never end if you keep adding <p> tags
for (let i = 0; i < paragraphs.length; i++) {
const newP = document.createElement('p');
document.body.appendChild(newP);
}
4. Working with the Results
Since an HTMLCollection is array-like but not an actual Array, you cannot use methods like .map() or .filter() directly.
Conversion to Array
To use modern array features, use the spread operator or Array.from():
const divs = document.getElementsByTagName('div');
const divArray = [...divs];
divArray.forEach(div => console.log(div.className));
Accessing by Name or ID
A unique feature of HTMLCollection is that it allows you to access elements by their id or name attribute directly as a key on the collection object.
// HTML: <form><input name="email" ...></form>
const inputs = document.getElementsByTagName('input');
const emailField = inputs['email']; // Direct access
5. Advanced Use: The Universal Selector (*)
Searching with "*" is particularly useful for layout debugging or reset scripts where you need to touch every node within a container.
const container = document.getElementById('widget');
const allDescendants = container.getElementsByTagName('*');
console.log(`The widget contains ${allDescendants.length} total elements.`);
