> ## Documentation Index
> Fetch the complete documentation index at: https://developers.vizito.eu/llms.txt
> Use this file to discover all available pages before exploring further.

# Signing a visitor in and out

> Create a visit from your own system, custom fields included.

A sign-in through the API is not a second-class visit. It goes through the same pipeline as a kiosk sign-in: the host is notified by email, SMS, Teams or Slack, the badge is printed if the visit type prints one, the confirmation email goes out and every integration and webhook fires.

## 1. Pick the visit type

If you leave `visit_type` out, the location's default visit type is used. That is fine for a single-flow reception. If you have several — "Visitor", "Contractor", "Delivery" — fetch them once and cache the ids:

```bash theme={null}
curl -G https://api.vizito.eu/api/companies/{company_id}/visittypes \
  -H "Authorization: Bearer $VIZITO_API_KEY" \
  -d active=true
```

## 2. Find out which fields it asks for

The questions a visitor answers are configured per visit type. `GET /api/companies/{company_id}/fields` returns them all, merged across visit types:

```json theme={null}
[
  { "field_name": "first_name", "field_description": "First name", "field_content_type": "text", "field_status": "required" },
  { "field_name": "company", "field_description": "Company", "field_content_type": "text", "field_status": "optional" },
  { "field_name": "badgenumber", "field_description": "Badge number", "field_content_type": "number", "field_status": "optional" }
]
```

A field's `field_name` is the key you send. Custom fields are no different from built-in ones — they are just extra keys in the body.

<Warning>
  The API does **not** enforce `field_status: "required"`. A visit created through the API with a required field missing is accepted, and shows up in the Backoffice with that column empty. Validate on your side if it matters to you.
</Warning>

## 3. Create the visit

```bash cURL theme={null}
curl -X POST https://api.vizito.eu/api/visitors \
  -H "Authorization: Bearer $VIZITO_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "company_id": "5f2a1b9c4d3e2f0011223344",
    "visit_type": "5f2a1b9c4d3e2f0011223399",
    "first_name": "Ada",
    "last_name": "Lovelace",
    "company": "Analytical Engines Ltd",
    "email": "ada@example.com",
    "phone": "+32470123456",
    "recipient": "Jane Doe",
    "recipient_mail": "jane.doe@example.com",
    "badgenumber": "A-1183",
    "signed_in_source": "0"
  }'
```

```json Response theme={null}
{
  "message": "Visitor added!",
  "data": {
    "_id": "66b0f1a2c3d4e5f600112233",
    "first_name": "Ada",
    "signed_in": "2026-08-29T07:58:11.000Z",
    "signed_in_source": 0,
    "visit_type": "5f2a1b9c4d3e2f0011223399"
  }
}
```

Keep `data._id` — it is the visitor id you need to sign them out again.

<Tip>
  Set `signed_in_source` to `"0"` so the visit is recorded as a Backoffice/API sign-in rather than a kiosk one. It shows up as such in the Backoffice and in exports.
</Tip>

### Notifying the right host

`recipient` is the host's name as it should appear on the badge and in the notification. `recipient_mail` is where the notification goes. If you send a `recipient` that matches a [host](/api-reference/hosts/listing-hosts) you already maintain in Vizito, use that host's exact `cn` so reporting per host stays clean.

### Backdating a sign-in

Send `signed_in_frombo` with an ISO 8601 timestamp to record a visit that happened earlier — useful when you are importing from another system:

```json theme={null}
{ "company_id": "...", "first_name": "Ada", "signed_in_frombo": "2026-08-28T14:03:00.000Z" }
```

## 4. Sign them out

```bash theme={null}
curl -X PUT https://api.vizito.eu/api/visitors/66b0f1a2c3d4e5f600112233 \
  -H "Authorization: Bearer $VIZITO_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "company_id": "5f2a1b9c4d3e2f0011223344", "signed_out_source": "0" }'
```

Leave `signed_out` out and the visitor is signed out now; send an ISO 8601 timestamp to record a departure that already happened.

To close several visits at once — an evacuation, an end-of-day sweep — use the bulk endpoint:

```bash theme={null}
curl -X POST https://api.vizito.eu/api/companies/{company_id}/visitors/signout \
  -H "Authorization: Bearer $VIZITO_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "ids": ["66b0f1a2c3d4e5f600112233", "66b0f1a2c3d4e5f600112244"] }'
```

It answers per id, so you can see exactly which ones were already signed out:

```json theme={null}
[
  { "id": "66b0f1a2c3d4e5f600112233", "status": "success", "message": "Visitor signed out" },
  { "id": "66b0f1a2c3d4e5f600112244", "status": "skipped", "reason": "Visitor not found or already signed out" }
]
```

## 5. See who is still inside

```bash theme={null}
curl https://api.vizito.eu/api/visitors/signed_current/{company_id} \
  -H "Authorization: Bearer $VIZITO_API_KEY"
```

Returns the full list of visitors that are signed in and not signed out, respecting the location's multi-day sign-out interval. This is the list an evacuation report should be built on.

<Card title="All visitor endpoints" icon="code" href="/api-reference/visitors/listing-visitors">
  Filtering, updating, anonymising and exporting visits.
</Card>


## Related topics

- [Signing out a visitor](/api-reference/visitors/signing-out-a-visitor.md)
- [Signing out several visitors](/api-reference/visitors/signing-out-several-visitors.md)
- [Signing in a visitor](/api-reference/visitors/signing-in-a-visitor.md)
- [Signing in registered visitors](/api-reference/registered-visitors/signing-in-registered-visitors.md)
- [Core concepts](/documentation/concepts.md)
