AI
AI-powered field detection
Automatically detect and create form fields from a document using AI.
Accounts on the v2 detection pipeline receive additional response metadata
(see pipeline property) and richer preferences on each field (canonical
key, per-field confidence, anchor_text, and anchor_method). See the
AI Field Detection Pipeline guide
for details. Existing consumers are unaffected — the new fields are
additive. On v2, callers may optionally send context to provide
advisory hints and expected canonical fields; legacy v1 silently ignores it.
POST
/
api
/
templates
/
{template_id}
/
ai
/
smart_create
AI-powered field detection
curl --request POST \
--url https://spitshake.io/api/templates/{template_id}/ai/smart_create \
--header 'Content-Type: application/json' \
--header 'X-Auth-Token: <api-key>' \
--data '
{
"detection_mode": "all",
"context": {
"document_hint": "Customs POA; signer is the importer of record.",
"instructions": "Skip the notary section.",
"expected_fields": [
{
"key": "importer_name",
"name": "Importer Name",
"type": "text"
}
],
"merge_mode": "extend",
"per_document": {
"550e8400-e29b-41d4-a716-446655440000": {
"document_hint": "CBP 4811 form"
}
}
}
}
'import requests
url = "https://spitshake.io/api/templates/{template_id}/ai/smart_create"
payload = {
"detection_mode": "all",
"context": {
"document_hint": "Customs POA; signer is the importer of record.",
"instructions": "Skip the notary section.",
"expected_fields": [
{
"key": "importer_name",
"name": "Importer Name",
"type": "text"
}
],
"merge_mode": "extend",
"per_document": { "550e8400-e29b-41d4-a716-446655440000": { "document_hint": "CBP 4811 form" } }
}
}
headers = {
"X-Auth-Token": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-Auth-Token': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
detection_mode: 'all',
context: {
document_hint: 'Customs POA; signer is the importer of record.',
instructions: 'Skip the notary section.',
expected_fields: [{key: 'importer_name', name: 'Importer Name', type: 'text'}],
merge_mode: 'extend',
per_document: {'550e8400-e29b-41d4-a716-446655440000': {document_hint: 'CBP 4811 form'}}
}
})
};
fetch('https://spitshake.io/api/templates/{template_id}/ai/smart_create', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://spitshake.io/api/templates/{template_id}/ai/smart_create",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'detection_mode' => 'all',
'context' => [
'document_hint' => 'Customs POA; signer is the importer of record.',
'instructions' => 'Skip the notary section.',
'expected_fields' => [
[
'key' => 'importer_name',
'name' => 'Importer Name',
'type' => 'text'
]
],
'merge_mode' => 'extend',
'per_document' => [
'550e8400-e29b-41d4-a716-446655440000' => [
'document_hint' => 'CBP 4811 form'
]
]
]
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"X-Auth-Token: <api-key>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://spitshake.io/api/templates/{template_id}/ai/smart_create"
payload := strings.NewReader("{\n \"detection_mode\": \"all\",\n \"context\": {\n \"document_hint\": \"Customs POA; signer is the importer of record.\",\n \"instructions\": \"Skip the notary section.\",\n \"expected_fields\": [\n {\n \"key\": \"importer_name\",\n \"name\": \"Importer Name\",\n \"type\": \"text\"\n }\n ],\n \"merge_mode\": \"extend\",\n \"per_document\": {\n \"550e8400-e29b-41d4-a716-446655440000\": {\n \"document_hint\": \"CBP 4811 form\"\n }\n }\n }\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("X-Auth-Token", "<api-key>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://spitshake.io/api/templates/{template_id}/ai/smart_create")
.header("X-Auth-Token", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"detection_mode\": \"all\",\n \"context\": {\n \"document_hint\": \"Customs POA; signer is the importer of record.\",\n \"instructions\": \"Skip the notary section.\",\n \"expected_fields\": [\n {\n \"key\": \"importer_name\",\n \"name\": \"Importer Name\",\n \"type\": \"text\"\n }\n ],\n \"merge_mode\": \"extend\",\n \"per_document\": {\n \"550e8400-e29b-41d4-a716-446655440000\": {\n \"document_hint\": \"CBP 4811 form\"\n }\n }\n }\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://spitshake.io/api/templates/{template_id}/ai/smart_create")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["X-Auth-Token"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"detection_mode\": \"all\",\n \"context\": {\n \"document_hint\": \"Customs POA; signer is the importer of record.\",\n \"instructions\": \"Skip the notary section.\",\n \"expected_fields\": [\n {\n \"key\": \"importer_name\",\n \"name\": \"Importer Name\",\n \"type\": \"text\"\n }\n ],\n \"merge_mode\": \"extend\",\n \"per_document\": {\n \"550e8400-e29b-41d4-a716-446655440000\": {\n \"document_hint\": \"CBP 4811 form\"\n }\n }\n }\n}"
response = http.request(request)
puts response.read_body{
"fields": [
{
"uuid": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"name": "<string>",
"type": "text",
"submitter_uuid": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"required": true,
"readonly": true,
"key": "<string>",
"default_value": "<string>",
"placeholder": "<string>",
"pattern": "<string>",
"validation": "ssn",
"options": [
"<string>"
],
"formula": "<string>",
"areas": [
{
"x": 23.07,
"y": 20.35,
"w": 25,
"h": 5,
"page": 1,
"attachment_uuid": "3c90c3cc-0d44-4b50-8888-8dd25736052a"
}
],
"preferences": {}
}
],
"count": 123,
"pipeline": {
"version": "v2",
"request_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"latency_ms": 123,
"anchor_hits": 123,
"anchor_misses": 123,
"corrections_applied": 123,
"critic_ran": true,
"documents_scanned": 123,
"verifier_ran": true
}
}Authorizations
ApiTokenSessionCookie
API token generated at Settings > API
Path Parameters
Body
application/json
⌘I
AI-powered field detection
curl --request POST \
--url https://spitshake.io/api/templates/{template_id}/ai/smart_create \
--header 'Content-Type: application/json' \
--header 'X-Auth-Token: <api-key>' \
--data '
{
"detection_mode": "all",
"context": {
"document_hint": "Customs POA; signer is the importer of record.",
"instructions": "Skip the notary section.",
"expected_fields": [
{
"key": "importer_name",
"name": "Importer Name",
"type": "text"
}
],
"merge_mode": "extend",
"per_document": {
"550e8400-e29b-41d4-a716-446655440000": {
"document_hint": "CBP 4811 form"
}
}
}
}
'import requests
url = "https://spitshake.io/api/templates/{template_id}/ai/smart_create"
payload = {
"detection_mode": "all",
"context": {
"document_hint": "Customs POA; signer is the importer of record.",
"instructions": "Skip the notary section.",
"expected_fields": [
{
"key": "importer_name",
"name": "Importer Name",
"type": "text"
}
],
"merge_mode": "extend",
"per_document": { "550e8400-e29b-41d4-a716-446655440000": { "document_hint": "CBP 4811 form" } }
}
}
headers = {
"X-Auth-Token": "<api-key>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {'X-Auth-Token': '<api-key>', 'Content-Type': 'application/json'},
body: JSON.stringify({
detection_mode: 'all',
context: {
document_hint: 'Customs POA; signer is the importer of record.',
instructions: 'Skip the notary section.',
expected_fields: [{key: 'importer_name', name: 'Importer Name', type: 'text'}],
merge_mode: 'extend',
per_document: {'550e8400-e29b-41d4-a716-446655440000': {document_hint: 'CBP 4811 form'}}
}
})
};
fetch('https://spitshake.io/api/templates/{template_id}/ai/smart_create', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://spitshake.io/api/templates/{template_id}/ai/smart_create",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'detection_mode' => 'all',
'context' => [
'document_hint' => 'Customs POA; signer is the importer of record.',
'instructions' => 'Skip the notary section.',
'expected_fields' => [
[
'key' => 'importer_name',
'name' => 'Importer Name',
'type' => 'text'
]
],
'merge_mode' => 'extend',
'per_document' => [
'550e8400-e29b-41d4-a716-446655440000' => [
'document_hint' => 'CBP 4811 form'
]
]
]
]),
CURLOPT_HTTPHEADER => [
"Content-Type: application/json",
"X-Auth-Token: <api-key>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://spitshake.io/api/templates/{template_id}/ai/smart_create"
payload := strings.NewReader("{\n \"detection_mode\": \"all\",\n \"context\": {\n \"document_hint\": \"Customs POA; signer is the importer of record.\",\n \"instructions\": \"Skip the notary section.\",\n \"expected_fields\": [\n {\n \"key\": \"importer_name\",\n \"name\": \"Importer Name\",\n \"type\": \"text\"\n }\n ],\n \"merge_mode\": \"extend\",\n \"per_document\": {\n \"550e8400-e29b-41d4-a716-446655440000\": {\n \"document_hint\": \"CBP 4811 form\"\n }\n }\n }\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("X-Auth-Token", "<api-key>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://spitshake.io/api/templates/{template_id}/ai/smart_create")
.header("X-Auth-Token", "<api-key>")
.header("Content-Type", "application/json")
.body("{\n \"detection_mode\": \"all\",\n \"context\": {\n \"document_hint\": \"Customs POA; signer is the importer of record.\",\n \"instructions\": \"Skip the notary section.\",\n \"expected_fields\": [\n {\n \"key\": \"importer_name\",\n \"name\": \"Importer Name\",\n \"type\": \"text\"\n }\n ],\n \"merge_mode\": \"extend\",\n \"per_document\": {\n \"550e8400-e29b-41d4-a716-446655440000\": {\n \"document_hint\": \"CBP 4811 form\"\n }\n }\n }\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://spitshake.io/api/templates/{template_id}/ai/smart_create")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["X-Auth-Token"] = '<api-key>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"detection_mode\": \"all\",\n \"context\": {\n \"document_hint\": \"Customs POA; signer is the importer of record.\",\n \"instructions\": \"Skip the notary section.\",\n \"expected_fields\": [\n {\n \"key\": \"importer_name\",\n \"name\": \"Importer Name\",\n \"type\": \"text\"\n }\n ],\n \"merge_mode\": \"extend\",\n \"per_document\": {\n \"550e8400-e29b-41d4-a716-446655440000\": {\n \"document_hint\": \"CBP 4811 form\"\n }\n }\n }\n}"
response = http.request(request)
puts response.read_body{
"fields": [
{
"uuid": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"name": "<string>",
"type": "text",
"submitter_uuid": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"required": true,
"readonly": true,
"key": "<string>",
"default_value": "<string>",
"placeholder": "<string>",
"pattern": "<string>",
"validation": "ssn",
"options": [
"<string>"
],
"formula": "<string>",
"areas": [
{
"x": 23.07,
"y": 20.35,
"w": 25,
"h": 5,
"page": 1,
"attachment_uuid": "3c90c3cc-0d44-4b50-8888-8dd25736052a"
}
],
"preferences": {}
}
],
"count": 123,
"pipeline": {
"version": "v2",
"request_id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"latency_ms": 123,
"anchor_hits": 123,
"anchor_misses": 123,
"corrections_applied": 123,
"critic_ran": true,
"documents_scanned": 123,
"verifier_ran": true
}
}
