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

# Create an Employee

> Write a new employee into the customer's HRIS.

Creating an employee writes a person into the customer's HRIS. The connector defines what that write accepts, so the schema comes first. Nothing in Bindbee removes the record once it lands.

<Info>
  **Before you start**

  * You've confirmed the integration supports this write - see [Check write support](/guides/reading-writing/writing-data/meta-apis#supported-operations).
  * You can generate a stable idempotency key per person - see [Idempotency](/guides/reading-writing/writing-data/idempotency).
</Info>

## Steps

<Steps>
  <Step title="Fetch the schema">
    ```bash theme={null}
    curl --request GET \
      --url 'https://api.bindbee.dev/api/hris/v1/employees/meta/post' \
      --header 'Authorization: Bearer <BINDBEE_API_KEY>' \
      --header 'X-Connector-Token: <CONNECTOR_TOKEN>'
    ```

    Employee creation differs by platform and by tenant, so read the field list from the schema rather than hardcoding it.

    The response is JSON Schema with Bindbee's own `isRequired` and `enumInformation` keywords on top - see [Meta APIs](/guides/reading-writing/writing-data/meta-apis).

    **Result:** The contract for this integration.
  </Step>

  <Step title="Assemble the body from the schema">
    Work through the `required` array on the root object, then on each nested object you include.

    ```json theme={null}
    {
      "first_name": "Ada",
      "last_name": "Lovelace",
      "work_email": "ada@example.com",
      "start_date": "2026-09-01",
      "home_location": {
        "street_1": "12 Analytical Way",
        "city": "London",
        "country": "GB"
      }
    }
    ```

    A nested object that's optional at the top level still enforces its own required fields once you send it. So a partial address fails validation where omitting it entirely would pass.

    **Result:** A body conforming to the schema.
  </Step>

  <Step title="Add integration-specific values if the schema asks for them">
    The Meta response defines whether this connector expects `integration_params` or `additional_attributes`, and what belongs in each - see [Integration-specific fields](/guides/reading-writing/writing-data/meta-apis#integration-specific-fields).

    Where it does, the values reference configuration that already exists in the customer's HRIS, such as an employment type ID, a pay group or a legal entity.

    **Result:** The platform-specific values this connector needs.
  </Step>

  <Step title="Send with an idempotency key">
    ```bash theme={null}
    curl --request POST \
      --url 'https://api.bindbee.dev/api/hris/v1/employees' \
      --header 'Authorization: Bearer <BINDBEE_API_KEY>' \
      --header 'X-Connector-Token: <CONNECTOR_TOKEN>' \
      --header 'X-Idempotency-Key: <UNIQUE_KEY>' \
      --header 'Content-Type: application/json' \
      --data @employee.json
    ```

    <Warning>
      Derive the key from your own record for this person, so a retry reuses it - see [Idempotency](/guides/reading-writing/writing-data/idempotency). A new key on retry is a new creation request.
    </Warning>

    **Result:** The employee is created upstream.
  </Step>

  <Step title="Match the record after the next sync">
    The write confirms the create without returning the Bindbee `id`. The employee reaches your reads on the next sync - see [Syncing](/guides/reading-writing/syncing).

    Find them by a stable upstream identifier such as `work_email` or `employee_number`, then store the Bindbee `id` from that read. Key your own record on the `id`, since source systems reissue employee numbers and `remote_id` values on rehire or transfer - see [Reading employees](/guides/data-models/employee-data).

    **Result:** Your record linked to a stable Bindbee `id`.
  </Step>
</Steps>

<Note>
  A rehire or transfer is a new employment rather than a new employee, and creating one duplicates the person - see [Reading employees](/guides/data-models/employee-data).
</Note>

## Frequently Asked Questions

<AccordionGroup>
  <Accordion title="The employee was created twice">
    The retry carried a different `X-Idempotency-Key`, so Bindbee read it as a new creation - see [Idempotency](/guides/reading-writing/writing-data/idempotency).

    There is no delete endpoint for employees, so the duplicate has to be merged or removed in the customer's HRIS.
  </Accordion>

  <Accordion title="The write returns 403">
    The credentials are valid but don't permit the operation. Check the connector token belongs to this API category, and that writes are enabled on the model.

    Where both hold, the source system is refusing the write itself, which is a permission to fix in the customer's HRIS - see [Origin-system errors](/guides/troubleshooting/errors#origin-system-errors).
  </Accordion>
</AccordionGroup>

## Related

* [Create Employee](/hris/employee/create-employee) - the endpoint, and how the request body is assembled
* [Get Create Employee Meta](/hris/employee/get-create-employee-meta) - the schema endpoint step 1 fetches
