# Get a client Source: https://docs.salesask.com/api-reference/clients/get-a-client /openapi.json get /v1/clients/{id} Fetch a single client by its document id. To look up by external CRM id or email, use GET /v1/clients?crmEntityId= or GET /v1/clients?email=. # List clients Source: https://docs.salesask.com/api-reference/clients/list-clients /openapi.json get /v1/clients Returns clients in your organization, newest first. Supports opaque cursor pagination. Pass `crmEntityId` or `email` to look up a single client (returns the list shape with 0 or 1 client). Email lookup is an exact, case-sensitive match and returns at most one client when several share an address. # Recording integration updated Source: https://docs.salesask.com/api-reference/recording-integration-updated /openapi.json webhook recording.integration_updated Fired when a recording is synced to a CRM via the integration sync action. Only delivered to webhooks that explicitly subscribe to this event. Your endpoint must return a 2xx response. # Recording processed Source: https://docs.salesask.com/api-reference/recording-processed /openapi.json webhook recording.processed Fired when a recording finishes AI analysis. Delivered to webhooks subscribed to this event whose trigger matches the recording source. Your endpoint must return a 2xx response. # Get a recording Source: https://docs.salesask.com/api-reference/recordings/get-a-recording /openapi.json get /v1/recordings/{id} Returns a single processed recording by ID, including all AI-generated fields. # Get a recording transcript Source: https://docs.salesask.com/api-reference/recordings/get-a-recording-transcript /openapi.json get /v1/recordings/{id}/transcript Returns the recording's transcript as an ordered list of utterances with resolved speaker names. The transcript is an empty array until the recording has been processed. # List recordings Source: https://docs.salesask.com/api-reference/recordings/list-recordings /openapi.json get /v1/recordings Returns processed recordings for your organization, ordered by most recent first. # Create or update an appointment Source: https://docs.salesask.com/api-reference/scheduled-tasks/create-or-update-an-appointment /openapi.json post /v1/scheduled-tasks Creates or updates a scheduled appointment by event_id (upsert). # Delete an appointment Source: https://docs.salesask.com/api-reference/scheduled-tasks/delete-an-appointment /openapi.json delete /v1/scheduled-tasks/{event_id} # Get an appointment by event ID Source: https://docs.salesask.com/api-reference/scheduled-tasks/get-an-appointment-by-event-id /openapi.json get /v1/scheduled-tasks/{event_id} # List appointments Source: https://docs.salesask.com/api-reference/scheduled-tasks/list-appointments /openapi.json get /v1/scheduled-tasks Returns scheduled appointments for your organization. # Update an appointment Source: https://docs.salesask.com/api-reference/scheduled-tasks/update-an-appointment /openapi.json put /v1/scheduled-tasks/{event_id} # Get statistics Source: https://docs.salesask.com/api-reference/stats/get-statistics /openapi.json get /v1/stats Aggregated call metrics grouped by user or team, over processed recordings. `groupBy` is required. Optionally scope by date range, teams, emails, AI template, and tags. Unknown emails are returned in `errors[]` rather than failing the request. # List teams Source: https://docs.salesask.com/api-reference/teams/list-teams /openapi.json get /v1/teams Returns all teams in your organization. Member UIDs are replaced with emails so internal IDs are never exposed. Use the returned team `id` values with GET /v1/stats?teamIds=... # List users Source: https://docs.salesask.com/api-reference/users/list-users /openapi.json get /v1/users Returns all active users in your organization with their activity data. # List webhooks Source: https://docs.salesask.com/api-reference/webhooks/list-webhooks /openapi.json get /v1/webhooks Returns all registered webhook URLs for your organization. # Send a test webhook Source: https://docs.salesask.com/api-reference/webhooks/send-a-test-webhook /openapi.json post /v1/webhooks/test POSTs a test payload to the given URL using the provided recording. # Scheduled tasks Source: https://docs.salesask.com/guides/scheduled-tasks Push upcoming appointments into Sales Ask so recordings can be matched to your CRM jobs. ## Overview When your CRM books an appointment, you can push it to Sales Ask via `POST /v1/scheduled-tasks`. Appointments are keyed by your **event\_id** (e.g. CRM job or calendar event ID). Use the same **event\_id** to update or delete the appointment later. Sales Ask stores the appointment with the assigned rep (resolved from **user\_email**). When that rep records a call around the appointment time, Sales Ask can match the recording and include your event\_id in webhook payloads so your system can look up the original job. ## Create or update an appointment (upsert) Send `event_id`, `user_email`, and `start_time`. If an appointment with that `event_id` already exists for your organization, it is updated; otherwise it is created. ```bash theme={null} curl -X POST https://integrations.salesask.com/v1/scheduled-tasks \ -H "x-api-key: " \ -H "Content-Type: application/json" \ -d '{ "event_id": "CRM-JOB-9871", "user_email": "rep@company.com", "start_time": "2026-03-01T14:00:00.000Z", "end_time": "2026-03-01T15:00:00.000Z", "title": "Discovery call", "customer": { "id": "cust_123", "name": "John Doe", "email": "john@example.com" } }' ``` All times must be UTC date-time strings (e.g. `2026-03-01T14:00:00.000Z`). ```json theme={null} { "appointment": { "id": "task_abc123", "event_id": "CRM-JOB-9871", "startTime": "2026-03-01T14:00:00.000Z", "customerName": "John Doe", "customerEmail": "john@example.com", "scheduledAt": "2026-03-01T14:15:00.000Z", "status": "scheduled", "metadata": {}, "createdAt": "2026-02-28T09:00:00.000Z", "updatedAt": "2026-02-28T09:00:00.000Z" } } ``` ### Required fields | Field | Type | Description | | ------------ | ------------ | -------------------------------------------------------------------------------------------------- | | `event_id` | string | Your CRM/external event ID. Unique per organization; used for upsert and for matching in webhooks. | | `user_email` | string | Sales rep email. Must be an active member of your organization; resolved to `repUid`. | | `start_time` | string (UTC) | Appointment start (e.g. `2026-03-01T14:00:00.000Z`). | ### Optional fields | Field | Type | Description | | ---------- | ------------ | ------------------------------------------------------------------------- | | `end_time` | string (UTC) | Appointment end. | | `title` | string | Appointment title. | | `customer` | object | `id`, `name`, `email`; stored as customerId, customerName, customerEmail. | Always set `event_id` to your CRM's job or appointment ID. This is what you will receive in webhook payloads when a matching recording is processed. ## Update an appointment (partial) Update only the fields you send. Path parameter is your **event\_id**. ```bash theme={null} curl -X PUT https://integrations.salesask.com/v1/scheduled-tasks/CRM-JOB-9871 \ -H "x-api-key: " \ -H "Content-Type: application/json" \ -d '{ "start_time": "2026-03-01T15:00:00.000Z", "customer": { "name": "Jane Doe" } }' ``` ## List appointments ```bash theme={null} curl "https://integrations.salesask.com/v1/scheduled-tasks?fromDate=2026-03-01&toDate=2026-03-31" \ -H "x-api-key: " ``` Filter by rep email: ```bash theme={null} curl "https://integrations.salesask.com/v1/scheduled-tasks?user_email=rep@company.com" \ -H "x-api-key: " ``` Results are paginated. Use `nextCursor` from the response as `startAfter` for the next page. Optional query params: `fromDate`, `toDate`, `user_email`, `limit` (1–100, default 25), `startAfter`. ## Get one appointment ```bash theme={null} curl "https://integrations.salesask.com/v1/scheduled-tasks/CRM-JOB-9871" \ -H "x-api-key: " ``` ## Delete an appointment Use your **event\_id** in the path: ```bash theme={null} curl -X DELETE https://integrations.salesask.com/v1/scheduled-tasks/CRM-JOB-9871 \ -H "x-api-key: " ``` ## Finding the rep The `user_email` must match an active user in your organization. The API resolves it to an internal rep identifier; no rep IDs are returned in API responses. # Webhooks Source: https://docs.salesask.com/guides/webhooks Receive push notifications when recordings are processed or synced to a CRM. ## How it works Sales Ask sends a `POST` request to every active webhook URL registered for your organization when a subscribed event occurs. No polling required. ```text theme={null} Sales Ask ──POST──▶ https://your-crm.com/hooks/salesask ``` Webhook URLs and event subscriptions are configured in Sales Ask under **Settings → Organization → Webhooks**. ## Events | Event | Fired when | | ------------------------------- | -------------------------------------------------------------------------------------------- | | `recording.processed` | AI analysis finishes (transcription, speaker identification, notes, coaching, action items). | | `recording.integration_updated` | A recording is synced to a CRM via the integration sync action. | Organizations with no explicit event subscription default to `recording.processed` only. To receive `recording.integration_updated` events, explicitly subscribe via the Events dropdown in webhook settings. ## Webhook envelope Every webhook delivery wraps the payload in an envelope with the event name: ```json theme={null} { "event": "recording.processed", "data": { "id": "abc123", "name": "Call with John Doe", "actionItems": "Action items from meeting\n- Follow up on quote\nClient action items\n- Send contract", "notes": "Rep discussed pricing and timeline. Customer showed strong buying intent.", "meetingUrl": "https://app.salesask.com/meetings/abc123", "process": "1. Discovery question: \nAnswer: Yes\n\nProcess Summary: Good discovery.", "processFollowed": 3, "processMissed": 1, "processTotal": 4 } } ``` ### Payload fields (inside `data`) | Field | Type | Description | | ----------------- | ------- | ----------------------------------------------------------------- | | `id` | string | Recording ID. Use with `GET /v1/recordings/:id` for full details. | | `name` | string | Recording name. | | `actionItems` | string | Formatted action items text (explicit + client). | | `notes` | string | Plain-text notes from AI analysis. | | `meetingUrl` | string | Link to the recording in the Sales Ask app. | | `process` | string | Process Q\&A and summary text. | | `processFollowed` | integer | Count of process questions answered yes. | | `processMissed` | integer | Count of process questions not answered yes. | | `processTotal` | integer | Total process questions. | Custom fields from the recording are merged at the top level of `data`. ### recording.processed Fired after AI analysis completes. Only delivered to webhooks whose trigger matches the recording source (or trigger is set to `all`). ### recording.integration\_updated Fired after a recording is synced to a CRM. The `data` payload is the same shape as `recording.processed`. ## Responding to events Your endpoint must return a **2xx** status to acknowledge receipt. Sales Ask does not retry failed deliveries, so if your endpoint is down you will miss the event. Requests time out after 10 seconds. Respond quickly and offload heavy work to a background job. ## List webhooks Returns all webhook URLs registered for your organization (configured in Sales Ask). ```bash theme={null} curl https://integrations.salesask.com/v1/webhooks \ -H "x-api-key: " ``` Response includes `id`, `url`, `active`, `trigger`, and `events` for each webhook. ## Send a test webhook POST a test payload to a URL using a recording you provide. The recording must have `status: "processed"` (e.g. from `GET /v1/recordings` or `GET /v1/recordings/:id`). ```bash theme={null} curl -X POST https://integrations.salesask.com/v1/webhooks/test \ -H "x-api-key: " \ -H "Content-Type: application/json" \ -d '{ "url": "https://your-crm.com/hooks/salesask", "recording": { "id": "rec_123", "status": "processed", ... } }' ``` The payload sent to `url` is the same shape as the outbound webhook payload above (integration format). Use this to verify your endpoint without waiting for a real processing event. # Introduction Source: https://docs.salesask.com/introduction The Sales Ask API lets you pull call recordings, push appointments, and receive webhook events when recordings are processed. ## What you can do The API is organized around three main resources: Pull processed recordings with AI-generated notes, summaries, coaching, and action items. Push upcoming appointments so Sales Ask can match them to recordings after the call. Subscribe to `recording.processed` and `recording.integration_updated` events to get notified when recordings are analyzed or synced to a CRM. ## Authentication Every request requires your organization API key in the `x-api-key` header. Keys are scoped to an organization — all data returned is filtered to your organization automatically. ```bash theme={null} x-api-key: ``` API keys are generated by admins in the Sales Ask app under **Settings → Organization → Organization API Key**. See [Quickstart](/quickstart) for step-by-step instructions. ## Base URL ``` https://integrations.salesask.com ``` ## Response format All endpoints return JSON. Successful responses use HTTP `200` with a top-level key matching the resource name. Errors return an appropriate HTTP status code with a `message` field. ```json theme={null} { "message": "Recording not found" } ``` ## Timestamps All timestamps are returned as ISO 8601 strings in UTC, for example `2026-03-01T14:22:00.000Z`. Duration fields (such as `duration`, `avgDurationMs`) are in milliseconds. # Quickstart Source: https://docs.salesask.com/quickstart Get your API key and make your first request in under five minutes. ## Step 1: Get your API key You must be an **admin** of your Sales Ask organization. 1. Log in to [integrations.salesask.com](https://integrations.salesask.com) 2. Go to **Settings → Organization** 3. Scroll to the **Organization API Key** section 4. Click the refresh icon to generate a key 5. Copy the key using the copy button next to the field Regenerating your key will immediately invalidate any existing integrations using the old key. Store it securely — it grants access to all recordings in your organization. ## Step 2: Fetch your recordings Pass the key in the `x-api-key` header. The following request returns the 10 most recent processed recordings: ```bash theme={null} curl "https://integrations.salesask.com/v1/recordings?limit=10" \ -H "x-api-key: " ``` ```json theme={null} { "recordings": [ { "id": "abc123", "name": "Call with John Doe", "status": "processed", "createdAt": "2026-03-01T14:22:00.000Z", "duration": 1800000, "summary": "Rep discussed pricing and timeline...", "recording": "https://integrations.salesask.com/meetings/abc123" } ], "nextCursor": "2026-02-28T09:10:00.000Z", "hasMore": true } ``` ## Step 3: Filter by date range Use `fromDate` and `toDate` to scope results to a specific period: ```bash theme={null} curl "https://integrations.salesask.com/v1/recordings?fromDate=2026-03-01&toDate=2026-03-31&limit=50" \ -H "x-api-key: " ``` ## Step 4: Paginate When `hasMore` is `true`, pass `nextCursor` as `startAfter` to fetch the next page: ```bash theme={null} curl "https://integrations.salesask.com/v1/recordings?startAfter=2026-02-28T09:10:00.000Z" \ -H "x-api-key: " ``` ## Next steps Send upcoming appointment data so Sales Ask can associate recordings with your CRM jobs. Get notified automatically when a recording finishes processing.