Webhooks
Stuur elke inzending als JSON naar een adres van uzelf, op het moment dat hij binnenkomt.
Eén POST per reactie
Verstuurd zodra het antwoord is opgeslagen, zonder de respondent te laten wachten.
Een stabiele JSON-vorm
Publieke typenamen en permanente veld-ID's, dus een vraag hernoemen breekt uw code nooit.
10 seconden, één poging
Fillio wacht tien seconden op uw endpoint en probeert het daarna niet opnieuw.
Een webhook aanzetten
Open het formulier, ga naar het tabblad Instellingen en zet Webhook aan. Plak het adres dat de inzendingen moet ontvangen; Fillio slaat het een moment nadat u stopt met typen op en bevestigt dat op het scherm. Elk formulier draagt één adres, en de schakelaar weer uitzetten wist het.
Het adres moet HTTPS zijn
Fillio roept alleen adressen aan die met https:// beginnen. Een http://-adres wordt door het instellingenveld geaccepteerd maar nooit aangeroepen, dus een webhook die opgeslagen lijkt, levert stilletjes niets af.
Adressen die naar een privénetwerk wijzen worden eveneens geweigerd: elke host op 10.x, 127.x, 169.254.x, 172.16-31.x of 192.168.x, elk IPv6-adres, en elke naam die localhost is of eindigt op .local of .internal. Uw endpoint moet bereikbaar zijn vanaf het publieke internet.
Het verzoek
Een POST met een JSON-body. Er reizen vier headers mee.
| Header | Beschrijving |
|---|---|
| Content-Type: application/json | De body is altijd JSON. |
| User-Agent: Fillio Webhooks/1.0 | Identificeert de aanroeper als Fillio, wat handig is wanneer één endpoint naar meerdere diensten luistert. |
| X-Fillio-Event: FORM_RESPONSE | De naam van de gebeurtenis. FORM_RESPONSE is vandaag de enige waarde die Fillio verstuurt. |
| X-Fillio-Event-Id | Een verse UUID voor deze aflevering, herhaald als eventId in de body. |
De payload
Een envelop die de gebeurtenis beschrijft, en een data-object dat de reactie beschrijft.
{
"eventId": "8f2c1d7a-4b09-4e5c-9a13-6d0f8b2e77c4",
"eventType": "FORM_RESPONSE",
"createdAt": "2026-08-26T09:14:22.481Z",
"data": {
"responseId": "Qh3Rk9wZm1sVtY7cN2xP",
"formId": "7bTn4Kq2Wx",
"formName": "Workshop signup",
"createdAt": "2026-08-26T09:14:22.481Z",
"fields": [
{
"key": "V1StGXR8_Z5jdHi6B-myT",
"label": "Full name",
"type": "INPUT_TEXT",
"value": "Mira Kaya"
},
{
"key": "kM4pQz7LxAe2Rn0BsTvUw",
"label": "Which session?",
"type": "MULTIPLE_CHOICE",
"value": "c9XbNf3JdQ",
"options": [
{ "id": "c9XbNf3JdQ", "text": "Morning" },
{ "id": "eR2mYt8KpL", "text": "Afternoon" }
]
},
{
"key": "zA6cWn1FyH4tXd9QrLbEs",
"label": "How likely are you to recommend us?",
"type": "LINEAR_SCALE",
"value": 9
}
]
}
}| Eigenschap | Beschrijving |
|---|---|
| eventId | Een unieke ID voor deze aflevering. |
| eventType | Altijd FORM_RESPONSE. |
| createdAt | Wanneer de reactie is verstuurd, als ISO 8601-tijdstempel in UTC. |
| data.responseId | De ID van de opgeslagen reactie. |
| data.formId | De ID van het formulier, dezelfde die in de publieke link staat. |
| data.formName | De formuliertitel als platte tekst, met alle opmaak verwijderd. |
| data.fields | Eén item per beantwoorde vraag. |
In fields
Elk item draagt vier eigenschappen, en een vraag met opties draagt er een vijfde.
| Eigenschap | Beschrijving |
|---|---|
| key | De permanente ID van de vraag. Hij overleeft elke wijziging in de formulering, dus match hierop en niet op het label. |
| label | De vraag zoals die in de editor geschreven staat. |
| type | Het vraagtype, uit de lijst hieronder. |
| value | Het antwoord, in de vorm waarin die vraag het opslaat. |
| options | Alleen bij vragen met opties: de ID en de tekst van elke optie, zodat u een antwoord weer in een label kunt omzetten. |
Alleen beantwoorde vragen komen binnen
Een vraag die de respondent onaangeroerd liet, ontbreekt in de array in plaats van als lege waarde te worden verstuurd, en een vraag die door voorwaardelijke logica verborgen is, verschijnt helemaal niet. Zoek elk antwoord op via zijn key in plaats van te vertrouwen op de positie of op een vast aantal items.
Keuzeantwoorden dragen ID's, geen labels
Een antwoord op een dropdown of meerkeuzevraag is de ID van de gekozen optie, en een antwoord op selectievakjes, multiselect of rangschikking is een array van optie-ID's. Zoek ze op in de optielijst van datzelfde item. Een rangschikkingsantwoord behoudt de volgorde waarin de respondent de items heeft gezet.
De optie Anders
Wanneer een respondent in een Anders-veld schrijft, is de waarde geen optie-ID maar de tekst __OTHER__: gevolgd door wat er getypt is. Haal dat voorvoegsel weg om het antwoord te lezen.
"value": "__OTHER__:Heard about it from a friend"Bestanden en handtekeningen
Een antwoord op een bestandsupload is een downloadlink naar het bestand in de opslag van Fillio. Een handtekeningantwoord is een base64-PNG-data-URL, die u direct kunt opslaan of weergeven.
Veldtypen
Het type is een stabiele publieke naam, dus een verandering binnen Fillio bereikt uw integratie nooit. Alles wat Fillio niet kan toewijzen, komt binnen als INPUT_TEXT.
| Type | Vraag | Waarde |
|---|---|---|
| INPUT_TEXT | Kort antwoord | Tekst |
| TEXTAREA | Lang antwoord | Tekst |
| INPUT_EMAIL | Tekst | |
| INPUT_PHONE_NUMBER | Telefoonnummer | Tekst |
| INPUT_NUMBER | Nummer | Het getal als tekst, precies zoals het is getypt |
| INPUT_LINK | Link | Tekst |
| INPUT_DATE | Datum | Een datum, als YYYY-MM-DD |
| INPUT_TIME | Tijd | Een tijd, als HH:MM op een 24-uursklok |
| DROPDOWN | Vervolgkeuzelijst | Eén optie-ID |
| MULTIPLE_CHOICE | Keuzerondje | Eén optie-ID |
| CHECKBOXES | Selectievakje | Een array van optie-ID's |
| MULTI_SELECT | Meervoudige selectie | Een array van optie-ID's |
| RATING | Sterbeoordeling | Een getal |
| LINEAR_SCALE | Lineaire schaal | Een getal |
| RANKING | Rangschikking | Een array van optie-ID's, in de volgorde van de respondent |
| FILE_UPLOAD | Bestand uploaden | Een downloadlink |
| SIGNATURE | Handtekening | Een base64-PNG-data-URL |
Als uw endpoint niet antwoordt
Fillio wacht tien seconden. Een time-out, een verbindingsfout of een status buiten het 2xx-bereik telt als een mislukte aflevering, en daarmee houdt het op: er is geen nieuwe poging en geen wachtrij om opnieuw af te spelen.
De reactie zelf wordt nooit geraakt. Hij wordt opgeslagen voordat het verzoek wordt gedaan en blijft in uw dashboard staan, wat uw endpoint ook doet, zodat het dashboard het volledige archief blijft, ook als een aflevering verloren gaat.
Er is geen handtekening
Fillio ondertekent het verzoek niet en stuurt geen gedeeld geheim mee, dus de body alleen bewijst niet waar hij vandaan komt. Moet uw endpoint zeker zijn, geef het dan een adres dat alleen u kent: een lang, onraadbaar pad of query string. Behandel alles wat elders binnenkomt als onbetrouwbaar.
Elke aflevering draagt een eigen event-ID, zowel in de header X-Fillio-Event-Id als in de body. De ID's bijhouden die u al hebt afgehandeld is de eenvoudigste manier om uw endpoint veilig twee keer aanroepbaar te maken.
Richt de webhook op een willekeurig endpoint dat verzoeken inspecteert en verstuur uw eigen formulier één keer. U ziet dan precies de payload die uw formulier oplevert, met uw eigen veld-ID's erin. Dat is de snelste manier om de mapping aan uw kant te schrijven.