SEO / Portfolio / Public Site

Modernizing the Protocol5 Website

Report summary

Protocol5’s live site is already conceptually split between a public, content-heavy shell and richer interactive tooling. The homepage presents two sibling sections, Mathematics and UAI, plus shared About, Links, and Contact pages; the About page explicitly says the current architecture separates ed

Status
Research archive item
Category
SEO / Portfolio / Public Site
Length
4,802 words
Reading time
22 minutes
Report type
architecture

Key topics

  • SEO / Portfolio / Public Site
  • SEO
  • Portfolio
  • Public Site
  • UAI
  • .NET
  • C#
  • TypeScript
  • Runtime

Research provenance

Archive status
Research archive item
Content identity
sha256:19ebf5b9fe18bf318a7d3f0ae219d0f357f3f4622fee97ebfb6b2d515daccb9d

For citation, use the report title and canonical URL. Archival presence does not establish authorship or promote report statements into portfolio evidence.

Source availability: 49 citation markers in the source export have no recoverable source links. Those markers are omitted from this reader; any supplied bibliography and ordinary links remain. Check the original sources before relying on the cited claims.

This page renders the archived Markdown as safe, formatted HTML. It is background research and does not become a portfolio claim without evidence review.

Full report

On this page

Executive summary

Protocol5’s live site is already conceptually split between a public, content-heavy shell and richer interactive tooling. The homepage presents two sibling sections, Mathematics and UAI, plus shared About, Links, and Contact pages; the About page explicitly says the current architecture separates editorial/static pages from an interactive calculator surface and “hosts a Blazor calculator shell.” One crawled tool page also surfaced an “An unhandled error has occurred” message, which is a strong signal that the next redesign should harden the line between stable server-rendered content and more failure-prone client runtime islands.

The best-fit modernization path is not a wholesale SPA rewrite. The strongest architecture for Protocol5 is to keep ASP.NET MVC with Razor as the canonical rendering layer, replace Bootstrap and jQuery with a design-token-driven CSS system plus ES modules/TypeScript, and introduce interactivity through selective “islands” rather than site-wide client routing. That preserves crawlability, stable URLs, low-JavaScript content delivery, and the existing route/content model, while still allowing spectacular visual differentiation where it matters most. Google’s own guidance is that while Google Search can render JavaScript, server-side rendering, static rendering, or hydration are preferred over heavier workarounds, and crawlable links should remain real <a href> links.

For the frontend layer, the highest-confidence recommendation is a two-tier strategy. Use plain Razor + semantic HTML + modern CSS for the shell, page layouts, content pages, forms, tables, and blog/article templates. Add Lit-based web components for reusable interactive islands where framework-agnostic embedding matters, and reserve React or Vue islands only if a specific surface becomes sufficiently stateful to justify their runtime and ecosystem weight. Lit’s strongest advantage is that it is built on standard web components and is explicitly designed to work in any HTML environment; React and Vue both support partial-page mounting/hydration, but they are a larger architectural commitment. Lit SSR also exists, but its current SSR package is still documented as experimental, which is another reason to keep Razor as the primary SSR engine.

Visually, the target aesthetic should be ultra-minimal, computational, high-precision, and image-free: dense monochrome or near-monochrome foundations, accent spectra used sparingly, procedural SVG/WebGL motion, deep typographic hierarchy, grid geometry, and restrained but deliberate transitions. WebGPU is promising, but it is still not Baseline on MDN; if you want a premium motion layer at the top of the site, Three.js’s WebGPURenderer is attractive precisely because it can fall back to WebGL 2, which is Baseline and broadly available. That makes progressive enhancement the right rule: HTML first, CSS/SVG second, WebGL third, WebGPU only when detected.

If executed with discipline, this program can yield a site that feels dramatically more advanced while also becoming lighter, more reliable, more accessible, and easier to evolve. The practical sweet spot is a medium-complexity delivery in roughly 420 to 560 hours, with a lower bound around 260 to 340 hours if the visual ambition stays mostly CSS/SVG and a higher-end “hero-experience” version around 680 to 900 hours if you add substantial procedural 3D/shader work and a larger interactive content system. Those ranges assume the site remains an ASP.NET MVC application and does not simultaneously absorb a CMS or platform migration.

Current site audit and baseline

The public site structure visible from the live shell is compact but semantically meaningful: a parent Protocol5 homepage, a Mathematics section, a UAI section, and shared About, Links, and Contact pages. The UAI section is especially content-dense and includes specification-like pages, translations, machine-readable assets, schemas, registries, a validator/workbench area, and downloadable packages. That combination matters because it means Protocol5 is not just a marketing site; it is also a documentation/support surface with machine-discoverable assets, which strongly favors preserving stable server-rendered HTML and avoiding a JavaScript-dependent site shell.

