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

# Teams

> Manage teams, team membership, and invitations.

All requests use a single endpoint: `POST https://api.helpgenie.ai/v1` with `resource: "teams"`.

## Access control

<Note>
  Access varies by action. Team owners and internal admins have full access to all actions. Team members have read-only access to `get` and `members`. Any authenticated user can create a team.
</Note>

| Action                | Any user | Team member     | Team owner | Admin |
| --------------------- | -------- | --------------- | ---------- | ----- |
| `get`                 | No       | Yes (read-only) | Yes        | Yes   |
| `create`              | Yes      | --              | --         | Yes   |
| `update`              | No       | No              | Yes        | Yes   |
| `delete`              | No       | No              | Yes        | Yes   |
| `members`             | No       | Yes             | Yes        | Yes   |
| `invite`              | No       | No              | Yes        | Yes   |
| `invitations`         | No       | No              | Yes        | Yes   |
| `cancel-invite`       | No       | No              | Yes        | Yes   |
| `resend-invite`       | No       | No              | Yes        | Yes   |
| `remove-member`       | No       | No              | Yes        | Yes   |
| `get-branding`        | No       | Yes             | Yes        | Yes   |
| `update-branding`     | No       | No              | Yes        | Yes   |
| `clear-branding`      | No       | No              | Yes        | Yes   |
| `share-genie`         | No       | No              | Yes        | Yes   |
| `grant-genie-access`  | No       | No              | Yes        | Yes   |
| `remove-genie-access` | No       | No              | Yes        | Yes   |

<Warning>
  Only team owners and internal admins can manage invitations and remove members. Regular team members have read-only access to `get` and `members` actions only.
</Warning>

### Team management workflow

<Steps>
  <Step title="Create a team">
    Use the `create` action to set up a new team. The authenticated user automatically becomes the team owner.
  </Step>

  <Step title="Invite members">
    Use the `invite` action to send invitations by email. Track pending invitations with the `invitations` action.
  </Step>

  <Step title="Members accept">
    Invited users accept the invitation to join the team. Their profile is updated with the `team_id`.
  </Step>

  <Step title="Manage the team">
    Use `members` to view the roster, `remove-member` to remove users, and `cancel-invite` to revoke pending invitations.
  </Step>
</Steps>

***

## Get a team

Retrieves a specific team by ID with all team members.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"get"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="team" type="object">
      <Expandable title="properties">
        <ResponseField name="id" type="number" />

        <ResponseField name="name" type="string" />

        <ResponseField name="brand" type="string" />

        <ResponseField name="branding" type="object" />

        <ResponseField name="owner_id" type="string" />
      </Expandable>
    </ResponseField>

    <ResponseField name="members" type="object[]">
      <Expandable title="properties">
        <ResponseField name="id" type="string" />

        <ResponseField name="full_name" type="string" />

        <ResponseField name="email" type="string" />

        <ResponseField name="avatar_url" type="string" />

        <ResponseField name="role" type="string">
          Either `"Owner"` or `"Member"`.
        </ResponseField>
      </Expandable>
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{
    team: Team;
    members: TeamMember[];
  }>({
    resource: "teams",
    action: "get",
    id: "123",
  });
  ```
</CodeGroup>

***

## Create a team

Creates a new team. The authenticated user automatically becomes the team owner.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"create"`
</ParamField>

<ParamField body="data" type="object" required>
  <Expandable title="properties">
    <ParamField body="name" type="string" required>
      Team name.
    </ParamField>

    <ParamField body="brand" type="string" required>
      Team brand name.
    </ParamField>

    <ParamField body="branding" type="object">
      Branding configuration (e.g. colors, logos).
    </ParamField>
  </Expandable>
</ParamField>

### Response (status 201)

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="team" type="object">
      The newly created team object.
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{ team: Team }>(
    {
      resource: "teams",
      action: "create",
      data: {
        name: "Marketing Team",
        brand: "ACME Corp",
        branding: { color: "#FF0000" },
      },
    },
    201
  );
  ```
</CodeGroup>

***

## Update a team

Updates team settings such as name, brand, and branding.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"update"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

<ParamField body="data" type="object" required>
  <Expandable title="properties">
    <ParamField body="name" type="string">
      Updated team name.
    </ParamField>

    <ParamField body="brand" type="string">
      Updated brand name.
    </ParamField>

    <ParamField body="branding" type="object">
      Updated branding configuration.
    </ParamField>

    <ParamField body="owner_id" type="string">
      Admin only. Transfers team ownership to this user ID. The new owner must already be a member of the team and cannot be the current owner.
    </ParamField>
  </Expandable>
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="team" type="object">
      The updated team object.
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{ team: Team }>({
    resource: "teams",
    action: "update",
    id: "123",
    data: {
      name: "Updated Team Name",
    },
  });
  ```
</CodeGroup>

***

## Delete a team

