PortForm

Form submissions in your inbox, without a backend.

Already have a form? Point it at PortForm and every submission lands in your inbox. No server to run, no JavaScript required. 300 submissions every 30 days free.

No credit card · No trial clock · The demo needs no signup

index.html
<form action="https://app.portform.co/api/submit" method="POST">
  <input type="hidden" name="access_key"
         value="your-access-key" />
  <input type="email" name="email" required />
  <textarea name="message" required></textarea>
  <button type="submit">Send</button>
</form>
a submission arrives

New submission from PortForm

reply-to: jordan@example.com

New submission via Contact form.

nameJordan Fisher
emailjordan@example.com
messageDo you support file uploads on the Pro plan?

Sent by PortForm

Stored first
Every submission is saved before we try to deliver it.
Retried, not dropped
Failed deliveries are retried, then flagged for you.
300 free / 30 days
A real free tier on a rolling window. No card, no trial clock.

What is PortForm?

PortForm is the backend for your forms. Point a form’s action at us and we handle what happens after submit, so you can launch a contact form, waitlist, or signup page without building the storage, spam filtering, email, and retries behind it. You could build all that yourself; PortForm is for when you’d rather not.

The PortForm dashboard: a sidebar of forms and workspace pages, quota for the period, total submissions, spam blocked, a 30 day submission history chart, and a list of forms.
The dashboard behind every form: quota, delivery health, and a 30-day history. Open it in the live demo, no signup.

Nothing gets silently lost.

Storage happens first. Email and integrations are best-effort on top of a record that already exists — a failed integration delivery is retried, then flagged, never dropped without a trace.

Committed — written before anything else runs.
Best-effort — retried, then flagged. Never silent.
  1. Submission arrives

    Validated at the endpoint

  2. Stored

    Guaranteed

    Written to the database before anything else

  3. Emailed

    Sent to your inbox, reply-to the submitter

  4. Forwarded

    Delivered to Slack, Sheets, a webhook

  5. Retried

    5× · ~2.5h

    Onward deliveries — then flagged for you, never dropped

A record, not just a notification.

Every submission is stored and sorted into views. Open one and you see exactly what was posted, which form it came through, whether the honeypot caught it, and whether the send landed.

  • Inbox
  • Needs attention
  • Spam
  • Failed
  • Test
  • All
The submission log: today's count, delivery rate, average delivery time and spam blocked across the top, then Inbox, Needs attention, Spam, Failed, Test and All views, a list of submissions on the left, and the selected one expanded on the right showing name, email, message and a delivered badge.

Bots don’t reach your inbox.

Four checks run on every submission before it counts as real. Blocked attempts are logged so you can see them, never emailed, never counted against your quota.

  • honeypotA hidden field people never see and bots fill in.
  • disposable_addressKnown throwaway email domains are filtered as spam.
  • link_densityBodies that are mostly URLs are held back.
  • rate_limitPer-key limits blunt bursts from one source.

Add a visible challenge when you want one. None is on by default.

  • hCaptchaEvery plan
  • reCAPTCHAPro
  • Cloudflare TurnstilePro

Describe your form. Let AI wire it up.

Say what fields you need and get a prompt that makes Claude, ChatGPT, Cursor or v0 write the form, already pointed at PortForm with the honeypot and access key in place. No SDK, no backend for the assistant to invent.

Or let an agent create forms and read submissions
Prompt
Build an HTML form and connect it to PortForm, a form-to-email backend. I don't want to write or run any server code. PortForm receives the submission, stores it, filters spam, and emails it to me.

What I want:
A contact form with name, email, and a message.

Wire it to PortForm:
- Make it a plain <form action="https://app.portform.co/api/submit" method="POST"> that works even with zero JavaScript.
- Add this hidden field so the submission reaches my inbox:
  <input type="hidden" name="access_key" value="your-access-key" />
- Keep this honeypot field exactly as written, it's how spam bots are caught:
  <input type="checkbox" name="botcheck" style="display:none" tabindex="-1" autocomplete="off" />
- Do NOT write any backend, database, or email-sending code. PortForm does all of that.

