Skip to main contentSkip to main content

Get 15% off your first order — use code WELCOME15 at checkout

Index:
03
Industry:
Hospitality & Restaurants
Year:
2026
Status:
Delivered
The Thai — Bar & Restaurant · Hospitality & Restaurants

The Thai

A statically generated Next.js rebuild of thethai.uk that turned a PDF-only menu into 42 crawlable dishes, moved 28 blog posts off WordPress without dropping a URL, and brought the navy and gold of the printed menu onto the web.

https://thethai.ukGGX
The Thai — Hospitality & Restaurants project by Glasgow GFX
The Challenge

The old thethai.uk was WordPress, and its menu was a PDF. Every dish, every price and every allergen note sat inside a file that search engines cannot read as a menu and that a phone will not display well, so the single thing most people arrive at a restaurant site to look at was effectively invisible. The blog was the other half of the problem. Twenty-eight posts had built up on WordPress URL shapes, /uncategorized/ post paths, category and author archives, per-post RSS feeds and year, month and day date archives, and a rebuild that changed the URL structure would have thrown away whatever those links were worth. On top of that, the site did not look like the restaurant: the printed menu in the room was navy and gold, and the website was not.

The Solution

We rebuilt the site from scratch as a statically generated Next.js App Router build with Tailwind, and took the brand off the printed menu rather than inventing one, navy and gold tokens plus Marcellus and Figtree as the type pairing. The menu became the centrepiece: 42 dishes across nine sections, rendered as real HTML with descriptions, prices, per-variant pricing and allergen labels, and emitted as Menu JSON-LD so a search engine reads it as a menu rather than as a link to a download. On top of that sits a client-side filter, vegetarian dishes, mild or no spice, and exclusion of any of the eleven allergens present in the data, all with no page reload and no server call. The blog moved across as Markdown with Article structured data, and we wrote 25 redirect rules covering the old post URLs, the category and author archives, the per-post RSS feeds, the date archives and the wp-content menu PDF that every old Menu link pointed at. Restaurant JSON-LD in the layout carries the address, geo coordinates, opening hours and award. Photography and video are served from Vercel Blob rather than committed to the repository. The site also stopped handing reservations to a third-party widget: booking now happens on the site itself, with a staff diary behind it.

Plate 01

Rebrand & Homepage

The restaurant already had a brand, it just was not on the website. We took the navy and gold off the printed menu, built them into design tokens with Marcellus for display and Figtree for body, and rebuilt the homepage around the restaurant photography rather than around a theme.

  • Navy and gold palette and type pairing taken from the printed menu, not invented
  • Homepage rebuilt around the restaurant photography and the essentials, hours, location, menu and booking
  • Statically generated App Router build with Tailwind, no CMS and no plugin stack to maintain
  • Photography and video served from Vercel Blob, keeping large media out of the repository
Rebrand & HomepageGGX
The Thai — Rebrand & Homepage
Plate 01 · Rebrand & Homepage
Plate 02

The Menu, Rebuilt as HTML

This is the page the rebuild was really for. The menu moved out of a PDF and into typed data rendered as HTML: 42 dishes across nine sections, with descriptions, prices, per-variant pricing where a dish comes as veggie, chicken or prawn, and allergen labels on every item. A client-side filter sits on top so a guest can narrow to vegetarian dishes, to mild or no spice, or exclude specific allergens before they ever phone.

  • 42 dishes across nine sections rendered as indexable HTML with prices and descriptions
  • Per-variant pricing handled properly, so a dish offered as veggie, chicken or prawn shows all three
  • Allergen labels on every dish, drawn from the same data the filter uses
  • Filter chips for vegetarian, mild or no spice, and exclusion of any of eleven allergens, client-side and instant
  • Menu JSON-LD with a MenuSection per course and an Offer per price, so the menu is readable by search engines
  • The PDF is still linked for anyone who wants it, it is just no longer the only version
The Menu, Rebuilt as HTMLGGX
The Thai — The Menu, Rebuilt as HTML
The Menu, Rebuilt as HTMLGGX
The Thai — The Menu, Rebuilt as HTML detail
9:41
The Thai — The Menu, Rebuilt as HTML detail
Plate 02 · The Menu, Rebuilt as HTML
Plate 03

Blog Migration & Local SEO

Twenty-eight posts came across from WordPress as Markdown. The interesting work was not the content, it was the URLs: WordPress had been serving those posts under /uncategorized/ paths, with category and author archives, a per-post RSS feed each, and year, month and day date archives all linked from the old post cards. Every one of those shapes now redirects permanently to its equivalent on the new site.

  • 28 posts migrated from WordPress as Markdown with Article structured data
  • 25 permanent redirect rules covering post URLs, category and author archives, RSS feeds and date archives
  • The wp-content menu PDF URL, which every old Menu link pointed at, redirected to the new menu page
  • Restaurant JSON-LD in the layout with address, geo coordinates, opening hours and award
  • Per-page metadata, canonical URLs, sitemap and robots generated at build time
