Appointment request form template

    A preferred date and time, a second choice and the reason for the visit — a request you confirm, not a calendar.

    Reviewed by Ritu Fadadu · Last reviewed

    Preview and code

    Preview

    Code — replace YOUR_ENDPOINT_ID with your form's ID

    <style>
      .fb-form { display: grid; gap: 1rem; max-width: 36rem; }
      .fb-field { display: flex; flex-direction: column; gap: 0.375rem; }
      .fb-fieldset { margin: 0; padding: 0; border: 0; min-width: 0; }
      .fb-label { font-weight: 600; }
      .fb-optional { font-weight: 400; color: #6b7280; }
      .fb-help { margin: 0; font-size: 0.875rem; color: #6b7280; }
      .fb-input { box-sizing: border-box; width: 100%; padding: 0.625rem 0.75rem; border: 1px solid #d1d5db; border-radius: 0.5rem; background: #fff; color: #111827; font: inherit; }
      .fb-input:focus { border-color: #2563eb; outline: 2px solid #2563eb; outline-offset: 1px; }
      .fb-options { display: flex; flex-direction: column; gap: 0.5rem; }
      .fb-option { display: flex; align-items: center; gap: 0.5rem; }
      .fb-check { width: 1.125rem; height: 1.125rem; margin: 0; accent-color: #2563eb; }
      .fb-button { justify-self: start; min-height: 44px; padding: 0.625rem 1.25rem; border: 0; border-radius: 0.5rem; background: #2563eb; color: #fff; font: inherit; font-weight: 600; cursor: pointer; }
      .fb-button:hover { background: #1d4ed8; }
      .fb-button:focus-visible { outline: 2px solid #2563eb; outline-offset: 2px; }
      .fb-button:disabled { opacity: 0.6; cursor: wait; }
      .fb-status { margin: 0; min-height: 1.5em; }
      @media (min-width: 640px) {
        .fb-form { grid-template-columns: 1fr 1fr; }
        .fb-field, .fb-button, .fb-status { grid-column: 1 / -1; }
        .fb-field--half { grid-column: auto; }
      }
    </style>
    
    <form id="fb-form" class="fb-form" action="https://formboost.app/f/YOUR_ENDPOINT_ID" method="POST">
      <div class="fb-field fb-field--half">
        <label for="fb-name" class="fb-label">Full name</label>
        <input type="text" id="fb-name" name="name" class="fb-input" required autocomplete="name">
      </div>
      <div class="fb-field">
        <label for="fb-email" class="fb-label">Email</label>
        <input type="email" id="fb-email" name="email" class="fb-input" required autocomplete="email">
      </div>
      <div class="fb-field fb-field--half">
        <label for="fb-phone" class="fb-label">Phone <span class="fb-optional">(optional)</span></label>
        <input type="tel" id="fb-phone" name="phone" class="fb-input" autocomplete="tel">
      </div>
      <div class="fb-field fb-field--half">
        <label for="fb-service" class="fb-label">Type of appointment</label>
        <select id="fb-service" name="service" class="fb-input" required>
          <option value="">Choose…</option>
          <option value="consultation">Consultation</option>
          <option value="follow-up">Follow-up</option>
          <option value="something-else">Something else</option>
        </select>
      </div>
      <div class="fb-field fb-field--half">
        <label for="fb-date" class="fb-label">Preferred date</label>
        <input type="date" id="fb-date" name="date" class="fb-input" required>
      </div>
      <div class="fb-field fb-field--half">
        <label for="fb-time" class="fb-label">Preferred time</label>
        <input type="time" id="fb-time" name="time" class="fb-input" required>
      </div>
      <div class="fb-field">
        <label for="fb-alternative" class="fb-label">
          A second choice of date and time
          <span class="fb-optional">(optional)</span>
        </label>
        <input
          type="text"
          id="fb-alternative"
          name="alternative"
          class="fb-input"
          placeholder="e.g. Thursday afternoon"
        >
      </div>
      <div class="fb-field">
        <label for="fb-notes" class="fb-label">
          Anything we should know beforehand?
          <span class="fb-optional">(optional)</span>
        </label>
        <textarea id="fb-notes" name="notes" class="fb-input" rows="3"></textarea>
      </div>
      <!-- Honeypot: keep it hidden. People never see it; bots fill it in and get flagged as spam. -->
      <div
        aria-hidden="true"
        style="position:absolute;left:-9999px;width:1px;height:1px;overflow:hidden"
      >
        <label for="fb-honey">Leave this field empty</label>
        <input type="text" id="fb-honey" name="_honey" tabindex="-1" autocomplete="off">
      </div>
      <input type="hidden" name="_subject" value="New appointment request">
      <button type="submit" class="fb-button">Request appointment</button>
    </form>
    

    About this template

    This form collects a request, not a booking. It does not check your calendar or hold a slot; it gives you a preferred date and time plus a second choice, and you confirm one. For a small practice, a studio or a consultant that is often all the scheduling needed, and it keeps double-booking impossible because you are the one confirming.

    Date and time use the browser's native pickers, which are accessible and need no JavaScript library. Asking for a second choice up front saves the back-and-forth when the first one is taken.

    Say on the page how you will confirm, and how soon. A custom redirect to a “we'll confirm within one working day” page sets that expectation; on Starter and above, Auto Reply sends it by email too.

    Fields in this template

    FieldNameTypeRequiredWhy it is there
    Full namenameShort textYesRequired.
    EmailemailEmailYesRequired: it is where the confirmation goes.
    PhonephonePhoneNoOptional, for last-minute changes.
    Type of appointmentserviceDropdownYesRequired, so you know how long to book.
    Preferred datedateDateYesRequired native date picker.
    Preferred timetimeTimeYesRequired native time picker.
    A second choice of date and timealternativeShort textNoOptional free text — easier to answer than a second pair of pickers.
    Anything we should know beforehand?notesLong textNoOptional context before the appointment.

    Each name becomes a column in your dashboard and a row in the notification email. The hidden _honey field is the honeypot; _subject sets the email's subject line. Both are reserved fields and never appear in the field table.

    Make it yours

    • Add min to the date field (for example tomorrow's date, set from JavaScript) to stop requests for the past.
    • List your opening hours next to the form; the time picker does not know them.
    • Rename the service options to your own and keep them few — each is a different length of slot.
    • If you work from more than one location, add a single-choice location question above the date, so every request names the place as well as the time and nobody turns up at the wrong door.

    Where the submissions go

    • Each request is stored and emailed to you. With the HTML + JS or React version, replying to the notification goes straight to the person who asked.
    • A Telegram or Slack message per request helps you confirm quickly, on any plan.
    • On Starter and above, Auto Reply acknowledges the request immediately, and a webhook can pass it to your calendar tool.

    Lead Generation: plans, destinations and a worked setup →

    Before you publish it

    1. Create a form in the Formboost dashboard and replace YOUR_ENDPOINT_ID with its ID.
    2. Pick one variant: HTML posts and reloads, HTML + JS and React send JSON with fetch() and stay on the page.
    3. For the plain HTML version, add a hidden _redirect with an https:// thank-you page on the same site as the form — anything else falls back to Formboost's page.
    4. Submit it once from the live page and check the submission in your dashboard. Every request is acknowledged, so the dashboard is the real test. Troubleshooting covers the rest.

    More form templates

    Put the appointment request form live

    Free forever: 500 submissions a month across 10 forms, no card.