How to Build a Client Appointment Booking App with Claude or ChatGPT

Updated onΒ 
June 26, 2026
Joyce Kettering
DevRel at WeWeb

If your clients book appointments by email or phone today, this guide shows you how to replace that with a simple app. Clients request a time on a public page, and your team approves or rejects each request from a private staff page. Approving a request sends the client a confirmation email.

You'll build it by prompting Claude or ChatGPT, connected to WeWeb through the WeWeb MCP server. Then you'll check and secure what it made in the visual editor. The example is a dental clinic, but the same app works for salons, tutors, consultants or any business that confirms appointments by hand.

What you're building

The app has two pages:

  • A public booking page. Clients pick an appointment type, a preferred date and time, and leave their contact details. No account needed.
  • A private staff page. Staff see every request, filter by status, and approve or reject each one. Approving sends a confirmation email.

Submitting the form is a request, not a booking. Staff check the schedule before confirming, so nothing is booked until a person has decided. That keeps the first version small: no client logins, no live availability, no calendar sync. You can add those later if your process needs them.

The dental example calls clients patients and calls staff with access admins. Swap in your own words when you adapt it.

How a request moves through the app

Every booking has one of three statuses: Pending, Approved or Rejected.

  1. The patient submits a request. They choose an appointment type (Cleaning, Checkup, Whitening, Emergency or Consultation), a preferred date and time, and enter their name, email, phone number and any notes. The app saves it as Pending.
  2. The patient sees "Request received". Not "booked" or "confirmed", because nobody has checked the schedule yet.
  3. Staff review it. On the staff page, they filter to Pending and check the time against the clinic's schedule.
  4. Staff approve or reject it. Approving sets the status to Approved and emails the patient a confirmation. Rejecting sets it to Rejected and sends nothing, so staff call or email the patient to offer another time.

πŸ’‘ Keeping "Emergency" as a type? Nobody watches a request form in real time. Tell patients on the page when requests are reviewed and how to reach the clinic if they can't wait.

The booking table

The whole app runs on one table. Each row is one request.

Field What it stores
id Unique ID for the booking
patient_name Patient's full name
patient_email Where the confirmation email goes
patient_phone So staff can call about changes
appointment_type Cleaning, Checkup, Whitening, Emergency or Consultation
appointment_date Preferred date
appointment_time Preferred time
notes Optional message from the patient
status Pending, Approved or Rejected. New requests start as Pending
created_at When the request was submitted

Staff accounts don't go in this table. WeWeb's built-in authentication stores staff users and their roles separately.

Step 1: Get set up

Tick these off before you prompt AI:

Step 2: Give the agent the prompt

Here's the prompt from the video. Replace [URL] with your project URL.

Help me build a simple client portal for a dental clinic with appointment scheduling.

Project: [URL]

Use the HabitPlus Design System present in this folder for the UI components, spacing, typography, colors, and design patterns.

Build two main pages:

1. Patient booking page

Patients should be able to:
- Select an appointment type, such as Cleaning, Checkup, Whitening, Emergency, or Consultation
- Choose a preferred appointment date
- Choose a preferred appointment time
- Enter their full name
- Enter their email address
- Enter their phone number
- Add optional notes
- Submit the appointment request
- See a confirmation message after submitting

When a patient submits a booking, create a new booking record with the status set to "Pending."

2. Admin bookings page

Clinic staff should be able to:
- View all appointment booking requests
- See the patient name, email, phone number, appointment type, requested date, requested time, notes, status, and created date
- Filter bookings by status: Pending, Approved, and Rejected
- Approve a pending booking
- Reject a pending booking

When the admin clicks "Approve":
- Update the booking status to "Approved"
- Send a confirmation email to the patient using WeWeb Email

Use this email content:

Subject:
Your dental appointment is confirmed

Body:
Hi {{patient_name}},

Your appointment request for {{appointment_type}} on {{appointment_date}} at {{appointment_time}} has been approved.

We look forward to seeing you at the clinic.

Best,
The Dental Clinic Team

When the admin clicks "Reject":
- Update the booking status to "Rejected"

Data structure:
Create a table with these fields:
- id
- patient_name
- patient_email
- patient_phone
- appointment_type
- appointment_date
- appointment_time
- notes
- status
- created_at

