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:
- Hyva Checkout — a full React application (covered in the previous post). It owns the entire checkout route.
- 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