Another important live-site clue is route shape. Public pages include classic MVC-style URLs such as /Home/About, /Home/Contact, and /Home/Links, while the about copy states that the current site keeps the mathematical/editorial core separate from an interactive calculator shell. That is exactly the sort of topology that benefits from incrementally modernizing the front end while leaving the server-side page model intact.

The modernization work should begin with a formal audit, even if the site appears modest. The right baseline package is: a headless crawl of all nav-reachable pages; an asset inventory of scripts, styles, fonts, SVGs, downloads, and third-party requests; a CSS/JS dependency graph; and page-template clustering so you know which files are genuinely unique versus layout derivatives. Playwright is a strong fit for page navigation and page-level automation, and Chrome DevTools Coverage is useful for finding unused CSS/JS and identifying how much Bootstrap or legacy JS is actually exercised per template.

A practical audit output should answer six questions. First, where are Bootstrap classes used and which ones are truly relied on. Second, where is jQuery actually needed versus merely loaded. Third, which interactions are content-shell interactions versus app-like tools. Fourth, what percentage of CSS and JS is unused on each template. Fifth, what pages need rich interactivity at all. Sixth, which pages are SEO-critical and therefore must remain plain-HTML-first. The result should not just be a spreadsheet; it should become a migration map with explicit replacement targets such as “Bootstrap grid to CSS Grid/subgrid,” “jQuery AJAX to fetch,” and “Bootstrap collapse/modal to native disclosure/dialog patterns or small custom components.” The underlying reason for doing this carefully is the same one Chrome documents for code coverage: finding unused code is easy, but correctly refactoring each page to ship only what it needs depends heavily on your stack and template structure.

A good crawl harness for the discovery phase can be very small. The point is not sophistication first; it is evidence first.

// audit/crawl.ts
import { chromium } from 'playwright';

const seeds = [
  'https://protocol5.com/',
  'https://protocol5.com/Mathematics',
  'https://protocol5.com/UAI',
  'https://protocol5.com/Home/About',
  'https://protocol5.com/Home/Links',
  'https://protocol5.com/Home/Contact'
];

const sameOrigin = (u: string) => u.startsWith('https://protocol5.com');

(async () => {
  const browser = await chromium.launch();
  const context = await browser.newContext();
  const visited = new Set<string>();
  const queue = [...seeds];
  const assets: Array<{ page: string; url: string; type: string }> = [];

  while (queue.length) {
    const url = queue.shift()!;
    if (visited.has(url)) continue;
    visited.add(url);

    const page = await context.newPage();
    page.on('requestfinished', req => {
      const r = req.resourceType();
      if (['script', 'stylesheet', 'font', 'image', 'xhr', 'fetch'].includes(r)) {
        assets.push({ page: url, url: req.url(), type: r });
      }
    });

    await page.goto(url, { waitUntil: 'networkidle' });

    for (const href of await page.locator('a').evaluateAll(as =>
      as.map(a => (a as HTMLAnchorElement).href).filter(Boolean)
    )) {
      if (sameOrigin(href) && !visited.has(href)) queue.push(href);
    }

    await page.close();
  }

  console.log(JSON.stringify({
    pages: [...visited],
    assets
  }, null, 2));

  await browser.close();
})();

This should be supplemented by a manual Bootstrap/jQuery grep in the source tree and a DevTools Coverage pass on the most important templates, because Coverage is specifically intended to reveal unused JavaScript and CSS and export a report for analysis.

My main limitation here is that I could not extract a full live HTML asset manifest from the Protocol5 site through the browsing outputs available in this session, so the user’s instruction that Bootstrap and jQuery are present should be treated as a project assumption that must be validated in source during Phase A. What is independently clear is the broader architecture: content shell plus richer tool surfaces, which is enough to design a sound migration strategy.

Framework and rendering architecture

The architectural principle should be simple: keep server-rendered MVC/Razor as the source of truth for navigation, SEO, metadata, and page composition; mount client frameworks only inside explicit islands. React explicitly supports partially built pages with multiple roots, and hydrateRoot is the supported path when the HTML already exists from a server render. Vue says the same thing in different words: multiple Vue app instances can coexist on one page, and if Vue is only enhancing specific parts of a server-rendered page, multiple small mounts are preferred over handing the entire page to one client app. Solid also supports SSR/hydration and has a very lean rendering model. Those facts make an islands architecture technically straightforward inside ASP.NET MVC.

