TL:DR doing whatever it took to get the big element on the page first

Get the big element on your page as quick as you can

That means get it there before as many other things happen as you can.

This means prioritising it in your loading and making sure the HTML renders as early as possible.

I found this way of thinking about it much easier then trying to optimise everything (faster server response, inline critical css, minimize non-critical JS, reduce image size etc. etc.)

This realisation led to the two things which helped our LCP the most in our Rails app.

a) Server side render any LCP element. Waiting for JS to run to render your element always means there’s an avoidable delay.

b) preload the image as early as possible for the LCP element.

TL:DR — install the heroku-builds plugin locally and cancel via their CLI


Were you a bit too eager with your kicking off a deploy? Did you suddenly remember that embarrassing console.log you don’t really want the world to see?

There’s currently no way of cancelling builds through the heroku UI on .

How to do it

Install the heroku-builds plugin and cancel via the CLI.

# from the terminalheroku plugins:install heroku-buildsheroku builds:cancel -a app-name

Resources that helped a lot is the bible for Core Web Vitals (CWV). There’s a ton of links and a lot of words but it is worth going through them all as best you can.

Addy Osmani is excellent and this video is probably the most useful thing you can watch around CWV.

Smashing Magazine’s An In-Depth Guide To Measuring Core Web Vitals by Barry Pollard is the most comprehensive view on CWV data and specifically the section on CRUX p75 helped me so much in understanding why the data moved liked it does.

This guide by Adam Ribaudo was so useful in setting…

Chrome UX Report in DataStudio

Field data.

Is powered by real user measurement aggregated from Chrome users who have opted-in to syncing their browsing history.

We set up reporting in DataStudio following these guides

Pros: Real user data. Lots of data. What Google is using. Source of truth. Compare to competitors. Shows historical data.
Cons: Only monthly data. Have to wait for second Tuesday of month for previous month’s data. Can’t see breakdown of what pages contribute to which scores. Only measures Chrome users.

PageSpeed Insights

Lab data and Field data (from Chrome UX Report) Link

Can show both field and lab data for a specific…

This is a collection of posts about how we passed Google’s Core Web Vitals.

check out how we’re doing today

  1. Go to
  2. Click on Show Origin Summary
  3. It should say “Over the previous 28-day collection period, the aggregate experience of all pages served from this origin passes the Core Web Vitals assessment” — if not we’ve screwed it up since writing this post!

Getting started

How we passed Core Web Vitals — our favourite resources

Things that helped us pass our Core Web Vitals assessment

Fixing things


How we identify our LCP (Largest Contentful Paint) element and get quick feedback

How we passed Core Web Vitals — LCP —…

We’re going to use the Javascript code snippet from and the chrome extension cjs which will inject that Javascript into the page.

Step 1. Add cjs chrome extension to your Chrome browser (any other JS injecting extensions will likely work fine. this is the one I use.)

Step 2. Navigate to the page you want to measure. Let’s do

Step 3. Copy the code snippet from, open the cjs Chrome Extension and paste it in and click save

image of the code snippet pasted into the cjs Chrome Extension

Step 4. Open up the Chrome devTools by…

Make them shitty. Yeah, just publish your first draft. If you’re reading this in hope of learning how to write a lot of blog posts you probably don’t have an audience who’ll be sad about you writing shitty words. I don’t even tag my posts on here so they shouldn’t show up in anyone’s feeds. I have no idea how anyone finds my blog posts to be honest. I publish them here so they’re easier to find for me later, as I haven’t managed to stick with any note-taking app as long as I’ve been writing here. And sometimes people…

TL:DR We moved the logic to show/hide the cookie banner from the client to the server to reduce CLS on every page.

This was the very first ticket we had incredibly high hopes for. Based on our lab data it was our main source of CLS. (this was a lie, lab data lies, a lot).

The problem

We show the cookie banner on every page to customers who have not dismissed the cookie banner.

We decide whether to hide/show it based on a cookie in the customer’s browser.

Move logic from client to server for initial check

Because we were doing this check client-side the banner appeared at the top of…

TL:DR — When moving to SSR we cached our prerendered HTML to hit our LCP target

Caching server-side rendered react

When we server-side render react we move the job of turning our JS React into HTML from the customer’s browser to our server.

This is faster to do on the server but it is still slow. Therefore we cache the outputted HTML so we don’t need to do the hard work every time.

How we do it

Rails makes fragment caching straightforward so we can wrap our react_component with a cache block.

<%= react_component "ListingCarousel", { listing: @listing } prerender: true %>

<% cache…

TL:DR — We stopped doing Server Side rendering (SSR) for bots as it was causing timeouts on our servers.

The presenting complaint

We started seeing lots of timeouts and an increase in our server response time anytime we did a “botify” crawl. Botify help us with our SEO and they send a bot to hit all our pages for reasons (I’m not close to this area :))

SSR was the culprit

We’d been doing these botify crawls for months and it had only started happening recently.

The culprit turned out to be the introduction of Server Side rendering of the Listing Carousel on PDP.

The solution — only SSR the carousel for humans!

We made a…

Kevin McCarthy

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store