core-web-vitals — community core-web-vitals, seucampusmate-web, community, ide skills, Claude Code, Cursor, Windsurf

v1.0
GitHub

About this Skill

Perfect for Web Optimization Agents needing to analyze and improve Core Web Vitals metrics like LCP, INP, and CLS. Web companion for Southeast University students. Academic tools, campus info, and student resources in one place.

sayeedjoy sayeedjoy
[0]
[0]
Updated: 3/5/2026

Agent Capability Analysis

The core-web-vitals skill by sayeedjoy is an open-source community AI agent skill for Claude Code and other IDE workflows, helping agents execute tasks with better context, repeatability, and domain-specific guidance.

Ideal Agent Persona

Perfect for Web Optimization Agents needing to analyze and improve Core Web Vitals metrics like LCP, INP, and CLS.

Core Value

Empowers agents to optimize web pages for better Google Search ranking and user experience by targeting the 75th percentile of page loads, leveraging metrics such as Largest Contentful Paint (LCP), Input Delay (INP), and Cumulative Layout Shift (CLS) to ensure fast loading times, interactivity, and visual stability.

Capabilities Granted for core-web-vitals

Analyzing LCP metrics to reduce loading times below 2.5s
Optimizing INP for faster interactivity with input delays under 200ms
Debugging CLS issues to maintain visual stability with scores under 0.1

! Prerequisites & Limits

  • Requires understanding of Google's Core Web Vitals metrics
  • Optimization targets are based on the 75th percentile of page loads
Labs Demo

Browser Sandbox Environment

⚡️ Ready to unleash?

Experience this Agent in a zero-setup browser environment powered by WebContainers. No installation required.

Boot Container Sandbox

core-web-vitals

Install core-web-vitals, an AI agent skill for AI agent workflows and automation. Works with Claude Code, Cursor, and Windsurf with one-command setup.

SKILL.md
Readonly

Core Web Vitals optimization

Targeted optimization for the three Core Web Vitals metrics that affect Google Search ranking and user experience.

The three metrics

MetricMeasuresGoodNeeds workPoor
LCPLoading≤ 2.5s2.5s – 4s> 4s
INPInteractivity≤ 200ms200ms – 500ms> 500ms
CLSVisual Stability≤ 0.10.1 – 0.25> 0.25

Google measures at the 75th percentile — 75% of page visits must meet "Good" thresholds.


LCP: Largest Contentful Paint

LCP measures when the largest visible content element renders. Usually this is:

  • Hero image or video
  • Large text block
  • Background image
  • <svg> element

Common LCP issues

1. Slow server response (TTFB > 800ms)

Fix: CDN, caching, optimized backend, edge rendering

2. Render-blocking resources

html
1<!-- ❌ Blocks rendering --> 2<link rel="stylesheet" href="/all-styles.css"> 3 4<!-- ✅ Critical CSS inlined, rest deferred --> 5<style>/* Critical above-fold CSS */</style> 6<link rel="preload" href="/styles.css" as="style" 7 onload="this.onload=null;this.rel='stylesheet'">

3. Slow resource load times

html
1<!-- ❌ No hints, discovered late --> 2<img src="/hero.jpg" alt="Hero"> 3 4<!-- ✅ Preloaded with high priority --> 5<link rel="preload" href="/hero.webp" as="image" fetchpriority="high"> 6<img src="/hero.webp" alt="Hero" fetchpriority="high">

4. Client-side rendering delays

javascript
1// ❌ Content loads after JavaScript 2useEffect(() => { 3 fetch('/api/hero-text').then(r => r.json()).then(setHeroText); 4}, []); 5 6// ✅ Server-side or static rendering 7// Use SSR, SSG, or streaming to send HTML with content 8export async function getServerSideProps() { 9 const heroText = await fetchHeroText(); 10 return { props: { heroText } }; 11}

LCP optimization checklist

markdown
1- [ ] TTFB < 800ms (use CDN, edge caching) 2- [ ] LCP image preloaded with fetchpriority="high" 3- [ ] LCP image optimized (WebP/AVIF, correct size) 4- [ ] Critical CSS inlined (< 14KB) 5- [ ] No render-blocking JavaScript in <head> 6- [ ] Fonts don't block text rendering (font-display: swap) 7- [ ] LCP element in initial HTML (not JS-rendered)