The default routing recommendation is therefore MVC routes at site scope, client routing only inside self-contained applications. Vue Router is explicitly a client-side SPA router, and Solid Router is likewise oriented around client/server app routing. Both are useful, but they should be constrained to genuinely app-like areas such as a workbench, validator, or complex calculator—not used to replace the public page topology. Keeping real anchors with real href values is also aligned with Google’s crawl guidance.

For state management, Protocol5 should adopt a state hierarchy rather than “pick one store for everything.” Use server-rendered HTML and Razor models for content state. Use local component state for ephemeral UI state. Use URL/query-string state for filter/search/sort state that should survive refresh/share. Use a server-state library only when client-side data fetching becomes complex enough to justify caching and synchronization; TanStack Query is purpose-built for fetching, caching, synchronizing, and updating server state, while Pinia, Redux Toolkit, RTK Query, Solid signals/stores, and React reducer/context patterns are better reserved for richer client applications rather than the site shell.

Vite is the most pragmatic build tool for this program. Its production build emits deployable bundles, it supports modern browser targets by default, and its build.target is configurable if the browser policy changes. That aligns well with the user’s stated assumption of “modern evergreen browsers.” On the .NET side, ASP.NET Core can serve versioned static assets with MapStaticAssets/asp-append-version, while classic MVC 5 still has bundling and minification support but should generally be treated as legacy infrastructure if you adopt Vite-generated manifests.

Candidate framework comparison

CandidateMVC integration fitStrengthsTradeoffsBest use on Protocol5Primary sources
Lit and standard Web ComponentsExcellent. Web components are standard-browser primitives and Lit is explicitly positioned as lightweight web components that work in any HTML environment.Framework-agnostic embedding, scoped styles, reuse across Razor views, minimal architectural commitment.Lit SSR exists, but the current Lit SSR package is documented as part of Lit Labs and still marked experimental.Default choice for reusable interactive islands and cross-template components.
VueVery good. Vue supports multiple small app instances and createSSRApp/hydration.Balanced ergonomics, clear SSR story, official router and official Pinia state layer.Slightly heavier commitment than Lit; easy to let Vue spread too far if boundaries are weak.Strong alternative when a feature wants richer declarative interactivity without fully becoming a mini-SPA.
ReactVery good. React explicitly supports partially built pages with multiple roots and server hydration.Huge ecosystem, mature patterns, many engineers already know it.More runtime and hydration complexity than Lit; no official router from React itself; can easily become over-applied.Good for a future workbench/validator or complex calculator surfaces if the team is React-strong.
SvelteGood. Svelte compiles work out of the browser and supports imperative mount/hydrate; its docs/search results also indicate custom-element compilation.Small bundles, excellent performance profile, terse authoring model.The most common “official” routing path is SvelteKit, which is not what you want for an MVC-preserved shell.Viable for very performance-sensitive islands if the team already likes Svelte.
SolidGood. Solid supports fine-grained signals, stores, SSR string/stream rendering, and client hydration.Excellent runtime performance, precise reactivity, good SSR primitives.Smaller ecosystem and smaller labor pool than React/Vue.Best reserved for highly interactive, performance-sensitive micro-apps.

The upshot is clear: if the goal is the best modernization-to-risk ratio, Lit-first islands over Razor is the most elegant default. If the team later needs a heavier app surface, Vue is the easiest second choice for a disciplined islands model, while React is the safest third choice when organizational familiarity outweighs runtime minimalism.

flowchart LR
    A[Browser] --> B[ASP.NET MVC Controllers]
    B --> C[Razor Layouts and Views]
    C --> D[HTML-first shell]
    C --> E[Progressively enhanced islands]
    E --> F[Lit by default]
    E --> G[React or Vue only for complex tools]
    C --> H[SEO metadata, structured content, anchors]
    I[Vite build] --> J[Hashed JS and CSS manifest]
    J --> C
    K[JSON or MVC endpoints] --> E
    L[SVG and CSS visuals] --> D
    M[WebGL hero layer] --> E

This design preserves what the current site already does well—clear sections, public routes, machine-readable assets, utility pages—while giving you room to build a much more advanced visual layer without handing basic page delivery to a client runtime.

Razor integration patterns

A clean Razor integration pattern is to treat each interactive entry as a Vite entrypoint and each island as a mountable custom element or client root. The MVC layout owns discovery, metadata, and the asset manifest; pages opt into scripts only where needed.

@* Views/Shared/_Layout.cshtml *@
<!doctype html>
<html lang="en">
<head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <title>@ViewBag.Title</title>
    <partial name="_HeadAssets" />
    @RenderSection("Head", required: false)
