/** * Font Delivery Health — read-only visibility panel (free build). * * Uses the free ui-kit + Tailwind pr: utilities so it is visually * native to the free Asset Optimisation page. Same read-only data contract as * premium: GET /prorank-seo/v1/font-optimization/health (which reuses the * existing FontOptimizationModule::get_stats() — single source of truth). No * toggles, no mutation; preload suggestions are advisory only. */ import { useState, useEffect, useCallback } from '@wordpress/element'; import { __ } from '@wordpress/i18n'; import apiFetch from '@wordpress/api-fetch'; import { Alert, Button, Card } from '../../../components/ui'; import * as React from 'react'; interface HealthFlag { code: string; severity: 'critical' | 'high' | 'medium' | 'low'; message: string; recommendation: string; } interface FontHealth { status?: string; settings?: { host_google_fonts_locally?: boolean; font_display_swap?: boolean; font_subsetting_enabled?: boolean; smart_fonts_enabled?: boolean; font_preload_enabled?: boolean; font_preload_url_count?: number; }; cache?: { cached_font_files?: number; cached_bytes?: number; cached_human?: string; google_fonts_found_by_scanner?: number; }; rendered?: { fetched?: boolean; external_google_fonts?: boolean; external_google_count?: number; prorank_local_served?: boolean; self_hosted_owner?: string; font_display_swap_seen?: number; preloaded_fonts?: string[]; preload_suggestions?: string[]; }; flags?: HealthFlag[]; } interface HealthResponse { success: boolean; health: FontHealth; } const yesNo = (v: boolean | undefined): string => v ? __('Yes', 'prorank-seo') : __('No', 'prorank-seo'); const FontDeliveryHealthPanel: React.FC = () => { const [health, setHealth] = useState(null); const [loading, setLoading] = useState(true); const [error, setError] = useState(''); const load = useCallback(async () => { setLoading(true); setError(''); try { const r = await apiFetch({ path: '/prorank-seo/v1/font-optimization/health', }); if (r?.success && r.health) { setHealth(r.health); } else { setError(__('Unexpected response from the font health endpoint.', 'prorank-seo')); } } catch (e) { setError((e as Error)?.message || __('Failed to load font delivery health.', 'prorank-seo')); } finally { setLoading(false); } }, []); useEffect(() => { load(); }, [load]); const s = health?.settings || {}; const c = health?.cache || {}; const r = health?.rendered || {}; const flags = health?.flags || []; const sevClass = (sev: string): string => sev === 'critical' || sev === 'high' ? 'pr:border-red-500' : sev === 'medium' ? 'pr:border-amber-500' : 'pr:border-gray-400'; return (

{__('Font Delivery Health', 'prorank-seo')}

{health && ( {String(health.status || 'unknown').toUpperCase()} )}

{__( 'Read-only view of how fonts are delivered. Toggles live in the Font Optimisation card above — this only reports state and advisory suggestions.', 'prorank-seo' )}

{loading && (

{__('Checking font delivery…', 'prorank-seo')}

)} {!loading && error && } {!loading && !error && health && ( <>
{__('Local Google Fonts hosting', 'prorank-seo')}
{yesNo(s.host_google_fonts_locally)}
{__('External Google Fonts on page', 'prorank-seo')}
{r.fetched ? r.external_google_fonts ? `${__('Yes', 'prorank-seo')} (${r.external_google_count})` : __('No', 'prorank-seo') : __('Not checked', 'prorank-seo')}
{__('ProRank local fonts served', 'prorank-seo')}
{r.fetched ? yesNo(r.prorank_local_served) : __('Not checked', 'prorank-seo')}
{__('Self-hosted font owner', 'prorank-seo')}
{r.self_hosted_owner || '—'}
{__('Cached font files', 'prorank-seo')}
{(c.cached_font_files ?? 0).toLocaleString()} ({c.cached_human || '0 B'})
{__('font-display: swap', 'prorank-seo')}
{s.font_display_swap ? __('Enabled', 'prorank-seo') : __('Disabled', 'prorank-seo')}
{__('Critical preload', 'prorank-seo')}
{s.font_preload_enabled ? `${__('Enabled', 'prorank-seo')} (${s.font_preload_url_count ?? 0})` : __('Disabled', 'prorank-seo')}
{__('Preloaded fonts', 'prorank-seo')}
{(r.preloaded_fonts || []).length}
{flags.length === 0 ? ( ) : (
{flags.map((f) => (
[{f.severity.toUpperCase()}] {f.message}
{f.recommendation && (
{f.recommendation}
)}
))}
)} {(r.preload_suggestions || []).length > 0 && (
    {(r.preload_suggestions || []).map((u) => (
  • {u}
  • ))}

{__( 'Not applied automatically. Add under Resource Hints → Font preload only if genuinely above-the-fold.', 'prorank-seo' )}

)}
)}
); }; export default FontDeliveryHealthPanel;