Blog Migration & Local SEOGGX
The Thai — Blog Migration & Local SEO
Plate 03 · Blog Migration & Local SEO
Plate 04

Booking & Contact

The old site handed reservations to a third-party widget. Booking now lives on the site: availability is computed from the restaurant tables and areas held in Postgres, guests amend or cancel from a tokenised link sent with their confirmation, and staff work the diary in an admin area. Reservations that arrive by email from First Table are parsed and land on the same diary, so there is one list rather than two.

  • First-party booking flow with availability computed from the tables and areas in Postgres
  • Guests amend or cancel from a tokenised link, no account and no login
  • Staff diary in an admin area, with web and email reservations in one place
  • First Table reservations ingested from the restaurant mailbox onto the same diary
  • Contact page with map, address, phone and the opening hours that drive the structured data
Booking & ContactGGX
The Thai — Booking & Contact
Booking & ContactGGX
The Thai — Booking & Contact detail
9:41
The Thai — Booking & Contact detail
Plate 04 · Booking & Contact
Results
42
Dishes indexed
28
Posts migrated
25
Redirect rules
11
Allergen filters
  • 01A PDF-only menu replaced by 42 dishes across nine sections as crawlable HTML, each with description, price, variant pricing and allergen labels
  • 02Menu JSON-LD emitted per section and per dish, including prices, so the menu is machine-readable rather than a link to a download
  • 03Client-side filters for vegetarian dishes, mild or no spice, and exclusion of any of eleven allergens, with no page reload
  • 0428 blog posts migrated off WordPress with 25 redirect rules covering post URLs, category and author archives, per-post RSS feeds, date archives and the old menu PDF
  • 05Restaurant JSON-LD carrying address, geo, opening hours and award, alongside per-page metadata, sitemap and robots
  • 06Navy and gold rebrand taken from the printed menu, so the site and the room finally match
  • 07Bookings taken on the site itself, with availability computed from the restaurant tables and a staff diary behind it, replacing the third-party reservation widget
  • 08First Table reservations that arrive by email parsed and landed on the same diary as web bookings
  • 09Photography and video served from Vercel Blob rather than committed to the repository
Spec Sheet
Architecture
Framework
Next.js 16 with React 19, App Router and React Server Components
Rendering
Static generation for the marketing site, with the booking and admin routes dynamic
Content
Menu as typed JSON and blog posts as Markdown, both read at build time, no CMS
Database
PostgreSQL via Drizzle ORM for tables, areas, bookings and the staff diary
Styling
Tailwind CSS 4 with navy and gold brand tokens as CSS variables
Deployment
Vercel, with large media in a Vercel Blob store rather than git
Integrations
Structured Data
Restaurant JSON-LD in the layout, Menu JSON-LD on the menu, Article on each post
First Table
Reservation emails polled from the restaurant mailbox over IMAP and parsed onto the diary
Vercel Blob
Photography and video served from a dedicated blob store, referenced through next/image
Maps
Google Maps link and embed on the contact page, matching the geo in the structured data
Performance
Menu
Rendered at build time from typed data, filtering happens in the browser with no server call
Images
next/image against the blob store, with the repository kept free of large media
Fonts
Marcellus and Figtree loaded through next/font, self-hosted and subset
Redirects
Handled at the edge by Next.js config rather than by a plugin or a htaccess file
Code Quality
  • TypeScript strict mode throughout
  • Menu data typed and read through a single loader, so a malformed dish fails the build
  • Vitest coverage over booking slot generation and booking API validation
  • Secrets in environment variables only, never in the repository
  • Semantic HTML for the menu, so the filter enhances a page that already works without it
Technologies
  • Next.js 16
  • React 19
  • TypeScript
  • Tailwind CSS 4
  • Drizzle ORM
  • PostgreSQL
  • Vercel Blob
  • Vitest
  • Vercel
Next Project

Flora & Fable Floristry

Brand identity, bespoke e-commerce storefront, postcode delivery engine, and self-service admin dashboard for a Glasgow floristry business.

Flora & Fable Floristry — E-commerce & Retail project by Glasgow GFX

Have a project?

Web, software and brand work for businesses across the UK. Tell us what you are building.

Glasgow GFX Print Studio

Visit
The Pentagon Business Centre
Unit 204b, 36–38 Washington Street
Glasgow G3 8AZ
Hours
Mon–Fri 9:00–18:00
Sat 10:00–18:00
Sun closed
Service area
Glasgow, Hamilton, Paisley, East Kilbride, Motherwell. Free delivery across Central Scotland on orders over £50.