LCP element identification

javascript
1// Find your LCP element 2new PerformanceObserver((list) => { 3 const entries = list.getEntries(); 4 const lastEntry = entries[entries.length - 1]; 5 console.log('LCP element:', lastEntry.element); 6 console.log('LCP time:', lastEntry.startTime); 7}).observe({ type: 'largest-contentful-paint', buffered: true });

INP: Interaction to Next Paint

INP measures responsiveness across ALL interactions (clicks, taps, key presses) during a page visit. It reports the worst interaction (at 98th percentile for high-traffic pages).

INP breakdown

Total INP = Input Delay + Processing Time + Presentation Delay

PhaseTargetOptimization
Input Delay< 50msReduce main thread blocking
Processing< 100msOptimize event handlers
Presentation< 50msMinimize rendering work

Common INP issues

1. Long tasks blocking main thread

javascript
1// ❌ Long synchronous task 2function processLargeArray(items) { 3 items.forEach(item => expensiveOperation(item)); 4} 5 6// ✅ Break into chunks with yielding 7async function processLargeArray(items) { 8 const CHUNK_SIZE = 100; 9 for (let i = 0; i < items.length; i += CHUNK_SIZE) { 10 const chunk = items.slice(i, i + CHUNK_SIZE); 11 chunk.forEach(item => expensiveOperation(item)); 12 13 // Yield to main thread 14 await new Promise(r => setTimeout(r, 0)); 15 // Or use scheduler.yield() when available 16 } 17}

2. Heavy event handlers

javascript
1// ❌ All work in handler 2button.addEventListener('click', () => { 3 // Heavy computation 4 const result = calculateComplexThing(); 5 // DOM updates 6 updateUI(result); 7 // Analytics 8 trackEvent('click'); 9}); 10 11// ✅ Prioritize visual feedback 12button.addEventListener('click', () => { 13 // Immediate visual feedback 14 button.classList.add('loading'); 15 16 // Defer non-critical work 17 requestAnimationFrame(() => { 18 const result = calculateComplexThing(); 19 updateUI(result); 20 }); 21 22 // Use requestIdleCallback for analytics 23 requestIdleCallback(() => trackEvent('click')); 24});

3. Third-party scripts

javascript
1// ❌ Eagerly loaded, blocks interactions 2<script src="https://heavy-widget.com/widget.js"></script> 3 4// ✅ Lazy loaded on interaction or visibility 5const loadWidget = () => { 6 import('https://heavy-widget.com/widget.js') 7 .then(widget => widget.init()); 8}; 9button.addEventListener('click', loadWidget, { once: true });

4. Excessive re-renders (React/Vue)

javascript
1// ❌ Re-renders entire tree 2function App() { 3 const [count, setCount] = useState(0); 4 return ( 5 <div> 6 <Counter count={count} /> 7 <ExpensiveComponent /> {/* Re-renders on every count change */} 8 </div> 9 ); 10} 11 12// ✅ Memoized expensive components 13const MemoizedExpensive = React.memo(ExpensiveComponent); 14 15function App() { 16 const [count, setCount] = useState(0); 17 return ( 18 <div> 19 <Counter count={count} /> 20 <MemoizedExpensive /> 21 </div> 22 ); 23}

INP optimization checklist

markdown
1- [ ] No tasks > 50ms on main thread 2- [ ] Event handlers complete quickly (< 100ms) 3- [ ] Visual feedback provided immediately 4- [ ] Heavy work deferred with requestIdleCallback 5- [ ] Third-party scripts don't block interactions 6- [ ] Debounced input handlers where appropriate 7- [ ] Web Workers for CPU-intensive operations

INP debugging

javascript
1// Identify slow interactions 2new PerformanceObserver((list) => { 3 for (const entry of list.getEntries()) { 4 if (entry.duration > 200) { 5 console.warn('Slow interaction:', { 6 type: entry.name, 7 duration: entry.duration, 8 processingStart: entry.processingStart, 9 processingEnd: entry.processingEnd, 10 target: entry.target 11 }); 12 } 13 } 14}).observe({ type: 'event', buffered: true, durationThreshold: 16 });