Default status should be "Pending."

Make sure the booking submission flow, admin approval flow, status updates, databases, APIs and WeWeb Email action are all connected properly.

Step 3: Approve the plan and turn on authentication

Before it builds anything, the agent shows you its plan. Check that it names your project and covers both pages, the bookings table and the approve and reject actions. If something's missing, ask for it now. It's easier to change the plan than the finished app. Then approve it.

Partway through the build, the agent will ask you to turn on WeWeb's authentication so staff can sign in. Go to Data & API β†’ Authentication, switch it on, and tell the agent to continue. You can watch this at 2:52 in the video.

Step 4: Decide who can see and change bookings

The first prompt builds what each page does. This one sets who can use them. Until you add access rules, the staff page and its booking data aren't locked to your team. For a real clinic, that would mean:

  • Anyone could read patient details, including names, emails, phone numbers and notes.
  • Anyone could approve or reject bookings, such as confirming a slot or rejecting a real patient's request.
  • The form could be tricked into saving a request that's already marked Approved.

Give the agent this second prompt before you test the app or share its link:

Now add access rules to the app:
- Create an "admin" role. Only signed-in users with this role can open the admin bookings page.
- Only users with the "admin" role can load bookings or approve and reject them.
- The patient booking page stays public, but it can only create new bookings. It cannot read existing ones.
- Always set the status of a new booking to "Pending" in the backend, whatever the form sends.

Step 5: Check what the agent built

When the agent finishes, open the project in the WeWeb editor. Everything it made shows up as real pages, tables and workflows that you can click into, check and change. Look for these five things:

  1. The booking page has every form field from the prompt, and the message after submitting says "Request received", not "confirmed".
  2. The staff page lists bookings with a status filter and Approve and Reject buttons.
  3. The bookings table in Data & API β†’ Tables has the ten fields above.
  4. The submit workflow creates a booking and sets the status to Pending itself, rather than copying a status from the form.
  5. The approve workflow changes the status to Approved, then runs the Send Email action. The reject workflow only changes the status.

If something is missing or wrong, ask the agent to fix that one piece, or change it yourself in the editor.

Step 6: Confirm the access rules

Check that the agent applied every access rule from Step 4. This step decides whether patient details are protected or exposed.

  1. Check the role. In Data & API β†’ Authentication β†’ Roles, there should be a role called admin. If there isn't, click Insert and create it.
  2. Add your staff. In the Users tab, click + Insert to add each staff member, then give them the admin role. Add one more test user without the role; you'll need it in Step 7.
  3. Check the page. Open the staff page's settings, go to Private access, and allow only authenticated users with the admin role.
  4. Check the data. Open the bookings view in Data & API β†’ Tables, set its access to Authenticated, and restrict it to admin.
  5. Check the actions. In Data & API β†’ Backend Workflows, open the approve and reject endpoints and set their Security to the admin role.

Check all three: page, data and actions. Hiding the page isn't enough on its own, because anyone who calls a public data view directly can still read every booking. WeWeb's docs explain how roles protect pages, views and endpoints. Joyce makes the page and view changes from 4:21 in the video.

πŸ’‘ Building a portal with client logins next? This guide shows how to give each client access to only their own data.

Step 7: Test your app

Ask WeWeb AI to test it. Open the AI assistant in the WeWeb editor and give it these tests:

Test my app in preview, using made-up patients and [your email address]:
1. Submit a booking request. Check that "Request received" appears and the booking is saved as Pending.
2. Approve it on the admin bookings page. Check the status changes to Approved.
3. Submit a second request and reject it. Check the status changes to Rejected.
4. Sign out and try to open the admin bookings page. Check you're blocked.
5. Submit two requests for the same date and time. Check both are saved as Pending.
Tell me what fails, and list the test bookings you create.

Then watch it test your app. It clicks through each page, fills in the form and checks the results, and you can take over at any time. If something fails, it shows you what it found and asks before fixing it. Its test bookings are real records, so delete them afterwards.

Then run the same tests yourself in the published app. Also check that the confirmation email reached your inbox (look in spam too), and that your test user without the admin role can't open the staff page.

