個人ブログやポートフォリオサイトを運営していると、「お問い合わせフォームを設置したい」と考える場面があるかと思います。しかし、自前でフォームを実装しようとすると、APIサーバーの構築やメール送信処理(SMTP設定)、スパム対策など、多くの専門知識と手間が必要になります。
そこでおすすめなのが、サーバー構築不要で簡単にお問い合わせフォームを実装できるFormspreeというサービスです。
この記事では、Formspreeの基本的な使い方からメリット、無料枠の範囲、さらにはNext.jsなどのモダンな環境での実践的なコード例まで、実務目線で詳しく解説します。
Formspreeとは?#
Formspree(フォームスプリー)は、HTMLの<form>タグに専用のエンドポイント(URL)を指定するだけで、フォームから送信された内容を直接指定したメールアドレスに転送してくれるサービスです。
通常、お問い合わせフォームを自作する場合、以下のようなバックエンド(サーバー側)の処理が必要になります。
- APIサーバーの用意(Node.js, PHP, Pythonなど)
- メール送信の仕組み(SendGridやAmazon SESなどの外部サービス連携、またはSMTPサーバーの設定)
- セキュリティ対策(CORS設定、バリデーション、スパムボット対策)
Formspreeを利用すれば、これらのバックエンド処理をすべてFormspree側が肩代わりしてくれます。フロントエンドのコード(HTML/CSS/JavaScript)を書くだけで完結するため、バックエンドを持たない静的サイト(SSG)やサーバーレス環境と非常に相性が良いのが特徴です。
Formspreeの主なメリット#
1. サーバー不要で圧倒的に導入が簡単#
最大のメリットは、サーバーサイドのコードを一切書かずに済む点です。発行されたURLをHTMLのaction属性に設定するだけで、すぐにフォームが機能し始めます。学習コストが低く、数分で実装が完了します。
2. 優秀な無料枠(Freeプラン)#
Formspreeには無料で使える「Freeプラン」が用意されており、個人開発や小規模なブログであれば十分なスペックを持っています。
- 月間送信数: 50件まで(※時期やプラン改定により変動する可能性があります)
- フォーム作成数: 無制限
月に50件ものお問い合わせが来る個人ブログは稀ですので、基本的には無料で運用を続けることが可能です。
3. 静的サイトジェネレーター(SSG)との相性が抜群#
Hugo、Astro、Next.js、Gatsbyなどの静的サイトジェネレーターや、Cloudflare Pages、Vercel、Netlifyなどのホスティングサービスで構築されたサイトにおいて、バックエンドを用意せずにフォームを設置できる最適なソリューションとなります。
4. 安心のセキュリティとスパム対策#
フォームを公開すると必ず直面するのが「スパムメール」の問題です。Formspreeでは、独自のスパムフィルターに加えて、Google reCAPTCHAを利用したスパム対策が標準で組み込まれています。悪意のあるBotからの大量送信を防ぎ、安全に運用することができます。
Formspreeのデメリット・注意点#
もちろん、導入前に知っておくべき注意点もいくつか存在します。
- 大規模サイトには不向き: お問い合わせが頻繁に発生するコーポレートサイトやECサイトでは、無料枠の50件はすぐに超過してしまいます。その場合は有料プラン(月額$10〜)へのアップグレードが必要になります。
- 複雑な処理はカスタマイズしにくい: 「送信内容に応じて自動返信メールの内容を動的に変える」「データベースに直接保存しつつ別のAPIを叩く」といった複雑な要件がある場合は、自前でAPIを実装する方が適しています。
Formspreeの導入手順(3ステップ)#
それでは、実際にFormspreeを使ってお問い合わせフォームを作成する手順を解説します。驚くほど簡単です。
ステップ1: アカウント登録#
まずは Formspreeの公式サイト にアクセスし、「Get Started」からアカウントを作成します。メールアドレスとパスワードを登録し、認証メールのリンクをクリックして本登録を完了させてください。
ステップ2: フォームの作成とエンドポイント取得#
Formspreeでは以下のように、シンプルなUIでフォームを作成できます。 数クリックで設定できるため、初心者でも迷いません。

