A page of web components shows nothing until its scripts have run. A prerendered page has the shadow tree of every component in its markup, as a declarative shadow root, so the browser draws the page as soon as the markup arrives. When the scripts arrive, each component takes over its own tree.
scripts/prerender.mjs makes such a page. It opens a page in a headless Chrome and writes it
back out with the browser's own getHTML. It works for a page with open shadow roots, whatever
it was built with.
The script is in the npm package, as the command baredom-prerender.
Serve the page, then:
node scripts/prerender.mjs http://localhost:8000/page.html page.prerendered.html
With the package installed, the same is:
npx baredom-prerender http://localhost:8000/page.html page.prerendered.html
Give more pairs of a URL and a file to write more pages. One browser opens them all, which is much quicker than a run for each page:
node scripts/prerender.mjs http://localhost:8000/ index.html http://localhost:8000/about/ about/index.html
Four pages are open at once, each in a tab of its own, or fewer on a machine with fewer
processors. --tabs says how many:
node scripts/prerender.mjs --tabs 8 http://localhost:8000/ index.html ...
Each page is written when it is done, so the pages are written in the order in which they are done, not in the order they were given. Each line that the script prints names its file.
More tabs help as far as the machine does. On a machine with ten processors, 120 pages from a plain file server took 13 seconds with one tab, 6.9 with four and 5.6 with eight. 351 pages of a blog took 38 seconds with one tab and 18 with four, the work of the blog's own server included. More tabs than processors do not help.
A page that fails stops the run: no tab takes another page, the pages that are open are written, and the script ends with the first error and says how many more failed. The pages written before it stay written.
It needs Node 22 or later, and Chrome. Set CHROME_PATH when Chrome is not found, and
CHROME_FLAGS for more flags, such as --no-sandbox in a container.
Write the output beside the page it was made from, so the relative URLs in it still resolve.
The script waits until every custom element on the page is defined, and then for two frames.
A page that loads more after that puts data-loading on its html element and removes it when
it is ready. The script waits for that too.
It then waits until every image has loaded or failed, in the page and in every shadow tree. An
image that the browser loads lazily is loaded for this, and is lazy again in what is written.
So an x-image is written as loaded, and the same page gives the same file each time. The script
stops and names an image that never finishes.
The directory of an output file is made when it is not there.
With --static before the URL, the output has no script and no noscript element, and its
html element has data-static. The page can use that attribute in its style to hide what
needs a script. bare-html/mirror.html does.
x-image whose picture
the page has already is loaded at once, with no shimmer and no fade.sync. It is not made again.list.append(row), shows every row twice. A script must bring the page to its state and add
nothing. BareMirror's sync does that: it finds the keyed rows that are there and makes only
the ones that are missing.x-table-row and x-tab included. The script stops and names an
element that is never defined.autofocus takes it. One page with an x-otp-input and an input that both have
autofocus was written the same with the focus as without it.Can you improve this documentation?Edit on GitHub
cljdoc builds & hosts documentation for Clojure/Script libraries
| Ctrl+k | Jump to recent docs |
| ← | Move to previous article |
| → | Move to next article |
| Ctrl+/ | Jump to the search field |