A form endpoint for static sites: you point an HTML form at their URL and submissions arrive in your inbox, with spam filtering and a dashboard of what came in.
Build me a form endpoint that replaces Formspree: my static site posts to it, the submission arrives, and the spam does not. STACK - Node 20+ with Fastify - SQLite through better-sqlite3, WAL mode - No client-side framework — this must work from a plain HTML form with no JavaScript at all - Caddy in front THE DATA MODEL - forms: id, uid, name, target_emails_json, redirect_url, allowed_origins_json, is_active, requires_captcha, created_at - submissions: id, form_id, payload_json, spam_score, spam_reasons_json, status, ip_hash, referrer, user_agent_bucket, country, created_at — status is delivered, queued, spam or rejected - files: id, submission_id, field, path, sha256, mime, bytes, scan_status - deliveries: id, submission_id, target_kind, target, status, attempts, response_excerpt, at - blocklist: id, kind, value, reason, added_at — an address, a domain, a phrase, an address hash - Every submission stored, including the ones judged spam. A false positive that was silently dropped is a customer you never knew wrote to you THE ENDPOINT - POST to /f/:uid as form-encoded or multipart, exactly as a browser sends it - Answers with a redirect to the form's thank-you page, or with JSON if the request asked for JSON. Both paths must work - No JavaScript required anywhere. The whole point is a static site with an ordinary HTML form - Origin checked against the form's allowed list, and a submission from elsewhere is rejected and recorded - Field names taken as they come; no schema required, because the form's author owns the fields - Reserved fields for the redirect, the subject and the reply-to address, all validated SPAM, WHICH IS THE ENTIRE PRODUCT AFTER WEEK ONE - A honeypot field, documented, that a real form includes hidden and a bot fills in - A minimum time between the page being rendered and the form arriving, carried in a signed token. Bots post instantly - Rate limits per address hash, per form and globally, with a burst allowance - Content signals scored rather than judged: link count, all-capitals, a body that is a URL, known spam phrases, a mismatched or absent referrer, a user agent that is a library - A score with the reasons attached, and a threshold per form. Above it the submission is held for review, not discarded - Optional third-party spam checking, off by default, and the README says plainly that turning it on sends the submission text to somebody else - A review queue where a held submission can be released, and releasing one teaches the blocklist in reverse DELIVERY - Email to one or more addresses, with the fields formatted readably and the reply-to set to the submitter's address if one was given — so replying works, which is what people actually want - Webhook with an HMAC signature, retried with backoff, idempotent by submission id - Optional forwarding into a spreadsheet or an automation tool through the same webhook machinery - Every attempt recorded with the response - A daily digest option instead of one email per submission, for a busy form FILES - Multipart upload streamed to disk, never buffered whole - Type from content, not from the filename; a size cap and a per-form quota - Executables and archives refused by default with a clear message - Scanned if a scanner is configured, and held until the scan finishes - Stored outside the web root and served through a signed, expiring link in the notification email — never attached, because attachments are what get the notification itself marked as spam THE DASHBOARD - Submissions per form, searchable, with the spam ones in their own tab - Export CSV and JSON, complete, in one click - The form's own snippet shown ready to paste, with the honeypot and the token included - Dark and light DELIVERABILITY - Send from your own domain with SPF, DKIM and DMARC configured — the README lists the records - The From address is yours; the submitter's address is only ever the reply-to. Sending as somebody else's domain is how you get your mail rejected everywhere - Bounces consumed and a failing target address flagged rather than retried forever OPERATIONS - .env: DATABASE_PATH, STORAGE_PATH, BASE_URL, SMTP_URL, FROM_ADDRESS, SESSION_SECRET, HASH_SALT, SIGNING_SECRET - Migrations on boot, each once - Nightly backup off the machine, restore script - Health endpoint that checks the mail connection WHAT MATTERS MOST Spam scoring with reasons, and never dropping anything. Build the honeypot, the timing token and the review queue first, then leave a form public for a fortnight and read what arrives. Every homemade form endpoint works beautifully for three weeks and then becomes a stream of casino links. Give me the repository, migrations, .env.example, the HTML snippet, and a README with deploy steps behind Caddy and the mail DNS records.
What you lose
- Spam filtering tuned against traffic from thousands of sites, which is most of the value once a form has been public for a month
- A submissions dashboard, exports and integrations you did not build
- An endpoint that works from a purely static host with no backend at all
If you would rather not build
- Netlify Forms, if you already deploy there
- A serverless function, which is about forty lines
What it costs
read from their page 15 Aug 2026
| Plan | Billed monthly | Billed yearly | Last read |
|---|---|---|---|
| — | $10/mo | — | 15 Aug 2026 |
Their pricing page is where these came from. Seeing a different price? Tell us.
The escape hatch
open source · no votes, no paid placement
Formbricks
$0Self-hosted forms and surveys with a submissions dashboard.
formbricks/formbricksfree · open source
Why this verdict
our own opinion · changed only by a person
89/100
Verdict yes at 89. A form endpoint is one insert and one email. The three-layer spam defence in the prompt handles almost everything without a captcha.
History
tracked since 10 Aug 2026 · nothing is ever overwritten
Questions about Formspree
answered from the record above
Is Formspree free?
No — the plan we track is $10 a month. Personal at $10/month billed monthly, around $8 annually, for 1,000 submissions.
Can you replace Formspree by building your own?
YES. Replaceable in one session with an AI coding agent. Replacement score 89 out of 100, build time one session. Read what you lose before you decide.
How much does Formspree cost?
$10 a month on Personal — $120 a year. Recorded 9 Aug 2026.
What do you lose by replacing Formspree?
Spam filtering tuned against traffic from thousands of sites, which is most of the value once a form has been public for a month; A submissions dashboard, exports and integrations you did not build; An endpoint that works from a purely static host with no backend at all. If any of those carry weight for you, keep paying.
Is there an open-source alternative to Formspree?
Yes: Formbricks, OhMyForm. The prompt on this page is for when you want it your way instead.
Related entries
same category first, most replaced first
Every week, something stops being worth paying for.
New verdicts, prices that moved, entries added. One email a week. Unsubscribe in one click. Nothing is being sent yet — your address is kept here, and the first issue is the first thing it is used for.
free forever · no tracking pixel · stored here, never passed to anyone

