# Reseller

Oh Dear's reseller program allows agencies, hosting providers, and consultants to offer website monitoring services to their clients under their own brand. As a reseller, you can use the API to create and manage multiple client teams, each with their own [monitors](/docs/api/monitors.md) and users.

To become a reseller, [contact us](mailto:support@ohdear.app) to discuss your needs and how our program can fit into your business model.

All reseller endpoints are prefixed with `/api/reseller/{resellerTeamId}/` -- replace `{resellerTeamId}` with your reseller team's ID.

**Example request:**

```bash
$ OHDEAR_TOKEN="your API token"
$ curl https://ohdear.app/api/reseller/11111/managed-teams \
    -H "Authorization: Bearer $OHDEAR_TOKEN" \
    -H 'Accept: application/json' \
    -H 'Content-Type: application/json'
```

All endpoints use the same [authentication](/docs/api/introduction.md#authenticate-against-the-api) as the regular Oh Dear API.

## Managed team response fields
<!-- toc: Response fields -->

Every managed team endpoint returns an object with these fields:

```json
{
  "id": 12345,
  "name": "Client Company",
  "timezone": "UTC",
  "created_at": "2024-01-15T10:30:00.000000Z",
  "monitors_count": 5
}
```

- `id`: unique identifier for the team
- `name`: the team name
- `timezone`: the team's timezone
- `created_at`: when the team was created (UTC)
- `monitors_count`: number of [monitors](/docs/api/monitors.md) in this team

## Get a managed team
<!-- toc: Get one -->

<pre>GET /api/reseller/{resellerTeamId}/managed-teams/{managedTeamId}</pre>

Returns a single managed team by its ID. The response follows the [managed team shape](#managed-team-response-fields) above.

## List all managed teams
<!-- toc: List all -->

<pre>GET /api/reseller/{resellerTeamId}/managed-teams</pre>

Returns a paginated list of all teams managed by your reseller account. Each item follows the same [managed team shape](#managed-team-response-fields) above.

**Query parameters:**

- `filter[name]` (string, optional) -- filter by team name (partial match)
- `filter[timezone]` (string, optional) -- filter by timezone (exact match)
- `sort` (string, optional) -- sort by `name` or `created_at` (default ordering is by team ID)
- `page[number]` (integer, optional) -- page number for pagination
- `page[size]` (integer, optional) -- results per page (default `200`, max `1000`)

## Create a managed team
<!-- toc: Creating -->

<pre>POST /api/reseller/{resellerTeamId}/managed-teams</pre>

Creates a new team managed by your reseller account.

**Request body (JSON):**

- `name` (string, required) -- the name of the team
- `timezone` (string, optional) -- team timezone (defaults to reseller's timezone)
- `default_uptime_check_location` (string, optional) -- default [uptime check location](/docs/api/data-types.md#uptime-check-locations) for new monitors

Returns the [managed team object](#managed-team-response-fields).

## Update a managed team
<!-- toc: Updating -->

<pre>PUT /api/reseller/{resellerTeamId}/managed-teams/{managedTeamId}</pre>

Updates the details of an existing managed team. All fields are optional.

**Request body (JSON):**

- `name` (string, optional) -- the new team name
- `timezone` (string, optional) -- team timezone
- `default_uptime_check_location` (string, optional) -- default [uptime check location](/docs/api/data-types.md#uptime-check-locations) for new monitors

Returns the updated [managed team object](#managed-team-response-fields).

## Decouple a managed team
<!-- toc: Decoupling -->

<pre>POST /api/reseller/{resellerTeamId}/managed-teams/{managedTeamId}/decouple</pre>

Removes the reseller relationship from a managed team, making it independent.

When decoupling:
- The team is no longer managed by your reseller account
- All monitors and configuration are retained
- The team no longer inherits your reseller subscription status; monitoring behavior depends on the managed team's own subscription

> **Handing off to an end-customer:** the Oh Dear app's reseller settings page offers a "decouple" action that also transfers ownership of the managed team to an end-customer email. The new owner receives an email with a password-setup link, sets their own password, and takes over the team. The API endpoint above does not perform this handoff, it only removes the reseller relationship.

## Delete a managed team
<!-- toc: Deleting -->

<pre>DELETE /api/reseller/{resellerTeamId}/managed-teams/{managedTeamId}</pre>

Deletes a managed team and all its associated data. This action cannot be undone. All monitors are deleted, all users are detached, and all pending invitations are revoked.

Returns `204 No Content` on success.

## Add a user to a managed team
<!-- toc: Add user -->

<pre>POST /api/reseller/{resellerTeamId}/managed-teams/{managedTeamId}/users</pre>

Adds a user to a managed team. If the user doesn't have an Oh Dear account yet, one will be created.

**Request body (JSON):**

- `email` (string, required) -- email address of the user
- `name` (string, required) -- full name of the user
- `role` (string, required) -- user role. Possible values: `admin`, `member`, `guest`

User roles:
- `admin` -- can perform any action
- `member` -- can perform all actions except team management
- `guest` -- can perform all actions except creating, updating, or deleting monitors

## Generate a login link
<!-- toc: Login link -->

<pre>POST /api/reseller/{resellerTeamId}/managed-teams/{managedTeamId}/users/{userId}/generate-login-link</pre>

Generates a secure, time-limited login link for a user of a managed team. The link is valid for 5 minutes.

Here's what the response looks like:

```json
{
  "login_url": "https://ohdear.app/reseller-login/98765/12345?expires=1640995200&signature=abc123...",
  "valid_until": "2025-01-01 12:05:00"
}
```

- `login_url`: the one-time login URL
- `valid_until`: when the link expires (UTC)

## Managing monitors

Once you've created managed teams, use the standard [monitors API](/docs/api/monitors.md) to manage monitors for those teams. Pass the managed team's ID as the `team_id` when [creating monitors](/docs/api/monitors.md#add-a-monitor-through-the-api).
