🎨
HubDB × サーバレス関数でHubSpotフォームの送信上限を実現する方法【コード付き】💻
|
Reina
|
HubSpot,
HubSpot CMS

目次
はじめに 🌿
HubSpotのフォームに「送信上限」をつけられない。このもやもやを解決するために、HubDBとサーバレス関数を使って実装してみました💻
この記事では、その構成や実装手順をコード付きで解説しています✨ まずはざっくり流れを知りたい人は、前編の記事もあわせて読んでね!
デモ動画 🎥
この仕組みでは、こんな動きをしてるよ!
-
サーバレス関数経由でHubDBの数値をカウントアップ
-
上限数に達したらフォーム非表示(メッセージ表示)
-
申込み期限(UTC基準)を過ぎたら自動でフォーム非表示!
前提について少し整理 ☕️
シナリオ 🍵
-
HubSpotフォームを使って申し込んでもらう
-
予約者数に制限をかけたい
-
定数超えたらフォームを自動非表示に
-
ついでに、フォーム送信ができる期限のタイミングもつけたい
構成イメージ 🌎
-
HubDBでフォームごとに情報を管理
-
CMSテンプレート内で利用
-
フォーム送信時にカウントアップ
-
サーバレス関数側でHubDB APIを使って更新
使った技術 ・ ファイル ・ ツール ⚡️
-
JavaScript (hbspt.forms)
実装コードの概要 🔧
HubDB のテーブル
カラム名 | 用途 | データ型 |
---|---|---|
form_guid | 対象のフォームID(送信元の特定に使用) | 文字列(text) |
current_submissions | 現在の送信数 | 数値(number) |
max_submissions | 送信可能な最大数 | 数値(number) |
deadline | 申込み締切日時(UTC) | 日時(datetime) |
📝
このテーブルは フォームごとの送信状態を管理するためのもので、テンプレート側のif文で送信数の上限や締切日をもとにフォームの表示/非表示を切り替えます
テンプレート内のHubL
Page template
{# 今この瞬間のローカル時間を取得してUNIXタイムに変換してるよ #}
{% set today = unixtimestamp(local_dt) %}
{# HubDBのテーブルIDを指定してデータを取得! #}
{% set table = hubdb_table_rows("HUBDB_ID_HERE") %}
{% for row in table %}
{% if row.form_guid "FORM_GUID_HERE" %}
{% set current_submissions = row.current_submissions %}
{% set submission_limit = row.max_submissions %}
{% set deadline_timestamp = row.deadline %}
{% if current_submissions < submission_limit and today < deadline_timestamp %}
{# 送信数も期限もOKならフォームを表示するよ! #}
<div id="my-form-wrapper">
<div id="my-form-target"></div>
<script src="https://js.hsforms.net/forms/v2.js"></script>
<script>
hbspt.forms.create({
region: "na1",
portalId: "YOUR_PORTAL_ID",
formId: "FORM_GUID_HERE",
target: '#my-form-target',
onFormSubmit: function($form) {
// 送信時にカウントアップするためにサーバレス関数を叩く!
fetch('/_hcms/api/update-form-submissions', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ form_guid: 'FORM_GUID_HERE' })
});
}
});
</script>
</div>
{% else %}
{# 上限達成または締切すぎたら、締め切りメッセージを出す! #}
<div class="form-closed-message">
<p>このフォームは締め切りました🙇♀️</p>
</div>
{% endif %}
{% endif %}
{% endfor %}
📝
if current_submissions < submission_limit and today < deadline_timestampで、送信数も期限にも制限に達していない場合のみフォームが表示されるようになっているよ
サーバレス関数
form-limit-updater.js
const HUBSPOT_PRIVATE_APP_TOKEN = process.env.FORM_LIMIT_MANAGER; // 環境変数にトークンをセット!
exports.main = async (context = {}, sendResponse) => {
try {
const body = context.body || {};
const formGuid = body.form_guid;
const tableId = 'YOUR_TABLE_ID'; //HubDBのテーブルIDを指定
if (!formGuid) {
return sendResponse({ statusCode: 400, body: { message: 'form_guid がリクエストに含まれていません' } });
}
// HubDBの行データを取得して、該当するform_guidを探す
const recordsResponse = await fetch(`https://api.hubapi.com/cms/v3/hubdb/tables/${tableId}/rows`, { ... });
const records = await recordsResponse.json();
const targetRecord = records.results.find(record => record.values.form_guid = formGuid);
if (!targetRecord) {
return sendResponse({ statusCode: 404, body: { message: '該当レコードが見つかりませんでした' } });
}
// 現在の送信数を+1する準備!
const rowResponse = await fetch(`https://api.hubapi.com/cms/v3/hubdb/tables/${tableId}/rows/${targetRecord.id}`, { ... });
const rowData = await rowResponse.json();
const updatedValues = {
...rowData.values,
current_submissions: (targetRecord.values.current_submissions || 0) + 1
};
// draftに更新して...
await fetch(`https://api.hubapi.com/cms/v3/hubdb/tables/${tableId}/rows/${targetRecord.id}/draft`, { ... });
// そしてpublishして確定!
await fetch(`https://api.hubapi.com/cms/v3/hubdb/tables/${tableId}/draft/publish`, { ... });
return sendResponse({ statusCode: 200, body: { message: '送信数を更新して公開しました', newCount: updatedValues.current_submissions } });
} catch (error) {
return sendResponse({ statusCode: 500, body: { message: 'エラーが発生しました', error: error.message } });
}
};
serverless.json
{"runtime":"nodejs18.x","version":"1.0","secrets":["FORM_LIMIT_MANAGER"],"endpoints":{"update-form-submissions":{"method":"POST","file":"form-limit-updater.js"}}}
📝
このサーバレス関数はフォーム送信がされたイベントをトリガーとしてリクエストが実行されて、HubDBの "current_submissions" 列の値を +1 します
注意ポイント ⚡
-
deadlineやmax_submissionsを手動で管理する必要あり
-
今のテンプレートはテンプレート内で form guid を指定しているから、複数フォームが出てきたときの処理に工夫が必要かも
-
HubDBのドラフト更新・公開の流れをミスらないように注意!
まとめ ✨
HubSpotの標準機能だけでは難しかった「送信上限&期限制御」も、 ちょっとカスタムすればここまでできる!
仕組みをしっかり作り込めば、イベントやワークショップ管理がとっても楽になるよ🌸
無理せず楽しくHubSpotを育てていこうね〜!
あわせて読みたい 📖
サーバレス関数の作り方について詳しく学ぶなら、以下シリーズがおすすめ!💡:
💬 コメントしてみる?