</head>
<body class="theme-core">
    @RenderBody()
    @RenderSection("Scripts", required: false)
</body>
</html>

ASP.NET Core layouts, partials, and static asset handling are first-class concepts, which makes this pattern natural. Partial views are specifically intended to break large markup files into smaller pieces, while layouts own shared UI and scripts. Static asset versioning via asp-append-version or the newer static asset pipeline keeps cache-busting clean.

A Vite manifest helper can keep the server-side integration deterministic.

// Infrastructure/ViteManifest.cs
public sealed record ViteChunk(string file, string[]? css, string[]? imports);

public interface IViteManifest
{
    ViteChunk Entry(string key);
}

public sealed class ViteManifest : IViteManifest
{
    private readonly IReadOnlyDictionary<string, ViteChunk> _manifest;

    public ViteManifest(IWebHostEnvironment env)
    {
        var path = Path.Combine(env.WebRootPath, "dist", ".vite", "manifest.json");
        using var stream = File.OpenRead(path);
        _manifest = JsonSerializer.Deserialize<Dictionary<string, ViteChunk>>(stream)
                    ?? new Dictionary<string, ViteChunk>();
    }

    public ViteChunk Entry(string key) => _manifest[key];
}
@* Views/Shared/_HeadAssets.cshtml *@
@inject IViteManifest Vite
@{
    var site = Vite.Entry("src/site.ts");
}
@if (site.css is not null)
{
    foreach (var css in site.css)
    {
        <link rel="stylesheet" href="~/dist/@css" asp-append-version="true" />
    }
}
<script type="module" src="~/dist/@site.file" asp-append-version="true"></script>

Vite’s build system is well-suited to this because it emits production bundles for static serving and targets a modern-browser baseline by default.

A Lit island is especially clean in Razor because the server merely emits HTML.

@* Views/Home/Index.cshtml *@
@{
    ViewBag.Title = "Protocol5";
}
<section class="hero-shell">
    <p5-signal-field density="0.35" intensity="0.8"></p5-signal-field>
    <div class="hero-copy">
        <h1>Protocol5</h1>
        <p>Mathematics tools plus UAI-1 .NET package distribution.</p>
    </div>
</section>
// src/hero.ts
import { LitElement, css, html } from 'lit';

class P5SignalField extends LitElement {
  static properties = {
    density: { type: Number },
    intensity: { type: Number }
  };

  static styles = css`
    :host { display:block; inline-size:100%; block-size:min(72vh, 54rem); }
    canvas, svg { inline-size:100%; block-size:100%; display:block; }
  `;

  density = 0.35;
  intensity = 0.8;

  render() {
    return html`<canvas part="canvas" aria-hidden="true"></canvas>`;
  }

  firstUpdated() {
    // initialize procedural canvas/WebGL effect here
  }
}

customElements.define('p5-signal-field', P5SignalField);

This works because standard custom elements integrate naturally into any HTML document, and Lit’s component model is built directly on that foundation.

If a page truly needs React, keep it island-scoped:

<div id="registry-browser-root"
     data-endpoint="@Url.Action("RegistryData", "UaiApi")"
     data-locale="@System.Threading.Thread.CurrentThread.CurrentUICulture.Name">
</div>

@section Scripts {
  <script type="module" src="~/dist/registry-browser.js"></script>
}
import { createRoot } from 'react-dom/client';
import { RegistryBrowser } from './RegistryBrowser';

const el = document.getElementById('registry-browser-root')!;
createRoot(el).render(
  <RegistryBrowser
    endpoint={el.dataset.endpoint!}
    locale={el.dataset.locale!}
  />
);

React explicitly documents this “partially built page” pattern with multiple roots, which is why it is appropriate for islands but unnecessary for the whole shell.

Visual system and component patterns

The desired look should feel like advanced instrumentation rather than startup marketing. That means sharp geometry, high information density where appropriate, very careful spacing, and motion that feels computational rather than decorative. The visual language should come primarily from layout, type, shader-backed fields, SVG linework, and animated vector systems, not from stock photos, raster illustrations, or faux-cyber ornament. The live site is already mostly textual and structural, so the redesign should amplify that identity instead of replacing it with generic “tech brand” imagery.

The most reliable stack for this is a layered one. Use modern CSS for the majority of the aesthetic: design tokens, custom properties, gradients, blur, mask effects, grid, subgrid, and high-contrast theming. Use SVG for logos, iconography, connection diagrams, waveform/mesh overlays, editorial illustrations, and code-themed dividers. Add WebGL for a single premium hero surface or a few carefully bounded experimental sections. Use WebGPU only as progressive enhancement because MDN still marks WebGPU as limited availability, while Three.js’s WebGPURenderer is explicitly designed to fall back to WebGL 2.