CLS: Cumulative Layout Shift

CLS measures unexpected layout shifts. A shift occurs when a visible element changes position between frames without user interaction.

CLS Formula: impact fraction × distance fraction

Common CLS causes

1. Images without dimensions

html
1<!-- ❌ Causes layout shift when loaded --> 2<img src="photo.jpg" alt="Photo"> 3 4<!-- ✅ Space reserved --> 5<img src="photo.jpg" alt="Photo" width="800" height="600"> 6 7<!-- ✅ Or use aspect-ratio --> 8<img src="photo.jpg" alt="Photo" style="aspect-ratio: 4/3; width: 100%;">

2. Ads, embeds, and iframes

html
1<!-- ❌ Unknown size until loaded --> 2<iframe src="https://ad-network.com/ad"></iframe> 3 4<!-- ✅ Reserve space with min-height --> 5<div style="min-height: 250px;"> 6 <iframe src="https://ad-network.com/ad" height="250"></iframe> 7</div> 8 9<!-- ✅ Or use aspect-ratio container --> 10<div style="aspect-ratio: 16/9;"> 11 <iframe src="https://youtube.com/embed/..." 12 style="width: 100%; height: 100%;"></iframe> 13</div>

3. Dynamically injected content

javascript
1// ❌ Inserts content above viewport 2notifications.prepend(newNotification); 3 4// ✅ Insert below viewport or use transform 5const insertBelow = viewport.bottom < newNotification.top; 6if (insertBelow) { 7 notifications.prepend(newNotification); 8} else { 9 // Animate in without shifting 10 newNotification.style.transform = 'translateY(-100%)'; 11 notifications.prepend(newNotification); 12 requestAnimationFrame(() => { 13 newNotification.style.transform = ''; 14 }); 15}

4. Web fonts causing FOUT

css
1/* ❌ Font swap shifts text */ 2@font-face { 3 font-family: 'Custom'; 4 src: url('custom.woff2') format('woff2'); 5} 6 7/* ✅ Optional font (no shift if slow) */ 8@font-face { 9 font-family: 'Custom'; 10 src: url('custom.woff2') format('woff2'); 11 font-display: optional; 12} 13 14/* ✅ Or match fallback metrics */ 15@font-face { 16 font-family: 'Custom'; 17 src: url('custom.woff2') format('woff2'); 18 font-display: swap; 19 size-adjust: 105%; /* Match fallback size */ 20 ascent-override: 95%; 21 descent-override: 20%; 22}

5. Animations triggering layout

css
1/* ❌ Animates layout properties */ 2.animate { 3 transition: height 0.3s, width 0.3s; 4} 5 6/* ✅ Use transform instead */ 7.animate { 8 transition: transform 0.3s; 9} 10.animate.expanded { 11 transform: scale(1.2); 12}

CLS optimization checklist

markdown
1- [ ] All images have width/height or aspect-ratio 2- [ ] All videos/embeds have reserved space 3- [ ] Ads have min-height containers 4- [ ] Fonts use font-display: optional or matched metrics 5- [ ] Dynamic content inserted below viewport 6- [ ] Animations use transform/opacity only 7- [ ] No content injected above existing content

CLS debugging

javascript
1// Track layout shifts 2new PerformanceObserver((list) => { 3 for (const entry of list.getEntries()) { 4 if (!entry.hadRecentInput) { 5 console.log('Layout shift:', entry.value); 6 entry.sources?.forEach(source => { 7 console.log(' Shifted element:', source.node); 8 console.log(' Previous rect:', source.previousRect); 9 console.log(' Current rect:', source.currentRect); 10 }); 11 } 12 } 13}).observe({ type: 'layout-shift', buffered: true });

Measurement tools

Lab testing

  • Chrome DevTools → Performance panel, Lighthouse
  • WebPageTest → Detailed waterfall, filmstrip
  • Lighthouse CLInpx lighthouse <url>

Field data (real users)

  • Chrome User Experience Report (CrUX) → BigQuery or API
  • Search Console → Core Web Vitals report
  • web-vitals library → Send to your analytics
