Prefetch, preload, prerender, etc

Edit Page

Woow: DNS Prefetch, Preconnect, Preload, HTTP/2 Server Push, Prefetch and Prerender.

All those technologies can all be collectively called Resource Hints and the last two; prefetch & prerender, can also recognized as prebrowsing; coined from term predictive browsing.

===

Resource hints can be divided into exactly 6 types. Note that the only one not implemented is HTTP/2 Server Push as it is as of time of writing, still unsupported by major web servers, apache and nginx.

To recap, techniques are:

  1. DNS Prefetching / current page (dns-prefetch)
  2. Domain Preconnect / current page (preconnect)
  3. Resource Preload / current page (preload now supersedes subresource that is depreciated)
  4. HTTP/2 Server Push / current page
  5. Link prefetching / next page (prefetch)
  6. Prerendering / next page

As most of there technologies should be somehow aware of the real site content and/or user behavior, the best way to trigger them is from Wordpress, not from server side.

There are couple of optimizations that can be achieved most easily directly from server, notably from Google Pagespeed module, and you should use these immediately.

I expect a lot of plugins for these purpose in the future, but for now, there are already couple of good ones in existence.

DNS prefetching

DNS resolution speed can be improved with DNS Prefetching, a technique adopted by most modern browsers.

There a couple of domains obvious to prefetch DNS and those include both your specific domain CDN and any public CDN’s you probably use (Google for example).

<link rel="dns-prefetch" href="//fonts.googleapis.com"> <!-- Google Fonts -->
<link rel="dns-prefetch" href="//www.google-analytics.com"> <!-- Google Analytics -->
<link rel="dns-prefetch" href="//www.googletagmanager.com"> <!-- Google Tag Manager -->

I read somewhere that it is not recommended to use more than 5 URLs for DNS prefetching, but that’s simply not true.

Good candidates for DNS prefetching are:

  • Resources on different domains hidden behind 301 redirects
  • Resources accessed from JavaScript code
  • Resources for analytics which usually come from different domains, but this will browser figure out alone, without help.

Pagespeed filter insert_dns_prefetch puts <link rel="dns-prefetch"> tags in page head and it does it automaticly for all domains present in the document.

Good article on this theme.

Preconnect

Preconnect is used to indicate origins for resources on current page. We use preconnect to pre-open a new TCP connection.

It is perfect when you are not sure of a full resource URL, but you surely know the origin domain from which the resources are going to be fetched.

We can call it extended DNS prefetch, as it very similar but so much powerful as it initiates a complete early connection, which includes the DNS lookup, TCP handshake, and optional TLS negotiation.

Usage example:

<link href='https://fonts.gstatic.com' rel='preconnect' crossorigin>
<link href='https://fonts.googleapis.com/css?family=Roboto+Slab:700|Open+Sans' rel='stylesheet'>

Application can also invoke preconnects dynamicly, with JavaScript.

Preload

The reference material is on link type preload and on HTTP/2 Server Push is this document: Preload.

If you use this technique, preload only the most important resources and make sure they are cacheable by the browser. Images, CSS, JavaScript, and font files are good candidates for preload, but HTML responses are not since they aren’t cacheable.

Unlike DNS prefetching, resource prefetching is a more expensive operation; be mindful of how and when to use it.

<link rel='preload' href='critical.js'>
<link rel='preload' href='main.css'>

Preload is a mandatory and high-priority fetch for a resource that is necessary for the current navigation.

Note: Preloading was in the past known as Subresource prefetching. Old syntax rel=subresource is deprecated as of january 2016 and is superseded with the new, rel=preload syntax.

HTTP/2 Server Push

Server push is similar to Preloading, but it eliminates the request roundtrip between client and server for the declared preload link resource.

Not sure how it’s working, but I expect we just have to enable server support for this option to work out of the box?

Prefetch

Prefetch is an optional browser mechanism, lowest priority fetch for a resource that might be used by a subsequent navigation. In another words, it usualy utilizes browser idle time to download resources that the user might visit in the near future.

Also known as link prefetching and is already adopted by most major browsers.

<link rel='prefetch' href='secondary.js'>

Prefetching does work across domains, including pulling cookies from those sites.

Prerendering

It is similar to prefetch but now the whole document with all its resources is fetched and rendered in background.

So we must very carefully to try to predict users actions and optimistically load resources ahead of time for better performance.

Luckily, we can trigger prerendering by inserting a link element with a rel='prerender', for example:

<link rel='prerender' href='http://www.mypage.com'>

Luckily, we can inject prerendering hints at runtime, based on user action, which is probably the most realistic usage scenario.

var hint =document.createElement("link")
hint.setAttribute("rel","prerender")
hint.setAttribute("href","next-page.html")
document.getElementsByTagName("head")[0].appendChild(hint)

For example, if a user hovers over an element long enough, we can start prerendering. Great usage of similar idea is a JS plugin that prerenders pages on link hovers - smoothState.js. It already has proper Wordpress integrations implemented here

