Perf Lighthouse

作者 tech-leads-club120b67676388無授權條款收錄於 2026年10月8日更新於 2026年10月8日

Run Lighthouse audits locally via CLI or Node API, parse and interpret reports, and set performance budgets. Use when measuring site performance, understanding Lighthouse scores, setting up budgets, or integrating audits into CI. Triggers on: lighthouse, run lighthouse, lighthouse score, performance audit, performance budget. Do NOT use for fixing specific performance issues (use perf-web-optimization or core-web-vitals) or Astro-specific optimization (use perf-astro).

AI 產生的概覽

指導透過 CLI、Node API、效能預算與 CI 整合執行 Lighthouse 效能稽核。

功能
此技能提供透過 CLI 或 Node API 在本機執行 Lighthouse 稽核的說明,包括裝置形態、節流與類別選擇等常用參數。它展示如何在 budget.json 中定義效能預算,以及如何解析 Lighthouse JSON 報告以取得分數、Core Web Vitals 與未通過的稽核項目。它也涵蓋 Lighthouse CI 設定、GitHub Actions 設定、建置比較與疑難排解。
適用情境
適用於衡量網站效能、解讀 Lighthouse 分數、設定效能預算,或將稽核整合至 CI。它不用於修正特定效能問題或 Astro 專屬最佳化。
執行需求
需要 Node.js 與 npm 來安裝 Lighthouse 或 @lhci/cli,需要 Chrome/Chromium 瀏覽器(可能需要設定 CHROME_PATH),並需要網路存取以稽核 URL。CI 範例涉及 GitHub Actions 與選用的 LHCI_GITHUB_APP_TOKEN 密鑰。此技能不附帶指令碼,僅為說明文件。

Lighthouse Audits

CLI Quick Start

bash
# Installnpm install -g lighthouse
# Basic auditlighthouse https://example.com
# Mobile performance only (faster)lighthouse https://example.com --preset=perf --form-factor=mobile
# Output JSON for parsinglighthouse https://example.com --output=json --output-path=./report.json
# Output HTML reportlighthouse https://example.com --output=html --output-path=./report.html

Common Flags

bash
--preset=perf           # Performance only (skip accessibility, SEO, etc.)--form-factor=mobile    # Mobile device emulation (default)--form-factor=desktop   # Desktop--throttling-method=devtools  # More accurate throttling--only-categories=performance,accessibility  # Specific categories--chrome-flags="--headless"   # Headless Chrome

Performance Budgets

Create budget.json:

json
[  {    "resourceSizes": [      { "resourceType": "script", "budget": 200 },      { "resourceType": "image", "budget": 300 },      { "resourceType": "stylesheet", "budget": 50 },      { "resourceType": "total", "budget": 500 }    ],    "resourceCounts": [{ "resourceType": "third-party", "budget": 5 }],    "timings": [      { "metric": "interactive", "budget": 3000 },      { "metric": "first-contentful-paint", "budget": 1500 },      { "metric": "largest-contentful-paint", "budget": 2500 }    ]  }]

Run with budget:

bash
lighthouse https://example.com --budget-path=./budget.json

Node API

javascript
import lighthouse from 'lighthouse'import * as chromeLauncher from 'chrome-launcher'
async function runAudit(url) {  const chrome = await chromeLauncher.launch({ chromeFlags: ['--headless'] })
  const result = await lighthouse(url, {    port: chrome.port,    onlyCategories: ['performance'],    formFactor: 'mobile',    throttling: {      cpuSlowdownMultiplier: 4,    },  })
  await chrome.kill()
  const { performance } = result.lhr.categories  const { 'largest-contentful-paint': lcp } = result.lhr.audits
  return {    score: Math.round(performance.score * 100),    lcp: lcp.numericValue,  }}

GitHub Actions

yaml
# .github/workflows/lighthouse.ymlname: Lighthouse
on:  pull_request:  push:    branches: [main]
jobs:  lighthouse:    runs-on: ubuntu-latest    steps:      - uses: actions/checkout@v4
      - name: Build site        run: npm ci && npm run build
      - name: Run Lighthouse        uses: treosh/lighthouse-ci-action@v11        with:          urls: |            http://localhost:3000            http://localhost:3000/about          budgetPath: ./budget.json          uploadArtifacts: true          temporaryPublicStorage: true        env:          LHCI_GITHUB_APP_TOKEN: ${{ secrets.LHCI_GITHUB_APP_TOKEN }}

Lighthouse CI (LHCI)

For full CI integration with historical tracking:

bash
# Installnpm install -g @lhci/cli
# Initialize configlhci wizard

Creates lighthouserc.js:

javascript
module.exports = {  ci: {    collect: {      url: ['http://localhost:3000/', 'http://localhost:3000/about'],      startServerCommand: 'npm run start',      numberOfRuns: 3,    },    assert: {      assertions: {        'categories:performance': ['error', { minScore: 0.9 }],        'categories:accessibility': ['warn', { minScore: 0.9 }],        'first-contentful-paint': ['error', { maxNumericValue: 1500 }],        'largest-contentful-paint': ['error', { maxNumericValue: 2500 }],        'cumulative-layout-shift': ['error', { maxNumericValue: 0.1 }],      },    },    upload: {      target: 'temporary-public-storage', // or 'lhci' for self-hosted    },  },}

Run:

bash
lhci autorun

Parse JSON Report

javascript
import fs from 'fs'
const report = JSON.parse(fs.readFileSync('./report.json'))
// Overall scores (0-1, multiply by 100 for percentage)const scores = {  performance: report.categories.performance.score,  accessibility: report.categories.accessibility.score,  seo: report.categories.seo.score,}
// Core Web Vitalsconst vitals = {  lcp: report.audits['largest-contentful-paint'].numericValue,  cls: report.audits['cumulative-layout-shift'].numericValue,  fcp: report.audits['first-contentful-paint'].numericValue,  tbt: report.audits['total-blocking-time'].numericValue,}
// Failed auditsconst failed = Object.values(report.audits)  .filter((a) => a.score !== null && a.score < 0.9)  .map((a) => ({ id: a.id, score: a.score, title: a.title }))

Compare Builds

bash
# Save baselinelighthouse https://prod.example.com --output=json --output-path=baseline.json
# Run on PRlighthouse https://preview.example.com --output=json --output-path=pr.json
# Compare (custom script)node compare-reports.js baseline.json pr.json

Simple comparison script:

javascript
const baseline = JSON.parse(fs.readFileSync(process.argv[2]))const pr = JSON.parse(fs.readFileSync(process.argv[3]))
const metrics = ['largest-contentful-paint', 'cumulative-layout-shift', 'total-blocking-time']
metrics.forEach((metric) => {  const base = baseline.audits[metric].numericValue  const current = pr.audits[metric].numericValue  const diff = (((current - base) / base) * 100).toFixed(1)  const emoji = current <= base ? '✅' : '❌'  console.log(`${emoji} ${metric}: ${diff}% (${base.toFixed(0)} → ${current.toFixed(0)})`)})

Troubleshooting

IssueSolution
Inconsistent scoresRun multiple times (--number-of-runs=3), use median
Chrome not foundSet CHROME_PATH env var
TimeoutsIncrease with --max-wait-for-load=60000
Auth requiredUse --extra-headers or puppeteer script

來源與署名

來源:tech-leads-club/agent-skills位於packages/skills-catalog/skills/(performance)/perf-lighthouse提交120b676

授權條款: 無授權條款

內容歸原作者所有。SourceWeft 從公開儲存庫中收錄這些內容。

檢舉或申請下架