---
title: "ServiceMenu"
slug: servicemenu
date: 2026-07-20
url: https://mohammadhameed.dev/projects/servicemenu
status: published
tags: ["fullstack", "ai"]
technologies: ["Next.js", "TypeScript", "PostgreSQL", "Tailwind CSS", "Stripe"]
---

{/* Sample case study for the design refresh — verify metrics and swap in
    real product screenshots before this stands as public copy. */}

ServiceMenu started with a small observation: the businesses that need a web
presence the most are the ones least equipped to maintain one. A great
detailing shop can have a five-star shop floor and a page that looks like it
was assembled from a 2011 template.

## The problem

Brochure sites describe a business. They rarely let you *do* anything —
compare services, see what a visit actually involves, book the thing. And
every time the owner wants to change a price, they open a ticket with whoever
built the site.

We wanted the opposite: a page that behaves like a product, where the
business owner edits content and instantly sees it as a customer would.

<Callout type="insight" title="Design constraint">
If the owner can't update it themselves on a phone in ten minutes, the page
rots. Freshness is a feature, not a nice-to-have.
</Callout>

## How it works

Everything the owner edits is structured content — services, options,
pricing, media — stored once and rendered as real routes with structured
data. The builder is a live split view: form on one side, the actual page on
the other, updating as you type.

```ts
type Service = {
  id: string;
  name: string;            // "Ceramic coating"
  duration: string;        // "3 hrs"
  tiers: Tier[];           // bronze / silver / ceramic
  faqs: { q: string; a: string }[];
  bookable: boolean;
};
```

That single shape powers the public page, the structured data, the share
cards, and the booking flow — one source of truth, many surfaces.

<Figure src="/images/projects/servicemenu-alt.svg" alt="Service tiers rendered as a public page" caption="The tier block — prices, inclusions, and a booking hook — rendered from one schema." />

## Inside the product

The public page is treated like an app screen, not a printout:

| Surface | What it does |
| --- | --- |
| Service index | Every service on its own URL, crawlable and shareable |
| Tier comparison | Side-by-side inclusions so customers choose without calling |
| Live booking | Hooks into the business's calendar, no third-party widget sprawl |
| Share kit | Per-page OG images so links look native in chat apps |

## What we shipped first

The first release is deliberately small: services, tiers, FAQs, booking, and
a shareable link. No blogs, no coupons, no "all-in-one" suite. A service
business's whole job is answering *what do you do, what does it cost, when
can you do it* — so the page answers exactly those.

<PullQuote author="Product principle">
A page is finished when a customer never needs to phone to ask a basic
question.
</PullQuote>

## What I work on now

- Turning the preview engine into an AI-assisted copy editor for owners.
- Multi-location support (one shop, three addresses, one identity).
- Hardening the booking conflict edge cases across time zones.

If you run a service business — or you're curious whether the no-code promise
is real this time, [the site is live](https://servicemenu.io), and
[my inbox is open](/contact).
