Skip to main content
All work

XB Labs FiveM

A custom storefront for my FiveM scripts, with checkout on Tebex.

Role
Design, development and hosting
Year
2026
The XB Labs FiveM home page, with the hero and a featured package card.
pages prerendered
8
automated browser tests
26
WCAG 2.2 accessibility
AA
cookies or trackers
0

The brief

I sell FiveM scripts and resources. Tebex already handles the catalogue and checkout, but I wanted a shop that looks like my other sites and keeps buyers on a page I control until they pay.

The store had to work from a public token only: no backend, no Tebex.js, no private key, and nothing stored on the server. Payments stay on checkout.tebex.io. It also had to meet the same bar as everything else I ship: 360px phones, keyboard and screen-reader use, reduced motion, and readable HTML with JavaScript off.

What I built

  • A home page, store listing, package page, basket, and the complete and cancel return pages
  • Live catalogue and basket calls to the Tebex Headless API, using the public token only
  • Sign in with Cfx.re through Tebex’s basket auth, so the licence goes to the buyer’s account
  • Friendly errors when Tebex is down or identity verification is still pending
  • Privacy, terms and contact pages written for UK law, with no cookies or analytics

Engineering highlights

  • Real HTML for every page

    The same prerendered React Router 7 setup as my other sites, so the shop loads as real HTML and still works if JavaScript is off. The catalogue then hydrates from Tebex in the browser.

  • Public token only

    The Tebex private key never enters the repo, the client bundle or the container. Checkout happens on Tebex’s own pages, so this site never sees card details.

  • A strict security policy

    No inline scripts or styles. The Content Security Policy stays at “default-src 'self'”, with connect-src only for the Headless API and images from Tebex’s CDN.

  • Accessibility tested on every change

    Built to WCAG 2.2 AA. Twenty-six automated browser tests run axe checks on every page, at phone and desktop sizes, before each release.

  • Private by design

    No cookies, no analytics and no server-side storage. The basket id lives in sessionStorage only for that visit, and the privacy notice says so.

  • Lean, repeatable hosting

    A small read-only container behind the same shared Caddy proxy as my other sites, deployed with one script that runs every check and keeps the previous release for rollback.

Built with

  • React 18
  • React Router 7
  • TypeScript
  • Vite
  • SCSS modules
  • Vitest
  • Playwright
  • axe-core
  • Docker
  • Caddy
  • Tebex Headless API

Screens

Got a project in mind?