ddtcorex

07 Sept 2026 · 3 min read

Hyva React components and the GraphQL storefront

How to build custom React components on top of Hyva using the Magento GraphQL API — when it helps, how it differs from Alpine/Tailwind, and how to keep it inside the Hyva theme.

Part 12 of the Hyva series — advanced storefront work. Implementation-focused.

Two React surfaces in Hyva

Hyva has two distinct places React appears, and conflating them causes confusion:

  1. Hyva Checkout — a full React application (covered in the previous post). It owns the entire checkout route.
  2. Hyva React (the module) — the ability to drop React components into otherwise-Tailwind/Alpine pages, talking to Magento over GraphQL.

This post is about the second: embedding React where it earns its keep, without turning the whole storefront into a React app.

When React earns its place

The rest of Hyva is Tailwind + Alpine for good reason — most storefront UI is declarative markup with light interactivity, and Alpine covers it with near-zero payload. Reach for React only when a component is genuinely stateful or complex:

  • A configurator with many interdependent inputs.
  • A live-search or autocomplete with debounced GraphQL queries and result rendering.
  • A heavily animated or canvas-based widget.

If a component is "show/hide on click," that is Alpine. If it is "maintain a derived UI from a graph of inputs," that is React. The discipline is to use React surgically, not as a default.

Talking to GraphQL

Hyva React components use the same Magento GraphQL endpoint the PWA storefront uses. A minimal query for product data:

query ProductCard($sku: String!) {
  products(filter: { sku: { eq: $sku } }) {
    items {
      name
      price_range { minimum_price { regular_price { value } } }
    }
  }
}

The component fetches via the store's GraphQL URL (the same one the admin's Swagger/GraphQL introspection exposes). The key difference from Alpine: the request and its result shape are handled by React state and effects, so you get component-scoped re-rendering rather than a whole-page Alpine refresh.

Keeping React inside the Hyva theme

A Hyva React component is mounted into a Tailwind page through a small bridge — a PHTML template that renders a mount point and a script that boots the React tree into it. The surrounding page (header, footer, category chrome) stays Tailwind/Alpine; only the widget is React.

This preserves the performance story: the heavy lifting of the page is still the small Hyva payload, and React loads only for the component that needs it. Budget the React bundle carefully — a single heavy component should not pull in a framework-sized chunk for the whole route.

Pitfalls

  • Don't rebuild the theme in React. Once you start rendering category grids in React, you have a headless storefront with none of the Hyva tooling. Use React for the widget, Tailwind for the page.
  • Cache the GraphQL responses. Product and config queries are cacheable; add appropriate cache tags so Varnish/FPC can serve them, the same as any other Magento request.
  • Match the CSP. React bundles load as scripts; your CSP (see the performance post) must allow them, or the widget silently fails to mount.

What's next

The last post in the series hardens performance: CSP configuration, layout resets, full-page-cache interaction, and how to measure the before/after so the gains are provable.

Next in this series: Hyva performance hardening — CSP, FPC, and measurement — /blog/magento2-hyva-performance

magento2hyvafrontendreactgraphql