---
title: "Add a Contact Form to Any Static Website (2025 Guide)"
description: "Learn how to add a contact form to any static website for free. Compare FormSubmit, Static Forms, Web3Forms, and more, with step-by-step setup and privacy tips."
date: 2026-07-15
categories: ["web-development"]
tags: ["astro","static-sites"]
---

import YouTubeEmbed from "../../components/widgets/YouTubeEmbed.astro";
import Notice from "../../components/widgets/Notice.astro";
import ListCheck from "../../components/widgets/ListCheck.astro";
import Accordion from "../../components/widgets/Accordion.astro";
import Tabs from "../../components/widgets/Tabs.astro";
import Tab from "../../components/widgets/Tab.astro";
import Button from "../../components/widgets/Button.astro";

Static websites built with Astro, Hugo, Jekyll, or plain HTML don't have a backend, so you can't just write a PHP script to handle form submissions. You need an external service to act as your form handler.

In an earlier tutorial I covered [adding a contact form to Astro](/add-contact-form-astro/) using OpnForms, but that approach has changed since then (email notifications moved behind a paywall). More options have appeared since then, with multiple free and privacy-first services now available.

This guide covers the simplest free option (FormSubmit.co), its known issues, the best alternatives like Static Forms and Web3Forms, a feature comparison table, privacy considerations, and a self-hosted path for advanced users. Whether you're [building a free blog with Astro and Cloudflare](/build-astro-blog-free/) or running any static site, you'll find a solution that fits.

## Why add a contact form to a static website

A contact form adds credibility and trust to any website. Instead of publishing your email address where bots can scrape it, visitors fill out a form and the submission gets forwarded to you. This is especially important for:

- **Lead generation**: potential clients or collaborators can reach you directly
- **User trust**: a contact form signals that you're approachable and professional
- **Spam reduction**: forms with CAPTCHA are harder to abuse than a raw email address
- **Structured data**: you get consistent fields (name, email, message) instead of freeform emails

Since static sites have no server-side code, you need a **static website form handler**: either a third-party service or a lightweight self-hosted backend. There are several free options that require zero backend code.

## Method 1: FormSubmit.co (simplest free option)

FormSubmit.co was the go-to recommendation when this article was first published. It's still the simplest option. No signup required, just point your form's `action` attribute to their endpoint. Here's how it works.

### 1. Create your HTML form

Design a form using standard HTML elements. Include a `name` attribute on every field you want to receive data for:

```html
<form id="contact-form">
  <label for="name">Name:</label>
  <input type="text" id="name" name="name" required />
  <label for="email">Email:</label>
  <input type="email" id="email" name="email" required />
  <label for="message">Message:</label>
  <textarea id="message" name="message" required></textarea>
  <button type="submit">Send</button>
</form>
```

### 2. Point the form action to FormSubmit

Add the FormSubmit endpoint as your form's `action` attribute with your email address:

```html
<form
  id="contact-form"
  action="https://formsubmit.co/your@email.com"
  method="POST"
>
  <label for="name">Name:</label>
  <input type="text" id="name" name="name" required />
  <label for="email">Email:</label>
  <input type="email" id="email" name="email" required />
  <label for="message">Message:</label>
  <textarea id="message" name="message" required></textarea>
  <button type="submit">Send</button>
</form>
```

### 3. Verify your email address

Submit the form once (or visit the FormSubmit URL in your browser). You'll receive a confirmation email with a link. Click it to verify that you own the email address. This is a one-time step.

### 4. Customize form options

FormSubmit supports several hidden input fields to customize behavior:

**Redirect after submission:**

```html
<input
  type="hidden"
  name="_next"
  value="https://yourdomain.com/thanks.html"
/>
```

**Carbon copy to additional recipients:**

```html
<input
  type="hidden"
  name="_cc"
  value="another@email.com,yetanother@email.com"
/>
```

**Add reCAPTCHA:**

```html
<input type="hidden" name="_captcha" value="true" />
```

