Examples

Copy, paste, ship.

Production-ready patterns for HTML forms, JavaScript submissions, file uploads, captcha tokens, and every integration point.

Basic HTML contact form

Works from static HTML and returns the hosted success page unless a valid redirect is supplied.

<form action="https://api.formsfort.com/submit" method="POST">
  <input type="hidden" name="access_key" value="YOUR_ACCESS_KEY" />
  <input type="text" name="name" required />
  <input type="email" name="email" required />
  <textarea name="message" required></textarea>
  <input type="checkbox" name="botcheck" style="display:none" />
  <button type="submit">Send</button>
</form>

Advanced all options

Combines the Web3Forms-compatible reserved fields supported by the baseline API.

<form action="https://api.formsfort.com/submit" method="POST" enctype="multipart/form-data">
  <input type="hidden" name="access_key" value="YOUR_ACCESS_KEY" />
  <input type="hidden" name="subject" value="New Submission" />
  <input type="hidden" name="from_name" value="Website Contact" />
  <input type="hidden" name="replyto" value="[email protected]" />
  <input type="hidden" name="ccemail" value="[email protected]; [email protected]" />
  <input type="hidden" name="webhook" value="https://example.com/webhook" />
  <input type="hidden" name="redirect" value="https://example.com/thanks" />
  <input type="checkbox" name="botcheck" style="display:none" />
  <input type="hidden" name="recaptcha_response" id="recaptchaResponse" />
  <input type="file" name="attachment" />
  <input type="email" name="email" required />
  <textarea name="message" required></textarea>
  <button type="submit">Send</button>
</form>

Ajax JavaScript form

JavaScript submissions receive JSON with the request id, queued delivery id, and echoed submitted fields.

const response = await fetch("https://api.formsfort.com/submit", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Accept": "application/json"
  },
  body: JSON.stringify({
    access_key: "YOUR_ACCESS_KEY",
    name: "Ada",
    email: "[email protected]",
    message: "Hello"
  })
});

const result = await response.json();

Multi-column contact form

Layout is pure frontend markup; the API receives the same named fields.

<form class="contact-grid" action="https://api.formsfort.com/submit" method="POST">
  <input type="hidden" name="access_key" value="YOUR_ACCESS_KEY" />
  <input name="first_name" placeholder="First name" required />
  <input name="last_name" placeholder="Last name" required />
  <input name="email" type="email" placeholder="Email" required />
  <input name="phone" placeholder="Phone" />
  <textarea name="message" class="full" required></textarea>
  <button class="full" type="submit">Send</button>
</form>

JavaScript validation

Validate before calling the public endpoint, then render the API message.

const form = document.querySelector("form");
const status = document.querySelector("[data-status]");

form.addEventListener("submit", async (event) => {
  event.preventDefault();
  if (!form.reportValidity()) return;

  const response = await fetch("https://api.formsfort.com/submit", {
    method: "POST",
    body: new FormData(form)
  });
  const result = await response.json();
  status.textContent = result.message;
});

Contact form with dark mode

Visual theme changes do not affect the submission contract.

<form class="dark-contact" action="https://api.formsfort.com/submit" method="POST">
  <input type="hidden" name="access_key" value="YOUR_ACCESS_KEY" />
  <input name="name" required />
  <input name="email" type="email" required />
  <textarea name="message" required></textarea>
  <button type="submit">Send</button>
</form>

<style>
  .dark-contact {
    background: #111816;
    color: #e7f4ed;
    padding: 24px;
  }
</style>

Raw contact form

Use this minimal version when a builder or CMS strips extra attributes.

<form action="https://api.formsfort.com/submit" method="POST">
  <input name="access_key" value="YOUR_ACCESS_KEY" />
  <input name="name" />
  <input name="email" />
  <textarea name="message"></textarea>
  <button>Submit</button>
</form>

hCaptcha, reCAPTCHA, and Turnstile tokens

Enable the provider in the dashboard, then submit the provider token with the matching reserved field name.

<!-- hCaptcha -->
<input type="hidden" name="h-captcha-response" value="TOKEN" />

<!-- Google reCAPTCHA v3 -->
<input type="hidden" name="recaptcha_response" value="TOKEN" />

<!-- Cloudflare Turnstile -->
<input type="hidden" name="cf-turnstile-response" value="TOKEN" />

File upload form

Paid/manual forms can accept multipart attachments after upload settings and scanning are configured.

<form action="https://api.formsfort.com/submit" method="POST" enctype="multipart/form-data">
  <input type="hidden" name="access_key" value="YOUR_ACCESS_KEY" />
  <input name="email" type="email" required />
  <input type="file" name="attachment" accept="application/pdf,image/*" />
  <button type="submit">Send</button>
</form>

Advanced file uploader

The helper script reserves object-storage uploads and submits clean storage keys without forwarding them as custom data.

<form action="https://api.formsfort.com/submit" method="POST">
  <input type="hidden" name="access_key" value="YOUR_ACCESS_KEY" />
  <input
    type="file"
    name="resume"
    data-advanced="true"
    data-max-files="3"
    data-max-file-size="3MB"
    multiple />
  <button type="submit">Send</button>
</form>
<script src="https://api.formsfort.com/client/script.js" async defer></script>

Multiple checkbox values

Repeated field names are accepted and delivered as comma-separated values.

<label><input type="checkbox" name="interest" value="Product" /> Product</label>
<label><input type="checkbox" name="interest" value="Sales" /> Sales</label>
<label><input type="checkbox" name="interest" value="Support" /> Support</label>

Custom redirect

Non-JavaScript form posts may redirect to a same-host HTTPS page after delivery is queued. Cross-domain redirects require a paid/manual entitlement.

<input type="hidden" name="redirect" value="https://example.com/thanks" />

CC recipients

Paid/manual entitlements can copy extra recipients on the queued notification email.

<input type="hidden" name="ccemail" value="[email protected]; [email protected]" />

Webhook forwarding

Paid/manual entitlements can queue a JSON webhook delivery alongside email forwarding.

<input type="hidden" name="webhook" value="https://example.com/webhook" />

Recipient verification

Generated access keys stay blocked until the recipient verifies ownership of the inbox.

POST /v1/forms/{formId}/recipient-verifications
POST /v1/forms/{formId}/verify-recipient