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

# Introduction

> Overview of the Daysync Integration API — what it is, how it is structured, and the conventions every endpoint follows.

The Daysync Integration API lets approved partner applications read and write tour data on behalf of a Daysync user — tours, schedules, venues, accommodation, guest lists, bulletins, and organization membership.

It is a REST/JSON API. Every call runs against Daysync's production business logic, so the same permissions, validation, and entity rules that apply inside the Daysync app apply to the API.

## Base URL

```text theme={null}
https://integration.daysync.com
```

All endpoints are versioned under the `/v1` path prefix, e.g.

```text theme={null}
GET https://integration.daysync.com/v1/organizations
```

### Two hostnames

/

The API uses two hostnames, each with a distinct purpose:

| Hostname                   | Purpose                                                                                                 |
| -------------------------- | ------------------------------------------------------------------------------------------------------- |
| `integrations.daysync.com` | Integrations Portal — OAuth authorize & token endpoints; used **only** to mint and refresh user tokens. |
| `integration.daysync.com`  | The API itself — all `/v1/*` data endpoints.                                                            |

<Warning>
  These two hostnames differ by a single letter: the **portal** is `integrations` (plural), the **API** is `integration` (singular). Send OAuth requests to the plural host and data requests to the singular one.
</Warning>

You authenticate against `integrations.daysync.com`, then call `integration.daysync.com` with the resulting token. See [Authentication](/authentication).

## Data model at a glance

Everything hangs off an **organization**. A tour belongs to one organization; days belong to one tour; day-scoped resources (schedule items, guest list entries) belong to one day.

```mermaid theme={null}
flowchart TD
    ORG["Organization<br/><i>UUID</i>"] --> TOUR["Tour<br/><i>UUID</i>"]
    ORG --> MEMBERS["Org members<br/><i>user UUIDs + roles</i>"]
    TOUR --> DAY["Day<br/><i>integer ID</i>"]
    TOUR --> TMEMBERS["Tour members & invites<br/><i>user UUIDs / invite IDs</i>"]
    TOUR --> BULLETIN["Bulletins<br/><i>string ID</i>"]
    TOUR --> ACCOM["Accommodation<br/><i>integer ID — can span multiple days</i>"]
    DAY --> ITEM["Schedule items<br/><i>integer ID</i>"]
    DAY --> GUEST["Guest list entries<br/><i>integer ID</i>"]
    DAY --> VENUE["Venues<br/><i>integer ID — linked to a day</i>"]
```

Practical consequences:

* Every integration starts with `GET /v1/organizations` to obtain an `org_id`, then `GET /v1/tours?org_id=…` for tours and their `tourDays` (the day IDs).
* Schedule and guest list routes are **day-scoped** (`/tours/{tourId}/days/{dayId}/…`); venues, accommodation, and bulletins are **tour-scoped** (`/tours/{tourId}/…`).
* Deleting a tour (or a day via [`day_list`](/endpoints/tours#edit-a-tour)) takes its children with it.

## How a request is processed

Every request passes through the same pipeline:

1. **Partner authentication** — your `x-api-key` / `x-api-secret` pair identifies and authenticates your application.
2. **User authentication** — the `Authorization: Bearer <token>` identifies the Daysync user the call acts on behalf of.
3. **Scope check** — the endpoint's required scope must be among the scopes granted to your partner application.
4. **Business rules** — subscription status, soft-delete state, and input validation are enforced before the request reaches Daysync's services.
5. **Execution** — the request runs as the authenticated user, honouring that user's roles and access.

See [Authentication](/authentication) and [Scopes & Permissions](/scopes).

## Conventions

### Content type

Requests with a body must send `Content-Type: application/json` and a valid JSON body. Malformed JSON returns `400 INVALID_JSON`. Request bodies are limited to **512 KB** (`413 PAYLOAD_TOO_LARGE` if exceeded).

### Success envelope

Every successful (`2xx`) response uses the same envelope:

```json theme={null}
{
  "status": true,
  "message": "Success",
  "data": { }
}
```

* `status` — always `true` on success.
* `message` — a human-readable result message.
* `data` — the resource payload. Shape depends on the endpoint (object, array, or `null`).

### Error envelope

Errors return a machine-readable `error` code plus a message and numeric status:

```json theme={null}
{
  "error": "INSUFFICIENT_SCOPE",
  "message": "Partner does not have the required scope: tours.read",
  "status": 403
}
```

See [Errors](/errors) for the full list of codes.

### Identifiers

| Resource         | ID type     | Example                |
| ---------------- | ----------- | ---------------------- |
| Organization     | UUID string | `org_id=2f1c…`         |
| Tour             | UUID string | `/v1/tours/2f1c…`      |
| Day              | Integer     | `/days/1843`           |
| Schedule item    | Integer     | `/schedule/items/9021` |
| Venue            | Integer     | `/venues/512`          |
| Accommodation    | Integer     | `/accommodation/318`   |
| Guest list entry | Integer     | `/guestlist/77`        |
| Bulletin         | ID string   | `/bulletins/a8e2…`     |

Tours and organizations are referenced by UUID strings; most child resources use integer IDs. Passing the wrong type generally results in a `400` or `404`.

### Field naming

ID field names are **not** consistent across resources. Most resources use `snake_case` (`tour_id`, `day_id`, `org_id`), but **Accommodation** and **Bulletins** use `camelCase` (`tourId`, `dayId`):

| Resource               | ID fields           | Case        |
| ---------------------- | ------------------- | ----------- |
| Tours (create)         | `org_id`            | snake\_case |
| Schedule (create)      | `tour_id`, `day_id` | snake\_case |
| Venues (create)        | `tour_id`, `day_id` | snake\_case |
| Guest List (create)    | `tour_id`, `day_id` | snake\_case |
| Accommodation (create) | `tourId`, `dayId`   | camelCase   |
| Bulletins (create)     | `dayId`             | camelCase   |

<Warning>
  Always check the endpoint reference for the exact field name. Using the wrong case (`tourId` where `tour_id` is expected, or vice-versa) results in a validation error or the field being silently ignored.
</Warning>

### Pagination

<Warning>
  **No pagination.** List endpoints return **all** matching records in a single response — there are no `limit` / `offset` parameters.
</Warning>

For tours with large amounts of data (hundreds of schedule items, venues, etc.), responses may be several megabytes. Plan your integration accordingly:

* Cache responses where possible.
* Avoid polling list endpoints on short intervals.
* Pagination support is planned for a future API version.

### Dates & times

Date-time fields (tour `start_date`/`end_date`, tour day `date`, schedule `start_time`/`end_time`) use **ISO 8601 / AWSDateTime** format, e.g. `2026-06-01T00:00:00Z`. Time zones are **IANA names**, e.g. `Australia/Sydney`. Accommodation check-in/check-out fields use numeric date/time values — see the [Accommodation](/endpoints/accommodation) page.

### Rate limits

<Info>
  Rate limiting is **not currently enforced**, but limits may be introduced in a future version. Design your integration to handle `429 Too Many Requests` responses gracefully — implement exponential backoff and avoid tight polling loops.
</Info>

### Retries & idempotency

The API does **not** support idempotency keys. Whether a retry is safe depends on the method:

| Method   | Retry safety                                                                                                                                             |
| -------- | -------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `GET`    | Always safe.                                                                                                                                             |
| `PUT`    | Safe — re-sending the same payload produces the same end state.                                                                                          |
| `DELETE` | Safe — resources are soft-deleted; a repeat delete is a no-op (or `404`).                                                                                |
| `POST`   | **Not safe** — every successful `POST` creates a new record. A retry after a timeout can create a **duplicate** if the first request actually succeeded. |

<Warning>
  **Network timeouts on `POST` are the dangerous case.** If your request times out, you cannot tell whether the record was created. Before retrying a `POST`, re-read the relevant list endpoint and check whether the record already exists (match on your own fields, e.g. name + day), or design your sync to tolerate and clean up duplicates.
</Warning>

Which **responses** are worth retrying:

| Response                                 | Retry?                                                                                                                             |
| ---------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------- |
| `5xx`, network timeout, connection reset | Yes — with exponential backoff (e.g. 1s → 2s → 4s, max 3 attempts). Mind the `POST` duplicate caveat above.                        |
| `429` (future)                           | Yes — back off and retry.                                                                                                          |
| `401` / `403`                            | No — fix credentials, scopes, or refresh the user token first.                                                                     |
| `400` / `404` / `402`                    | No — the request itself is wrong (or the resource/subscription state blocks it); retrying the same payload returns the same error. |

### Versioning

All endpoints are prefixed with `/v1`. When breaking changes are introduced, they will be released under a new prefix (`/v2`), and the previous version will continue to be served for a transition period so existing integrations keep working.

### Webhooks & real-time updates

The API does **not** currently support webhooks or event subscriptions. To detect changes, poll the relevant list endpoints. Webhook support is planned for a future release.

### OpenAPI specification

A machine-readable OpenAPI specification is **not yet published**. The API follows standard REST conventions and can be used with any HTTP client. Once a spec is available it will be linked here for use with Postman, Swagger UI, and client-code generators.

## Next steps

* [Quickstart](/quickstart) — make your first call in a few minutes.
* [Authentication](/authentication) — the dual auth model and OAuth flow.
* [Scopes & Permissions](/scopes) — what each scope unlocks.
* [Errors](/errors) — status codes and error handling.
* [Endpoint reference](/endpoints/organizations) — every endpoint, grouped by resource.