Permanently deletes a team and removes all members.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"delete"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="success" type="boolean" />

    <ResponseField name="message" type="string">
      Deletion result description.
    </ResponseField>

    <ResponseField name="errors" type="string[]">
      Array of any cleanup errors, if applicable.
    </ResponseField>
  </Expandable>
</ResponseField>

<Warning>
  This permanently deletes the team and removes all member associations.
</Warning>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{
    success: boolean;
    message: string;
  }>({
    resource: "teams",
    action: "delete",
    id: "123",
  });
  ```
</CodeGroup>

***

## List team members

Retrieves all members of a team.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"members"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="members" type="object[]">
      <Expandable title="properties">
        <ResponseField name="id" type="string" />

        <ResponseField name="full_name" type="string" />

        <ResponseField name="email" type="string" />

        <ResponseField name="avatar_url" type="string" />

        <ResponseField name="role" type="string">
          Either `"Owner"` or `"Member"`.
        </ResponseField>
      </Expandable>
    </ResponseField>

    <ResponseField name="count" type="number">
      Total number of members.
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{
    members: TeamMember[];
    count: number;
  }>({
    resource: "teams",
    action: "members",
    id: "123",
  });
  ```
</CodeGroup>

***

## Invite a member

Sends a team invitation to an email address. If a previous invitation exists for the same email, it is replaced. The invitee receives an email and must accept before joining.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"invite"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

<ParamField body="data" type="object" required>
  <Expandable title="properties">
    <ParamField body="email" type="string" required>
      Email address of the person to invite.
    </ParamField>

    <ParamField body="impersonatedUserId" type="string">
      Admin only. Sends the invitation on behalf of this user ID.
    </ParamField>
  </Expandable>
</ParamField>

### Response (status 201)

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="invitation" type="object">
      <Expandable title="properties">
        <ResponseField name="id" type="string">
          Invitation UUID.
        </ResponseField>

        <ResponseField name="email" type="string">
          Email address the invitation was sent to.
        </ResponseField>

        <ResponseField name="status" type="string">
          Always `"pending"` for a newly created invitation.
        </ResponseField>

        <ResponseField name="invited_at" type="string">
          ISO 8601 timestamp of when the invitation was sent.
        </ResponseField>

        <ResponseField name="accepted_at" type="string | null">
          ISO 8601 timestamp of acceptance, or `null` if not yet accepted.
        </ResponseField>

        <ResponseField name="expires_at" type="string | null">
          ISO 8601 expiry timestamp, or `null` if no expiry is set.
        </ResponseField>
      </Expandable>
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{ invitation: TeamInvitation }>({
    resource: "teams",
    action: "invite",
    id: "123",
    data: {
      email: "user@example.com",
    },
  });
  ```

  ```bash cURL theme={null}
  curl -X POST https://api.helpgenie.ai/v1/teams \
    -H "Authorization: Bearer hg_live_YOUR_KEY" \
    -H "Content-Type: application/json" \
    -d '{
      "resource": "teams",
      "action": "invite",
      "id": "123",
      "data": {
        "email": "newmember@example.com"
      }
    }'
  ```
</CodeGroup>

***

## List pending invitations

Retrieves all pending invitations for a team.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"invitations"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="invitations" type="object[]">
      <Expandable title="properties">
        <ResponseField name="id" type="string">
          Invitation UUID.
        </ResponseField>

        <ResponseField name="email" type="string">
          Invited email address.
        </ResponseField>

        <ResponseField name="status" type="string">
          Current invitation status (e.g. `"pending"`).
        </ResponseField>

        <ResponseField name="invited_at" type="string">
          ISO 8601 timestamp of when the invitation was sent.
        </ResponseField>

        <ResponseField name="accepted_at" type="string | null">
          ISO 8601 timestamp of acceptance, or `null` if not yet accepted.
        </ResponseField>

        <ResponseField name="expires_at" type="string | null">
          ISO 8601 expiry timestamp, or `null` if no expiry is set.
        </ResponseField>
      </Expandable>
    </ResponseField>

    <ResponseField name="count" type="number">
      Number of pending invitations.
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{
    invitations: TeamInvitation[];
    count: number;
  }>({
    resource: "teams",
    action: "invitations",
    id: "123",
  });
  ```
</CodeGroup>

***

## Cancel an invitation

Cancels a pending team invitation.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"cancel-invite"`
</ParamField>

<ParamField body="id" type="string" required>
  The invitation UUID.
</ParamField>

<ParamField body="data" type="object" required>
  <Expandable title="properties">
    <ParamField body="teamId" type="number" required>
      The team ID the invitation belongs to.
    </ParamField>
  </Expandable>
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="success" type="boolean" />
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{ success: boolean }>({
    resource: "teams",
    action: "cancel-invite",
    id: "invitation-uuid",
    data: {
      teamId: 123,
    },
  });
  ```
</CodeGroup>

***

## Resend an invitation