Reference:
- Integration guide: https://www.portform.co/docs
- Machine-readable spec: https://www.portform.co/llms.txt
Open it in
Or copy it for your coding agent

Manage your forms from Claude Code.

PortForm speaks MCP. Point any MCP client at your workspace with a workspace token. It acts as you and never above you — the token carries your own role, and the server exposes eight tools for forms and submissions. Billing, members and integrations stay in the dashboard.

  • Create forms
  • Read submissions
  • Send a test submission
  • Diagnose form markup

Add the server

.mcp.json
{
  "mcpServers": {
    "portform": {
      "url": "https://app.portform.co/api/v1/mcp",
      "headers": { "Authorization": "Bearer ${PORTFORM_TOKEN}" }
    }
  }
}

Then just ask

claude
> create a contact form for acme.com

● portform · create_form
  ↳ name: "Acme contact"
    destination: hello@acme.com
  ✓ form created, access key ready

> is this contact form wired up right?

● portform · diagnose
  ✓ action points at PortForm
  ✓ access_key matches this key
  ! no honeypot field — add the hidden botcheck input
See the MCP tools in the demo

Agent sandbox

Build before you sign up.

An AI agent can create a real PortForm endpoint anonymously — no account, no token — wire it into your code, send a few test submissions, and confirm they arrived. When it works, it hands you a claim link: you sign in and keep the exact same form and access key. The building happens before the signup, not after.

  1. 1. Create

    The agent calls the public sandbox endpoint and gets a real access key back, with no account.

  2. 2. Wire

    It drops the snippet into your form, or points existing markup at the key.

  3. 3. Test

    Up to 5 test submissions prove the form end to end. They are stored, never emailed.

  4. 4. Verify

    A status check confirms the submissions were received.

  5. 5. Claim

    You open the claim link and sign in. The form becomes yours — same id, same submit URL, test history intact.

Sandboxes are temporary — for building and testing, not production. An unclaimed one expires within a day; claim it to keep the form.

See how agents work with PortForm

Send every submission to Slack, Sheets, or a webhook.

Deliveries are signed, retried, and logged, with a success rate and retry queue you can see. Which plan each part belongs to is in the pricing table.

New submission

from any form

Native integrations

  • Slack
  • Discord
  • Telegram
  • Google Sheets
  • Notion
  • Airtable
  • HubSpot

Via webhooks & automation

  • Webhooks
  • Zapier
  • Make
  • n8n
The integrations page: connected count, delivered today, success rate and retry queue across the top, three connected integrations (Slack, a webhook and Google Sheets), then the catalogue grouped into Notifications and Developer.
Connected integrations with delivered-today, success rate and retry queue: monitored, not fire-and-forget.
Explore integrations →

More once a form is doing real work.

See what’s on each plan →
  • Autoresponders

    Reply to whoever submitted with a confirmation email.

  • CC recipients

    Copy extra addresses on a form’s notifications.

  • File attachments

    Accept uploads alongside the other fields.

  • Choose which websites can submit

    Only accept submissions from websites you specify: a convenience control, not a security boundary.

One tag on the form you already have.

  1. 1

    Create a form

    Sign up and you get an access key and a destination address straight away.

  2. 2

    Paste the snippet

    Set your form action to our endpoint and drop the key in a hidden input.

  3. 3

    Read your mail

    Submissions arrive by email and stay in the dashboard for 30 days.

index.html
<form action="https://app.portform.co/api/submit" method="POST">
  <input type="hidden" name="access_key" value="your-access-key" />
  <input type="email" name="email" required />
  <textarea name="message" required></textarea>
  <button type="submit">Send</button>
</form>

The people filling in your forms are your data subjects.

You’re the controller, we’re the processor, and there’s a DPA you can read before you sign up.

  • Kept, then purged : submissions and request and delivery logs are retained for 30 days, then deleted.
  • Delete on demand : remove any submission from the dashboard the moment you no longer need it.
  • One-click export : pull everything (keys, submissions, integrations and audit events) as one JSON file, or a form’s submissions as CSV.

