Skip to main content
New:Build with AI agents

Jekyll contact forms
without Ruby mail code.

Keep your Jekyll site static and point the generated form at Form Plume for email notifications, dashboard storage, spam filtering, file uploads, integrations, and signed webhooks.

Free foreverNo credit cardJekyll endpoint ready in under a minute
_includes/contact-form.html
<form action="{{ site.formplume_endpoint }}" method="POST">
  <input type="hidden" name="source" value="jekyll">
  <input name="name" autocomplete="name" required>
  <input name="email" type="email" autocomplete="email" required>
  <textarea name="message" required></textarea>
  <button type="submit">Send</button>
</form>

The full guide

A hosted backend for Jekyll includes.

Use Liquid includes and config values to generate a plain form that works from GitHub Pages or any static host.

  1. 1
    Create your Form Plume accountStart free and give your Jekyll form a hosted endpoint for email, submissions, spam filtering, uploads, integrations, and webhooks.Start free
  2. 2
    Create the form and copy the endpointCopy the endpoint URL from Form Plume. It looks like https://api.formplume.com/f/your-slug
  3. 3
    Connect it inside JekyllPut the endpoint in Jekyll config or data, render it through a Liquid include, build the site, and inspect the _site output. Send one test submission from the real Jekyll app or preview environment and confirm it reaches Form Plume.

You can use this AI prompt to hand the platform-specific wiring to an assistant without accidentally creating a backend.

Use a Liquid include

Jekyll sites should keep shared form markup in _includes/contact-form.html. The final output is plain HTML, but the include keeps the endpoint and fields consistent across pages.

<form action="{{ site.formplume_endpoint }}" method="POST">
  <input type="hidden" name="source" value="jekyll">
  <input type="hidden" name="_redirect" value="/thanks/">
 
  <label for="contact-name">Name</label>
  <input id="contact-name" name="name" autocomplete="name" required>
 
  <label for="contact-email">Email</label>
  <input id="contact-email" type="email" name="email" autocomplete="email" required>
 
  <label for="contact-message">Message</label>
  <textarea id="contact-message" name="message" rows="5" required></textarea>
 
  <button type="submit">Send message</button>
</form>

Render the include from a page or layout.

{% include contact-form.html %}

Configure the endpoint once

Add the endpoint to _config.yml, an environment-specific config file, or a data file if your build pipeline prefers _data.

formplume_endpoint: "PASTE_YOUR_FORM_PLUME_ENDPOINT_HERE"

Run bundle exec jekyll build, then inspect _site/contact/index.html. You should see a normal form with the real endpoint in the action.

No Ruby server required

After deployment, Jekyll is just static HTML. You do not need mail, Net::SMTP, a plugin, a serverless function, or a database for the contact form. Form Plume receives the browser POST and handles email notifications, storage, spam filtering, uploads, integrations, and webhooks.

Uploads

File uploads use the same HTML you would write anywhere else.

<form
  action="{{ site.formplume_endpoint }}"
  method="POST"
  enctype="multipart/form-data"
>
  <input type="file" name="attachment" accept=".pdf,.png,.jpg">
  <button type="submit">Send file</button>
</form>

If a theme wraps your content, inspect the built _site HTML to make sure the theme did not strip method, action, enctype, or hidden fields.

Primary sources

FAQ

Jekyll form questions
before deploy.

Yes. GitHub Pages serves static HTML, and the browser can post that form directly to Form Plume.

One line. Zero backend.

The form backend you don’t have to build.

Free foreverNo credit cardSet up in under a minute