# Users

## List users

> Returns a list of all users with access to the account.

```json
{"openapi":"3.1.0","info":{"title":"Users","version":"1.0.0"},"servers":[{"url":"https://api.integrator.io","description":"Production (US / default region)"},{"url":"https://api.eu.integrator.io","description":"Production (EU region)"}],"security":[{"bearerAuth":[]}],"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer"}},"parameters":{"Include":{"name":"include","in":"query","required":false,"description":"Comma-separated list of fields to project into each returned record.\nTriggers **summary projection** on supported list endpoints: the server\nreturns a minimal identity set for each record (`_id`, `name`, plus a\nresource-specific always-on set like `adaptorType` on exports/imports,\nor richer defaults on `ashares`, `audit`, `httpconnectors`, `transfers`,\netc.) and adds any listed fields that exist on the record. Listed fields\nthe record doesn't carry are silently dropped.\n\nDot notation is supported for projecting nested sub-fields — e.g.\n`include=ftp.directoryPath` on `/v1/exports` returns just that nested\nfield inside `ftp` for FTP-type exports (and omits `ftp` entirely for\nnon-FTP exports).\n\nRules:\n- Value regex is `{a-z A-Z . _}` (letters, dots, underscores) plus the\n  comma separator; digits are also accepted in practice. Any other\n  character returns **400 `invalid_query_params`**.\n- Empty value (`include=`) or bare `include` is ignored — the full\n  default record is returned.\n- `include` and `exclude` are **mutually exclusive**. Passing both\n  returns **400 `invalid_query_params`**: *\"Please provide either\n  include or exclude param in the request query and not both.\"*\n- Array-bracket syntax (`include[]=...`) is not supported and can return\n  a 500.\n- Only list endpoints honor projection — on GET-by-id the parameter is\n  silently ignored.\n- A small set of list endpoints explicitly reject both `include` and\n  `exclude` with **400 `invalid_query_params`** and a message of the form\n  *\"Include or exclude query params are not applicable for `<resource>`\n  resource.\"* Known rejections: `/v1/ediprofiles`, `/v1/environments`,\n  `/v1/iClients`, `/v1/lookupcaches`, `/v1/tags`.","schema":{"type":"string"}},"Exclude":{"name":"exclude","in":"query","required":false,"description":"Comma-separated list of fields to remove from the default response on\nsupported list endpoints. Unlike `include`, `exclude` does NOT trigger\nsummary projection — callers get the standard full-record shape with the\nnamed fields stripped out.\n\nRules:\n- Value regex is `{a-z A-Z . _}` (letters, dots, underscores) plus the\n  comma separator; digits are also accepted in practice. Any other\n  character returns **400 `invalid_query_params`**.\n- Empty value (`exclude=`) is ignored.\n- Certain protected identity fields **cannot be stripped** — e.g.\n  `exclude=name` on `/v1/exports` is silently ignored and `name` remains\n  in the response. Protected sets vary per resource.\n- `include` and `exclude` are **mutually exclusive**. Passing both\n  returns **400 `invalid_query_params`**: *\"Please provide either\n  include or exclude param in the request query and not both.\"*\n- Only list endpoints honor stripping — on GET-by-id the parameter is\n  silently ignored.\n- A small set of list endpoints explicitly reject both `include` and\n  `exclude` with **400 `invalid_query_params`** and a message of the form\n  *\"Include or exclude query params are not applicable for `<resource>`\n  resource.\"* Known rejections: `/v1/ediprofiles`, `/v1/environments`,\n  `/v1/iClients`, `/v1/lookupcaches`, `/v1/tags`.","schema":{"type":"string"}}},"schemas":{"Response":{"type":"object","description":"Account user object representing a user's access to the account","allOf":[{"$ref":"#/components/schemas/Request"},{"type":"object","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for this user in the account."},"accepted":{"type":"boolean","readOnly":true,"description":"Whether the user has accepted the invitation to join the account."},"lastSignIn":{"type":"string","format":"date-time","readOnly":true,"description":"Last sign-in timestamp for the user (if available)."},"dismissed":{"type":"boolean","description":"Indicates if the invitation has been declined by the user."},"sharedWithUser":{"type":"object","readOnly":true,"description":"Embedded details about the invited/shared user.","properties":{"_id":{"type":"string","format":"objectId","description":"The user's own account ID."},"email":{"type":"string","format":"email","description":"Email address of the user."},"allowedToResetMFA":{"type":"boolean","description":"Whether the current requester is allowed to reset MFA for this user."},"accountSSOLinked":{"type":"string","description":"SSO linkage status for the user in this account.","enum":["not_linked","this_account"]}},"additionalProperties":true}}},{"$ref":"#/components/schemas/ResourceResponse"},{"$ref":"#/components/schemas/IAResourceResponse"}]},"Request":{"type":"object","description":"Fields that can be sent when inviting or updating an account user","properties":{"disabled":{"type":"boolean","description":"Set to False to enable a disabled user, or True to maintain disabled"},"accessLevel":{"type":"string","description":"Account-level access for the user.\n\n**CRITICAL**: This controls account-wide access. Choose your strategy:\n\n- Integration-only access: omit `accessLevel` and specify integrations in `integrationAccessLevel`\n- Account-wide monitoring + selective management: set `accessLevel: monitor` and use `integrationAccessLevel`\n  to grant `manage` access for specific integrations\n- Full account access: set `accessLevel: manage` or `accessLevel: administrator` and leave\n  `integrationAccessLevel` undefined/empty\n\nChoose the value based on what the user should be able to do across the account (applies to current and future integrations unless you use integration-specific access):\n\n- `administrator`: full account administration (but not owner-only actions)\n  - Can: edit account settings, all resources and integrations; invite/manage users; troubleshoot flow errors\n  - Cannot: transfer account ownership; manage owner permissions\n\n- `manage`: manage integrations but not account settings/users\n  - Can: edit all integrations/resources; troubleshoot flow errors\n  - Cannot: view/edit account settings; invite/manage users\n\n- `monitor`: read/operate flows without modifying configuration\n  - Can: view all integrations; run flows; troubleshoot flow errors (retry/resolve and edit retry data)\n  - Cannot: modify integrations/flows/steps; enable/disable flows; view/modify account resources (e.g., connections, API tokens); view/edit account settings; invite/manage users\n\nIf per-integration level permissions are needed, omit `accessLevel` and instead populate `integrationAccessLevel`.","enum":["monitor","manage","administrator"]},"integrationAccessLevel":{"type":"array","description":"Per-integration access levels for the user.\n\nUse this for granting access to specific integrations.\n\n- If `accessLevel` is omitted, this creates **integration-only** access.\n- If `accessLevel` is `monitor`, this grants **elevated access** (typically `manage`) for specific integrations.\n- If `accessLevel` is `manage` or `administrator`, do not set `integrationAccessLevel`.","items":{"type":"object","properties":{"_integrationId":{"type":"string","format":"objectId","description":"Integration ID the user should have access to."},"accessLevel":{"type":"string","description":"Access level for this integration.","enum":["monitor","manage"]}}}},"accountSSORequired":{"type":"boolean","description":"Whether SSO is required for this user in this account."},"accountMFARequired":{"type":"boolean","description":"Whether MFA is required for this user in this account."},"allowAccessToAPIM":{"type":"boolean","description":"Whether the user is allowed to access API Management (APIM) features for this account."},"allowToEditRetryData":{"type":"boolean","description":"Whether the user is allowed to edit retry data when troubleshooting flow run errors (Error Management).\n\nAll users with **Monitor** access can view, retry, and resolve errant records. This flag controls whether they\ncan also **edit the retry data payload**. If set to false, the user cannot edit retry data for flow runs in any\nintegration workspace where they only have **Monitor** access.\n\nThis setting only applies when:\n- `accessLevel` is `monitor`, or\n- an entry in `integrationAccessLevel` grants `monitor` access for a specific integration."}}},"ResourceResponse":{"type":"object","description":"Core response fields shared by all Celigo resources","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for the resource.\n\nThe _id is used in:\n- API endpoints that operate on a specific resource (e.g., GET, PUT, DELETE)\n- References from other resources (e.g., flows that use this resource)\n- Job history and error tracking\n\nFormat: 24-character hexadecimal string\n"},"createdAt":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was initially created.\n\nThis read-only field is automatically set during resource creation and cannot\nbe modified. It provides an audit trail for when the resource was first added\nto the system, which can be useful for:\n\n- Resource lifecycle management\n- Audit and compliance reporting\n- Troubleshooting integration timelines\n- Identifying older resources that may need review\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\n"},"lastModified":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was most recently updated.\n\nThis read-only field is automatically updated whenever any property of the\nresource is modified. It provides an audit trail that can be used for:\n\n- Determining if a resource has changed since it was last reviewed\n- Monitoring configuration changes during troubleshooting\n- Implementing cache invalidation strategies\n- Synchronizing related resources based on modification time\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix)\nand will always be equal to or later than the createdAt timestamp.\n"},"deletedAt":{"type":["string","null"],"format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was marked for deletion.\n\nWhen this field is present and contains a valid timestamp, it indicates\nthat the resource has been soft-deleted (moved to the recycle bin) but not\nyet permanently removed from the system. This allows for recovery of\naccidentally deleted resources within a specified retention period.\n\nThe deletedAt timestamp enables:\n- Filtering deleted resources from active resource listings\n- Implementing time-based retention policies for permanent deletion\n- Tracking deletion events for audit and compliance purposes\n- Resource recovery workflows with clear timeframes\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\nWhen null or absent, the resource is considered active.\n"}},"required":["_id"]},"IAResourceResponse":{"type":"object","description":"Integration app response fields for resources that are part of integration apps","properties":{"_integrationId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the specific integration instance that contains this resource.\n\nThis field is only populated for resources that are part of an integration app\ninstallation. It contains the unique identifier (_id) of the integration\nresource that was installed in the account.\n\nThe integration instance represents a specific installed instance of an\nintegration app, with its own configuration, settings, and runtime environment.\n\nThis reference enables:\n- Tracing the resource back to its parent integration instance\n- Permission and access control based on integration ownership\n- Lifecycle management (enabling/disabling, updating, or uninstalling)\n"},"_connectorId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the integration app that defines this resource.\n\nThis field is only populated for resources that are part of an integration app.\nIt contains the unique identifier (_id) of the integration app (connector)\nthat defines the structure, behavior, and templates for this resource.\n\nThe integration app is the published template that can be installed\nmultiple times across different accounts, with each installation creating\na separate integration instance (referenced by _integrationId).\n\nThis reference enables:\n- Identifying the source integration app for this resource\n- Determining which template version is being used\n- Linking to documentation, support, and marketplace information\n"}}}},"responses":{"401-unauthorized":{"description":"Unauthorized. The request lacks a valid bearer token, or the provided token\nfailed to authenticate.\n\nNote: the 401 response is produced by the auth middleware **before** the\nrequest reaches the endpoint handler, so it does **not** follow the\nstandard `{errors: [...]}` envelope. Instead the body is a bare\n`{message: string}` object with no `code`, no `errors` array. Callers\nhandling 401s should key off the HTTP status and the `message` string,\nnot try to destructure an `errors[]`.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","description":"Human-readable description of the auth failure. Known values:\n- `\"Unauthorized\"` — no `Authorization` header on the request.\n- `\"Bearer Authentication Failed\"` — header present but token\n  is invalid, revoked, or expired."}},"required":["message"]}}}}}},"paths":{"/v1/ashares":{"get":{"summary":"List users","description":"Returns a list of all users with access to the account.","operationId":"listUsers","tags":["Users"],"parameters":[{"$ref":"#/components/parameters/Include"},{"$ref":"#/components/parameters/Exclude"}],"responses":{"200":{"description":"Successfully retrieved list of users","headers":{"Link":{"description":"RFC-5988 pagination links. When more pages remain, includes a `<...>; rel=\"next\"` entry;\nabsent on the final page.\n","schema":{"type":"string"}}},"content":{"application/json":{"schema":{"type":"array","items":{"$ref":"#/components/schemas/Response"}}}}},"204":{"description":"No users exist in the account"},"401":{"$ref":"#/components/responses/401-unauthorized"}}}}}}
```

## Get a user

> Retrieve a single user (ashare) record by its id.

```json
{"openapi":"3.1.0","info":{"title":"Users","version":"1.0.0"},"servers":[{"url":"https://api.integrator.io","description":"Production (US / default region)"},{"url":"https://api.eu.integrator.io","description":"Production (EU region)"}],"security":[{"bearerAuth":[]}],"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer"}},"schemas":{"Response":{"type":"object","description":"Account user object representing a user's access to the account","allOf":[{"$ref":"#/components/schemas/Request"},{"type":"object","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for this user in the account."},"accepted":{"type":"boolean","readOnly":true,"description":"Whether the user has accepted the invitation to join the account."},"lastSignIn":{"type":"string","format":"date-time","readOnly":true,"description":"Last sign-in timestamp for the user (if available)."},"dismissed":{"type":"boolean","description":"Indicates if the invitation has been declined by the user."},"sharedWithUser":{"type":"object","readOnly":true,"description":"Embedded details about the invited/shared user.","properties":{"_id":{"type":"string","format":"objectId","description":"The user's own account ID."},"email":{"type":"string","format":"email","description":"Email address of the user."},"allowedToResetMFA":{"type":"boolean","description":"Whether the current requester is allowed to reset MFA for this user."},"accountSSOLinked":{"type":"string","description":"SSO linkage status for the user in this account.","enum":["not_linked","this_account"]}},"additionalProperties":true}}},{"$ref":"#/components/schemas/ResourceResponse"},{"$ref":"#/components/schemas/IAResourceResponse"}]},"Request":{"type":"object","description":"Fields that can be sent when inviting or updating an account user","properties":{"disabled":{"type":"boolean","description":"Set to False to enable a disabled user, or True to maintain disabled"},"accessLevel":{"type":"string","description":"Account-level access for the user.\n\n**CRITICAL**: This controls account-wide access. Choose your strategy:\n\n- Integration-only access: omit `accessLevel` and specify integrations in `integrationAccessLevel`\n- Account-wide monitoring + selective management: set `accessLevel: monitor` and use `integrationAccessLevel`\n  to grant `manage` access for specific integrations\n- Full account access: set `accessLevel: manage` or `accessLevel: administrator` and leave\n  `integrationAccessLevel` undefined/empty\n\nChoose the value based on what the user should be able to do across the account (applies to current and future integrations unless you use integration-specific access):\n\n- `administrator`: full account administration (but not owner-only actions)\n  - Can: edit account settings, all resources and integrations; invite/manage users; troubleshoot flow errors\n  - Cannot: transfer account ownership; manage owner permissions\n\n- `manage`: manage integrations but not account settings/users\n  - Can: edit all integrations/resources; troubleshoot flow errors\n  - Cannot: view/edit account settings; invite/manage users\n\n- `monitor`: read/operate flows without modifying configuration\n  - Can: view all integrations; run flows; troubleshoot flow errors (retry/resolve and edit retry data)\n  - Cannot: modify integrations/flows/steps; enable/disable flows; view/modify account resources (e.g., connections, API tokens); view/edit account settings; invite/manage users\n\nIf per-integration level permissions are needed, omit `accessLevel` and instead populate `integrationAccessLevel`.","enum":["monitor","manage","administrator"]},"integrationAccessLevel":{"type":"array","description":"Per-integration access levels for the user.\n\nUse this for granting access to specific integrations.\n\n- If `accessLevel` is omitted, this creates **integration-only** access.\n- If `accessLevel` is `monitor`, this grants **elevated access** (typically `manage`) for specific integrations.\n- If `accessLevel` is `manage` or `administrator`, do not set `integrationAccessLevel`.","items":{"type":"object","properties":{"_integrationId":{"type":"string","format":"objectId","description":"Integration ID the user should have access to."},"accessLevel":{"type":"string","description":"Access level for this integration.","enum":["monitor","manage"]}}}},"accountSSORequired":{"type":"boolean","description":"Whether SSO is required for this user in this account."},"accountMFARequired":{"type":"boolean","description":"Whether MFA is required for this user in this account."},"allowAccessToAPIM":{"type":"boolean","description":"Whether the user is allowed to access API Management (APIM) features for this account."},"allowToEditRetryData":{"type":"boolean","description":"Whether the user is allowed to edit retry data when troubleshooting flow run errors (Error Management).\n\nAll users with **Monitor** access can view, retry, and resolve errant records. This flag controls whether they\ncan also **edit the retry data payload**. If set to false, the user cannot edit retry data for flow runs in any\nintegration workspace where they only have **Monitor** access.\n\nThis setting only applies when:\n- `accessLevel` is `monitor`, or\n- an entry in `integrationAccessLevel` grants `monitor` access for a specific integration."}}},"ResourceResponse":{"type":"object","description":"Core response fields shared by all Celigo resources","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for the resource.\n\nThe _id is used in:\n- API endpoints that operate on a specific resource (e.g., GET, PUT, DELETE)\n- References from other resources (e.g., flows that use this resource)\n- Job history and error tracking\n\nFormat: 24-character hexadecimal string\n"},"createdAt":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was initially created.\n\nThis read-only field is automatically set during resource creation and cannot\nbe modified. It provides an audit trail for when the resource was first added\nto the system, which can be useful for:\n\n- Resource lifecycle management\n- Audit and compliance reporting\n- Troubleshooting integration timelines\n- Identifying older resources that may need review\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\n"},"lastModified":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was most recently updated.\n\nThis read-only field is automatically updated whenever any property of the\nresource is modified. It provides an audit trail that can be used for:\n\n- Determining if a resource has changed since it was last reviewed\n- Monitoring configuration changes during troubleshooting\n- Implementing cache invalidation strategies\n- Synchronizing related resources based on modification time\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix)\nand will always be equal to or later than the createdAt timestamp.\n"},"deletedAt":{"type":["string","null"],"format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was marked for deletion.\n\nWhen this field is present and contains a valid timestamp, it indicates\nthat the resource has been soft-deleted (moved to the recycle bin) but not\nyet permanently removed from the system. This allows for recovery of\naccidentally deleted resources within a specified retention period.\n\nThe deletedAt timestamp enables:\n- Filtering deleted resources from active resource listings\n- Implementing time-based retention policies for permanent deletion\n- Tracking deletion events for audit and compliance purposes\n- Resource recovery workflows with clear timeframes\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\nWhen null or absent, the resource is considered active.\n"}},"required":["_id"]},"IAResourceResponse":{"type":"object","description":"Integration app response fields for resources that are part of integration apps","properties":{"_integrationId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the specific integration instance that contains this resource.\n\nThis field is only populated for resources that are part of an integration app\ninstallation. It contains the unique identifier (_id) of the integration\nresource that was installed in the account.\n\nThe integration instance represents a specific installed instance of an\nintegration app, with its own configuration, settings, and runtime environment.\n\nThis reference enables:\n- Tracing the resource back to its parent integration instance\n- Permission and access control based on integration ownership\n- Lifecycle management (enabling/disabling, updating, or uninstalling)\n"},"_connectorId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the integration app that defines this resource.\n\nThis field is only populated for resources that are part of an integration app.\nIt contains the unique identifier (_id) of the integration app (connector)\nthat defines the structure, behavior, and templates for this resource.\n\nThe integration app is the published template that can be installed\nmultiple times across different accounts, with each installation creating\na separate integration instance (referenced by _integrationId).\n\nThis reference enables:\n- Identifying the source integration app for this resource\n- Determining which template version is being used\n- Linking to documentation, support, and marketplace information\n"}}},"Error":{"type":"object","description":"Standard error response envelope returned by integrator.io APIs.","properties":{"errors":{"type":"array","description":"List of errors that occurred while processing the request.","items":{"type":"object","properties":{"code":{"oneOf":[{"type":"string"},{"type":"integer"}],"description":"Machine-readable error code. Usually a string like\n`invalid_ref`, `missing_required_field`, or `unauthorized`;\nmay be an **integer** when the error mirrors an upstream HTTP\nstatus (e.g. `500`) — most commonly returned by connection-ping\nand adaptor-proxy responses."},"message":{"type":"string","description":"Human-readable description of the error."},"field":{"type":"string","description":"Optional pointer to the document field that caused the error.\nUsed by structural validation errors (`missing_required_field`,\n`invalid_ref`) to indicate which field is at fault\n(e.g. `_id`, `type`, `http.baseURI`)."},"source":{"type":"string","description":"Optional origin layer for the error — e.g. `application` when\nthe error came from the remote system the adaptor called,\n`connector` when the adaptor itself rejected the request."}},"required":["message"]}}},"required":["errors"]}},"responses":{"401-unauthorized":{"description":"Unauthorized. The request lacks a valid bearer token, or the provided token\nfailed to authenticate.\n\nNote: the 401 response is produced by the auth middleware **before** the\nrequest reaches the endpoint handler, so it does **not** follow the\nstandard `{errors: [...]}` envelope. Instead the body is a bare\n`{message: string}` object with no `code`, no `errors` array. Callers\nhandling 401s should key off the HTTP status and the `message` string,\nnot try to destructure an `errors[]`.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","description":"Human-readable description of the auth failure. Known values:\n- `\"Unauthorized\"` — no `Authorization` header on the request.\n- `\"Bearer Authentication Failed\"` — header present but token\n  is invalid, revoked, or expired."}},"required":["message"]}}}},"404-not-found":{"description":"Not found. The requested resource does not exist or is not visible to the caller.\n","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}},"paths":{"/v1/ashares/{_id}":{"get":{"summary":"Get a user","operationId":"getUser","tags":["Users"],"description":"Retrieve a single user (ashare) record by its id.","parameters":[{"name":"_id","in":"path","required":true,"description":"User (ashare) id.","schema":{"type":"string","format":"objectId"}}],"responses":{"200":{"description":"Successfully retrieved user","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Response"}}}},"401":{"$ref":"#/components/responses/401-unauthorized"},"404":{"$ref":"#/components/responses/404-not-found"}}}}}}
```

## Update a user

> Update a user's role, access level, or scope within the account.

```json
{"openapi":"3.1.0","info":{"title":"Users","version":"1.0.0"},"servers":[{"url":"https://api.integrator.io","description":"Production (US / default region)"},{"url":"https://api.eu.integrator.io","description":"Production (EU region)"}],"security":[{"bearerAuth":[]}],"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer"}},"schemas":{"Request":{"type":"object","description":"Fields that can be sent when inviting or updating an account user","properties":{"disabled":{"type":"boolean","description":"Set to False to enable a disabled user, or True to maintain disabled"},"accessLevel":{"type":"string","description":"Account-level access for the user.\n\n**CRITICAL**: This controls account-wide access. Choose your strategy:\n\n- Integration-only access: omit `accessLevel` and specify integrations in `integrationAccessLevel`\n- Account-wide monitoring + selective management: set `accessLevel: monitor` and use `integrationAccessLevel`\n  to grant `manage` access for specific integrations\n- Full account access: set `accessLevel: manage` or `accessLevel: administrator` and leave\n  `integrationAccessLevel` undefined/empty\n\nChoose the value based on what the user should be able to do across the account (applies to current and future integrations unless you use integration-specific access):\n\n- `administrator`: full account administration (but not owner-only actions)\n  - Can: edit account settings, all resources and integrations; invite/manage users; troubleshoot flow errors\n  - Cannot: transfer account ownership; manage owner permissions\n\n- `manage`: manage integrations but not account settings/users\n  - Can: edit all integrations/resources; troubleshoot flow errors\n  - Cannot: view/edit account settings; invite/manage users\n\n- `monitor`: read/operate flows without modifying configuration\n  - Can: view all integrations; run flows; troubleshoot flow errors (retry/resolve and edit retry data)\n  - Cannot: modify integrations/flows/steps; enable/disable flows; view/modify account resources (e.g., connections, API tokens); view/edit account settings; invite/manage users\n\nIf per-integration level permissions are needed, omit `accessLevel` and instead populate `integrationAccessLevel`.","enum":["monitor","manage","administrator"]},"integrationAccessLevel":{"type":"array","description":"Per-integration access levels for the user.\n\nUse this for granting access to specific integrations.\n\n- If `accessLevel` is omitted, this creates **integration-only** access.\n- If `accessLevel` is `monitor`, this grants **elevated access** (typically `manage`) for specific integrations.\n- If `accessLevel` is `manage` or `administrator`, do not set `integrationAccessLevel`.","items":{"type":"object","properties":{"_integrationId":{"type":"string","format":"objectId","description":"Integration ID the user should have access to."},"accessLevel":{"type":"string","description":"Access level for this integration.","enum":["monitor","manage"]}}}},"accountSSORequired":{"type":"boolean","description":"Whether SSO is required for this user in this account."},"accountMFARequired":{"type":"boolean","description":"Whether MFA is required for this user in this account."},"allowAccessToAPIM":{"type":"boolean","description":"Whether the user is allowed to access API Management (APIM) features for this account."},"allowToEditRetryData":{"type":"boolean","description":"Whether the user is allowed to edit retry data when troubleshooting flow run errors (Error Management).\n\nAll users with **Monitor** access can view, retry, and resolve errant records. This flag controls whether they\ncan also **edit the retry data payload**. If set to false, the user cannot edit retry data for flow runs in any\nintegration workspace where they only have **Monitor** access.\n\nThis setting only applies when:\n- `accessLevel` is `monitor`, or\n- an entry in `integrationAccessLevel` grants `monitor` access for a specific integration."}}},"Response":{"type":"object","description":"Account user object representing a user's access to the account","allOf":[{"$ref":"#/components/schemas/Request"},{"type":"object","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for this user in the account."},"accepted":{"type":"boolean","readOnly":true,"description":"Whether the user has accepted the invitation to join the account."},"lastSignIn":{"type":"string","format":"date-time","readOnly":true,"description":"Last sign-in timestamp for the user (if available)."},"dismissed":{"type":"boolean","description":"Indicates if the invitation has been declined by the user."},"sharedWithUser":{"type":"object","readOnly":true,"description":"Embedded details about the invited/shared user.","properties":{"_id":{"type":"string","format":"objectId","description":"The user's own account ID."},"email":{"type":"string","format":"email","description":"Email address of the user."},"allowedToResetMFA":{"type":"boolean","description":"Whether the current requester is allowed to reset MFA for this user."},"accountSSOLinked":{"type":"string","description":"SSO linkage status for the user in this account.","enum":["not_linked","this_account"]}},"additionalProperties":true}}},{"$ref":"#/components/schemas/ResourceResponse"},{"$ref":"#/components/schemas/IAResourceResponse"}]},"ResourceResponse":{"type":"object","description":"Core response fields shared by all Celigo resources","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for the resource.\n\nThe _id is used in:\n- API endpoints that operate on a specific resource (e.g., GET, PUT, DELETE)\n- References from other resources (e.g., flows that use this resource)\n- Job history and error tracking\n\nFormat: 24-character hexadecimal string\n"},"createdAt":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was initially created.\n\nThis read-only field is automatically set during resource creation and cannot\nbe modified. It provides an audit trail for when the resource was first added\nto the system, which can be useful for:\n\n- Resource lifecycle management\n- Audit and compliance reporting\n- Troubleshooting integration timelines\n- Identifying older resources that may need review\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\n"},"lastModified":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was most recently updated.\n\nThis read-only field is automatically updated whenever any property of the\nresource is modified. It provides an audit trail that can be used for:\n\n- Determining if a resource has changed since it was last reviewed\n- Monitoring configuration changes during troubleshooting\n- Implementing cache invalidation strategies\n- Synchronizing related resources based on modification time\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix)\nand will always be equal to or later than the createdAt timestamp.\n"},"deletedAt":{"type":["string","null"],"format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was marked for deletion.\n\nWhen this field is present and contains a valid timestamp, it indicates\nthat the resource has been soft-deleted (moved to the recycle bin) but not\nyet permanently removed from the system. This allows for recovery of\naccidentally deleted resources within a specified retention period.\n\nThe deletedAt timestamp enables:\n- Filtering deleted resources from active resource listings\n- Implementing time-based retention policies for permanent deletion\n- Tracking deletion events for audit and compliance purposes\n- Resource recovery workflows with clear timeframes\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\nWhen null or absent, the resource is considered active.\n"}},"required":["_id"]},"IAResourceResponse":{"type":"object","description":"Integration app response fields for resources that are part of integration apps","properties":{"_integrationId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the specific integration instance that contains this resource.\n\nThis field is only populated for resources that are part of an integration app\ninstallation. It contains the unique identifier (_id) of the integration\nresource that was installed in the account.\n\nThe integration instance represents a specific installed instance of an\nintegration app, with its own configuration, settings, and runtime environment.\n\nThis reference enables:\n- Tracing the resource back to its parent integration instance\n- Permission and access control based on integration ownership\n- Lifecycle management (enabling/disabling, updating, or uninstalling)\n"},"_connectorId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the integration app that defines this resource.\n\nThis field is only populated for resources that are part of an integration app.\nIt contains the unique identifier (_id) of the integration app (connector)\nthat defines the structure, behavior, and templates for this resource.\n\nThe integration app is the published template that can be installed\nmultiple times across different accounts, with each installation creating\na separate integration instance (referenced by _integrationId).\n\nThis reference enables:\n- Identifying the source integration app for this resource\n- Determining which template version is being used\n- Linking to documentation, support, and marketplace information\n"}}},"Error":{"type":"object","description":"Standard error response envelope returned by integrator.io APIs.","properties":{"errors":{"type":"array","description":"List of errors that occurred while processing the request.","items":{"type":"object","properties":{"code":{"oneOf":[{"type":"string"},{"type":"integer"}],"description":"Machine-readable error code. Usually a string like\n`invalid_ref`, `missing_required_field`, or `unauthorized`;\nmay be an **integer** when the error mirrors an upstream HTTP\nstatus (e.g. `500`) — most commonly returned by connection-ping\nand adaptor-proxy responses."},"message":{"type":"string","description":"Human-readable description of the error."},"field":{"type":"string","description":"Optional pointer to the document field that caused the error.\nUsed by structural validation errors (`missing_required_field`,\n`invalid_ref`) to indicate which field is at fault\n(e.g. `_id`, `type`, `http.baseURI`)."},"source":{"type":"string","description":"Optional origin layer for the error — e.g. `application` when\nthe error came from the remote system the adaptor called,\n`connector` when the adaptor itself rejected the request."}},"required":["message"]}}},"required":["errors"]}},"responses":{"400-bad-request":{"description":"Bad request. The server could not understand the request because of malformed syntax or invalid parameters.\n","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401-unauthorized":{"description":"Unauthorized. The request lacks a valid bearer token, or the provided token\nfailed to authenticate.\n\nNote: the 401 response is produced by the auth middleware **before** the\nrequest reaches the endpoint handler, so it does **not** follow the\nstandard `{errors: [...]}` envelope. Instead the body is a bare\n`{message: string}` object with no `code`, no `errors` array. Callers\nhandling 401s should key off the HTTP status and the `message` string,\nnot try to destructure an `errors[]`.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","description":"Human-readable description of the auth failure. Known values:\n- `\"Unauthorized\"` — no `Authorization` header on the request.\n- `\"Bearer Authentication Failed\"` — header present but token\n  is invalid, revoked, or expired."}},"required":["message"]}}}}}},"paths":{"/v1/ashares/{_id}":{"put":{"summary":"Update a user","operationId":"updateUser","tags":["Users"],"description":"Update a user's role, access level, or scope within the account.","parameters":[{"name":"_id","in":"path","required":true,"description":"User (ashare) id.","schema":{"type":"string","format":"objectId"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/Request"}}}},"responses":{"200":{"description":"user updated successfully","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Response"}}}},"400":{"$ref":"#/components/responses/400-bad-request"},"401":{"$ref":"#/components/responses/401-unauthorized"}}}}}}
```

## Delete a user

> Remove a user (ashare) from the current account.

```json
{"openapi":"3.1.0","info":{"title":"Users","version":"1.0.0"},"servers":[{"url":"https://api.integrator.io","description":"Production (US / default region)"},{"url":"https://api.eu.integrator.io","description":"Production (EU region)"}],"security":[{"bearerAuth":[]}],"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer"}},"responses":{"401-unauthorized":{"description":"Unauthorized. The request lacks a valid bearer token, or the provided token\nfailed to authenticate.\n\nNote: the 401 response is produced by the auth middleware **before** the\nrequest reaches the endpoint handler, so it does **not** follow the\nstandard `{errors: [...]}` envelope. Instead the body is a bare\n`{message: string}` object with no `code`, no `errors` array. Callers\nhandling 401s should key off the HTTP status and the `message` string,\nnot try to destructure an `errors[]`.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","description":"Human-readable description of the auth failure. Known values:\n- `\"Unauthorized\"` — no `Authorization` header on the request.\n- `\"Bearer Authentication Failed\"` — header present but token\n  is invalid, revoked, or expired."}},"required":["message"]}}}},"404-not-found":{"description":"Not found. The requested resource does not exist or is not visible to the caller.\n","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}},"schemas":{"Error":{"type":"object","description":"Standard error response envelope returned by integrator.io APIs.","properties":{"errors":{"type":"array","description":"List of errors that occurred while processing the request.","items":{"type":"object","properties":{"code":{"oneOf":[{"type":"string"},{"type":"integer"}],"description":"Machine-readable error code. Usually a string like\n`invalid_ref`, `missing_required_field`, or `unauthorized`;\nmay be an **integer** when the error mirrors an upstream HTTP\nstatus (e.g. `500`) — most commonly returned by connection-ping\nand adaptor-proxy responses."},"message":{"type":"string","description":"Human-readable description of the error."},"field":{"type":"string","description":"Optional pointer to the document field that caused the error.\nUsed by structural validation errors (`missing_required_field`,\n`invalid_ref`) to indicate which field is at fault\n(e.g. `_id`, `type`, `http.baseURI`)."},"source":{"type":"string","description":"Optional origin layer for the error — e.g. `application` when\nthe error came from the remote system the adaptor called,\n`connector` when the adaptor itself rejected the request."}},"required":["message"]}}},"required":["errors"]}}},"paths":{"/v1/ashares/{_id}":{"delete":{"summary":"Delete a user","operationId":"deleteUser","tags":["Users"],"description":"Remove a user (ashare) from the current account.","parameters":[{"name":"_id","in":"path","required":true,"description":"User (ashare) id.","schema":{"type":"string","format":"objectId"}}],"responses":{"204":{"description":"user deleted successfully"},"401":{"$ref":"#/components/responses/401-unauthorized"},"404":{"$ref":"#/components/responses/404-not-found"}}}}}}
```

## Toggle a user's account access (disable or re-enable)

> Flips the \`disabled\` flag on an ashare. Despite the name, this endpoint is a\
> \*\*toggle\*\*, not a one-way disable:\
> \- First call on an enabled ashare → sets \`disabled: true\` (user can no longer sign in).\
> \- Next call on the disabled ashare → removes the \`disabled\` field entirely (re-enables it).\
> \
> The user record is never deleted; audit trails and historical attributions\
> remain intact regardless of direction. Takes an empty body — the target is\
> identified by the \`{\_userId}\` path parameter (the ashare id).\
> \
> The ashare must be in an \`accepted: true\` state. Calling this on a pending\
> invite (ashare with \`accepted: false\`/absent) returns \*\*400\
> \`invalid\_request\`\*\* with message \`"You can't disable this invitation\
> without it being accepted or dismissed by the invited user."\` — wait for\
> the invitee to accept, or delete the ashare outright instead.\
> \
> AI guidance:\
> \- This is the non-destructive alternative to \`DELETE /v1/ashares/{\_id}\`.\
> &#x20; Prefer toggle over delete when you need to preserve history for\
> &#x20; compliance or review.\
> \- \*\*To re-enable, call this endpoint again\*\* — there is no separate\
> &#x20; \`/enable\` path. \`PUT /v1/ashares/{\_id}\` with \`disabled: false\` returns 204\
> &#x20; but silently leaves the flag unchanged; the toggle is the only\
> &#x20; programmatic re-enable mechanism.\
> \- Read state first via \`GET /v1/ashares/{\_id}\` before calling — the call is\
> &#x20; idempotent against its own post-state, so repeatedly hitting it cycles\
> &#x20; between enabled/disabled.\
> \- The Celigo web UI uses \`PUT /api/ashares/{\_id}/disable\` for both the\
> &#x20; "Disable" and "Enable" actions (session-auth path), confirming the toggle\
> &#x20; semantics at the UI layer as well.\
> \- Confirm intent before calling — the target user loses access immediately\
> &#x20; when the toggle flips to disabled.

```json
{"openapi":"3.1.0","info":{"title":"Users","version":"1.0.0"},"servers":[{"url":"https://api.integrator.io","description":"Production (US / default region)"},{"url":"https://api.eu.integrator.io","description":"Production (EU region)"}],"security":[{"bearerAuth":[]}],"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer"}},"schemas":{"Error":{"type":"object","description":"Standard error response envelope returned by integrator.io APIs.","properties":{"errors":{"type":"array","description":"List of errors that occurred while processing the request.","items":{"type":"object","properties":{"code":{"oneOf":[{"type":"string"},{"type":"integer"}],"description":"Machine-readable error code. Usually a string like\n`invalid_ref`, `missing_required_field`, or `unauthorized`;\nmay be an **integer** when the error mirrors an upstream HTTP\nstatus (e.g. `500`) — most commonly returned by connection-ping\nand adaptor-proxy responses."},"message":{"type":"string","description":"Human-readable description of the error."},"field":{"type":"string","description":"Optional pointer to the document field that caused the error.\nUsed by structural validation errors (`missing_required_field`,\n`invalid_ref`) to indicate which field is at fault\n(e.g. `_id`, `type`, `http.baseURI`)."},"source":{"type":"string","description":"Optional origin layer for the error — e.g. `application` when\nthe error came from the remote system the adaptor called,\n`connector` when the adaptor itself rejected the request."}},"required":["message"]}}},"required":["errors"]}},"responses":{"401-unauthorized":{"description":"Unauthorized. The request lacks a valid bearer token, or the provided token\nfailed to authenticate.\n\nNote: the 401 response is produced by the auth middleware **before** the\nrequest reaches the endpoint handler, so it does **not** follow the\nstandard `{errors: [...]}` envelope. Instead the body is a bare\n`{message: string}` object with no `code`, no `errors` array. Callers\nhandling 401s should key off the HTTP status and the `message` string,\nnot try to destructure an `errors[]`.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","description":"Human-readable description of the auth failure. Known values:\n- `\"Unauthorized\"` — no `Authorization` header on the request.\n- `\"Bearer Authentication Failed\"` — header present but token\n  is invalid, revoked, or expired."}},"required":["message"]}}}}}},"paths":{"/v1/ashares/{_userId}/disable":{"put":{"operationId":"toggleAshareDisabled","tags":["Users"],"summary":"Toggle a user's account access (disable or re-enable)","description":"Flips the `disabled` flag on an ashare. Despite the name, this endpoint is a\n**toggle**, not a one-way disable:\n- First call on an enabled ashare → sets `disabled: true` (user can no longer sign in).\n- Next call on the disabled ashare → removes the `disabled` field entirely (re-enables it).\n\nThe user record is never deleted; audit trails and historical attributions\nremain intact regardless of direction. Takes an empty body — the target is\nidentified by the `{_userId}` path parameter (the ashare id).\n\nThe ashare must be in an `accepted: true` state. Calling this on a pending\ninvite (ashare with `accepted: false`/absent) returns **400\n`invalid_request`** with message `\"You can't disable this invitation\nwithout it being accepted or dismissed by the invited user.\"` — wait for\nthe invitee to accept, or delete the ashare outright instead.\n\nAI guidance:\n- This is the non-destructive alternative to `DELETE /v1/ashares/{_id}`.\n  Prefer toggle over delete when you need to preserve history for\n  compliance or review.\n- **To re-enable, call this endpoint again** — there is no separate\n  `/enable` path. `PUT /v1/ashares/{_id}` with `disabled: false` returns 204\n  but silently leaves the flag unchanged; the toggle is the only\n  programmatic re-enable mechanism.\n- Read state first via `GET /v1/ashares/{_id}` before calling — the call is\n  idempotent against its own post-state, so repeatedly hitting it cycles\n  between enabled/disabled.\n- The Celigo web UI uses `PUT /api/ashares/{_id}/disable` for both the\n  \"Disable\" and \"Enable\" actions (session-auth path), confirming the toggle\n  semantics at the UI layer as well.\n- Confirm intent before calling — the target user loses access immediately\n  when the toggle flips to disabled.","parameters":[{"name":"_userId","in":"path","required":true,"description":"Ashare id identifying the user-in-account relationship to disable.\nThis is the `_id` from `GET /v1/ashares` entries, **not** the\nunderlying user's `_userId`.","schema":{"type":"string","format":"objectId"}}],"requestBody":{"required":false,"content":{"application/json":{"schema":{"type":"object","description":"Empty body — the target is identified by the path parameter alone."}}}},"responses":{"204":{"description":"Ashare disabled. Empty response body."},"400":{"description":"Ashare is not in a disableable state. Most common cause:\n`{code: \"invalid_request\", message: \"You can't disable this invitation\nwithout it being accepted or dismissed by the invited user.\"}` — the\nashare is a pending invite and must be accepted or dismissed first.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401":{"$ref":"#/components/responses/401-unauthorized"},"404":{"description":"Ashare id not found. Response body:\n`{errors: [{code: \"invalid_ref\", message: \"AShare not found.\"}]}`.","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}}}}}}}
```

## Invite a user to the account

> Invites a user to the account.\
> \
> The user will appear in the users list and \`accepted\` will become true after the invite is accepted.

```json
{"openapi":"3.1.0","info":{"title":"Users","version":"1.0.0"},"servers":[{"url":"https://api.integrator.io","description":"Production (US / default region)"},{"url":"https://api.eu.integrator.io","description":"Production (EU region)"}],"security":[{"bearerAuth":[]}],"components":{"securitySchemes":{"bearerAuth":{"type":"http","scheme":"bearer"}},"schemas":{"InviteRequest":{"type":"object","description":"Request body for inviting a user to the account (`POST /v1/invite`)","properties":{"email":{"type":"string","format":"email","description":"Email address of the user to invite to the account."},"accessLevel":{"type":"string","description":"Account-level access for the invited user.\n\n**CRITICAL**: This controls account-wide access. Choose your strategy:\n\n- Integration-only access: omit `accessLevel` and specify integrations in `integrationAccessLevel`\n- Account-wide monitoring + selective management: set `accessLevel: monitor` and use `integrationAccessLevel`\n  to grant `manage` access for specific integrations\n- Full account access: set `accessLevel: manage` or `accessLevel: administrator` and leave\n  `integrationAccessLevel` undefined/empty","enum":["monitor","manage","administrator"]},"integrationAccessLevel":{"type":"array","description":"Per-integration access for the invited user.\n\nUse this to grant access to specific integrations.\n\n- If `accessLevel` is omitted, this creates **integration-only** access.\n- If `accessLevel` is `monitor`, this grants **elevated access** (typically `manage`) for specific integrations.\n- If `accessLevel` is `manage` or `administrator`, do not set `integrationAccessLevel`.","items":{"type":"object","properties":{"_integrationId":{"type":"string","format":"objectId","description":"Integration ID the user should have access to."},"accessLevel":{"type":"string","enum":["monitor","manage"],"description":"Access level for that integration."}}}},"accountSSORequired":{"type":"boolean","description":"Whether the invited user must use SSO to access this account."},"accountMFARequired":{"type":"boolean","description":"Whether the invited user must use MFA to access this account."},"allowAccessToAPIM":{"type":"boolean","description":"Whether the invited user is allowed to access API Management (APIM) features for this account."}},"required":["email"]},"Response":{"type":"object","description":"Account user object representing a user's access to the account","allOf":[{"$ref":"#/components/schemas/Request"},{"type":"object","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for this user in the account."},"accepted":{"type":"boolean","readOnly":true,"description":"Whether the user has accepted the invitation to join the account."},"lastSignIn":{"type":"string","format":"date-time","readOnly":true,"description":"Last sign-in timestamp for the user (if available)."},"dismissed":{"type":"boolean","description":"Indicates if the invitation has been declined by the user."},"sharedWithUser":{"type":"object","readOnly":true,"description":"Embedded details about the invited/shared user.","properties":{"_id":{"type":"string","format":"objectId","description":"The user's own account ID."},"email":{"type":"string","format":"email","description":"Email address of the user."},"allowedToResetMFA":{"type":"boolean","description":"Whether the current requester is allowed to reset MFA for this user."},"accountSSOLinked":{"type":"string","description":"SSO linkage status for the user in this account.","enum":["not_linked","this_account"]}},"additionalProperties":true}}},{"$ref":"#/components/schemas/ResourceResponse"},{"$ref":"#/components/schemas/IAResourceResponse"}]},"Request":{"type":"object","description":"Fields that can be sent when inviting or updating an account user","properties":{"disabled":{"type":"boolean","description":"Set to False to enable a disabled user, or True to maintain disabled"},"accessLevel":{"type":"string","description":"Account-level access for the user.\n\n**CRITICAL**: This controls account-wide access. Choose your strategy:\n\n- Integration-only access: omit `accessLevel` and specify integrations in `integrationAccessLevel`\n- Account-wide monitoring + selective management: set `accessLevel: monitor` and use `integrationAccessLevel`\n  to grant `manage` access for specific integrations\n- Full account access: set `accessLevel: manage` or `accessLevel: administrator` and leave\n  `integrationAccessLevel` undefined/empty\n\nChoose the value based on what the user should be able to do across the account (applies to current and future integrations unless you use integration-specific access):\n\n- `administrator`: full account administration (but not owner-only actions)\n  - Can: edit account settings, all resources and integrations; invite/manage users; troubleshoot flow errors\n  - Cannot: transfer account ownership; manage owner permissions\n\n- `manage`: manage integrations but not account settings/users\n  - Can: edit all integrations/resources; troubleshoot flow errors\n  - Cannot: view/edit account settings; invite/manage users\n\n- `monitor`: read/operate flows without modifying configuration\n  - Can: view all integrations; run flows; troubleshoot flow errors (retry/resolve and edit retry data)\n  - Cannot: modify integrations/flows/steps; enable/disable flows; view/modify account resources (e.g., connections, API tokens); view/edit account settings; invite/manage users\n\nIf per-integration level permissions are needed, omit `accessLevel` and instead populate `integrationAccessLevel`.","enum":["monitor","manage","administrator"]},"integrationAccessLevel":{"type":"array","description":"Per-integration access levels for the user.\n\nUse this for granting access to specific integrations.\n\n- If `accessLevel` is omitted, this creates **integration-only** access.\n- If `accessLevel` is `monitor`, this grants **elevated access** (typically `manage`) for specific integrations.\n- If `accessLevel` is `manage` or `administrator`, do not set `integrationAccessLevel`.","items":{"type":"object","properties":{"_integrationId":{"type":"string","format":"objectId","description":"Integration ID the user should have access to."},"accessLevel":{"type":"string","description":"Access level for this integration.","enum":["monitor","manage"]}}}},"accountSSORequired":{"type":"boolean","description":"Whether SSO is required for this user in this account."},"accountMFARequired":{"type":"boolean","description":"Whether MFA is required for this user in this account."},"allowAccessToAPIM":{"type":"boolean","description":"Whether the user is allowed to access API Management (APIM) features for this account."},"allowToEditRetryData":{"type":"boolean","description":"Whether the user is allowed to edit retry data when troubleshooting flow run errors (Error Management).\n\nAll users with **Monitor** access can view, retry, and resolve errant records. This flag controls whether they\ncan also **edit the retry data payload**. If set to false, the user cannot edit retry data for flow runs in any\nintegration workspace where they only have **Monitor** access.\n\nThis setting only applies when:\n- `accessLevel` is `monitor`, or\n- an entry in `integrationAccessLevel` grants `monitor` access for a specific integration."}}},"ResourceResponse":{"type":"object","description":"Core response fields shared by all Celigo resources","properties":{"_id":{"type":"string","format":"objectId","readOnly":true,"description":"Unique identifier for the resource.\n\nThe _id is used in:\n- API endpoints that operate on a specific resource (e.g., GET, PUT, DELETE)\n- References from other resources (e.g., flows that use this resource)\n- Job history and error tracking\n\nFormat: 24-character hexadecimal string\n"},"createdAt":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was initially created.\n\nThis read-only field is automatically set during resource creation and cannot\nbe modified. It provides an audit trail for when the resource was first added\nto the system, which can be useful for:\n\n- Resource lifecycle management\n- Audit and compliance reporting\n- Troubleshooting integration timelines\n- Identifying older resources that may need review\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\n"},"lastModified":{"type":"string","format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was most recently updated.\n\nThis read-only field is automatically updated whenever any property of the\nresource is modified. It provides an audit trail that can be used for:\n\n- Determining if a resource has changed since it was last reviewed\n- Monitoring configuration changes during troubleshooting\n- Implementing cache invalidation strategies\n- Synchronizing related resources based on modification time\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix)\nand will always be equal to or later than the createdAt timestamp.\n"},"deletedAt":{"type":["string","null"],"format":"date-time","readOnly":true,"description":"Timestamp indicating when the resource was marked for deletion.\n\nWhen this field is present and contains a valid timestamp, it indicates\nthat the resource has been soft-deleted (moved to the recycle bin) but not\nyet permanently removed from the system. This allows for recovery of\naccidentally deleted resources within a specified retention period.\n\nThe deletedAt timestamp enables:\n- Filtering deleted resources from active resource listings\n- Implementing time-based retention policies for permanent deletion\n- Tracking deletion events for audit and compliance purposes\n- Resource recovery workflows with clear timeframes\n\nThe timestamp is recorded in ISO 8601 format with UTC timezone (Z suffix).\nWhen null or absent, the resource is considered active.\n"}},"required":["_id"]},"IAResourceResponse":{"type":"object","description":"Integration app response fields for resources that are part of integration apps","properties":{"_integrationId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the specific integration instance that contains this resource.\n\nThis field is only populated for resources that are part of an integration app\ninstallation. It contains the unique identifier (_id) of the integration\nresource that was installed in the account.\n\nThe integration instance represents a specific installed instance of an\nintegration app, with its own configuration, settings, and runtime environment.\n\nThis reference enables:\n- Tracing the resource back to its parent integration instance\n- Permission and access control based on integration ownership\n- Lifecycle management (enabling/disabling, updating, or uninstalling)\n"},"_connectorId":{"type":"string","format":"objectId","readOnly":true,"description":"Reference to the integration app that defines this resource.\n\nThis field is only populated for resources that are part of an integration app.\nIt contains the unique identifier (_id) of the integration app (connector)\nthat defines the structure, behavior, and templates for this resource.\n\nThe integration app is the published template that can be installed\nmultiple times across different accounts, with each installation creating\na separate integration instance (referenced by _integrationId).\n\nThis reference enables:\n- Identifying the source integration app for this resource\n- Determining which template version is being used\n- Linking to documentation, support, and marketplace information\n"}}},"Error":{"type":"object","description":"Standard error response envelope returned by integrator.io APIs.","properties":{"errors":{"type":"array","description":"List of errors that occurred while processing the request.","items":{"type":"object","properties":{"code":{"oneOf":[{"type":"string"},{"type":"integer"}],"description":"Machine-readable error code. Usually a string like\n`invalid_ref`, `missing_required_field`, or `unauthorized`;\nmay be an **integer** when the error mirrors an upstream HTTP\nstatus (e.g. `500`) — most commonly returned by connection-ping\nand adaptor-proxy responses."},"message":{"type":"string","description":"Human-readable description of the error."},"field":{"type":"string","description":"Optional pointer to the document field that caused the error.\nUsed by structural validation errors (`missing_required_field`,\n`invalid_ref`) to indicate which field is at fault\n(e.g. `_id`, `type`, `http.baseURI`)."},"source":{"type":"string","description":"Optional origin layer for the error — e.g. `application` when\nthe error came from the remote system the adaptor called,\n`connector` when the adaptor itself rejected the request."}},"required":["message"]}}},"required":["errors"]}},"responses":{"400-bad-request":{"description":"Bad request. The server could not understand the request because of malformed syntax or invalid parameters.\n","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Error"}}}},"401-unauthorized":{"description":"Unauthorized. The request lacks a valid bearer token, or the provided token\nfailed to authenticate.\n\nNote: the 401 response is produced by the auth middleware **before** the\nrequest reaches the endpoint handler, so it does **not** follow the\nstandard `{errors: [...]}` envelope. Instead the body is a bare\n`{message: string}` object with no `code`, no `errors` array. Callers\nhandling 401s should key off the HTTP status and the `message` string,\nnot try to destructure an `errors[]`.","content":{"application/json":{"schema":{"type":"object","properties":{"message":{"type":"string","description":"Human-readable description of the auth failure. Known values:\n- `\"Unauthorized\"` — no `Authorization` header on the request.\n- `\"Bearer Authentication Failed\"` — header present but token\n  is invalid, revoked, or expired."}},"required":["message"]}}}}}},"paths":{"/v1/invite":{"post":{"summary":"Invite a user to the account","description":"Invites a user to the account.\n\nThe user will appear in the users list and `accepted` will become true after the invite is accepted.","operationId":"inviteUser","tags":["Users"],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/InviteRequest"}}}},"responses":{"200":{"description":"Invitation created/updated successfully","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Response"}}}},"400":{"$ref":"#/components/responses/400-bad-request"},"401":{"$ref":"#/components/responses/401-unauthorized"}}}}}}
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://developer.celigo.com/api/api-reference/users.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