ダッシュボードにログイン後、「+ New Project」または「+ New Form」ボタンをクリックします。
- Form name: 任意の名前(例:ブログお問い合わせ)
- Send emails to: 通知を受け取りたい自分のメールアドレス
作成が完了すると、https://formspree.io/f/xxxxxxxx のような固有のエンドポイントURLが発行されます。このURLをコピーしておきます。
ステップ3: HTMLに埋め込む#
あとは、自身のサイトのHTMLにフォームを記述するだけです。action属性に先ほどコピーしたURLを貼り付けます。
<form action="https://formspree.io/f/xxxxxxxx" method="POST">
<label>
お名前:
<input type="text" name="name" required />
</label>
<label>
メールアドレス:
<input type="email" name="email" required />
</label>
<label>
メッセージ:
<textarea name="message" required></textarea>
</label>
<button type="submit">送信する</button>
</form>これで実装は完了です!実際にブラウザから送信ボタンを押すと、Formspreeのスパムチェック画面(初回のみの場合あり)を経由して、登録したメールアドレスに通知が届きます。
【実践編】Next.js (React) での実装例#
モダンなフロントエンド開発において、ページ遷移を伴わない非同期通信(Ajax)でフォームを送信したいケースが多いでしょう。
以下は、Next.js環境でReactのuseStateを使って、「送信中」「送信成功」「エラー」の状態管理を取り入れた実務レベルのコード例です。
import { useState } from 'react';
export default function ContactForm() {
const [status, setStatus] = useState<'idle' | 'submitting' | 'success' | 'error'>('idle');
const handleSubmit = async (e: React.FormEvent<HTMLFormElement>) => {
e.preventDefault();
setStatus('submitting');
const form = e.currentTarget;
const formData = new FormData(form);
try {
// あなたのFormspreeエンドポイントURLに置き換えてください
const response = await fetch('https://formspree.io/f/xxxxxxxx', {
method: 'POST',
body: formData,
headers: {
Accept: 'application/json',
},
});
if (response.ok) {
setStatus('success');
form.reset(); // 送信成功時にフォームをクリア
} else {
setStatus('error');
}
} catch (error) {
setStatus('error');
}
};
return (
<div className="max-w-md mx-auto p-4 bg-white shadow rounded-lg">
<h2 className="text-2xl font-bold mb-4">お問い合わせ</h2>
{status === 'success' ? (
<div className="p-4 mb-4 text-green-700 bg-green-100 rounded">
お問い合わせを受け付けました。ご連絡までしばらくお待ちください。
</div>
) : (
<form onSubmit={handleSubmit} className="space-y-4">
<div>
<label htmlFor="email" className="block text-sm font-medium text-gray-700">メールアドレス</label>
<input
id="email"
type="email"
name="email"
required
className="mt-1 block w-full rounded-md border-gray-300 shadow-sm focus:border-blue-500 focus:ring-blue-500"
/>
</div>
<div>
<label htmlFor="message" className="block text-sm font-medium text-gray-700">メッセージ</label>
<textarea
id="message"
name="message"
rows={4}
required
className="mt-1 block w-full rounded-md border-gray-300 shadow-sm focus:border-blue-500 focus:ring-blue-500"
></textarea>
</div>
{status === 'error' && (
<p className="text-red-500 text-sm">送信に失敗しました。時間をおいて再度お試しください。</p>
)}
<button
type="submit"
disabled={status === 'submitting'}
className="w-full flex justify-center py-2 px-4 border border-transparent rounded-md shadow-sm text-white bg-blue-600 hover:bg-blue-700 focus:outline-none disabled:opacity-50"
>
{status === 'submitting' ? '送信中...' : '送信する'}
</button>
</form>
)}
</div>
);
}このように実装することで、ユーザー体験(UX)を損なうことなく、スタイリッシュなフォームを設置できます。
よくある質問(FAQ)#
Q1. 無料枠(月50件)を超えてしまった場合はどうなりますか?#
月間の送信上限である50件を超過した場合、それ以降のフォーム送信はエラーとなり、メッセージは受信できなくなります。ブログのアクセスが増え、月に50件以上のお問い合わせが来るようになった場合は、有料プランへの移行を検討するか、自前でAPIを実装するフェーズに入ったと考えるのが良いでしょう。
Q2. 迷惑メール(スパム)がたくさん来ないか心配です#
Formspreeには自動のスパムフィルターが搭載されています。また、管理画面から「reCAPTCHA」を有効にすることで、ボットによる自動送信を強力にブロックすることが可能です。無料プランでも十分なスパム対策が可能です。
Q3. 送信完了後の画面(サンクスページ)はカスタマイズできますか?#
通常のHTMLフォーム送信の場合、Formspreeが用意したデフォルトの送信完了画面に遷移してしまいます。独自のサンクスページにリダイレクトさせたい場合は、有料プランが必要になるケースがあります。ただし、上記のNext.jsの例のように、非同期通信(Ajax/fetch)で送信処理を自作すれば、無料で完全に画面遷移をコントロールすることが可能です。
まとめ:個人開発・ブログにはFormspreeが最適解#
この記事では、サーバー不要でお問い合わせフォームを実装できる「Formspree」について解説しました。
- バックエンド(サーバー・API)の構築が一切不要
- HTMLにURLを貼り付けるだけで稼働
- 個人ブログなら無料プラン(月50件)で十分対応可能
- Next.jsや静的サイト(SSG)との相性が抜群
特に立ち上げたばかりの個人ブログやポートフォリオサイトにおいて、お問い合わせフォームの実装に時間をかけるのはもったいないです。まずはFormspreeを使ってサクッとフォームを設置し、コンテンツ制作など本来注力すべき作業に時間を使いましょう!