javascript
1import {onLCP, onINP, onCLS} from 'web-vitals'; 2 3function sendToAnalytics({name, value, rating}) { 4 gtag('event', name, { 5 event_category: 'Web Vitals', 6 value: Math.round(name === 'CLS' ? value * 1000 : value), 7 event_label: rating 8 }); 9} 10 11onLCP(sendToAnalytics); 12onINP(sendToAnalytics); 13onCLS(sendToAnalytics);

Framework quick fixes

Next.js

jsx
1// LCP: Use next/image with priority 2import Image from 'next/image'; 3<Image src="/hero.jpg" priority fill alt="Hero" /> 4 5// INP: Use dynamic imports 6const HeavyComponent = dynamic(() => import('./Heavy'), { ssr: false }); 7 8// CLS: Image component handles dimensions automatically

React

jsx
1// LCP: Preload in head 2<link rel="preload" href="/hero.jpg" as="image" fetchpriority="high" /> 3 4// INP: Memoize and useTransition 5const [isPending, startTransition] = useTransition(); 6startTransition(() => setExpensiveState(newValue)); 7 8// CLS: Always specify dimensions in img tags

Vue/Nuxt

vue
1<!-- LCP: Use nuxt/image with preload --> 2<NuxtImg src="/hero.jpg" preload loading="eager" /> 3 4<!-- INP: Use async components --> 5<component :is="() => import('./Heavy.vue')" /> 6 7<!-- CLS: Use aspect-ratio CSS --> 8<img :style="{ aspectRatio: '16/9' }" />

References

FAQ & Installation Steps

These questions and steps mirror the structured data on this page for better search understanding.

? Frequently Asked Questions

What is core-web-vitals?

Perfect for Web Optimization Agents needing to analyze and improve Core Web Vitals metrics like LCP, INP, and CLS. Web companion for Southeast University students. Academic tools, campus info, and student resources in one place.

How do I install core-web-vitals?

Run the command: npx killer-skills add sayeedjoy/seucampusmate-web/core-web-vitals. It works with Cursor, Windsurf, VS Code, Claude Code, and 19+ other IDEs.

What are the use cases for core-web-vitals?

Key use cases include: Analyzing LCP metrics to reduce loading times below 2.5s, Optimizing INP for faster interactivity with input delays under 200ms, Debugging CLS issues to maintain visual stability with scores under 0.1.

Which IDEs are compatible with core-web-vitals?

This skill is compatible with Cursor, Windsurf, VS Code, Trae, Claude Code, OpenClaw, Aider, Codex, OpenCode, Goose, Cline, Roo Code, Kiro, Augment Code, Continue, GitHub Copilot, Sourcegraph Cody, and Amazon Q Developer. Use the Killer-Skills CLI for universal one-command installation.

Are there any limitations for core-web-vitals?

Requires understanding of Google's Core Web Vitals metrics. Optimization targets are based on the 75th percentile of page loads.

How To Install

  1. 1. Open your terminal

    Open the terminal or command line in your project directory.

  2. 2. Run the install command

    Run: npx killer-skills add sayeedjoy/seucampusmate-web/core-web-vitals. The CLI will automatically detect your IDE or AI agent and configure the skill.

  3. 3. Start using the skill

    The skill is now active. Your AI agent can use core-web-vitals immediately in the current project.

Related Skills

Looking for an alternative to core-web-vitals or another community skill for your workflow? Explore these related open-source skills.

View All

widget-generator

Logo of f
f

f.k.a. Awesome ChatGPT Prompts. Share, discover, and collect prompts from the community. Free and open source — self-host for your organization with complete privacy.

149.6k
0
AI

flags

Logo of vercel
vercel

flags is a Next.js feature management skill that enables developers to efficiently add or modify framework feature flags, streamlining React application development.

138.4k
0
Browser

zustand

Logo of lobehub
lobehub

The ultimate space for work and life — to find, build, and collaborate with agent teammates that grow with you. We are taking agent harness to the next level — enabling multi-agent collaboration, effortless agent team design, and introducing agents as the unit of work interaction.

72.8k
0
AI

data-fetching

Logo of lobehub
lobehub

The ultimate space for work and life — to find, build, and collaborate with agent teammates that grow with you. We are taking agent harness to the next level — enabling multi-agent collaboration, effortless agent team design, and introducing agents as the unit of work interaction.

72.8k
0
AI