Refreshes the timestamp on a pending invitation, triggering a new invitation email to the invitee.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"resend-invite"`
</ParamField>

<ParamField body="id" type="string" required>
  The invitation UUID to resend.
</ParamField>

<ParamField body="data" type="object" required>
  <Expandable title="properties">
    <ParamField body="teamId" type="number" required>
      The team ID the invitation belongs to.
    </ParamField>

    <ParamField body="impersonatedUserId" type="string">
      Admin only. Perform this action on behalf of this user ID.
    </ParamField>
  </Expandable>
</ParamField>

<Note>
  Only invitations with `status: "pending"` can be resent. Returns 404 if the invitation is not found or is no longer pending.
</Note>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="invitation" type="object">
      <Expandable title="properties">
        <ResponseField name="id" type="string">
          Invitation UUID.
        </ResponseField>

        <ResponseField name="email" type="string">
          Email address the invitation was sent to.
        </ResponseField>

        <ResponseField name="status" type="string">
          Always `"pending"` for a resent invitation.
        </ResponseField>

        <ResponseField name="invited_at" type="string">
          ISO 8601 timestamp updated to the time the invitation was resent.
        </ResponseField>

        <ResponseField name="accepted_at" type="string | null">
          ISO 8601 timestamp of acceptance, or `null` if not yet accepted.
        </ResponseField>

        <ResponseField name="expires_at" type="string | null">
          ISO 8601 expiry timestamp, or `null` if no expiry is set.
        </ResponseField>
      </Expandable>
    </ResponseField>
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{ invitation: TeamInvitation }>({
    resource: "teams",
    action: "resend-invite",
    id: "invitation-uuid",
    data: {
      teamId: 123,
    },
  });
  ```

  ```bash cURL theme={null}
  curl -X POST https://api.helpgenie.ai/v1 \
    -H "Content-Type: application/json" \
    -H "x-api-key: hg_live_YOUR_KEY" \
    -d '{
      "resource": "teams",
      "action": "resend-invite",
      "id": "invitation-uuid",
      "data": {
        "teamId": 123
      }
    }'
  ```
</CodeGroup>

***

## Remove a member

Removes a member from a team.

<ParamField body="resource" type="string" required>
  Must be `"teams"`
</ParamField>

<ParamField body="action" type="string" required>
  Must be `"remove-member"`
</ParamField>

<ParamField body="id" type="string" required>
  The team ID.
</ParamField>

<ParamField body="data" type="object" required>
  <Expandable title="properties">
    <ParamField body="memberId" type="string" required>
      The user UUID of the member to remove.
    </ParamField>
  </Expandable>
</ParamField>

### Response

<ResponseField name="success" type="boolean" />

<ResponseField name="data" type="object">
  <Expandable title="properties">
    <ResponseField name="success" type="boolean" />
  </Expandable>
</ResponseField>

<CodeGroup>
  ```typescript Example request theme={null}
  const response = await ApiService.invoke<{ success: boolean }>({
    resource: "teams",
    action: "remove-member",
    id: "123",
    data: {
      memberId: "user-uuid",
    },
  });
  ```
</CodeGroup>

***

## Branding actions

### `get-branding`

Returns the team's branding configuration.

**Parameters** — none (uses the authenticated user's team).

***

### `update-branding`

Updates the team's branding (colors, logo, gradient settings). Team owner or admin only.

**Parameters**

| Field             | Type    | Description                 |
| ----------------- | ------- | --------------------------- |
| `primaryColor`    | string  | Primary brand color (hex)   |
| `secondaryColor`  | string  | Secondary brand color (hex) |
| `logoUrl`         | string  | URL of the brand logo       |
| `gradientEnabled` | boolean | Whether gradient is enabled |

***

### `clear-branding`

Resets all branding fields to null. Team owner or admin only.

**Parameters** — none.

***

## Genie sharing actions

### `share-genie`

Shares a Genie with team members.

**Parameters**

| Field     | Type   | Required | Description         |
| --------- | ------ | -------- | ------------------- |
| `agentId` | string | Yes      | Genie UUID to share |

***

### `grant-genie-access`

Grants a team member access to a specific Genie.

**Parameters**

| Field     | Type   | Required | Description                      |
| --------- | ------ | -------- | -------------------------------- |
| `agentId` | string | Yes      | Genie UUID                       |
| `userId`  | string | Yes      | Team member UUID to grant access |

***

### `remove-genie-access`

Revokes a team member's access to a specific Genie.

**Parameters**

| Field     | Type   | Required | Description                |
| --------- | ------ | -------- | -------------------------- |
| `agentId` | string | Yes      | Genie UUID                 |
| `userId`  | string | Yes      | Team member UUID to revoke |

***

## Error responses

| Status | Code               | Description                             |
| ------ | ------------------ | --------------------------------------- |
| 400    | `VALIDATION_ERROR` | Missing or invalid required parameters  |
| 401    | `UNAUTHORIZED`     | No valid authentication token           |
| 403    | `FORBIDDEN`        | User lacks permission for the operation |
| 404    | `NOT_FOUND`        | Team or resource not found              |
| 500    | `INTERNAL_ERROR`   | Server error during processing          |