You can check all available options in the [FormSubmit.co documentation](https://formsubmit.co/documentation).

<YouTubeEmbed
  url="https://www.youtube.com/embed/vSABo52iPAs"
  label="Add Contact Form To Static Websites"
/>

## FormSubmit.co issues to know about

FormSubmit is easy to set up, but it has real problems you should be aware of before committing to it for a production site.

### Spam protection limitations

Users on Reddit report that spam gets through even with reCAPTCHA and honeypot enabled. One user in r/webdev noted: "I had the captcha and honeypot options enabled and still got daily spam messages." Others report that reCAPTCHA can cause 30+ second load times on form pages, which hurts user experience.

### Email address exposed in source code (GDPR risk)

Your email address is baked directly into the HTML source code via the form action URL:

```html
<form action="https://formsubmit.co/your@email.com">
```

This makes it harvestable by email scraping bots. It's also a potential GDPR liability. You're exposing a personal email address in a way that's trivially easy to collect automatically. If you're concerned about this, check our guide on how to [stop AI crawlers from scraping your website](/block-ai-crawlers/).

### Reliability concerns

The FormSubmit.co website was unreachable during multiple test requests. Users on Reddit report inconsistencies and wasted debugging time. Since FormSubmit has no paid plans (it's "free forever"), there's a question about long-term sustainability and support.

<Notice type="warning" title="Important caveat">
FormSubmit works for quick prototypes and low-stakes personal sites. For production websites where you can't afford to lose submissions, consider one of the alternatives below that offer dashboards, submission logs, and transparent uptime guarantees.
</Notice>

## Best FormSubmit alternatives for static sites

More form backend services have launched since 2024. Several now offer better spam protection, privacy guarantees, dashboards, and sustainable business models, many with generous free tiers. If you're interested in self-hosted form tools, you might also want to look at [OpnForm, an open-source form builder](/opnform-open-source/).

Before choosing a service, here's what to look for:

<ListCheck>
<ul>
<li>Privacy: does it expose your email in HTML source?</li>
<li>Spam protection: reCAPTCHA, Turnstile, Altcha, or ML-based filtering</li>
<li>Free tier limits: how many submissions per month before you pay</li>
<li>Dashboard: can you view past submissions without digging through email?</li>
<li>Integrations: Slack, Google Sheets, Zapier, webhooks</li>
<li>File uploads: can users attach files to form submissions?</li>
<li>Auto-responders: does the submitter get a confirmation email?</li>
</ul>
</ListCheck>

### Static Forms (best free tier, 500/mo)

[Static Forms](https://www.staticforms.dev/) offers the most generous free tier at 500 submissions/month. It supports reCAPTCHA v2, reCAPTCHA v3, Cloudflare Turnstile, and Altcha (privacy-first, GDPR-friendly, no user tracking). You also get webhooks, file uploads, a submission dashboard, and AI-powered auto-replies that draft responses based on a knowledge base.

The setup is similar to FormSubmit, point your form action to their endpoint, but uses an access key instead of your email address. Paid plans start at $7.50/month.

### Web3Forms (best for privacy, no email exposure)

[Web3Forms](https://web3forms.com/) uses an access key instead of your email address in the HTML, so your email stays hidden from scrapers. Free tier includes 250 submissions/month. It supports file uploads, reCAPTCHA, and is GDPR compliant by design.

Setup is straightforward. Create an account, get your access key, and add it as a hidden field:

```html
<form action="https://api.web3forms.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>
  <button type="submit">Send</button>
</form>
```

### Formspree (best for integrations)

[Formspree](https://formspree.io/) has been around since 2014 and is one of the most established players. Free tier is limited to 50 submissions/month, but the $10/month plan adds ML-based spam filtering, a dashboard, and integrations with Slack, Google Sheets, and Zapier. Good choice if you need submissions to flow into your existing workflow tools.

### Netlify Forms (best if hosted on Netlify)

If your site is already on Netlify, [Netlify Forms](https://docs.netlify.com/manage/forms/setup/) is built in. No extra service needed. Free tier includes 100 submissions/month with built-in spam filtering. Add `netlify` to your form tag and it just works:

```html
<form name="contact" method="POST" data-netlify="true">
  <input type="text" name="name" required />
  <input type="email" name="email" required />
  <textarea name="message" required></textarea>
  <button type="submit">Send</button>
</form>
```

### EmailJS (best for client-side only)

[EmailJS](https://www.emailjs.com/) lets you send emails directly from client-side JavaScript, with no form action redirect. Free tier includes 200 emails/month. It works with email templates and supports attachments. Good for single-page apps or sites where you want AJAX form submission without a page redirect.

## Feature comparison table: free contact form services

| Service | Free Submissions/mo | Spam Protection | File Uploads | Dashboard | Webhooks | Email Exposed? | Paid From |
|---------|-------------------|----------------|--------------|-----------|----------|----------------|-----------|
| FormSubmit | Unlimited* | reCAPTCHA, honeypot | No | No | No | Yes | Free only |
| Static Forms | 500 | reCAPTCHA v2/v3, Turnstile, Altcha | Yes | Yes | Yes | No (access key) | $7.50/mo |
| Web3Forms | 250 | reCAPTCHA | Yes | Yes | Yes | No (access key) | Paid plans |
| Formspree | 50 | ML filtering | Yes | Yes | Yes | No (form ID) | $10/mo |
| Netlify Forms | 100 | Built-in spam filter | Yes | Yes | Yes | No (form ID) | $9/mo |
| EmailJS | 200 | reCAPTCHA | Yes (templates) | Yes | Yes | No (service ID) | $9/mo |
| Forminit | 100 | reCAPTCHA | Yes (25MB) | Yes | Yes | No (form ID) | $19/mo |

*\*FormSubmit claims unlimited, but users report reliability issues.*

<Notice type="info" title="Tip">
If you expect fewer than 50 submissions/month, Formspree works fine. For higher volume, Static Forms or Web3Forms offer the best free tiers. If you're already on Netlify, their built-in forms are the path of least resistance.
</Notice>

## Privacy and GDPR considerations for contact forms

If you serve EU visitors (or care about privacy in general), the contact form service you choose has real implications for compliance.

### Email exposure in HTML source

FormSubmit embeds your email address directly in the HTML `action` attribute. This is visible to anyone who views source, and to every bot that crawls your site. Services like Web3Forms, Formspree, Forminit, and Static Forms use access keys or form IDs instead, keeping your email address server-side only.

<Notice type="warning" title="GDPR alert">
Exposing a personal email address in HTML source code can be considered a GDPR compliance issue. If your site serves EU visitors, use a service that uses form IDs or access keys instead of email addresses in the form action.
</Notice>

For broader privacy protection on your site, consider pairing a privacy-respecting form service with [Plausible Analytics](/install-plausible-analytics/), a privacy-focused alternative to Google Analytics.

### Privacy-first CAPTCHA options

Traditional Google reCAPTCHA tracks users across sites and loads heavy JavaScript. Newer alternatives are more privacy-friendly:

- **Cloudflare Turnstile**: invisible CAPTCHA that doesn't require user interaction and doesn't track users across sites. Static Forms supports it natively.
- **Altcha**: open-source, GDPR-friendly CAPTCHA with no user tracking. Works by solving a proof-of-work challenge in the browser. Supported by Static Forms.
- **Honeypot fields**: a hidden form field that bots fill in but humans don't. Simple and effective against basic spam bots, used by most services.

If privacy is a priority, choose a service that supports Turnstile or Altcha over Google reCAPTCHA.

## How to add a contact form in Astro

If you're using Astro with ViewTransitions, you may hit this error when submitting a form:

> Make sure your form has the method="POST" attribute

This happens because Astro's ViewTransitions intercept form submissions. The fix is to add the `data-astro-reload` attribute to your form element. This tells Astro to handle the form submission as a regular page navigation instead of intercepting it.

<Notice type="info" title="Astro tip">
This fix works regardless of which form service you use (FormSubmit, Web3Forms, Static Forms, or any other). The `data-astro-reload` attribute is an Astro-specific workaround, not tied to any particular form backend.
</Notice>

```html
<form
  id="contact-form"
  action="https://formsubmit.co/your@email.com"
  method="POST"
  data-astro-reload
>
  <label for="name">Name:</label>
  <input type="text" id="name" name="name" required />
  <label for="email">Email:</label>
  <input type="email" id="email" name="email" required />
  <label for="message">Message:</label>
  <textarea id="message" name="message" required></textarea>
  <button type="submit">Send</button>
</form>
```

If you're deploying your Astro site, check our guides on how to [deploy Astro on Cloudflare](/deploy-astrojs-cloudflare/) or [deploy a static Astro website on VPS](/deploy-astro-on-vps/). You might also find our tutorials on how to [display YouTube videos on your Astro blog](/add-youtube-videos-astro-blog/) and [add responsive YouTube videos to Astro MDX](/responsive-youtube-astrojs/) useful for other parts of your site.

## Self-hosted contact form option (advanced)

If you don't want to depend on a third-party service, or you need full control over your data, you can run your own form backend.

<Notice type="success" title="For self-hosters">
A self-hosted form handler gives you complete control over submissions, storage, and privacy. No third-party dependencies, no submission limits, no email exposure. You own the entire pipeline.
</Notice>

### Docker-based Go form backend

The [caffsoft/hugo-contact](https://github.com/caffsoft/hugo-contact) project is a lightweight Go-based contact form backend that runs in Docker using approximately 10MB of RAM. It's MIT licensed and designed for static sites.

The general approach:

1. Deploy the container on a VPS
2. Point your form action to the container's URL
3. The backend processes submissions and forwards them via email or stores them

If you need a VPS to run this, [affordable VPS from Hetzner](https://go.bitdoze.com/hetzner) starts at around €4/month with excellent performance. [Hostinger VPS](https://go.bitdoze.com/hostinger-vps) is another budget option with NVMe storage.

For more self-hosted solutions, see our guide on [self-hosted alternatives to popular SaaS tools](/coolify-install-heroku-alternative/).

### Cloudflare Workers approach

If you're already on Cloudflare, you can build a serverless form handler using Cloudflare Workers. The approach is:

1. Create a Worker that receives POST requests from your form
2. Forward submissions to your email (via SendGrid or Mailgun) or store them in Airtable/D1
3. Deploy the Worker alongside your Cloudflare Pages site

This gives you a form backend that runs at the edge with zero server management. It's free for up to 100,000 requests/day on Cloudflare's free plan.

## How to choose the right form service for your site

Different sites have different needs. Here's a quick decision guide:

<Tabs>
<Tab name="Just need it working">
**Use FormSubmit.co**

The fastest way to get a contact form live. No signup, no API keys, just add your email to the form action and verify once. Works for personal blogs and low-traffic sites where occasional spam or downtime isn't critical.

```html
<form action="https://formsubmit.co/your@email.com" method="POST">
```
</Tab>
<Tab name="Best free tier">
**Use Static Forms**

500 free submissions/month, plus a dashboard, file uploads, webhooks, and support for Turnstile and Altcha CAPTCHA. The most generous free tier with the most features. Sign up at [staticforms.dev](https://www.staticforms.dev/) to get your access key.
</Tab>
<Tab name="Privacy-first">
**Use Web3Forms**

Access key instead of email in HTML, GDPR compliant, 250 free submissions/month. Your email address never appears in the page source. Sign up at [web3forms.com](https://web3forms.com/).
</Tab>
<Tab name="Full control">
**Self-host with Docker**

Run your own form backend on a VPS with caffsoft/hugo-contact or build a Cloudflare Worker. No submission limits, no third-party dependencies, complete data ownership. Requires a server. Consider [Hetzner](https://go.bitdoze.com/hetzner) or [Hostinger VPS](https://go.bitdoze.com/hostinger-vps).
</Tab>
</Tabs>

## Frequently asked questions

<Accordion label="Can I add a contact form to a static website without a backend?" group="faq" expanded="true">
Yes, that's exactly what form backend services like FormSubmit, Web3Forms, and Static Forms do. They provide an endpoint URL that you set as your form's `action` attribute. When someone submits the form, the service receives the data and forwards it to your email (or stores it in a dashboard). No server-side code needed on your end.
</Accordion>

<Accordion label="Is FormSubmit.co still free in 2025?" group="faq">
Yes, FormSubmit.co is still free with no paid plans. However, users report reliability issues, spam getting through reCAPTCHA, and the service being intermittently unreachable. For production sites, consider Static Forms or Web3Forms which have more robust free tiers and transparent business models.
</Accordion>

<Accordion label="Which free form service has the highest submission limit?" group="faq">
Static Forms offers 500 submissions/month on its free tier, the highest among the services compared in this article. Web3Forms comes second at 250/month, followed by EmailJS at 200/month and Netlify Forms at 100/month.
</Accordion>

<Accordion label="Do I need a CAPTCHA on my contact form?" group="faq">
Yes, you should add some form of spam protection. The best options are Cloudflare Turnstile (invisible, no user tracking), Altcha (open-source, GDPR-friendly), or reCAPTCHA v3 (invisible scoring). Avoid standard reCAPTCHA v2 with checkboxes if possible. It hurts user experience and loads heavy JavaScript.
</Accordion>

<Accordion label="Can I use these form services with Astro, Hugo, or Jekyll?" group="faq">
Yes. These services work with any static site generator because they're just standard HTML forms. Point the `action` attribute to the service's endpoint and it works. If you're using Astro with ViewTransitions, add `data-astro-reload` to the form element to avoid the POST method error.
</Accordion>

## Conclusion

Adding a contact form to a static website is easier than ever. FormSubmit.co remains the quickest option for a prototype or personal site, just point and go. But for production use, Static Forms and Web3Forms offer better spam protection, privacy guarantees, and dashboards at no cost.

If privacy is your priority, choose a service that uses access keys instead of email addresses (Web3Forms, Static Forms). If you need integrations with Slack or Google Sheets, Formspree is solid. And if you want zero dependencies, a self-hosted Docker backend gives you full control.

If you're setting up a new Astro site, start with our guide to [adding a contact form to Astro](/add-contact-form-astro/). For broader privacy tooling, [Plausible Analytics](/install-plausible-analytics/) pairs well with a privacy-respecting form service.

<Button text="Explore Static Forms" link="https://www.staticforms.dev/" variant="solid" color="blue" size="md" icon="arrow-right" />
<Button text="Try Web3Forms" link="https://web3forms.com/" variant="outline" color="green" size="md" />