Resource hints provide a way to optimize the performance of your web page on the client side. As the name suggests, they provide the browser with hints about how the user will likely request resources such as fonts, images, and scripts while interacting with your site. By predicting the user’s expected behavior, the browser can prefetch, prerender, or preload resources in advance.
Types of resource hints
Technically speaking, resource hints are different values for the
rel attribute of the
<link> HTML element used for external resources. The user’s browser will use these values to prioritize resource links instead of treating them as if they’re of equal importance.
There are four types of resource hints, as specified by W3C:
Besides these four resource hints, there’s a fifth value of the
rel attribute that’s very similar to resource hints:
preload, which has its own W3C specs. It’s the upgraded version of the deprecated subresource prefetching feature that was available in Chrome and Opera for a while.
preload is not a resource hint (recommendation) but a mandatory directive that the browser must follow since it’s also a value for the
rel attribute, we’ll discuss it in this article too.
dns-prefetch is the most lightweight resource hint that allows you to prerequest the smallest portion of a remote resource: its numeric IP address.
dns-prefetch resource hint tells the browser to conduct a DNS lookup for the resource while the user keeps browsing the page. During the DNS lookup, the user’s browser connects to the domain name server of the resource and translates the domain name (e.g.,
http://www.example.com) into a numeric IP address. Since the browser performs this task in the background, the user won’t have to wait for the DNS resolution when they need the resource.
To use the DNS prefetch feature, add the
rel="dns-prefetch" attribute to the
<link rel="dns-prefetch" href="https://example.com">
<link> tag usually goes into the
<head> section of the document, resource hints are body-ok, so you can also use them in the
<body> section if you want.
dns-prefetch resolves only the domain name but doesn’t preconnect to the remote server or preload the resource, it requires little bandwidth. However, it can significantly improve DNS latency — the total request-response time between the DNS server and the user’s browser.
Latency can be high for a variety of reasons, such as when the DNS server is located far from the user’s machine or when many users attempt to access the server at the same time. So if you know that the domain where the resource is stored has high latency, it may be worth using DNS prefetch.
You’ll only need to use
dns-prefetch when the resource is hosted on a different domain, since you don’t need to resolve your own domain name.
dns-prefetch is typically recommended when prefetching domain names for:
- Web fonts, such as Google Fonts
- Analytics scripts
- Scripts coming from third-party resources
- Social media widgets or any widget that loads third-party content via the
- Resources hosted on a CDN
You should also consider DNS prefetch when the same domain is referenced on your site multiple times since it’s very likely that your user will request at least one resource from that domain.
preconnect is a resource hint that prerequests a somewhat larger portion of the remote resource.
Besides translating the domain name into a numeric IP address like DNS prefetch, it also preconnects to the server where the resource is hosted. This early connection includes the DNS lookup and TCP handshake in the case of an HTTP connection, plus the TLS negotiation in the case of a secure HTTPS connection.
preconnect, you need to use the
rel attribute together with the
<link rel="preconnect" href="https://example.com"> <link rel="preconnect" href="https://cdn.example.com" crossorigin>
To handle CORS requests, you can also add the
crossorigin attribute to the
<link> tag. Without a specified value, the
crossorigin attribute will prevent the browser from exchanging user credentials via cookies with the other-origin server (it’s identical to
For the most part, you can use the
preconnect resource hint for the same things as
dns-prefetch. You should choose it if you’re fairly sure the user will really request the script, font, stylesheet, or other resource from the third-party server.
preconnect exchanges more data, it also needs more bandwidth. So you have to be more careful with it to avoid slowing down the page and wasting your user’s bandwidth with redundant data.
The W3C specification also recommends preconnect for two specific use cases:
- Dynamic URL request
- Anonymizing redirects
You can use
preconnect for dynamic URL requests when the final URL will be constructed later. This way, you can speed up the resource fetching process because the browser will have already been connected to the third-party server by the time the dynamic URL is created.
You can also use
preconnect to secure and anonymize redirects. If you preconnect to the server ahead of time, you can remove sensitive data such as the user ID or purchase details from referrer links.
This is important when you redirect users to third-party sites, such as advertisers’ websites. Even though you might not want to remove everything from the referrer link, advertisers still shouldn’t know user data that’s related only to your site but not to theirs.
prefetch (link prefetch)
prefetch resource hint goes a step further: in addition to resolving the domain name and preconnecting to the remote server (if it’s necessary), it also prefetches the resource and stores it in the browser’s cache.
However, there’s an important difference between prefetch and
preconnect resource hints. While DNS prefetch and preconnect provide the browser with hints related to resources that will be loaded within the same page, prefetch focuses on resources that will be required by the next page/tab/navigation the user might visit after the current one.
To add the prefetch hint to a resource, you need to use the
rel attribute with the
<link rel="prefetch" href="https://example.com/video.mp4" as="video" crossorigin> <link rel="prefetch" href="next-page.html" as="document">
You can use
prefetch together with two optional parameters: the previously mentioned
crossorigin, which lets you define how to handle CORS-requests, and
as, which allows you to specify the type of the prefetched resource.
prefetch resource hint is mainly recommended for interactive applications when you have a high level of app-specific knowledge. You should only use this resource hint if you can predict with a high probability where the user will go next. Paginated content, image galleries, and step-driven flows are examples of when it can be reasonable to use prefetch.
The specs also mention that you can implement a reactive prefetch strategy by dynamically adding
prefetch to resources based on events generated by either the user or the application, such as clicks. When the event fires, you can start prefetching resources immediately when the navigation request/intent takes place so that they will be loaded sooner.
preconnect are only recommended for third-party resources,
prefetch not only connects to a server but also downloads the resource, so you can use it for resources stored on your own domain too.
If you want to prefetch resources on the current page instead of the next one, you’ll need to use the preload directive instead of prefetch (more on this later).
prerender resource hint also focuses on the next page the user will likely visit, similar to
prerender takes an additional step and also executes the resource in addition to prefetching (requesting and downloading) it.
prerender completely prepares the next page for view, including prefetching and executing all the subresources, such as images, videos, and scripts. With
prerender, you always fetch the next page as an HTML response, meaning a complete page. If you want to fetch a subsequent resource as another content type, such as an image or video, you should use the
prefetch hint instead.
To prerender the next page in the expected user flow, use the
rel attribute together with the
<link rel="prerender" href="next-page.html">
prerender is recommended for interactive applications in which user flows can be calculated with high probability. By prerendering the next page, you can implement an instant navigation experience within your application.
prerender doesn’t only prefetch the subsequent resources but also executes them, you have to be even more careful with it. You can waste a significant amount of bandwidth by making a wrong prediction.
Also note that browser support for
prerender is not very good at the moment; Firefox and Safari don’t support it at all. From a support point of view, if you want to give hints about resources on the next page, it makes more sense to use
prefetch since it comes with better browser support.
preload (not a resource hint)
As mentioned before,
preload is not a resource hint but a directive that has its own W3C specification. The main difference between
preload and resource hints is that hints are only recommendations with low priority, so the user’s browser only implements them if it has idle time.
preload, on the other hand, has a high priority — it’s a mandatory fetch for resources needed on the current page.
When it comes to functionality,
preload is similar to the
prefetch resource hint.
preload also requests and downloads the resource without executing it, but on the current page instead of the subsequent one. Plus, it’s obligatory for the browser as opposed to the optional
To preload a resource on the same page, add the
preload value to the
<link rel="preload" href="style.css" as="style"> <link rel="preload" href="https://example.com/font.woff2" as="font" crossorigin type="font/woff2">
prefetch, you can use
preload together with the optional
as attribute to specify the type of the preloaded resource. Note that if you preload a CORS-enabled resource from a third-party domain, you’ll also need to use the
The most important thing to remember is that the
preload directive is not the same thing as the browser’s built-in preloader. While the browser’s preloader only fetches resources defined within the HTML document, the
In addition, if you preload resources with the
preload directive, the fetching process won’t be stopped by render-blocking resources, which happens to resources being fetched by the browser’s preloader. So, you can use
preload to set resource priority based on the specific needs of your application.
One common use case for
preload is the early fetching of critical resources. The specs detail how to prefetch important resources while the main document parser is being stopped by a render-blocking script. This is possible because
preload only downloads the resource but doesn’t execute it.
All in all, you need to treat
preload different than resource hints. Since it’s mandatory, you give the user’s browser not a recommendation but a command. You can use it to improve performance by optimizing the delivery order of resources on the current page. MDN published some useful tips (and code examples) about how to properly preload resources.
The trade-off for each resource hint is essentially the same: improving performance versus risking bandwidth waste. If you use resource hints well, you can significantly improve page load times. However, it’s not always easy to find out which resource hint to use and when.
If you make the wrong predictions about the user’s likely behavior, on the other hand, their browser will request unnecessary resources. This will make your site resource-heavy, increase latency, and cost the user extra bandwidth — which is especially bad if they access your site on a mobile device and/or metered data connection.
You also need to consider browser support. Currently,
preconnect has better support than
prefetch has better support than
prerender. Since the mandatory
preload directive also has somewhat patchy support, you shouldn’t rely on it for functionality (meaning your scripts should also properly load on browsers that don’t support it); only use it for performance optimization on browsers that do support it.
Debugging code is always a tedious task. But the more you understand your errors the easier it is to fix them.