Day 19: Performance Optimization

Today I implemented comprehensive performance optimizations for the Shika Digital website. The goal was to improve Core Web Vitals, reduce bundle sizes, and enhance the overall user experience through strategic optimizations across images, fonts, CSS, and loading strategies.

What Was Built

1. Image Optimization

Configuration:

  • Installed sharp for fast image processing
  • Configured Astro image service in astro.config.mjs to use Sharp (faster than default Squoosh service)

Image Updates:

  • Header Logo: Added loading="eager", decoding="sync", and fetchpriority="high" for above-the-fold optimization
  • Footer Logo: Added loading="lazy" and decoding="async" for below-the-fold content
  • About Page Image: Migrated from <picture> to Astro’s <Image> component with:
    • Automatic WebP format conversion
    • Quality optimization (85%)
    • Lazy loading
    • Async decoding

Benefits:

  • Automatic format conversion (WebP/AVIF)
  • Responsive image generation
  • Proper lazy loading attributes
  • Reduced image file sizes (30-50% reduction expected)

2. Font Loading Optimization

Enhancements:

  • Added dns-prefetch hints for Google Fonts domains (fonts.googleapis.com and fonts.gstatic.com)
  • Maintained preconnect for faster connection establishment
  • Kept display=swap to prevent FOIT (Flash of Invisible Text)

Implementation:

  • Updated both BaseLayout.astro and ResultsLayout.astro
  • Added resource hints for both font domains

Benefits:

  • Faster font loading through DNS prefetching
  • Reduced layout shift with display=swap

3. CSS Optimization

Tailwind CSS v4:

  • Automatic CSS purging is built into Tailwind v4 via Vite plugin
  • Configuration verified in tailwind.config.ts:
    • Content globs cover all template types (.astro, .tsx, .ts, .jsx, .js, .md, .mdx)
    • Global CSS imports Tailwind via @import "tailwindcss"

Build Optimizations:

  • CSS minification via esbuild
  • HTML compression enabled (compressHTML: true)
  • Stylesheets inlined for better performance (inlineStylesheets: 'always')

Benefits:

  • Unused CSS automatically removed during build
  • Smaller CSS bundle sizes
  • Faster page loads

4. Lazy Loading

Implementation:

  • Astro’s <Image> component automatically adds lazy loading for below-fold images
  • Header logo uses loading="eager" for above-the-fold content
  • Footer logo uses loading="lazy" for below-the-fold content
  • About page image uses lazy loading via Image component

Benefits:

  • Reduced initial page load time
  • Better Core Web Vitals (LCP, FCP)
  • Improved perceived performance

Configuration Files Updated

  1. astro.config.mjs

    • Added Sharp image service configuration
    • Image optimization settings
  2. src/components/Header.astro

    • Optimized logo loading attributes
  3. src/components/Footer.astro

    • Optimized logo loading attributes
  4. src/pages/about.astro

    • Migrated to Astro Image component
  5. src/layouts/BaseLayout.astro

    • Enhanced font loading with DNS prefetch
  6. src/layouts/ResultsLayout.astro

    • Enhanced font loading with DNS prefetch

Expected Performance Improvements

  • Image Loading: 30-50% reduction in image file sizes (WebP conversion)
  • Font Loading: Faster DNS resolution and connection establishment
  • CSS: Smaller bundle sizes due to automatic purging
  • Lazy Loading: Improved LCP and FCP scores

Testing

To verify optimizations:

  1. Build the site:

    bun run build
  2. Preview locally:

    bun run preview
  3. Run Lighthouse:

    bun run lighthouse:local

    Note: Requires the preview server to be running

  4. Check build output:

    • Verify optimized images in dist/client/_astro/
    • Check CSS bundle sizes
    • Verify font loading in Network tab

Notes

  • Google Fonts may still impact mobile performance scores (60-70%) as documented in the definition of done
  • Desktop performance should be 90%+ as expected
  • All optimizations are production-ready and will take effect on next deployment