A very effective design rule for Protocol5 is to separate semantic content layers from aesthetic signal layers. The content should remain perfectly legible in static HTML/CSS. The motion layer should be optional, inert, and skippable. This is also where accessibility and performance align: reduce or disable non-essential motion when users prefer reduced motion, and never make the primary message depend on animation. The prefers-reduced-motion media feature exists specifically so authors can remove or replace non-essential motion, and WCAG 2.2 adds additional emphasis on focus visibility and target-size ergonomics.

Candidate 3D and procedural visual libraries

Library or approachBest fitStrengthsMain cautionRecommendationPrimary sources
Three.js with WebGL/WebGPU pathBrand hero, procedural meshes, custom shaders, background fieldsMature ecosystem; WebGPURenderer can use WebGPU and fall back to WebGL 2; TSL gives a structured shader authoring path.Can become bundle-heavy and engineer-heavy if used outside bounded surfaces.Best overall choice for premium hero work and shader-driven accents.
PlayCanvas EngineMore ambitious real-time scenes, richer post effects, future interactive demosDual WebGL2 + WebGPU backend, post effects, HDR pipeline, shader chunk customization, tree-shakable ESM.More engine-like than most marketing/documentation sites need.Excellent if Protocol5 wants a more “engineered” real-time lab aesthetic.
deck.glData-rich visualizations, maps, point clouds, technical registriesHigh-performance WebGPU/WebGL2 data visualization with interactive layers and picking.Not a general-purpose brand hero library.Use only if Protocol5 adds genuinely data-dense visual surfaces.
Native SVG + Canvas + WebGL2Most of the redesigned siteLowest lock-in, smallest moving parts, broad browser availability.Less turnkey than an engine; more custom authoring.Make this the default baseline, then enhance selectively.

The implication is that Protocol5 should not make 3D the whole site. Instead, it should make 3D the emotional top layer of the homepage and perhaps one or two section landing pages, while the rest of the experience remains typography-forward and extremely disciplined. That is faster, more accessible, easier to test, and more consistent with the site’s actual content mix.

Visual direction recommendations

A strong design system for this project would combine the following ingredients:

System areaRecommendation
ColorDeep charcoal/black foundations, cool near-white type, one electric accent family used sparingly, plus a second low-saturation support accent for focus/error/success.
TypeOne modern grotesk or neo-grotesk variable font for headings/body, one mono family for code, schemas, route labels, and numeric surfaces.
Geometry4px or 8px base rhythm; hard edges; occasional radius only where it signals interactivity rather than “soft card UI.”
TextureNo bitmap noise. Use gradients, layered SVG line fields, scanline-like masks, or shader-generated banding/noise where needed.
MotionSlow, deliberate, low-amplitude background motion; near-instant UI affordance motion; no continuous motion near dense reading zones.
DepthUse blur, glow, and layering minimally; make “precision” the identity, not “neon fog.”

Those are judgment calls rather than sourced facts, but they fit the underlying constraints: HTML-first delivery, image-free aesthetics, and selective high-end procedural surfaces.

Component patterns

A modernization like this succeeds or fails on component discipline more than on hero animation. The most important rule is that components should be headless in behavior and authored in semantic HTML first, with CSS defining the identity and only minimal JS adding interaction.

For navigation, use real <nav> and <a href> links, not JavaScript-only route transitions. On mobile, use a disclosure-style button controlling a link list. If you decide to implement menu-button semantics, follow the APG conventions for aria-haspopup, aria-expanded, and keyboard handling, but do not over-apply “application menu” semantics to ordinary site navigation. Google’s crawl guidance continues to favor crawlable anchors, and the APG menu button pattern shows the correct ARIA contract when a button truly opens a menu.

For the hero, make the content layer completely independent of the visual field. Use a server-rendered headline, value proposition, and primary CTAs. Under or behind that, run a procedural layer such as a node lattice, vector field, spectral line cloud, radial scan tunnel, or shader-based contour mesh. The hero should degrade to static CSS/SVG without changing layout or readability. If you use view transitions between pages, keep them same-origin and progressive only, because the View Transition API supports SPA and MPA transitions but cross-document opt-in via @view-transition is still limited availability.

For cards and section tiles, think “instrument panel,” not “marketing card.” Use sharply defined edges, top-edge labels, tiny monospace metadata strips, and one active accent line rather than filled color blocks. Cards should be content containers first and hover targets second. If you have metric cards or package-download cards, use SVG micro-graphs or line indicators rather than screenshots.