πŸ“ Before real patients use it. This tutorial builds a request-and-approval flow, not a compliant healthcare system. Check the privacy rules that apply to you, such as HIPAA in the US, before collecting real patient information.

Step 8: Lock what you've tested

Your app now stores patient details, and Step 6 decided who can see them. Before you ask the agent for more features, lock the parts that keep that data private, so no new prompt can change them by accident.

Turn on Protect from AI changes for:

  • The bookings table. This also locks every view built on it, including the admin-only one.
  • The approve and reject workflows, so only admins can change a booking.
  • The staff page, so its access settings stay as you tested them.

The agent can still read locked parts, so new features match them, but it can't edit or delete them. If a request needs something locked, it tells you which part and suggests another way.

When you do want to change a locked part, such as adding a rejection email, unlock it, make the change, rerun your tests and lock it again. This is how you keep building with AI on an app that holds sensitive data: you decide what the agent can touch, and nothing changes without you testing it.

Optional add-ons

The app works on its own. Add these once your team is using it and you know what's missing.

More emails with WeWeb Email

The approval email uses WeWeb's built-in Send Email action, which runs in a backend workflow without a separate email provider. You can reuse it for:

  • A rejection email inviting the patient to request another time.
  • A reply-to address your front desk reads, so patients can reply to cancel or reschedule instead of calling.

Reminders need their own workflow. Approving sends one email at that moment. A reminder the day before needs something that runs on a schedule, finds tomorrow's Approved bookings and emails each patient. WeWeb's built-in triggers respond to events such as sign-ups, not to a clock, so set up the schedule separately, for example in an automation tool your team already uses. Track which reminders have gone out so nobody gets the same one twice.

Slack alerts for new requests

If your team lives in Slack, post to a clinic channel whenever a request arrives so nobody has to keep the staff page open. The Slack integration adds a Send message action you can place in the submit workflow. Keep the message short, such as the appointment type and requested date, and let staff open the app for the patient's details.

Calendly instead of the request form

If you'd rather patients pick from real open slots, the Calendly integration embeds your Calendly scheduler in a WeWeb page, and Calendly handles availability and confirmation. This replaces the request flow rather than adding to it: Calendly bookings don't appear in your bookings table without extra work with Calendly's API or webhooks. Pick one route.

Protect finished work from the agent

As you keep asking the agent for changes, you can lock the parts you're happy with. If your plan includes Protect from AI changes, the agent can still read protected pages, tables and workflows for context but can't rewrite them. This controls what the agent can edit, not what visitors can see, so it doesn't replace the access settings from Step 6.

FAQs

Is an appointment confirmed as soon as the patient submits the form?

A request stays Pending until a staff member approves it. The patient sees "Request received" on screen and only gets the confirmation email after approval.

Can patients cancel or reschedule?

Not through the app in this build. Patients reply to the confirmation email (if you set a reply-to address your team reads) or contact the clinic. Letting patients manage their own appointments needs patient sign-in and rules for what they can change, which is a bigger build.

Does the app send reminders?

Not by default. The approval email is sent once. Reminders need a separately scheduled workflow, described in the add-ons above.

Do patients need an account?

The booking page is public and patients only enter their contact details. Only staff sign in, and only staff with the admin role can see bookings.

What happens if two patients request the same time?

Both arrive as Pending. The app doesn't check availability, so staff choose which to approve and contact the other patient. If you need patients to see only open slots, use the Calendly route or build availability logic as a separate project.

Can I use this for a business that isn't a dental clinic?

Yes. Change the appointment types, page copy and email text in the prompt, and the same flow works for salons, consultants, tutors or any service business that confirms appointments by hand. For more ideas, see what else you can build in a small business client portal.

Do I have to use Claude?

The WeWeb MCP server also works with ChatGPT and other MCP-compatible agents such as Claude Code, Cursor and Codex. You can also build the same app with WeWeb AI inside the editor, or by hand in the visual editor.

Launch a booking flow your team can manage

Once your tests pass, your team has one place to handle appointment requests: clients ask for a time, staff review each one, and an approval sends the confirmation. Everything stays visible in WeWeb's editor, so you can change the design and logic directly rather than starting over with a new prompt.

Start with the request flow, then add reminders, Slack alerts or a full client portal as your business needs them.

Start building in WeWeb