If you want to add custom columns to your user table, create them in Qobra settings > User attributes first.Those attributes will have an auto-generated API key that you can overwrite. This key will allow you to provide value for those attribute at user creation through API.
This endpoint is based on dynamic fields. This mean that all annotations
that look like <variable-key>, will have to or will be replaced by their
actual API keys.
This endpoint does not apply your payload during the request: it stores it and
creates an import that applies it in the background. The response gives you
the import_id of that import, and the number of items your request contained.
A 200 therefore means the import was created, not the payload was applied.
To know how it went, fetch the import with the
Fetch import route until its
status is finished, then read its error flag:
error: false — every item of your payload has been upserted.
error: true — read title in data_tables_details[].error to know what
happened. ValidationError means the payload was refused and nothing was
upserted, description listing the invalid items. PartialFailure means part
of it was applied: description counts the items that reported an issue, and
parsing_error_details names the skipped ones — the most recent 100 — each
with its line_number, row and details.
Imports of a company run one after the other, so an import can stay scheduled
for a while when another one is already running.A 400 is still returned during the request itself, for a malformed body or a
payload above the limit — in that case no import is created.
A payload above the limit of 200 has to be split across several calls, and each
call would otherwise create its own import — all queued behind one another.Pass debounce, a number of seconds, to hold the import open: every call to
the same endpoint made during that window joins the same import instead of
queuing a new one, and they all return the same import_id. The window is
opened by the first call, and a later call joins it without pushing its start
further.Each payload keeps its own validation. A refused payload upserts nothing, but
the payloads merged beside it are still applied — the import then reports the
reason of every refusal in data_tables_details[].error.Only calls to the same endpoint are merged: users, manager attributions and
group attributions always get their own import. This is deliberate, since
attributions need the users they reference to exist already — send your users
first, wait for their import to finish, then send the attributions.
Conflict Rule and upsert: Be careful, email field on user is unique. For each user, if it already exist (according to email), we will update the existing one and if it does not exist yet, we will create it.
Transaction: If there is at least one user that triggers an error at import, none of the users of your call are upserted and the import finishes in error. You have to fix your payload and send it to us again. And if the import finishes without error, it means that every users you sent us have been upserted. This all-or-nothing applies to the payload of your own call: when several calls share an import through debounce, a refused payload does not prevent the others from being applied
Repeated users: sending the same user twice in one payload does not refuse
the call. The first occurrence is upserted, and each later one is skipped and
reported in parsing_error_details with a details such as
"email: duplicated (jane@qobra.co)". Two users are the same when they share
the identifier we match on, compared case-insensitively for an email
Empty Field Rule: If you don’t specify a field in upsert, this field won’t be modified. If you want to empty a field, you have to send us a value null associated to the given field api key
Limit: you can’t upsert more than 200 users at a time.
Error behavior: a refused payload upserts none of its users, but a user
skipped on its own — a repeated user, or one we could not write — leaves all
the others upserted. Read the import rather than assuming an all-or-nothing
outcome
Optional (minimum: 0): debounce is the number of seconds we wait before starting the import. Every call to this endpoint made during that window joins the same import instead of queuing a new one, and they all return the same import_id. Use it when a payload above the limit of 200 has to be split across several calls. Only calls to this same endpoint are merged: users, manager attributions and group attributions always get their own import.
Body
application/json
The body contains the list of user data necessary to create a new user in Qobra
The upsert is performed as a background import: the response identifies the import you just created, not the upserted objects. Fetch the import to know how it went.
{"docsConfig":{"theme":"mint","$schema":"https://mintlify.com/docs.json","name":"Qobra public API documentation","description":"Reference and guides for integrating with Qobra: inbound/outbound data integrations, the v1 and v2 public REST API, and the MCP server for AI agents.","colors":{"primary":"#460629","light":"#FBF5DF","dark":"#460629"},"logo":{"light":"https://mintcdn.com/qobra/BOwfuCXh9Zd24PEc/logo/dark.svg?fit=max\u0026auto=format\u0026n=BOwfuCXh9Zd24PEc\u0026q=85\u0026s=89cd1b29990b669fb3daa20d2e46c52f","dark":"https://mintcdn.com/qobra/BOwfuCXh9Zd24PEc/logo/white.svg?fit=max\u0026auto=format\u0026n=BOwfuCXh9Zd24PEc\u0026q=85\u0026s=b7fa948d600e3558dc1307d622a4c7e2"},"favicon":"https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/favicon.svg?fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=8bd0cfde4ff59d84d6892e4bbdc66cf8","api":{"openapi":["api_reference/v1/openapi.json","api_reference/v2/openapi.json","mcp_documentation/openapi.json"]},"background":{"color":{"light":"#FFFFFF","dark":"#00161F"}},"navbar":{"links":[{"href":"https://app.qobra.co/auth","label":"Application"},{"href":"mailto:support@qobra.co","label":"Support"}],"primary":{"type":"button","label":"Book a demo!","href":"https://www.qobra.co/book-a-call"}},"footer":{"socials":{"github":"https://github.com/qobra-co","linkedin":"https://www.linkedin.com/company/qobra-co"}},"styling":{"latex":false},"navigation":{"global":{"anchors":[{"anchor":"Help center","icon":"hands-holding-heart","href":"https://help.qobra.co/en/"},{"anchor":"Blog","icon":"newspaper","href":"https://www.qobra.co/blog"},{"anchor":"Security","icon":"shield-check","href":"https://trust.qobra.co/"}]},"pages":[]}},"deployment":{"deploymentMetadataValue":{"subdomain":"qobra","hasAudioNarration":false,"actualSubdomain":"qobra","customDomains":["docs.qobra.co"],"gitSource":{"type":"github","owner":"qobra-co","repo":"public-api-doc","deployBranch":"main","contentDirectory":"","isPrivate":false,"mountPath":"","label":""},"chroma":{"liveDeploymentHistoryId":"6ae4650cd51aac6e910a0a07","collectionId":"0f761209-c499-4c20-ac4d-18192e4620fe","schemaVersion":"v3","latestBuiltDeploymentHistoryId":"6ae4650cd51aac6e910a0a07"},"feedback":{"thumbs":true,"issues":false},"entitlements":{"AI_CHAT":{"status":"ENABLED"},"WEB_MCP":{"status":"ENABLED"},"NARRATION":{"status":"ENABLED"}},"buildId":"6ae4650cd51aac6e910a0a07","clientVersion":"0.0.4021","searchFilterCounts":[{"language":"default","tag":"MCP server","count":78},{"language":"default","tag":"Qobra MCP server","count":78},{"language":"default","tag":"Tools","count":76},{"language":"default","tag":"Documentation","count":38},{"language":"default","tag":"Public API Documentation","count":20},{"language":"default","tag":"Integrations","count":16},{"language":"default","tag":"Inbound data integrations","count":15},{"language":"default","tag":"Data tables","count":11},{"language":"default","tag":"Endpoints","count":10},{"language":"default","tag":"Users","count":8}]},"assistantConfig":{"enableStarterQuestions":false},"basePath":"","hasChatPermissions":true,"hasWebMcpPermissions":true,"toggles":[{"name":"kill-isr","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"agent-mintlify-slack","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"agent-integrations-settings","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"automations-pr-grouping","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"custom-prefix","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"analytics-v7","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"user-flows-analytics","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"no-publish-flow","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-onboarding","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"llms-txt-v2","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"snapshot-serving-live","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"stripTemperatureMiddleware","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"support-platform-pylon-zendesk","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"snapshot-serving","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"instant-rollback","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"granular-notifications-server","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"granular-notifications","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"automations-fable","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"fixed-ai-action-pricing","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"automation-resolve-merge-conflict","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"scoped-publishing","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"mintql","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"page-level-analytics","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"editor-version-history-v2","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"billing-page-v2","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workspace-projects","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"assistant-v5","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"byok-sep-25","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"fork-pr-previews","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"revalidation-jwt","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"vite-origin","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"billing-updated-9-15","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-sso-scim","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"hobby-abuse-scan","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"dashboard-inbox","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-signup","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"workos-enabled","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false},{"name":"approve-review-flow","enabled":true,"variant":{"name":"disabled","enabled":false,"feature_enabled":true},"impressionData":false}],"googleFontsInlined":false},"customCss":[],"page":{"pagePath":"api_reference/v1/endpoints/users/upsert_bulk_user","slug":"/api_reference/v1/endpoints/users/upsert_bulk_user","pageMetadata":{"openapi":"put /v1/users/bulk","version":"v1","title":"Upsert users bulk","description":"Upsert users in bulk.","href":"/api_reference/v1/endpoints/users/upsert_bulk_user"},"description":{"compiledSource":"\"use strict\";\nconst {jsx: _jsx} = arguments[0];\nconst {useMDXComponents: _provideComponents} = arguments[0];\nfunction _createMdxContent(props) {\n const _components = {\n p: \"p\",\n ..._provideComponents(),\n ...props.components\n };\n return _jsx(_components.p, {\n children: \"Upsert users in bulk.\"\n });\n}\nfunction MDXContent(props = {}) {\n const {wrapper: MDXLayout} = {\n ..._provideComponents(),\n ...props.components\n };\n return MDXLayout ? _jsx(MDXLayout, {\n ...props,\n children: _jsx(_createMdxContent, {\n ...props\n })\n }) : _createMdxContent(props);\n}\nreturn {\n default: MDXContent\n};\n","frontmatter":{},"scope":{}},"pageType":"default","mdx":{"mdxSource":{"compiledSource":"\"use strict\";const{Fragment:_Fragment,jsx:_jsx,jsxs:_jsxs}=arguments[0];const{useMDXComponents:_provideComponents}=arguments[0];function _createMdxContent(props){const _components={a:`a`,code:`code`,em:`em`,li:`li`,p:`p`,pre:`pre`,span:`span`,strong:`strong`,ul:`ul`,..._provideComponents(),...props.components},{CodeBlock,Heading,OptimizedImage}=_components;if(!CodeBlock)_missingMdxReference(`CodeBlock`,true);if(!Heading)_missingMdxReference(`Heading`,true);if(!OptimizedImage)_missingMdxReference(`OptimizedImage`,true);return _jsxs(_Fragment,{children:[_jsx(_components.p,{children:`Create new users or update existing ones.`}),`\n`,_jsx(Heading,{level:`2`,id:`how-to-use-user-attributes`,children:`How to use user attributes`}),`\n`,_jsxs(_components.p,{children:[`If you want to add custom columns to your user table, create them in `,_jsx(_components.code,{children:`Qobra settings > User attributes`}),` first.`]}),`\n`,_jsx(OptimizedImage,{src:`https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=fbd4b1e35a9aa4961e9f472cdc600ae1`,alt:`Custom user attributes definition`,\"data-og-width\":`2878`,width:`2878`,\"data-og-height\":`1646`,height:`1646`,\"data-path\":`api_reference/v1/images/custom_user_attributes.png`,\"data-optimize\":`true`,\"data-opv\":`3`,srcset:`https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?w=280\u0026fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=8e30b3db63f83c9f1c2869ba85d3d31e 280w, https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?w=560\u0026fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=6a6a6d917f7e4d429405da97d55fab05 560w, https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?w=840\u0026fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=936bc65bd0e9df0fee6e91a096814086 840w, https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?w=1100\u0026fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=a9112564a3c180b1091e32a50623fdc6 1100w, https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?w=1650\u0026fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=3ee26e4241e5eec9415bf5665e2095f0 1650w, https://mintcdn.com/qobra/4g7tQyP7wYl6AlCt/api_reference/v1/images/custom_user_attributes.png?w=2500\u0026fit=max\u0026auto=format\u0026n=4g7tQyP7wYl6AlCt\u0026q=85\u0026s=e1680c64cb7cf04a97717532da2e4ece 2500w`}),`\n`,_jsx(_components.p,{children:`Those attributes will have an auto-generated API key that you can overwrite. This key will allow you to provide value for those attribute at user creation through API.`}),`\n`,_jsx(Heading,{level:`2`,id:`variable-api-keys`,children:`Variable api keys`}),`\n`,_jsxs(_components.p,{children:[`This endpoint is based on dynamic fields. This mean that all annotations\nthat look like `,_jsx(_components.code,{children:`\u003cvariable-key>`}),`, will have to or will be replaced by their\nactual API keys.`]}),`\n`,_jsx(Heading,{level:`2`,id:`asynchronous-upsert`,children:`Asynchronous upsert`}),`\n`,_jsxs(_components.p,{children:[`This endpoint does not apply your payload during the request: it stores it and\ncreates an `,_jsx(_components.strong,{children:`import`}),` that applies it in the background. The response gives you\nthe `,_jsx(_components.code,{children:`import_id`}),` of that import, and the number of items your request contained.`]}),`\n`,_jsx(CodeBlock,{filename:``,numberOfLines:`4`,language:`json`,children:_jsx(_components.pre,{className:`shiki shiki-themes github-light-default dark-plus`,style:{backgroundColor:`#ffffff`,\"--shiki-dark-bg\":`#0B0C0E`,color:`#1f2328`,\"--shiki-dark\":`#D4D4D4`},language:`json`,children:_jsxs(_components.code,{language:`json`,numberOfLines:`4`,children:[_jsx(_components.span,{className:`line`,children:_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`{`})}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#9CDCFE`},children:` \"import_id\"`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`: `}),_jsx(_components.span,{style:{color:`#0A3069`,\"--shiki-dark\":`#CE9178`},children:`\"QfejsQZ6mpOVHT5Tt1SdNLPZ\"`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`,`})]}),`\n`,_jsxs(_components.span,{className:`line`,children:[_jsx(_components.span,{style:{color:`#116329`,\"--shiki-dark\":`#9CDCFE`},children:` \"objects_imported\"`}),_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`: `}),_jsx(_components.span,{style:{color:`#0550AE`,\"--shiki-dark\":`#B5CEA8`},children:`2`})]}),`\n`,_jsx(_components.span,{className:`line`,children:_jsx(_components.span,{style:{color:`#1F2328`,\"--shiki-dark\":`#D4D4D4`},children:`}`})}),`\n`]})})}),`\n`,_jsxs(_components.p,{children:[`A `,_jsx(_components.code,{children:`200`}),` therefore means `,_jsx(_components.em,{children:`the import was created`}),`, not `,_jsx(_components.em,{children:`the payload was applied`}),`.\nTo know how it went, fetch the import with the\n`,_jsx(_components.a,{href:`/api_reference/v1/endpoints/imports/fetch_import`,children:`Fetch import route`}),` until its\n`,_jsx(_components.code,{children:`status`}),` is `,_jsx(_components.code,{children:`finished`}),`, then read its `,_jsx(_components.code,{children:`error`}),` flag:`]}),`\n`,_jsxs(_components.ul,{children:[`\n`,_jsxs(_components.li,{children:[_jsx(_components.code,{children:`error: false`}),` — every item of your payload has been upserted.`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.code,{children:`error: true`}),` — read `,_jsx(_components.code,{children:`title`}),` in `,_jsx(_components.code,{children:`data_tables_details[].error`}),` to know what\nhappened. `,_jsx(_components.code,{children:`ValidationError`}),` means the payload was refused and `,_jsx(_components.strong,{children:`nothing`}),` was\nupserted, `,_jsx(_components.code,{children:`description`}),` listing the invalid items. `,_jsx(_components.code,{children:`PartialFailure`}),` means part\nof it was applied: `,_jsx(_components.code,{children:`description`}),` counts the items that reported an issue, and\n`,_jsx(_components.code,{children:`parsing_error_details`}),` names the skipped ones — the most recent 100 — each\nwith its `,_jsx(_components.code,{children:`line_number`}),`, `,_jsx(_components.code,{children:`row`}),` and `,_jsx(_components.code,{children:`details`}),`.`]}),`\n`]}),`\n`,_jsxs(_components.p,{children:[`Imports of a company run one after the other, so an import can stay `,_jsx(_components.code,{children:`scheduled`}),`\nfor a while when another one is already running.`]}),`\n`,_jsxs(_components.p,{children:[`A `,_jsx(_components.code,{children:`400`}),` is still returned during the request itself, for a malformed body or a\npayload above the limit — in that case no import is created.`]}),`\n`,_jsxs(Heading,{level:`2`,id:`merging-successive-calls-with-debounce`,children:[`Merging successive calls with `,_jsx(_components.code,{children:`debounce`})]}),`\n`,_jsx(_components.p,{children:`A payload above the limit of 200 has to be split across several calls, and each\ncall would otherwise create its own import — all queued behind one another.`}),`\n`,_jsxs(_components.p,{children:[`Pass `,_jsx(_components.code,{children:`debounce`}),`, a number of seconds, to hold the import open: every call to\n`,_jsx(_components.strong,{children:`the same endpoint`}),` made during that window joins the same import instead of\nqueuing a new one, and they all return the same `,_jsx(_components.code,{children:`import_id`}),`. The window is\nopened by the first call, and a later call joins it without pushing its start\nfurther.`]}),`\n`,_jsxs(_components.p,{children:[`Each payload keeps its own validation. A refused payload upserts nothing, but\nthe payloads merged beside it are still applied — the import then reports the\nreason of every refusal in `,_jsx(_components.code,{children:`data_tables_details[].error`}),`.`]}),`\n`,_jsx(_components.p,{children:`Only calls to the same endpoint are merged: users, manager attributions and\ngroup attributions always get their own import. This is deliberate, since\nattributions need the users they reference to exist already — send your users\nfirst, wait for their import to finish, then send the attributions.`}),`\n`,_jsx(Heading,{level:`2`,id:`behavior`,children:`Behavior`}),`\n`,_jsxs(_components.ul,{children:[`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Conflict Rule and upsert`}),`: Be careful, email field on user is unique. For each user, if it already exist (according to email), we will update the existing one and if it does not exist yet, we will create it.`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Transaction`}),`: If there is at least one user that triggers an error at import, none of the users of your call are upserted and the import finishes in error. You have to fix your payload and send it to us again. And if the import finishes without error, it means that every users you sent us have been upserted. This all-or-nothing applies to the payload of your own call: when several calls share an import through `,_jsx(_components.code,{children:`debounce`}),`, a refused payload does not prevent the others from being applied`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Repeated users`}),`: sending the same user twice in one payload does not refuse\nthe call. The first occurrence is upserted, and each later one is skipped and\nreported in `,_jsx(_components.code,{children:`parsing_error_details`}),` with a `,_jsx(_components.code,{children:`details`}),` such as\n`,_jsx(_components.code,{children:`\"email: duplicated (jane@qobra.co)\"`}),`. Two users are the same when they share\nthe identifier we match on, compared case-insensitively for an email`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Empty Field Rule`}),`: If you don’t specify a field in upsert, this field won’t be modified. If you want to empty a field, you have to send us a value null associated to the given field api key`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Limit`}),`: you can’t upsert more than 200 users at a time.`]}),`\n`,_jsxs(_components.li,{children:[_jsx(_components.strong,{children:`Error behavior`}),`: a refused payload upserts none of its users, but a user\nskipped on its own — a repeated user, or one we could not write — leaves all\nthe others upserted. Read the import rather than assuming an all-or-nothing\noutcome`]}),`\n`]})]})}function MDXContent(props={}){const{wrapper:MDXLayout}={..._provideComponents(),...props.components};return MDXLayout?_jsx(MDXLayout,{...props,children:_jsx(_createMdxContent,{...props})}):_createMdxContent(props)}return{default:MDXContent};function _missingMdxReference(id,component){throw new Error(`Expected `+(component?`component`:`object`)+\" `\"+id+\"` to be defined: you likely forgot to import, pass, or provide it.\")}","frontmatter":{},"scope":{"config":{},"pageMetadata":{"openapi":"put /v1/users/bulk","version":"v1","title":"Upsert users bulk","description":"Upsert users in bulk.","href":"/api_reference/v1/endpoints/users/upsert_bulk_user"}}},"mdxSourceWithNoJs":null},"mdxExtracts":{"tableOfContents":[{"title":"How to use user attributes","slug":"how-to-use-user-attributes","depth":2,"children":[]},{"title":"Variable api keys","slug":"variable-api-keys","depth":2,"children":[]},{"title":"Asynchronous upsert","slug":"asynchronous-upsert","depth":2,"children":[]},{"title":"Merging successive calls with debounce","slug":"merging-successive-calls-with-debounce","depth":2,"children":[]},{"title":"Behavior","slug":"behavior","depth":2,"children":[]}],"codeExamples":{}},"jsLinks":[],"openApiReferenceData":{"operation":{"parameters":["70649f31-c1f0-4b16-92c7-0fad1c9c9a8e"],"tags":["public_api","v1","users"],"summary":"Upsert users bulk","description":"Upsert users in bulk.","operationId":"PUT_/v1/users/bulk","security":["09119cbb-5b22-4810-b698-de46d1ec0ed4"],"responses":{"200":"9fab8e58-5207-4508-88db-7a7d9876dc05","400":"634d0893-2f35-4f86-8f62-169071711a49"},"requestBody":"dc1b90ea-6dec-42a5-9001-71aada05de36","method":"put","type":"path","servers":["4c4bb5da-d2a6-46b9-85cb-f3b7db976fc4"],"path":"/v1/users/bulk","baseUrlOptions":["https://api.qobra.co"],"title":"Upsert users bulk","codeSamples":[],"requiredOnlyExamples":false,"requestExampleType":"generated","responseExampleType":"generated"},"dependencies":{"parameters":{"70649f31-c1f0-4b16-92c7-0fad1c9c9a8e":{"name":"debounce","in":"query","description":"Optional (minimum: 0): debounce is the number of seconds we wait before starting the import. Every call to this endpoint made during that window joins the same import instead of queuing a new one, and they all return the same import_id. Use it when a payload above the limit of 200 has to be split across several calls. Only calls to this same endpoint are merged: users, manager attributions and group attributions always get their own import.","schema":{"title":"Debounce","default":0,"type":"integer","isRequired":false,"description":"Optional (minimum: 0): debounce is the number of seconds we wait before starting the import. Every call to this endpoint made during that window joins the same import instead of queuing a new one, and they all return the same import_id. Use it when a payload above the limit of 200 has to be split across several calls. Only calls to this same endpoint are merged: users, manager attributions and group attributions always get their own import.","uniqueKey":"","typeLabel":"integer"},"required":false}},"requestBody":{"description":"The body contains the list of user data necessary to create a new user in Qobra","content":{"application/json":{"schema":{"type":"object","properties":{"data":{"title":"Data","type":"array","items":{"type":"object","properties":{"email":{"title":"Email","type":"string","description":"Email of the user","format":"email","isRequired":true,"uniqueKey":"data.items.[INDEX].email","typeLabel":"string\u003cemail>"},"name":{"title":"Name","type":"string","description":"Name of the user","isRequired":true,"uniqueKey":"data.items.[INDEX].name","typeLabel":"string"},"role":{"title":"Role","type":"string","description":"The role of the user you want to create. This will default to default role in Qobra, if no role is provided","uniqueKey":"data.items.[INDEX].role","typeLabel":"string"},"currency":{"description":"Allowed currency codes.","type":"string","enum":["AED","AFN","ALL","AMD","ANG","AOA","ARS","AUD","AWG","AZN","BAM","BBD","BDT","BGN","BHD","BIF","BMD","BND","BOB","BOV","BRL","BSD","BTN","BWP","BYR","BZD","CAD","CDF","CHF","CLF","CLP","CNY","COP","COU","CRC","CUC","CUP","CVE","CZK","DJF","DKK","DOP","DZD","EGP","ERN","ETB","EUR","FJD","FKP","GBP","GEL","GHS","GIP","GMD","GNF","GTQ","GYD","HKD","HNL","HRK","HTG","HUF","IDR","ILS","INR","IQD","IRR","ISK","JMD","JOD","JPY","KES","KGS","KHR","KMF","KPW","KRW","KWD","KYD","KZT","LAK","LBP","LKR","LRD","LSL","LTL","LVL","LYD","MAD","MDL","MGA","MKD","MMK","MNT","MOP","MRO","MUR","MVR","MWK","MXN","MYR","MZN","NAD","NGN","NIO","NOK","NPR","NZD","OMR","PAB","PEN","PGK","PHP","PKR","PLN","PYG","QAR","RON","RSD","RUB","RWF","SAR","SBD","SCR","SDG","SEK","SGD","SHP","SLL","SOS","SRD","STD","SVC","SYP","SZL","THB","TJS","TMT","TND","TOP","TRY","TTD","TWD","TZS","UAH","UGX","USD","UYI","UYU","UZS","VEF","VND","VUV","WST","XAG","XAU","XCD","XPD","XPT","XSU","YER","ZAR","ZMK","ZWL"],"title":"CurrencyCode","uniqueKey":"data.items.[INDEX].currency","typeLabel":"enum\u003cstring>"},"calculation_currency":{"description":"Allowed currency codes.","type":"string","enum":["AED","AFN","ALL","AMD","ANG","AOA","ARS","AUD","AWG","AZN","BAM","BBD","BDT","BGN","BHD","BIF","BMD","BND","BOB","BOV","BRL","BSD","BTN","BWP","BYR","BZD","CAD","CDF","CHF","CLF","CLP","CNY","COP","COU","CRC","CUC","CUP","CVE","CZK","DJF","DKK","DOP","DZD","EGP","ERN","ETB","EUR","FJD","FKP","GBP","GEL","GHS","GIP","GMD","GNF","GTQ","GYD","HKD","HNL","HRK","HTG","HUF","IDR","ILS","INR","IQD","IRR","ISK","JMD","JOD","JPY","KES","KGS","KHR","KMF","KPW","KRW","KWD","KYD","KZT","LAK","LBP","LKR","LRD","LSL","LTL","LVL","LYD","MAD","MDL","MGA","MKD","MMK","MNT","MOP","MRO","MUR","MVR","MWK","MXN","MYR","MZN","NAD","NGN","NIO","NOK","NPR","NZD","OMR","PAB","PEN","PGK","PHP","PKR","PLN","PYG","QAR","RON","RSD","RUB","RWF","SAR","SBD","SCR","SDG","SEK","SGD","SHP","SLL","SOS","SRD","STD","SVC","SYP","SZL","THB","TJS","TMT","TND","TOP","TRY","TTD","TWD","TZS","UAH","UGX","USD","UYI","UYU","UZS","VEF","VND","VUV","WST","XAG","XAU","XCD","XPD","XPT","XSU","YER","ZAR","ZMK","ZWL"],"title":"CurrencyCode","uniqueKey":"data.items.[INDEX].calculation_currency","typeLabel":"enum\u003cstring>"},"\u003cuser-attribute-1-api-key>":{"type":"string","description":"Value of user attribute 1","uniqueKey":"data.items.[INDEX].\u003cuser-attribute-1-api-key>","typeLabel":"string"},"\u003cuser-attribute-2-api-key>":{"type":"string","description":"Value of user attribute 2","uniqueKey":"data.items.[INDEX].\u003cuser-attribute-2-api-key>","typeLabel":"string"}},"required":["email","name"],"title":"UserPutBodyModel","uniqueKey":"data.items.[INDEX]","typeLabel":"UserPutBodyModel · object"},"isRequired":true,"uniqueKey":"data","typeLabel":"UserPutBodyModel · object[]"}},"required":["data"],"title":"PutManyInputModel[UserPutBodyModel]","uniqueKey":"","typeLabel":"PutManyInputModel[UserPutBodyModel] · object"},"examples":{"user-bulk-body":{"title":"user-bulk-body","value":{"data":[{"email":"user-test-1@company.com","name":"User 1","role":"Sales Rep","currency":"EUR","calculation_currency":"USD","country":"France","code":"AO32ND56","arrival_date":"2023-12-01","junior":true},{"email":"user-test-2@company.com","name":"User 2","role":"Manager","currency":"USD","calculation_currency":"USD","country":"Germany","code":"AO32ND57","arrival_date":"2024-01-01","junior":false},"..."]}}},"exampleType":"examples"}},"required":true,"exampleType":"examples"},"responses":{"9fab8e58-5207-4508-88db-7a7d9876dc05":{"description":"Import created","content":{"application/json":{"schema":{"type":"object","description":"The upsert is performed as a background import: the response identifies the import you just created, not the upserted objects. Fetch the import to know how it went.","properties":{"import_id":{"title":"Import Id","type":"string","format":"ObjectId","description":"unique identifier of the import you created","isRequired":true,"uniqueKey":"import_id","typeLabel":"string\u003cObjectId>"},"objects_imported":{"title":"Objects Imported","type":"integer","description":"number of items your request contained","isRequired":true,"uniqueKey":"objects_imported","typeLabel":"integer"}},"required":["import_id","objects_imported"],"title":"UsersImportModelResponse","uniqueKey":"","typeLabel":"UsersImportModelResponse · object"},"examples":{"user-bulk-import-created":{"title":"user-bulk-import-created","value":{"import_id":"QfejsQZ6mpOVHT5Tt1SdNLPZ","objects_imported":2}}},"exampleType":"examples"}},"exampleType":"examples"},"634d0893-2f35-4f86-8f62-169071711a49":{"description":"ClientError operation","content":{"application/json":{"schema":{"type":"object","description":"Returned when the request itself is refused, before any import is created. Errors found while validating the payload are reported on the import instead.","properties":{"count":{"description":"Errors count","type":"integer","isRequired":true,"uniqueKey":"count","typeLabel":"integer"},"errors":{"description":"Array of errors","type":"array","items":{"type":"object","properties":{"error":{"description":"Error type","type":"string","isRequired":true,"uniqueKey":"errors.items.[INDEX].error","typeLabel":"string"},"resource":{"description":"Resource the error is about","type":"string","isRequired":true,"uniqueKey":"errors.items.[INDEX].resource","typeLabel":"string"},"description":{"description":"Error description","type":"string","isRequired":true,"uniqueKey":"errors.items.[INDEX].description","typeLabel":"string"}},"required":["error","resource","description"],"title":"BulkUpsertClientErrorModel","uniqueKey":"errors.items.[INDEX]","typeLabel":"BulkUpsertClientErrorModel · object"},"isRequired":true,"uniqueKey":"errors","typeLabel":"BulkUpsertClientErrorModel · object[]"}},"required":["count","errors"],"title":"BulkUpsertClientErrorModelResponse","uniqueKey":"","typeLabel":"BulkUpsertClientErrorModelResponse · object"},"examples":{"user-bulk-errors":{"title":"user-bulk-errors","value":{"count":1,"errors":[{"error":"ValidationError","resource":"data","description":"Too many users, at most 200 can be sent per call"}]}}},"exampleType":"examples"}},"exampleType":"examples"}},"security":{"09119cbb-5b22-4810-b698-de46d1ec0ed4":{"api_key":{"type":"apiKey","name":"X-API-Key","in":"header","scopes":[]}}},"servers":{"4c4bb5da-d2a6-46b9-85cb-f3b7db976fc4":{"url":"https://api.qobra.co","description":"API"}},"processedSecurityOptions":[{"schemes":[{"scheme":{"type":"apiKey","name":"X-API-Key","in":"header","scopes":[]},"schema":{"title":"X-API-Key","type":"string","isRequired":true,"typeLabel":"string","deprecated":false},"schemeName":"api_key","name":"X-API-Key"}],"title":"api_key"}]},"originalFileLocation":"api_reference/v1/openapi.json"},"subdomain":"qobra","siteName":"Qobra public API documentation","title":"Upsert users bulk - Qobra public API documentation","navMaps":{"firstHrefInVersion":{"v1":{"href":"/api_reference/v1/endpoints/users/upsert_bulk_user","matchLevel":0},"v2":{"href":"/api_reference/v2/introduction","matchLevel":2}},"firstHrefInLanguage":{}},"lastModified":"2026-10-01T08:25:13.443Z","originalFileLocation":"api_reference/v1/endpoints/users/upsert_bulk_user.mdx"},"headHtml":"\u003cscript data-mint-head>(function(){var d=document.documentElement,p=null;if(!p){try{p=localStorage.getItem(\"isDarkMode\")}catch(e){}if(p==='true')p='dark';else if(p==='false')p='light';if(p!=='light'\u0026\u0026p!=='dark'\u0026\u0026p!=='system')p=\"system\"}var r=p==='system'?(matchMedia(\"(prefers-color-scheme: dark)\").matches?'dark':'light'):p;d.classList.remove(r==='dark'?'light':'dark');d.classList.add(r);d.setAttribute(\"data-theme-preference\",p)})();\u003c/script>\u003cmeta data-mint-head name=\"description\" content=\"Upsert users in bulk.\">\u003cmeta data-mint-head name=\"application-name\" content=\"Qobra public API documentation\">\u003cmeta data-mint-head name=\"generator\" content=\"Mintlify\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"192x192\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon/android-chrome-192x192.png\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"apple-touch-icon\" type=\"image/png\" sizes=\"180x180\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon/apple-touch-icon.png\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"16x16\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon/favicon-16x16.png\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"32x32\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon/favicon-32x32.png\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"shortcut icon\" type=\"image/x-icon\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon/favicon.ico\" media=\"(prefers-color-scheme: light)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"192x192\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon-dark/android-chrome-192x192.png\" media=\"(prefers-color-scheme: dark)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"16x16\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon-dark/favicon-16x16.png\" media=\"(prefers-color-scheme: dark)\">\u003clink data-mint-head rel=\"icon\" type=\"image/png\" sizes=\"32x32\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon-dark/favicon-32x32.png\" media=\"(prefers-color-scheme: dark)\">\u003clink data-mint-head rel=\"shortcut icon\" type=\"image/x-icon\" href=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon-dark/favicon.ico\" media=\"(prefers-color-scheme: dark)\">\u003cmeta data-mint-head property=\"og:title\" content=\"Upsert users bulk - Qobra public API documentation\">\u003cmeta data-mint-head property=\"og:description\" content=\"Upsert users in bulk.\">\u003cmeta data-mint-head property=\"og:site_name\" content=\"Qobra public API documentation\">\u003cmeta data-mint-head property=\"og:url\" content=\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user\">\u003cmeta data-mint-head property=\"og:type\" content=\"website\">\u003cmeta data-mint-head property=\"og:image\" content=\"https://qobra.mintlify.app/_mintlify/api/og/v2?division=User+management\u0026amp;title=Upsert+users+bulk\u0026amp;description=Upsert+users+in+bulk.\u0026amp;theme=3f6043674a55ff34ed6fbc78\u0026amp;signature=c8ef221da4b92358e6e4897e96527fc60c3bc032f43ab6fedbebb2b9b4695e99\">\u003cmeta data-mint-head property=\"og:image:width\" content=\"1200\">\u003cmeta data-mint-head property=\"og:image:height\" content=\"630\">\u003cmeta data-mint-head name=\"twitter:card\" content=\"summary_large_image\">\u003cmeta data-mint-head name=\"twitter:title\" content=\"Upsert users bulk - Qobra public API documentation\">\u003cmeta data-mint-head name=\"twitter:description\" content=\"Upsert users in bulk.\">\u003cmeta data-mint-head name=\"twitter:image\" content=\"https://qobra.mintlify.app/_mintlify/api/og/v2?division=User+management\u0026amp;title=Upsert+users+bulk\u0026amp;description=Upsert+users+in+bulk.\u0026amp;theme=3f6043674a55ff34ed6fbc78\u0026amp;signature=c8ef221da4b92358e6e4897e96527fc60c3bc032f43ab6fedbebb2b9b4695e99\">\u003cmeta data-mint-head name=\"twitter:image:width\" content=\"1200\">\u003cmeta data-mint-head name=\"twitter:image:height\" content=\"630\">\u003cmeta data-mint-head name=\"msapplication-config\" content=\"/mintlify-assets/_mintlify/favicons/qobra/LfZGqJYgKlEETanR/_generated/favicon/browserconfig.xml\">\u003cmeta data-mint-head name=\"apple-mobile-web-app-title\" content=\"Qobra public API documentation\">\u003cmeta data-mint-head name=\"msapplication-TileColor\" content=\"#460629\">\u003clink data-mint-head rel=\"canonical\" href=\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user\">\u003clink data-mint-head rel=\"alternate\" type=\"application/xml\" href=\"/sitemap.xml\">\u003clink data-mint-head rel=\"alternate\" type=\"text/markdown\" href=\"/api_reference/v1/endpoints/users/upsert_bulk_user.md\">\u003cscript data-mint-head type=\"application/ld+json\">{\"@context\":\"https://schema.org\",\"@graph\":[{\"@type\":\"Organization\",\"@id\":\"https://docs.qobra.co/#organization\",\"name\":\"Qobra public API documentation\",\"url\":\"https://docs.qobra.co\",\"logo\":{\"@type\":\"ImageObject\",\"url\":\"https://mintcdn.com/qobra/BOwfuCXh9Zd24PEc/logo/dark.svg?fit=max\u0026auto=format\u0026n=BOwfuCXh9Zd24PEc\u0026q=85\u0026s=89cd1b29990b669fb3daa20d2e46c52f\"}},{\"@type\":\"WebSite\",\"@id\":\"https://docs.qobra.co#website\",\"name\":\"Qobra public API documentation\",\"url\":\"https://docs.qobra.co\",\"publisher\":{\"@id\":\"https://docs.qobra.co/#organization\"}},{\"@type\":\"WebPage\",\"@id\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user#webpage\",\"url\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user\",\"name\":\"Upsert users bulk\",\"description\":\"Upsert users in bulk.\",\"dateModified\":\"2026-10-01T08:25:13.443Z\",\"isPartOf\":{\"@id\":\"https://docs.qobra.co#website\"},\"breadcrumb\":{\"@id\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user#breadcrumb\"}},{\"@type\":\"BreadcrumbList\",\"@id\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Public API Documentation\",\"item\":\"https://docs.qobra.co/api_reference/v1/introduction\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Endpoints\",\"item\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/fetch_users\"},{\"@type\":\"ListItem\",\"position\":3,\"name\":\"User management\",\"item\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/fetch_users\"},{\"@type\":\"ListItem\",\"position\":4,\"name\":\"Upsert users bulk\",\"item\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user\"}]},{\"@type\":[\"TechArticle\",\"APIReference\"],\"@id\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user#apireference\",\"headline\":\"Upsert users bulk\",\"name\":\"Upsert users bulk\",\"description\":\"Upsert users in bulk.\",\"url\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user\",\"mainEntityOfPage\":{\"@id\":\"https://docs.qobra.co/api_reference/v1/endpoints/users/upsert_bulk_user#webpage\"},\"dateModified\":\"2026-10-01T08:25:13.443Z\",\"publisher\":{\"@id\":\"https://docs.qobra.co/#organization\"},\"isPartOf\":{\"@id\":\"https://docs.qobra.co#website\"}}]}\u003c/script>\u003cscript data-mint-head type=\"application/ld+json\">{\"@context\":\"https://schema.org\",\"@type\":\"WebSite\",\"name\":\"Qobra public API documentation\",\"creator\":{\"@type\":\"Organization\",\"name\":\"Mintlify\",\"url\":\"https://mintlify.com\"}}\u003c/script>","siteName":"Qobra public API documentation","nav":{"global":{"anchors":[{"anchor":"Help center","icon":"hands-holding-heart","href":"https://help.qobra.co/en/"},{"anchor":"Blog","icon":"newspaper","href":"https://www.qobra.co/blog"},{"anchor":"Security","icon":"shield-check","href":"https://trust.qobra.co/"}]},"versions":[{"version":"v1","anchors":[{"anchor":"Documentation","icon":"book-open","groups":[{"group":"Inbound data integrations","pages":[{"title":"Introduction","href":"/integration_documentation/introductions/inbound_integration"},{"group":"Integrations","pages":[{"group":"CRMs","pages":[{"title":null,"href":"/integration_documentation/crms/salesforce"},{"title":null,"href":"/integration_documentation/crms/hubspot"},{"title":null,"href":"/integration_documentation/crms/pipedrive"},{"title":"Microsoft Dynamics","href":"/integration_documentation/crms/microsoft_dynamics"},{"title":null,"href":"/integration_documentation/crms/zoho"},{"title":null,"href":"/integration_documentation/crms/odoo"},{"title":null,"href":"/integration_documentation/crms/attio"}]},{"group":"Databases","pages":[{"title":"snowflake","href":"/integration_documentation/databases/snowflake"},{"title":null,"href":"/integration_documentation/databases/bigquery"},{"title":"PostgreSQL","href":"/integration_documentation/databases/postgresql"}]},{"group":"ERP","pages":[{"title":"NetSuite","href":"/integration_documentation/erp/netsuite"}]},{"group":"Files","pages":[{"title":null,"href":"/integration_documentation/files/s3"},{"title":"SFTP","href":"/integration_documentation/files/sftp"}]},{"group":"HRIS","pages":[{"title":"HRIS Connector","href":"/integration_documentation/hris/hris_connector"}]}]}]},{"group":"Outbound data integrations","pages":[{"title":"Introduction","href":"/integration_documentation/introductions/outbound_integration"},{"group":"Integrations","pages":[{"title":null,"href":"/integration_documentation/webhook/webhook"}]}]},{"group":"Public API Documentation","pages":[{"title":"Introduction","href":"/api_reference/v1/introduction"},{"title":"Migration guide v1 → v2","href":"/api_reference/v2/migration_guide"},{"group":"Endpoints","pages":[{"group":"User management","pages":[{"openapi":"get /v1/users","version":"v1","title":"Fetch users","description":"Retrieves users","href":"/api_reference/v1/endpoints/users/fetch_users"},{"openapi":"put /v1/users/bulk","version":"v1","title":"Upsert users bulk","href":"/api_reference/v1/endpoints/users/upsert_bulk_user"},{"openapi":"delete /v1/users/archive/bulk","version":"v1","title":"Archive users bulk","description":"Archive users in bulk.","href":"/api_reference/v1/endpoints/users/archive_users"},{"group":"Group attributions","pages":[{"openapi":"put /v1/users/groups/bulk","version":"v1","title":"Upsert group attributions bulk","href":"/api_reference/v1/endpoints/users/upsert_bulk_user_group"}]},{"group":"Manager attributions","pages":[{"openapi":"put /v1/users/managers/bulk","version":"v1","title":"Upsert manager attributions bulk","href":"/api_reference/v1/endpoints/users/upsert_bulk_user_manager"}]}]},{"group":"Data table","pages":[{"openapi":"get /v1/tables/{data_table_key}/records","version":"v1","title":"Fetch records","href":"/api_reference/v1/endpoints/data_tables/fetch_records_data"},{"openapi":"post /v1/tables/{data_table_key}/records/bulk","version":"v1","title":"Upsert records bulk","href":"/api_reference/v1/endpoints/data_tables/ingest_records"}]},{"group":"Imports","pages":[{"openapi":"get /v1/imports/{import_id}","version":"v1","title":"Fetch import","href":"/api_reference/v1/endpoints/imports/fetch_import"}]},{"group":"Reporting","pages":[{"openapi":"get /v1/reporting","version":"v1","deprecated":true,"title":"Fetch statement reporting data","href":"/api_reference/v1/endpoints/reporting/fetch_statement_reporting_data"},{"openapi":"get /v1/reporting/{data_table_id}/records","version":"v1","deprecated":true,"title":"Fetch record reporting data","href":"/api_reference/v1/endpoints/reporting/fetch_record_reporting_data"}]}]}]},{"group":"Authentication","pages":[{"title":"SSO","href":"/authentication_documentation/sso/sso_documentation"}]}]},{"anchor":"MCP server","icon":"plug","pages":[{"title":"MCP server","href":"/mcp_documentation/introduction"}]}]},{"version":"v2","pages":[{"title":"v2","href":"/api_reference/v2/introduction"}]}]},"title":"Upsert users bulk - Qobra public API documentation","buildId":"dpl_EnxDqhjaNc9a8MVa833TGULPd9uJ","deploymentId":"dpl_EnxDqhjaNc9a8MVa833TGULPd9uJ","dynamics":["c2aa737661","2b790eda92","b0f84f53ff","a74be98ba7","a9bb46feb3"],"chunks":["OpenApiReferenceProvider-26-lDe7V.js","utils-CWQmgYtH.js","cloneDeep-izs3Hzxb.js","_Uint8Array-BVIqJ90l.js","isObjectLike-C8vmzPEN.js","isArray-Dcu1dQ5t.js","utils-4-Aw3rSD.js","toString-BX-iyh8G.js","isSymbol-CSH9U2Gm.js","addUniqueKeysToSchema-C2zjXYA5.js","snippetPresets-DFmpFA7C.js","style-to-object-BY3JEAdk.js","v4-DIgz8zy6.js","ApiExamples-FJpQavWq.js","isEqual-BfaiBbcl.js","usePlaygroundInputsStore-D_GvPF7k.js","shallow-Bs2ZB0NO.js","getApiPlaygroundDisplay-DCcqJJk-.js","CodeSnippet-DzDxawVe.js","CodeSnippets-aUr7fU-7.js","Page-CT9uE8Ip.js","getPastedJson-Y1fKsj_I.js","icon-DI4zTsDr.js","MethodPill-C0nDlmSQ.js","DuplicateIcon-NUXbx2nQ.js","createIcon-BdTHrPAi.js","DynamicMarkdown-CtpgKJwj.js","SectionHeading-B3x35tOt.js","axios-vUo_bRtp.js","zoom-image-lightbox-CVZVK4hN.js","lightbox-handle-r17bVUz3.js","Markdown-3OmurJMP.js","clsx-DMKzROTp.js","lib-DuNMoZ05.js","lib-B8HbPgcC.js","html-void-elements-mCSPHezU.js","dist-1ms6tsT-.js","katex-YMM-FMeD.js","marked.esm-CZWythHk.js","AssistantPageLink-Ke9xIMFx.js"]}