For forms, never rely on placeholders as labels. MDN is explicit that placeholders are not a substitute for labels, and labels materially improve assistive technology behavior and click/tap usability. Use visible <label>s, predictable validation, and generous target sizes. Authentication or validation flows should also be checked against WCAG 2.2 additions around accessible authentication and target size.

For data tables, use native HTML <table> whenever possible. The APG table guidance explicitly encourages native tables instead of ARIA role tables where a native equivalent exists. Only move to grid-like widgets if you actually need spreadsheet-like interactivity, keyboard compression, sort/filter statefulness, or row-level controls.

For tabs, follow APG keyboard behavior and preloaded content guidance if activation follows focus. This is especially useful on pages with specification variants, localization toggles, schema/JSON/source tabs, or “human / rendered / machine” views.

For dialogs, if you ship complex modals, follow APG modal-dialog behavior: move focus into the dialog on open, trap Tab order within the dialog, close on Escape, and return focus appropriately when the dialog closes. Keep dialogs large-screen elegant but mobile-fullscreen where needed to avoid background motion confusion and focus loss.

For code samples and blog/article pages, keep them extremely readable: wide but bounded measure, strong heading rhythm, clearly styled code fences, and optional copy buttons. The UAI area already behaves like a documentation/specification surface, so the redesign should borrow the best parts of modern docs sites rather than the conventions of product landing pages.

A small CSS-token skeleton is enough to set the tone:

@layer reset, tokens, base, components, utilities, overrides;

@layer tokens {
  :root {
    --bg: oklch(8% 0.02 260);
    --panel: oklch(12% 0.03 260);
    --line: oklch(30% 0.04 260);
    --fg: oklch(94% 0.01 260);
    --muted: oklch(72% 0.02 260);
    --accent: oklch(72% 0.18 220);
    --accent-2: oklch(78% 0.12 160);
    --radius: 0.625rem;
    --space-1: 0.5rem;
    --space-2: 1rem;
    --space-3: 1.5rem;
    --space-4: 2.5rem;
    --max: 80rem;
  }
}

@layer base {
  html { color-scheme: dark; }
  body {
    margin: 0;
    background:
      radial-gradient(circle at 20% 20%, color-mix(in oklab, var(--accent) 12%, transparent), transparent 28rem),
      linear-gradient(180deg, var(--bg), oklch(7% 0.01 260));
    color: var(--fg);
    font-family: var(--font-sans, system-ui, sans-serif);
  }

  a { color: inherit; text-decoration: none; }
  :focus-visible {
    outline: 2px solid var(--accent);
    outline-offset: 3px;
  }

  @media (prefers-reduced-motion: reduce) {
    *, *::before, *::after {
      animation-duration: 0.01ms !important;
      animation-iteration-count: 1 !important;
      transition-duration: 0.01ms !important;
      scroll-behavior: auto !important;
    }
  }
}

That is enough to replace large sections of Bootstrap’s theming posture with something much more distinctive and much less dependent on third-party assumptions.

Delivery engineering

The engineering target should be modern evergreen browsers, which is compatible with Vite’s default production baseline of current widely available browsers. In practice, that means Protocol5 can design for modern CSS, native ES modules, Intersection Observer, content visibility, and WebGL 2 without apologizing for legacy IE-era compromises. At the same time, the project should explicitly treat WebGPU and cross-document view transitions as optional enhancements because MDN does not yet treat them as universally Baseline features.

Testing should be layered the same way the app is layered. Use unit/component tests for pure rendering logic and store behavior. Use Playwright for end-to-end template coverage, route smoke tests, and visual regressions on major breakpoints. Use Lighthouse CI on every commit or pull request for performance, accessibility, best-practice, and SEO regression gates. Lighthouse CI is specifically designed to run Lighthouse continuously, assert on results, compare runs, and prevent regressions.

The page-quality budget should combine lab and field measures. Lighthouse is a lab tool, but Google’s recommended experience thresholds for real users remain the most important North Star: LCP ≤ 2.5s, INP ≤ 200ms, and CLS ≤ 0.1 at the 75th percentile. For ongoing delivery discipline, a performance budget is still useful as a set of limits on payload, request count, and timing. web.dev’s performance-budget guidance remains directionally sound: budgets are there to force tradeoffs early rather than discover regressions late.

A realistic Protocol5 launch target for core templates would look like this:

Template classLighthouse targetsField targetsInitial payload guidance
Home / section landingPerformance ≥ 95, Accessibility ≥ 98, Best Practices ≥ 95, SEO ≥ 95p75 LCP ≤ 2.5s, INP ≤ 200ms, CLS ≤ 0.1Keep shell-critical CSS+JS small; lazy-load premium motion layer
Dense documentation / UAI pagesPerformance ≥ 95, Accessibility ≥ 98, SEO ≥ 95Same as abovePrefer almost-zero client JS over decorative enhancement
Tooling / workbench surfacesPerformance ≥ 90, Accessibility ≥ 95, SEO as applicableINP discipline especially importantHeavier JS acceptable if isolated and route-scoped

Those Lighthouse numbers are recommended project targets rather than vendor-mandated thresholds. The vendor-cited part is that Lighthouse exists to audit performance, accessibility, best practices, and SEO, and Lighthouse CI exists to automate that in continuous integration.

For SEO, the rules are straightforward. Keep canonical content in the HTML response. Keep links crawlable with actual anchors and hrefs. Preserve stable URLs and HTTP status codes. Do not rely on dynamic rendering as a long-term strategy. If client-rendered content matters for discovery, verify rendering with Search Console tools. This is especially important on Protocol5 because many pages behave like documentation/specification pages instead of pure marketing pages.

CI/CD can stay simple:

name: ci
on: [push, pull_request]

jobs:
  build-test-audit:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - uses: actions/setup-dotnet@v4
        with:
          dotnet-version: '9.0.x'

      - uses: actions/setup-node@v4
        with:
          node-version: '20'

      - run: npm ci
      - run: npm run build
      - run: dotnet restore
      - run: dotnet test --configuration Release
      - run: npx playwright test
      - run: npm install -g @lhci/cli@0.15.x
      - run: lhci autorun

Lighthouse CI’s official README and getting-started flow specifically support this kind of automated collection/assert/upload path.

Migration roadmap, estimates, risks, and rollback

The right migration pattern is incremental replacement, not branch-and-burn. Keep the current MVC routes, keep _Layout as the integration seam, and peel dependencies away by template class. Because the live site is already split between shell and tool surfaces, that natural boundary should be reused: shell first, tools second, premium motion last.

Migration phases and estimated hours

PhaseScopeLow effortMedium effortHigh effort
Discovery and dependency mapHeadless crawl, template inventory, Bootstrap/jQuery usage map, performance baseline, design audit244060
Design system foundationTokens, type scale, spacing, color system, CSS architecture, component principles325688
Build and asset pipelineVite integration, manifest loading, TS foundation, lint/format/test setup244064
Layout and shell migrationRebuild header, footer, nav, layout grid, section frames, shared shells4888140
Core component libraryButtons, hero, cards, alerts, forms, tabs, tables, code blocks, article styles56104180
jQuery and Bootstrap extractionReplace plugins/utilities, remove data attributes, remove unused CSS/JS, template cleanup3672140
Interactive islandsTool-specific islands, data loading, state handling, hydration or web components2464140
Premium visual layerSVG motion system, procedural hero, shader/WebGL work, reduced-motion fallback1656180
QA, accessibility, SEO, hardeningE2E, visual review, Lighthouse CI, search checks, browser/device verification244072
Launch, monitoring, rollback prepFeature flags, asset rollback plan, smoke checks, production validation122036
Delivery bandTotal estimated hours
Low296 – 340
Medium580 – 620
High1,100 – 1,140

Those phase totals are intentionally conservative at the high end because “spectacularly technological” can mean very different things. If the visual ambition remains mostly CSS/SVG with one restrained WebGL hero, the realistic working number is closer to 420–560 hours. If the hero becomes a custom shader-heavy, cross-page motion system with extensive interactive tooling, the upper range escalates quickly.

A practical, executive-friendly way to think about it is this:

Delivery profileDescriptionRecommended whenExpected range
LowRemove Bootstrap/jQuery, rebuild shell and core components, mostly CSS/SVG visualsSpeed and maintainability matter more than spectacle260–340 h
MediumLow profile plus stronger motion system, robust component library, a few interactive islandsBest balance of impact and risk420–560 h
HighMedium profile plus premium shader/3D hero and deeper tool-surface modernizationBrand theater and experimentation are strategic goals680–900 h
gantt
    title Indicative modernization timeline
    dateFormat YYYY-MM-DD

    section Discovery
    Audit and dependency map         :a1, 2026-05-04, 14d
    Visual direction and prototypes  :a2, 2026-05-11, 14d

    section Foundation
    Tokens and CSS architecture      :b1, 2026-05-18, 14d
    Vite and asset pipeline          :b2, 2026-05-18, 10d

    section Shell
    Layout and navigation rebuild    :c1, 2026-06-01, 14d
    Shared components                :c2, 2026-06-08, 21d

    section Extraction
    Bootstrap and jQuery removal     :d1, 2026-06-15, 21d
    Interactive island migration     :d2, 2026-06-22, 21d

    section Experience
    Procedural hero and motion layer :e1, 2026-07-06, 21d
    Accessibility and SEO hardening  :e2, 2026-07-13, 14d

    section Release
    Staging validation and rollout   :f1, 2026-07-27, 7d