Prerendering is the most costly of all techniques and misusing it can cause major bandwidth waste, especially on mobile devices.

We can test the prerendering with this simple tool.

Notes on prerendering

  • If you try to test for prerendering, please note that Chrome doesn’t use it when Developer Tools is open. You can see if a page is being prerendered at chrome://net-internals/#prerender.

  • Google Analytics supports this and it won’t count visits or any other stat coming from a prerendered page.



Domains:

<link rel="dns-prefetch" href="//cdn.save-up.at">
<link rel="preconnect" href="//cdn.save-up.at" crossorigin>

Prefetch is for next navigation, but subresource prefetch is for current:

<link rel="prefetch" href="/library.js" as="script">

The prerender link relation type is used to identify a resource that might be required by the next navigation:

<link rel="prerender" href="//example.com/next-page.html">

Hint probability?

In addition to specifying the hint type, the application may indicate the expected probability that the specified resource hint will be used.

<link rel="dns-prefetch" href="//widget.com" pr="0.75">
<link rel="preconnect" href="//cdn.example.com" pr="0.42">
<link rel="prefetch" href="//example.com/next-page.html" pr="0.75">
<link rel="prerender" href="//example.com/thankyou.html" pr="0.25">

Details on prerendering

The following reference document on Chrome Prerendering gives us explanation and an answer to very important questions.

Does a prerender follow 301 redirect? Yes, by default; but you can stop that on request.

If the server sends a redirect response for a subresource with a “Follow-Only-When-Prerender-Shown: 1” header, Chrome will hold off on following the redirect and on fetching the respective subresource until the prerender is shown to the user.

Are cookies set? They are set only if prerendered page is displayed.

Cookies made by the prerendered page are not visible to other tabs until the user has activated the page. If the user never uses a prerendered page, cookies will just disappear.

We can check the current prerender status on chrome://net-internals/#prerender page.

As for Firefox, they use term prefetch, not prerender. Important document from 2010 on HTML5 Link Prefetching explains couple of important notes:

  • Prefetching does work across domains, including pulling cookies from those sites.
  • Prefetching can throw off website statistics as the user doesn’t technically visit a given page.

What’s in it for us?

  1. DNS-prefetch our CDN, affiliate networks and public CDN’s

    I did notice that Pagespeed is not adding a CDN subdomain here, and it should do it.

  2. Preconnect to our CDN, for sure.

  3. Prefetch domain of our affiliate link on a page On shop pages, do it like this:

    • Based on the fact that prefetching does work across domains, including pulling cookies from those sites.

      Our /coupon/123 is a 301 redirect and it is noindex. On Shop page we link to /coupon/123 as nofollow. It is safe to prerender /coupon/123 and it will work. Index will not go there but browser will follow redirects and prerender valid page. Cookies would not be set, until user really visits that page.

      Please note that, if we have page-per-view links or tracking pixels, those statistics will be really off because of this.

    You can always prerender home page as it will probably at some point go there.

  4. Prerender some our page that will be next shop page: no idea what will be this? magazin page: home, menu items and/or then first shop that is displayed. We can prefetch & prerender all the pages from main menu links.

For now, only dns-prefech and preconnect are sure. The first one is easily done with pagespeed.


There is an perfect JS library schliflo/BoostR to help about dynamically using preconnect, preload and prerender.


Total explanation! Very important comment: Comments on the A List Apart Article One Step Ahead: Improving Performance with Prebrowsing

Prefetch is meant to be used for resources required by the next navigation, which means that they will be downloaded with low priority or not at all, and always after all other resources have finished loading. As a result, prefetch should not be used for hinting critical resources on the current page.

This is also the reason why Chrome introduced rel=subresource, for current page, but subresource has its own set of problems. so I wouldn’t recommend that either.

In short: use dns-prefetch for current and next pages; use prefetch and prerender to fetch resources for next navigation.


Wordpress plugins

  • WordPress Instant Articles is for various tags, but I’m using it only for inserting dns-prefetch for our CDN as for some unknown reason, pagespeed doesn’t do that properly. But, as Chrome will conclude on it’s own already, don’t use this plugin anymore.

  • DNS Prefetch is the simplest way to add dns-prefetch tags.

  • Prefetch can be simply applied in Wordpress with the help of a HTTP/2 Server Push plugin, but the name of the plugin is so misleading, that probably the quality of code is also questionable.

  • Behavior Flow is for basic prerendering, in a way that you can select prerender page for any existing page; nothing special and nothing automatic.


Resource Hints - What is Preload, Prefetch, and Preconnect? What Is the Preload Directive? - KeyCDN Support


Some Wordpress support?

#34292 (Support for DNS Prefetching & Prerender)


How I Sped Up My Site 68.35% With One Line of Code - iPullRank

date 01. Jan 0001 | modified 28. May 2021
filename: Pagespeed - Prefetch preload prerender