商业系统
表单
将 Kanorio 表单放置在您自己的前端,并为您处理机器人防护、文件上传、同意与联系人收集。
请在后台的 营销 › 在线表单 建立表单,然后将其显示在您的前端。Kanorio 会检查机器人与垃圾信息、保存提交内容、创建或更新联系人、发送确认与团队邮件,并触发 customers.form.submitted Webhook。
开始之前,请从后台复制表单 ID。如果浏览器从您自己的域名调用 API,请将该域名新增至 网站设置 › 开发者 下的 允许的来源。localhost 始终是被允许的。
选项 1:表单元素
<KanorioForm> 可渲染所有问题类型、文件上传与同意复选框,并为您执行机器人防护。这是最快的方法,且无需升级即可获得新的防护规则。
import { KanorioProvider, KanorioForm } from "@kanorio/elements"; import "@kanorio/elements/elements.css"; export function ContactSection() { return ( <KanorioProvider siteUrl="https://s-xxxxxxxxxxxx.kanorio.com"> <KanorioForm formId="cform12345678901234567890" siteName="Sourdough Studio" /> </KanorioProvider> ); }
若未使用 React,请使用 <kanorio-form site-url="…" form-id="…">。请参阅 Elements。
选项 2:您自己的标记
当您想要完全控制 HTML 时,请直接使用 Content Delivery API。
1. 加载表单
GET /api/v1/forms/{id} 会返回问题、同意设置以及表单是否正在接受回答。如果 availability.accepting 为 false,请显示关闭消息而非输入字段。
2. 在显示表单时获取机器人检查
GET /api/v1/forms/{id}/challenge 会返回此提交的机器人检查。其 provider 由网站拥有者在 网站设置 › 机器人防护 中设置:
kanorio(默认):altcha中的内置工作量证明挑战。SDK 会为您解决(在中端手机上约需半秒),并将结果作为_tk发送。turnstile、recaptcha或hcaptcha:拥有者自己的密钥。请使用siteKey和action(Turnstile 亦需cData)渲染该提供者的组件,并将其令牌作为captchaToken传递。服务器会根据网站设置决定验证哪个提供者,因此来自任何其他提供者的令牌将被拒绝。
每次提交请获取新的挑战:挑战与组件令牌皆为单次使用。
3. 提交
发送以问题 ID 为键的答案,并附上防护字段。蜜罐 (Honeypot) 字段必须为空。
import { forms } from "@kanorio/sdk/forms"; const SITE_URL = "https://s-xxxxxxxxxxxx.kanorio.com"; const FORM_ID = "cform12345678901234567890"; const client = forms.client({ siteUrl: SITE_URL }); // when the form is shown const renderedAt = Date.now(); const challenge = await client.challenge(FORM_ID); // when the visitor submits // built-in: the SDK solves the challenge; third-party: pass the widget token const protection = await forms.protectionFromChallenge(FORM_ID, challenge, renderedAt, { captchaToken: challenge.provider === "kanorio" ? undefined : widgetToken, }); const result = await client.submit(FORM_ID, { answers: { name: "Ada", email: "ada@example.com", message: "Do you ship?" }, consent: "checked", pagePath: window.location.pathname, protection, }); if (!result.ok) { // result.error.code, and result.error.issues for INVALID_ANSWERS }
若未使用 SDK,请使用此内容 POST /api/v1/forms/{id}/submit(显示内置检查;若使用第三方提供者,请发送 captchaToken 取代 _tk):
{ "answers": { "name": "Ada", "email": "ada@example.com" }, "consent": "checked", "pagePath": "/contact", "_hp": "", "_ts": 1793520000000, "_tk": "<solved ALTCHA payload>", "_ctx": "cform12345678901234567890" }
成功的提交会返回 200 与 {}。如果表单在此期间关闭,内容则为 { "state": "closed" }、"not_open" 或 "full"。
| 错误代码 | 处理方式 |
|---|---|
INVALID_ANSWERS | 显示 details.issues 中的消息,并以问题 ID 作为键值 |
VERIFICATION_EXPIRED | 获取新的验证挑战(并重置小工具)后重新提交 |
DUPLICATE_SUBMISSION | 告知访客表单已提交 |
RATE_LIMITED | 等待 Retry-After 指定的时间后重试 |
文件上传
对于文件问题,请先使用 POST /api/v1/forms/{id}/upload-request 请求上传票据,并附上问题 ID、文件名、类型与大小,以及来自 forms.uploadProtectionFromChallenge(FORM_ID, challenge, renderedAt, solved) 的防护字段:使用内置检查时,这与您提交时使用的已解决挑战相同;使用第三方提供者时,它会使用挑战的 uploadToken,因为组件令牌为单次使用且会在提交时检查。使用返回的 headers 将文件 PUT 至 uploadUrl,然后将 uploadId 作为该问题的答案发送。超过问题限制的文件会失败并返回 413 FILE_TOO_LARGE。
提交后
- 提交内容会出现在后台以及 Management API 的
submissions下。 - 联系人会根据电子邮件或电话答案进行创建或更新。
- 确认与团队邮件会按照表单设置发送。
- Webhook 订阅者会收到
customers.form.submitted。
从您的服务器转发
您可以从自己的服务器提交,例如 Next.js 服务器动作。速率限制适用于每位访客,因此直接从浏览器提交最能保护您的配额。如果您进行转发,请保持浏览器的防护字段不变。