Fix LCP Issues on Graphcms (Loading Speed) | OpsBlu Docs

Fix LCP Issues on Graphcms (Loading Speed)

Improve GraphCMS LCP by using built-in image resizing, optimizing GraphQL query depth, and enabling ISR on your frontend framework.

General Guide: See Global LCP Guide for universal concepts and fixes.

What is LCP?

Largest Contentful Paint measures when the largest content element becomes visible. Google recommends LCP under 2.5 seconds. Hygraph (formerly GraphCMS) is a headless GraphQL CMS, so LCP depends on your frontend framework's rendering strategy, GraphQL query efficiency, and Hygraph's built-in image pipeline.

Hygraph-Specific LCP Causes

  • Client-side GraphQL fetching -- browser-side queries add JS parse + network round-trip + render time before LCP
  • Unoptimized asset URLs -- Hygraph serves media through its CDN but default URLs deliver original-size assets
  • Deep GraphQL queries -- nested queries fetching relations, rich text ASTs, and multiple asset references create large payloads
  • Frontend hydration delay -- React/Next.js/Gatsby SPA hydration blocks content rendering
  • Rich text AST rendering -- Hygraph's rich text field returns an AST that must be parsed client-side

Fixes

1. Use SSG/ISR with Hygraph

// Next.js with Hygraph -- getStaticProps eliminates client waterfall
const HYGRAPH_ENDPOINT = process.env.HYGRAPH_ENDPOINT;

export async function getStaticProps() {
  const { data } = await fetch(HYGRAPH_ENDPOINT, {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({
      query: `{
        page(where: { slug: "home" }) {
          title
          heroImage { url width height }
          seo { title description }
        }
      }`
    }),
  }).then(r => r.json());

  return { props: { page: data.page }, revalidate: 60 };
}

2. Use Hygraph Image Transformations

Hygraph assets support URL-based transforms via its CDN:

// Hygraph image optimization helper
function optimizeHygraphImage(url, { width = 800, quality = 80 } = {}) {
  if (!url) return '';
  // Hygraph uses a transformation proxy
  return `${url}?width=${width}&quality=${quality}&format=auto`;
}

function HeroImage({ image }) {
  return (
    <img
      src={optimizeHygraphImage(image.url, { width: 1920 })}
      srcSet={`
        ${optimizeHygraphImage(image.url, { width: 640 })} 640w,
        ${optimizeHygraphImage(image.url, { width: 1024 })} 1024w,
        ${optimizeHygraphImage(image.url, { width: 1920 })} 1920w
      `}
      sizes="100vw"
      width={image.width}
      height={image.height}
      alt={image.alt || ''}
      loading="eager"
      fetchPriority="high"
    />
  );
}

3. Optimize GraphQL Queries

Request only the fields you need:

# BAD: Over-fetching with deep nesting
query { pages { title body heroImage { url } author { name avatar { url } posts { title } } } }

# GOOD: Minimal fields, no unnecessary relations
query HomePage {
  page(where: { slug: "home" }) {
    title
    heroImage { url width height }
    excerpt
  }
}

4. Preload LCP Image

import Head from 'next/head';

function PageHead({ heroImage }) {
  return (
    <Head>
      <link rel="preconnect" href="https://media.graphassets.com" />
      {heroImage && (
        <link rel="preload" as="image"
              href={optimizeHygraphImage(heroImage.url, { width: 1920 })} />
      )}
    </Head>
  );
}

5. Cache GraphQL Responses

// Edge cache for Hygraph API responses
const cache = new Map();

async function cachedQuery(query, variables = {}) {
  const key = JSON.stringify({ query, variables });
  if (cache.has(key)) return cache.get(key);

  const result = await fetch(HYGRAPH_ENDPOINT, {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({ query, variables }),
  }).then(r => r.json());

  cache.set(key, result);
  setTimeout(() => cache.delete(key), 300000); // 5 min TTL
  return result;
}

Measuring LCP on Hygraph

  1. Chrome DevTools Network tab -- filter for graphassets.com requests to see asset sizes and CDN response times
  2. Compare SSG vs CSR -- static generation should be 2-3x faster for LCP
  3. Hygraph Dashboard -- check API analytics for query performance
  4. Test page types: landing pages (hero images), blog listings (thumbnails), content pages (rich text)

Analytics Script Impact

Hygraph is headless -- analytics depends on your frontend. Use next/script with strategy="afterInteractive" or equivalent deferred loading in your framework.