The critical sequencing principle is that premium motion comes after the shell is stable, not before it. That prevents the classic failure mode where the team spends weeks on a visual headline while typography, forms, and tables are still inconsistent.

Risk matrix

RiskLikelihoodImpactWhy it mattersMitigationRollback trigger
Hidden jQuery plugin dependenciesMediumHighLegacy plugins often hide in partials and inline scriptsPerform source grep + crawl inventory before removals; replace one plugin family at a timeUser-visible regression in nav/forms/tool flows
Bootstrap class sprawlHighMediumUtility/class dependence can be broader than expectedStart with design tokens and mapped replacements for grid, spacing, buttons, cardsMany templates still require Bootstrap after shell rewrite
Hydration mismatch in framework islandsMediumMediumReact/Vue/Solid hydration requires server/client markup alignmentPrefer Lit or client-only islands first; hydrate only when SSR parity is neededConsole mismatch warnings or layout instability in test
Overusing client routingMediumHighHurts crawl clarity and increases complexity for content pagesKeep MVC routing canonical; use client routers only inside toolsSearch rendering or navigation smoke tests fail
WebGPU support variabilityMediumMediumMDN still marks WebGPU limited availabilityBuild WebGPU as optional enhancement with WebGL/SVG fallbackRendering failures or degraded devices show broken hero
Accessibility regressions from motion/visual chromeMediumHighFocus visibility, target size, motion sensitivity are easy to damage in “futuristic” UIsReduced-motion path, strong focus styles, minimum target sizing, keyboard QAAccessibility score drops or manual keyboard traps appear
Performance regression from hero visualsHighHighProcedural effects can dominate CPU/GPU and inflate JSLazy-load hero, cap frame rates, pause offscreen, disable on reduced motion/low-end heuristicsLighthouse or field metrics regress materially

The hydration-mismatch risk is not hypothetical: React, Vue, and Solid all document that hydration expects matching server/client output. WebGPU support variability is also documented by MDN, which is why the fallback story matters.

Rollback strategy

The safest rollback plan is template- and asset-level reversibility, not “revert the whole branch.” Specifically:

Rollback layerStrategy
LayoutKeep old and new layouts side by side behind a configuration flag during rollout.
AssetsVersion assets by manifest and deploy old/new bundles in parallel until cutover is proven.
ComponentsReplace page regions one template family at a time so a broken component can be swapped back without losing the whole shell.
Visual heroTreat the premium hero as optional and remotely disable it if performance or rendering breaks.
RoutingDo not change canonical public URLs during design migration; preserve route handlers and metadata shape.
ToolsMigrate rich tool surfaces separately from shell pages so shell improvements can ship even if an app island slips.

In operational terms, that means the rollout should be feature-flagged at the layout and hero levels, and the deployment package should retain the previous asset manifest until the new shell clears smoke tests, Lighthouse assertions, and a short production soak period.

Open questions and limitations

The largest unresolved item is purely practical: I was able to inspect the live site’s structure and some content behavior, but not a full raw source-level asset list through the browsing outputs available here. So while the user’s brief states that Bootstrap and jQuery are present and should be removed, I did not independently verify the exact scripts/styles currently loaded on every template. That should be the first source-of-truth check in the discovery phase.

I also prioritized libraries with strong, current primary-source coverage in the evidence gathered here. That is why Three.js, PlayCanvas, deck.gl, Lit, Vue, React, and Solid are evaluated more deeply than libraries like regl. If regl or another lower-level rendering library is a serious candidate, it deserves a narrow follow-on technical spike focused on authoring ergonomics, maintenance burden, and fallback behavior inside the MVC shell.

With those caveats, the high-confidence recommendation remains unchanged: keep ASP.NET MVC/Razor, replace Bootstrap and jQuery incrementally, adopt Vite + TypeScript, use HTML/CSS/SVG as the core visual substrate, use Lit as the default islands technology, and add Three.js-based procedural motion only where it creates real brand value without endangering content delivery, accessibility, or SEO.