XPath in Action
While researching XML, I encountered an article titled "Using XPath in 2023" that provides a concise overview of XPath and introduces an elegant wrapper for document.evaluate
, streamlining its implementation.
function* xpath(...args) { let path, root = document; if (args.length > 1) [root, path] = args; else [path] = args; const nodeIterator = document.evaluate( path, root, null, XPathResult.UNORDERED_NODE_ITERATOR_TYPE, null, ); for ( let node = nodeIterator.iterateNext(); node != null; node = nodeIterator.iterateNext() ) { yield node; } }
TypeScript types:
function xpath(path: string): Iterable<Node>; function xpath(root: Element, path: string): Iterable<Node>;
Example usage:
xpath('//body').next().value()
Potential alternative using plain document.evaluate
:
function xpath(xpathExpression) { const result = document.evaluate( xpathExpression, document, null, XPathResult.ANY_TYPE, null ); switch (result.resultType) { case XPathResult.UNORDERED_NODE_ITERATOR_TYPE: case XPathResult.ORDERED_NODE_ITERATOR_TYPE: const nodes = []; let node; while ((node = result.iterateNext())) { nodes.push(node); } return nodes; case XPathResult.FIRST_ORDERED_NODE_TYPE: case XPathResult.ANY_UNORDERED_NODE_TYPE: return result.singleNodeValue; case XPathResult.NUMBER_TYPE: return result.numberValue; case XPathResult.STRING_TYPE: return result.stringValue; case XPathResult.BOOLEAN_TYPE: return result.booleanValue; default: return null; } }
Example usage:
xpath('//body')[0]
Exercising XSLT
It turns out applying XSLT imperatively using the XSLTProcessor interface
isn't too difficult at all, and doing so enables the manipulation of XML documents using basic Javascript. To start, setup a new DOM and XSLT processor.
const domParser = new DOMParser(); const xsltProcessor = new XSLTProcessor();
Fetch the XSLT file and parse the response to a string.
const xslResponse = await fetch( "2025/01/exercising-xslt/exercising-xslt.xsl" ); const xslText = await xslResponse.text(); const xslStylesheet = domParser.parseFromString( xslText, "application/xml" ); xsltProcessor.importStylesheet(xslStylesheet);
After xSLTProcessor
has imported xslStylesheet
, it allows modifiying <xsl:param>
values, and executing transformations.
<?xml version="1.0" encoding="utf-8"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output doctype-public="" doctype-system="" indent="yes" method="html" /> <xsl:template match="/"> <xsl:for-each select="/x-ml/x-ml-item"> <x-ml-item-title> <link href="components/XMLItemTitle/XMLItemTitle.css" rel="stylesheet" /> <h3> <a> <xsl:attribute name="href"> <xsl:value-of select="normalize-space(x-ml-item-link)" /> </xsl:attribute> <xsl:value-of select="normalize-space(x-ml-item-title)" /> </a> </h3> </x-ml-item-title> </xsl:for-each> </xsl:template> </xsl:stylesheet>
An XML document is then loaded to a string. Here we'll utilize the <x-ml-item-title>
tag from this <x-ml-item>
source itself.
const xmlResponse = await fetch("2025/01/exercising-xslt/index.xml"); const xmlText = await xmlResponse.text(); const xmlDoc = domParser.parseFromString(xmlText, "application/xml");
Transform the node source to a document fragment and append the result to the target in the DOM.
const result = xsltProcessor.transformToFragment(xmlDoc, document); document.getElementById("exercising-xslt-target").append(result);
<div id="exercising-xslt-target"></div>
If JavaScript is enabled, the <x-ml-item-title>
should be rendered again, above the example HTML showing the id exercising-xslt-target
.
Aurora Borealis
Regular photos can be shared as well; for example, on New Year's Day, we were delighted to see the northern lights.

Why not use XML?
Why not use XML? Start it out like this:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?> <?xml-stylesheet href="components/index.xsl" type="text/xsl"?>
Notice the reference to the .xsl file? It is XSLT, which is most often used to convert data between different XML schemas or to convert XML data into web pages or PDF documents.