Form webhook
Point any form builder at one webhook URL and every submission becomes a scored, attributed lead.
The form webhook is universal — it works with any form builder that can send a webhook: WS Form, Gravity Forms, Cognito Forms, Typeform, Jotform, and others. Syft is deliberately form-agnostic: you keep the form builder you already have.
POST https://YOUR-INSTANCE/api/webhooks/form?org_slug=YOUR-ORG&secret=YOUR-SECRET
Your exact URL — with org slug and secret filled in — is in Settings → Setup Guide → section 2, along with a Send test lead button so you can verify the connection before touching your live form.
Setup in four steps
- Add a webhook to your form builder pointing at the URL above (method POST, format JSON).
- Map your form fields to the standard field names below.
- Make sure your BANT dropdown values match your scoring map — if your form has no scoring dropdowns, the AI extracts what it can from the message text instead.
- Add the hidden attribution fields below — the site-wide snippet fills them automatically on every page.
Standard field names
Map your form’s fields to these names in the webhook payload:
| Field | What it is |
|---|---|
name | Contact name |
email | Email address |
phone | Phone number |
company | Company name |
authority | Scoring dropdown — role / job title |
budget | Scoring dropdown — budget status |
need | Scoring dropdown — enquiry type |
timeline | Scoring dropdown — project timeline |
body | Free-text message field |
bant_score | Optional: a pre-computed score 0–100. If sent, Syft uses it instead of scoring server-side |
The dropdown fields are scored against your organisation’s scoring map — see
Lead scoring for how matching works and what the labels
should be. Cognito Forms’ PascalCase names (Name, Email, ContactNumber,
CompanyName, JobTitle, BudgetStatus, ProjectTimeline, …) are accepted
as fallbacks automatically.
Hidden attribution fields
Add hidden inputs to your form with these names. The site-wide snippet fills them before the form is submitted, so each lead carries its own attribution.
| Field name | Required? | What it gets | Example |
|---|---|---|---|
channel | required | Channel category | Paid Search |
channeldrilldown1 | required | Source / engine / network | |
channeldrilldown2 | required | Campaign | spring-2026-uk |
channeldrilldown3 | required | Ad content / keyword | hero-cta |
landingpage | required | First-touch landing URL | https://site.com/lp/abc |
landingpagegroup | required | Landing path only | /lp/abc |
gclid | required | Google Click ID | CjwKCA… |
referrer | optional | First-touch referrer host — add if you want it on the lead; not needed for scoring | www.bing.com |
transaction_id | optional | Only needed for Google Ads value restatement | UUID |
Plain UTM field names (utm_source, utm_medium, utm_campaign,
utm_term, utm_content) and direct attribution fields (page_url,
landing_url, anonymous_id) are also accepted in the payload.
If a submission arrives without hidden fields at all, Syft falls back to matching the beacon sent by the snippet (by IP and browser), so attribution usually survives even on forms you can’t modify.
Per-builder notes
WS Form
- For each row in the table above, add a Hidden field and set its Name to the value in the first column.
- Leave the default value blank — the snippet writes the value at page load.
- Add an action: Send (Webhook) pointing at your form webhook URL; POST, JSON.
Gravity Forms
Gravity doesn’t let you set an input’s name directly, so use CSS classes:
- Add a Hidden field per row above.
- Open Appearance → CSS Class Name and add the class
kq-attr-<name>— e.g.kq-attr-channel,kq-attr-gclid. The snippet matches on the class instead of the name. - Send submissions to the webhook via Gravity’s webhook add-on (or Zapier), mapping fields to the standard names above.
Everything else
The snippet matches hidden fields three ways, in order:
name="channel", class="kq-attr-channel", data-kq-attr="channel" —
use whichever your builder supports. Attributer-style [channel] placeholder
values are also recognised, so forms built for Attributer.io work unchanged.