Built by people who ship.

  • Swapped a flaky serverless function for one form tag. Submissions just show up in my inbox now, and I stopped thinking about it.

    Maya Osei

    Founder, Studio North

  • The stored-first thing is the whole reason I switched. A downstream delivery failed once, it was in the dashboard waiting, retried on its own. Nothing lost.

    Daniel Reyes

    Founder, Reyes Labs

  • Set up a contact form on a static site in about a minute, no backend, no card. The free tier is genuinely enough for what I ship.

    Priya Nair

    Founder, Fieldnote

Pricing that starts at nothing.

The free tier is a hard cap, not a trial: 300 submissions every rolling 30 days from your own last reset. Go over and submissions are refused with an error you can read, never billed by surprise, never silently dropped.

Personal

Free

Free forever

A hard cap, not a countdown

Create your form

No credit card required

  • Unlimited forms
  • 300 submissions per rolling 30 days
  • Accept submissions from any website
  • 2 verified destination addresses
  • Advanced spam protection
  • hCaptcha integration
  • Custom redirect page

Pro

Popular choice

$9/mo

Billed monthly

Save $17 a year with yearly billing

Secure payment by Paddle.

Cancel anytime.

  • Everything in Personal
  • 10,000 submissions per rolling 30 days
  • Team collaboration
  • File upload / attachments
  • reCAPTCHA & Cloudflare Turnstile
  • Autoresponders / auto reply
  • Choose which websites can submit
  • 3rd party integrations (webhooks)
  • Google Sheets, Notion, Slack, etc.
  • 10 verified destination addresses
  • Add CC emails & more

Agency & Team

$29/mo

Billed monthly

Save $60 a year with yearly billing

Secure payment by Paddle.

Cancel anytime.

  • Everything in Pro
  • 20,000 submissions per rolling 30 days
  • 20 verified destination addresses
  • Client workspaces — run each client from your own account
  • Add more destination addresses any time
  • Priority support — your tickets go to the front of the queue

Questions people actually ask

Is my access key a secret?

No, and it is not meant to be. It is a routing id, the same way a mailto: address is. It says where a submission goes, not who is allowed to send one. Anyone can read it in your page source, which is why the protection is per-key rate limiting, spam filtering and quota rather than secrecy. Leaking one is not an incident; if a key is being abused, rotate it in the dashboard.

What happens when I hit 300 submissions?

New submissions are rejected with a clear error until the window rolls over. Nothing is silently dropped, nothing is billed, and everything already stored stays where it is. The window is a rolling 30 days from your last reset, not a calendar month, so there is no first-of-the-month stampede and no short-February edge case. The dashboard warns you well before you get there, and shows the pace you are on.

How long are submissions kept?

Submissions, request logs and delivery logs are retained for 30 days, then purged. Export what you want to keep as CSV, or pull everything (keys, submissions, integrations and audit events) as one JSON file.

Do you send the email from my domain?

Notifications come from our sending domain with your submitter as the reply-to, so hitting reply answers the person who filled in the form. No DNS setup on your side.

What about the data of people who fill in my forms?

They are your data subjects, and we are the processor. There is a DPA you can read before you sign up, submissions are deletable from the dashboard, and a full export is one click.

Does it work with React, Vue, Astro, Hugo, WordPress?

Yes. The endpoint takes form encoding, multipart and JSON, so anything that can make an HTTP request can use it. The docs carry a ready-made snippet for each.

Everything else is in the docs.

Your form works in about a minute.

Create an account, copy your access key, paste the snippet. Or look around the demo first. It takes no signup and no email address.

OpenHunts Club MemberFeatured on LaunchBuffFeatured on Wired BusinessFeatured on AI LaunchPortForm on Better LaunchFeatured on Startup FameFeatured on Twelve ToolsFeatured on Findly.toolsOpenHunts Club MemberFeatured on LaunchBuffFeatured on Wired BusinessFeatured on AI LaunchPortForm on Better LaunchFeatured on Startup FameFeatured on Twelve ToolsFeatured on Findly.tools

We use optional analytics cookies to understand how the site is used. Necessary cookies for signing in and checkout always load. See our privacy policy.