Hidden fields and URL prefill

Use hidden fields to capture values from a form’s URL without asking respondents to enter them. You can also use a hidden field to prefill a visible field.

Declare hidden fields in form settings

Hidden fields are declared in form settings, separately from the form config. Each field’s name becomes its key in submission data. Read settings with GET /forms/{id}/settings or the MCP tool get_form. Write settings with the MCP tool update_form_settings.

hidden_fields defaults to []. Each entry requires a string name; id and boolean required are optional. Names must match ^[a-z][a-z0-9_]*$, be unique, and not clash case-insensitively with a field name in the draft or published config. The server generates an id when you omit it.

{ "hidden_fields": [ { "name": "utm_source", "required": false }, { "name": "prefill_email", "required": true } ] }

A settings write replaces the whole hidden_fields array, so include every entry you want to keep. Settings changes apply to a published form at once.

Keep each hidden field’s id exactly as returned when you send the array back. To rename a hidden field, keep its id and change its name. Sending an entry without its id under a new name creates a new field. An id cannot be changed for an existing name or used twice. The MCP tool refuses to remove or rename a hidden field referenced by a calculation.

The MCP tool rejects these reserved names: _gotcha, _redirect, _session_id, _attribution, _idempotency_key, _email_verification, cf-turnstile-response, and _turnstile. In embed URLs, hidden field names also cannot start with __mf_ or mk-, or be mf_locale, pc, ac, fg, pfg, bg, ft, or embedPreview.

Pass values in the URL

Hosted forms read hidden-field values from the page URL’s query string. For example:

https://makeform.ai/f/FORM_ID?utm_source=newsletter&prefill_email=alex%40example.com

Only query keys matching declared hidden-field names are kept. Values must be strings under 1,000 characters. Hidden-field URL values override field defaults and saved progress.

The mf_locale query key selects the form language. It works on embeds on every plan, but on direct form pages it requires Pro. Translations load only when the form owner is on Pro.

Prefill a visible field

To prefill a visible field, declare a hidden field and set the visible field’s defaultValue to {{hidden_name}}. A URL key matching a visible field’s name is ignored unless that name is also declared as a hidden field. There is no direct ?field=value prefill for arbitrary questions.

defaultValue is a string. For single_select, its value must match one of the field’s options. Date and time defaults must use the field’s format. Numeric field types parse the result as a number. multi_select, checkboxes, and multiple_choice do not take a default.

{ "mode": "page", "start": { "id": "start", "type": "start", "ui": [] }, "pages": [ { "type": "form", "id": "p1", "ui": [ { "type": "email_input", "name": "email", "label": "Email address", "defaultValue": "{{prefill_email}}" } ] } ], "end": [ { "id": "e0", "type": "end", "ui": [] } ] }

With prefill_email declared in settings, a URL such as https://makeform.ai/f/FORM_ID?prefill_email=alex%40example.com can supply the visible field’s default.

Use static values in an embed URL

The MCP tool get_form_embed accepts static values for declared hidden fields through its hidden_fields object. Values can be strings, finite numbers, or booleans. Undeclared hidden fields return the invalid_hidden_fields error. The form must be a published hosted form: drafts return publish_required, and Headless forms return headless_form. The encoded embed URL is limited to 8,000 bytes. See Embedding forms for embed details.