From cabd2e2fc11ff4f8c0ae8b5fc3274a85047564af Mon Sep 17 00:00:00 2001 From: Waleed Date: Sat, 15 Aug 2026 18:48:46 -0700 Subject: [PATCH] feat(datadog): extend to 40 tools and align every operation with the published OpenAPI specs (#6745) * feat(datadog): add incidents, SLOs, dashboards, synthetics, Cloud SIEM, and APM tools Extends the Datadog block from 12 to 39 operations, all verified against Datadog's published OpenAPI specs: - Incidents (v2, public beta): list, get, create, update, add todo - SLOs (v1): list, get, create, update, delete, history - Dashboards (v1): list, get, create, delete - Synthetics (v1): list tests, get test, latest results, trigger, pause/resume - Cloud SIEM (v2): search signals, get signal, update triage state, assign, list detection rules - APM: search spans (v2), list Service Catalog definitions (v2) Adds tools/datadog/utils.ts so every tool builds its URL from the configured site/region and shares the JSON:API-aware error extraction, and handles the v1 flat vs v2 envelope shapes and cursor pagination per endpoint. * fix(datadog): align every operation with the published OpenAPI specs Validated all 39 shipped operations (plus the 12 pre-existing ones that had never been spec-checked) against the DataDog v1 and v2 OpenAPI schemas. - `POST /api/v2/downtime` requires `monitor_identifier`, so a downtime created without a monitor id was rejected. Default to the `*` monitor tag. - A one-time downtime schedule declares `additionalProperties: false` and accepts only `start`/`end`; the timezone moves to `display_timezone`. - `GET /api/v2/downtime` has no `monitor_id` filter, and the response carries no `disabled` attribute. Downtime ids are UUID strings, not numbers. - Drop scaffold types for operations that do not exist (metric metadata, event query, monitor update/delete/unmute, host listing) along with their fields. - Note that monitor mute is no longer published in the v1 specification. - Add browser Synthetic test results, which the browser-specific endpoint returns with its own camelCase step-count shape. - Replace every `any` with a spec-derived interface, keeping the polymorphic service-definition schema opaque. * fix(datadog): remove remaining any types and declare every returned output field Replace the six surviving `Record` request-body and response-cast sites with concrete spec-derived shapes, and declare the output fields that transformResponse already returned but outputs omitted: - create_downtime / list_downtimes: timezone, created, modified - create_monitor / get_monitor: options, creator - list_monitors: message, priority, options, created, modified, creator - query_logs: content.attributes, content.tags - update_security_signal_state / _assignee: type; assignee also gained the archiveReason/archiveComment pair its sibling already declared - query_timeseries: series gained the items shape it never described * fix(datadog): stop dropping downtime targeting inputs in the block mapping create_downtime accepts monitorTags, timezone and muteFirstRecoveryNotification, but the block exposed no inputs for them and never forwarded them. Monitor-tag targeting silently fell back to the `*` tag, so a downtime meant for one team's monitors muted every monitor in scope. Adds the three advanced sub-blocks and wires them through. Also routes list_downtimes' currentOnly through toSwitchBoolean. A switch yields the strings 'true'/'false', and 'false' is truthy, so turning the toggle off still sent current_only=true. Every other switch in the block already used the helper; this was the last raw one. * fix(datadog): correct metric type codes, stop SLO update data loss, drop unpublished mute Independent re-validation of all 39 operations against the DataDog/datadog-api-client-go generator specs (v1 and v2 openapi.yaml) rather than the client-rendered docs site. Correctness: - submit_metrics sent inverted MetricIntakeType codes (gauge as 0/unspecified, rate as 1/count, count as 2/rate), silently changing how Datadog aggregated every submitted series. The spec enum is 0 unspecified, 1 count, 2 rate, 3 gauge; an unrecognized type is now omitted so Datadog infers it. Also stops stamping an invented `resources: [{name:'host'}]` default and now forwards `interval`, which Datadog requires for count and rate metrics. - update_slo replaced the whole SLO with only the fields the caller filled in, so editing one field erased description, tags, query, monitor_ids, groups, thresholds, and timeframe. PUT /api/v1/slo/{slo_id} is a full replacement, so the stored SLO is now read first and the supplied edits are overlaid onto it, with the read-only fields stripped. - update_incident admitted empty strings, so a blank input could blank a stored incident title or fail as an invalid date-time. - query_timeseries reported a failed query as success: Datadog returns 200 with a non-ok `status` and the reason in `error`. - create_monitor swallowed malformed options JSON and created a monitor with no thresholds. - send_logs rebuilt each entry from a fixed field list, discarding the custom attributes Datadog accepts as additionalProperties, and padded absent optional fields with empty strings. Removed: - mute_monitor. /api/v1/monitor/{monitor_id}/mute is absent from the v1 spec entirely, there is no unmute counterpart to reverse it, and downtimes are the supported mechanism. Contract accuracy: - Security signal search advertised relative times ("now-1h"); the spec types filter.from/to as format: date-time. Descriptions, placeholders, and wand prompts now produce ISO-8601. - list_incidents advertised an `include` value ("integrations") that is not in the spec enum, and neither incident tool trimmed the comma-separated list, so "users, attachments" 400d. - Invalid "ok" group state dropped from both monitor descriptions. - time_slice removed from SLO create input, which cannot build one without an SLI specification. - DatadogSite gains ap2, uk1, and us2.ddog-gov.com. Pagination and errors: - list_downtimes silently truncated at Datadog's default 30 with no way to page; adds page[limit]/page[offset] and surfaces totalCount. - query_logs returned a cursor it had no way to accept back. - Error extraction consolidated onto datadogErrorMessage, which now also reads the dictionary-shaped errors of the SLO delete conflict. Ten tools were reading `.detail` off plain strings or the raw entry off objects, degrading every failure to a bare status line. - Debug logging removed from list_monitors. Adds 29 regression tests, each verified to fail when its fix is reverted. * fix(datadog): add SEV-0, document page-size caps, drop unsourced output defaults - The severity dropdown omitted SEV-0, which IncidentSeverity allows and both incident tool descriptions already advertised. - Page-size descriptions now state Datadog's documented default of 10 and cap of 100 instead of an arbitrary example, so an agent does not request an out-of-range page. - trigger_synthetics_tests emitted an explicit null for a string-typed optional output, and update_synthetics_status reported 'live' on the error path regardless of what the caller actually requested. * fix(datadog): keep mute_monitor and add the missing unmute counterpart Reverses the removal in the previous commit. Absence from the datadog-api-client-go generator spec showed the endpoint is unpublished there, not that it is retired: Datadog's official Python client still implements it on master as `Monitor.mute(id, scope=, end=)` and `Monitor.unmute(id, scope=, all_scopes=)` (datadogpy datadog/api/monitors.py), which `_trigger_class_action` resolves to `POST /api/v1/monitor/{id}/mute` and `/unmute` with exactly those body fields. mute_monitor has also been in the block since #2175 in December, so dropping it would have broken existing workflows for an endpoint that two independent sources agree is live. The genuine defect was that muting was a one-way trapdoor: Sim could mute a monitor but had no way to reverse it. Adds datadog_unmute_monitor, sharing the monitor ID and scope inputs with mute, so the operation is recoverable from the same block. Also: mute no longer discards the response body (it now reports the monitor id, name, and state), routes errors through datadogErrorMessage, encodes the monitor ID in the path, and stops dropping an explicit `end` of 0. * fix(datadog): make downtime targeting explicit and reach downtime pagination from the block Addresses the review findings on the previous round. - create_downtime accepted both a monitor ID and monitor tags but `monitor_identifier` is a oneOf, so it silently kept the ID and dropped the tags, muting a different set of monitors than the caller asked for. It now rejects the ambiguous combination. - create_downtime ran Number.parseInt on the monitor ID with no validation, so a non-numeric value became NaN and serialized as null inside monitor_identifier. It now uses the same parseMonitorIds guard the SLO path already had, naming the offending value. - list_downtimes gained limit/offset in the tool but the block exposed neither, so no block-driven call could page past Datadog's default. Adds the two sub-blocks and wires them through the params mapper. - The block did not declare the totalCount the tool now returns, so nothing downstream could bind to it. * fix(datadog): tolerate non-string list inputs and keep the shipped mute subblock ids Both defects were introduced by this branch. - splitCommaList called .split on its argument, so routing create_downtime's monitorId through it turned a legitimate numeric input into a TypeError before the request was built. A reference to get_monitor or list_monitors resolves to a number, and an LLM tool call can pass a number or an array, so the helper now normalizes all three shapes. The previous Number.parseInt path had accepted a number by coercion. - Adding the unmute operation renamed the mute subblock ids scope/end to muteScope/muteEnd. Workflow state is persisted by subblock id, so every existing Mute Monitor block would have kept the old keys and silently lost its scope and end time. Restored the shipped ids; both are still unique block-wide and no operation reads another operation's value. * fix(datadog): compare downtime targets after parsing, not before A whitespace-only Monitor ID is truthy as a raw string but parses to no monitor, so the oneOf conflict guard rejected a valid tag-targeted downtime whenever the untouched Monitor ID field carried blank text. Both sides are now compared after parsing. --- .../content/docs/en/integrations/datadog.mdx | 937 ++++++++- apps/sim/blocks/blocks/datadog.ts | 1706 ++++++++++++++++- apps/sim/lib/integrations/integrations.json | 120 +- apps/sim/tools/datadog/add_incident_todo.ts | 127 ++ apps/sim/tools/datadog/cancel_downtime.ts | 5 +- apps/sim/tools/datadog/create_dashboard.ts | 149 ++ apps/sim/tools/datadog/create_downtime.ts | 80 +- apps/sim/tools/datadog/create_event.ts | 26 +- apps/sim/tools/datadog/create_incident.ts | 162 ++ apps/sim/tools/datadog/create_monitor.ts | 34 +- apps/sim/tools/datadog/create_slo.ts | 148 ++ apps/sim/tools/datadog/datadog.test.ts | 456 +++++ apps/sim/tools/datadog/delete_dashboard.ts | 76 + apps/sim/tools/datadog/delete_slo.ts | 88 + .../datadog/get_browser_synthetics_results.ts | 145 ++ apps/sim/tools/datadog/get_dashboard.ts | 81 + apps/sim/tools/datadog/get_incident.ts | 115 ++ apps/sim/tools/datadog/get_monitor.ts | 14 +- apps/sim/tools/datadog/get_security_signal.ts | 93 + apps/sim/tools/datadog/get_slo.ts | 99 + apps/sim/tools/datadog/get_slo_history.ts | 134 ++ .../tools/datadog/get_synthetics_results.ts | 139 ++ apps/sim/tools/datadog/get_synthetics_test.ts | 85 + apps/sim/tools/datadog/index.ts | 58 + apps/sim/tools/datadog/list_dashboards.ts | 110 ++ apps/sim/tools/datadog/list_downtimes.ts | 45 +- apps/sim/tools/datadog/list_incidents.ts | 135 ++ apps/sim/tools/datadog/list_monitors.ts | 38 +- apps/sim/tools/datadog/list_security_rules.ts | 134 ++ .../tools/datadog/list_security_signals.ts | 154 ++ apps/sim/tools/datadog/list_services.ts | 121 ++ apps/sim/tools/datadog/list_slos.ts | 135 ++ .../tools/datadog/list_synthetics_tests.ts | 115 ++ apps/sim/tools/datadog/mute_monitor.ts | 49 +- apps/sim/tools/datadog/query_logs.ts | 33 +- apps/sim/tools/datadog/query_timeseries.ts | 47 +- apps/sim/tools/datadog/search_spans.ts | 163 ++ apps/sim/tools/datadog/send_logs.ts | 32 +- apps/sim/tools/datadog/submit_metrics.ts | 62 +- .../tools/datadog/trigger_synthetics_tests.ts | 118 ++ apps/sim/tools/datadog/types.ts | 1065 +++++++--- apps/sim/tools/datadog/unmute_monitor.ts | 108 ++ apps/sim/tools/datadog/update_incident.ts | 180 ++ .../update_security_signal_assignee.ts | 104 + .../datadog/update_security_signal_state.ts | 119 ++ apps/sim/tools/datadog/update_slo.ts | 185 ++ .../tools/datadog/update_synthetics_status.ts | 93 + apps/sim/tools/datadog/utils.ts | 235 +++ apps/sim/tools/generated/tool-ids.ts | 2 +- apps/sim/tools/generated/tool-metadata.ts | 2 +- apps/sim/tools/generated/tool-outputs.ts | 2 +- apps/sim/tools/registry.ts | 58 + 52 files changed, 8202 insertions(+), 519 deletions(-) create mode 100644 apps/sim/tools/datadog/add_incident_todo.ts create mode 100644 apps/sim/tools/datadog/create_dashboard.ts create mode 100644 apps/sim/tools/datadog/create_incident.ts create mode 100644 apps/sim/tools/datadog/create_slo.ts create mode 100644 apps/sim/tools/datadog/datadog.test.ts create mode 100644 apps/sim/tools/datadog/delete_dashboard.ts create mode 100644 apps/sim/tools/datadog/delete_slo.ts create mode 100644 apps/sim/tools/datadog/get_browser_synthetics_results.ts create mode 100644 apps/sim/tools/datadog/get_dashboard.ts create mode 100644 apps/sim/tools/datadog/get_incident.ts create mode 100644 apps/sim/tools/datadog/get_security_signal.ts create mode 100644 apps/sim/tools/datadog/get_slo.ts create mode 100644 apps/sim/tools/datadog/get_slo_history.ts create mode 100644 apps/sim/tools/datadog/get_synthetics_results.ts create mode 100644 apps/sim/tools/datadog/get_synthetics_test.ts create mode 100644 apps/sim/tools/datadog/list_dashboards.ts create mode 100644 apps/sim/tools/datadog/list_incidents.ts create mode 100644 apps/sim/tools/datadog/list_security_rules.ts create mode 100644 apps/sim/tools/datadog/list_security_signals.ts create mode 100644 apps/sim/tools/datadog/list_services.ts create mode 100644 apps/sim/tools/datadog/list_slos.ts create mode 100644 apps/sim/tools/datadog/list_synthetics_tests.ts create mode 100644 apps/sim/tools/datadog/search_spans.ts create mode 100644 apps/sim/tools/datadog/trigger_synthetics_tests.ts create mode 100644 apps/sim/tools/datadog/unmute_monitor.ts create mode 100644 apps/sim/tools/datadog/update_incident.ts create mode 100644 apps/sim/tools/datadog/update_security_signal_assignee.ts create mode 100644 apps/sim/tools/datadog/update_security_signal_state.ts create mode 100644 apps/sim/tools/datadog/update_slo.ts create mode 100644 apps/sim/tools/datadog/update_synthetics_status.ts create mode 100644 apps/sim/tools/datadog/utils.ts diff --git a/apps/docs/content/docs/en/integrations/datadog.mdx b/apps/docs/content/docs/en/integrations/datadog.mdx index 1e3a3e0e7d..1f87000e75 100644 --- a/apps/docs/content/docs/en/integrations/datadog.mdx +++ b/apps/docs/content/docs/en/integrations/datadog.mdx @@ -41,7 +41,7 @@ Submit custom metrics to Datadog. Use for tracking application performance, busi | Parameter | Type | Required | Description | | --------- | ---- | -------- | ----------- | -| `series` | string | Yes | JSON array of metric series to submit. Each series should include metric name, type \(gauge/rate/count\), points \(timestamp/value pairs\), and optional tags. | +| `series` | string | Yes | JSON array of metric series to submit. Each entry needs "metric" and "points" \(objects with "timestamp" in POSIX seconds and a numeric "value"\); timestamps cannot be more than 10 minutes in the future or 1 hour in the past. Optional per entry: "type" \("count", "rate", or "gauge"; omit to let Datadog infer\), "interval" in seconds \(required by Datadog for count and rate\), "tags", "unit", "sourceTypeName", and "resources". | | `apiKey` | string | Yes | Datadog API key | | `site` | string | No | Datadog site/region \(default: datadoghq.com\) | @@ -72,6 +72,11 @@ Query metric timeseries data from Datadog. Use for analyzing trends, creating re | Parameter | Type | Description | | --------- | ---- | ----------- | | `series` | array | Array of timeseries data with metric name, tags, and data points | +| ↳ `metric` | string | Metric name | +| ↳ `tags` | array | Tags attached to the series | +| ↳ `points` | array | Data points | +| ↳ `timestamp` | number | Point timestamp \(Unix seconds\) | +| ↳ `value` | number | Point value | | `status` | string | Query status | ### Datadog Create Event @@ -143,6 +148,8 @@ Create a new monitor/alert in Datadog. Monitors can track metrics, service check | ↳ `overall_state` | string | Current monitor state | | ↳ `created` | string | Creation timestamp | | ↳ `modified` | string | Last modification timestamp | +| ↳ `options` | json | Monitor options \(thresholds, notification settings\) | +| ↳ `creator` | json | Monitor creator \(email, handle, name\) | ### Datadog Get Monitor @@ -153,7 +160,7 @@ Retrieve details of a specific monitor by ID. | Parameter | Type | Required | Description | | --------- | ---- | -------- | ----------- | | `monitorId` | string | Yes | The ID of the monitor to retrieve \(e.g., "12345678"\) | -| `groupStates` | string | No | Comma-separated group states to include \(e.g., "alert,warn", "alert,warn,no data,ok"\) | +| `groupStates` | string | No | Comma-separated group states to include. Valid values are "all", "alert", "warn", and "no data" \(e.g., "alert,warn"\). | | `withDowntimes` | boolean | No | Include downtime data with the monitor | | `apiKey` | string | Yes | Datadog API key | | `applicationKey` | string | Yes | Datadog Application key | @@ -174,6 +181,8 @@ Retrieve details of a specific monitor by ID. | ↳ `overall_state` | string | Current monitor state | | ↳ `created` | string | Creation timestamp | | ↳ `modified` | string | Last modification timestamp | +| ↳ `options` | json | Monitor options \(thresholds, notification settings\) | +| ↳ `creator` | json | Monitor creator \(email, handle, name\) | ### Datadog List Monitors @@ -183,7 +192,7 @@ List all monitors in Datadog with optional filtering by name, tags, or state. | Parameter | Type | Required | Description | | --------- | ---- | -------- | ----------- | -| `groupStates` | string | No | Comma-separated group states to filter by \(e.g., "alert,warn", "alert,warn,no data,ok"\) | +| `groupStates` | string | No | Comma-separated group states to filter by. Valid values are "all", "alert", "warn", and "no data" \(e.g., "alert,warn"\). | | `name` | string | No | Filter monitors by name with partial match \(e.g., "CPU", "Production"\) | | `tags` | string | No | Comma-separated list of tags to filter by \(e.g., "env:prod,team:backend"\) | | `monitorTags` | string | No | Comma-separated list of monitor tags to filter by \(e.g., "service:api,priority:high"\) | @@ -203,12 +212,18 @@ List all monitors in Datadog with optional filtering by name, tags, or state. | ↳ `name` | string | Monitor name | | ↳ `type` | string | Monitor type | | ↳ `query` | string | Monitor query | +| ↳ `message` | string | Notification message | | ↳ `overall_state` | string | Current state | | ↳ `tags` | array | Tags | +| ↳ `priority` | number | Monitor priority | +| ↳ `options` | json | Monitor options \(thresholds, notification settings\) | +| ↳ `created` | string | Creation timestamp | +| ↳ `modified` | string | Last modification timestamp | +| ↳ `creator` | json | Monitor creator \(email, handle, name\) | ### Datadog Mute Monitor -Mute a monitor to temporarily suppress notifications. +Mute a monitor to temporarily suppress its notifications. Use Unmute Monitor to reverse it, or schedule a downtime instead when you want a planned, auditable maintenance window. #### Input @@ -216,7 +231,7 @@ Mute a monitor to temporarily suppress notifications. | --------- | ---- | -------- | ----------- | | `monitorId` | string | Yes | The ID of the monitor to mute \(e.g., "12345678"\) | | `scope` | string | No | Scope to mute \(e.g., "host:myhost", "env:prod"\). If not specified, mutes all scopes. | -| `end` | number | No | Unix timestamp in seconds when the mute should end \(e.g., 1705323600\). If not specified, mutes indefinitely. | +| `end` | number | No | Unix timestamp in seconds when the mute should end \(e.g., 1705323600\). If not specified, the monitor stays muted until it is unmuted. | | `apiKey` | string | Yes | Datadog API key | | `applicationKey` | string | Yes | Datadog Application key | | `site` | string | No | Datadog site/region \(default: datadoghq.com\) | @@ -226,6 +241,33 @@ Mute a monitor to temporarily suppress notifications. | Parameter | Type | Description | | --------- | ---- | ----------- | | `success` | boolean | Whether the monitor was successfully muted | +| `monitorId` | number | ID of the muted monitor | +| `name` | string | Name of the muted monitor | +| `overallState` | string | Monitor state after muting | + +### Datadog Unmute Monitor + +Unmute a monitor so it resumes sending notifications. Reverses Mute Monitor, either for one scope or for every scope at once. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `monitorId` | string | Yes | The ID of the monitor to unmute \(e.g., "12345678"\) | +| `scope` | string | No | Scope to unmute \(e.g., "host:myhost"\). Leave blank to unmute the monitor itself rather than a single scope. | +| `allScopes` | boolean | No | Clear the mute settings for every scope on this monitor | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `success` | boolean | Whether the monitor was successfully unmuted | +| `monitorId` | number | ID of the unmuted monitor | +| `name` | string | Name of the unmuted monitor | +| `overallState` | string | Monitor state after unmuting | ### Datadog Query Logs @@ -239,6 +281,7 @@ Search and retrieve logs from Datadog. Use for troubleshooting, analysis, or mon | `from` | string | Yes | Start time in ISO-8601 format or relative time \(e.g., "now-1h", "now-15m", "2024-01-15T10:00:00Z"\) | | `to` | string | Yes | End time in ISO-8601 format or relative time \(e.g., "now", "now-5m", "2024-01-15T12:00:00Z"\) | | `limit` | number | No | Maximum number of logs to return \(e.g., 50, 100, max: 1000\) | +| `cursor` | string | No | Pagination cursor from a previous call, taken from its nextLogId output. Omit for the first page. | | `sort` | string | No | Sort order: "timestamp" for oldest first, "-timestamp" for newest first | | `indexes` | string | No | Comma-separated list of log indexes to search | | `apiKey` | string | Yes | Datadog API key | @@ -257,6 +300,8 @@ Search and retrieve logs from Datadog. Use for troubleshooting, analysis, or mon | ↳ `service` | string | Service name | | ↳ `message` | string | Log message | | ↳ `status` | string | Log status/level | +| ↳ `attributes` | json | Free-form log attributes | +| ↳ `tags` | array | Log tags | | `nextLogId` | string | Cursor for pagination | ### Datadog Send Logs @@ -302,12 +347,15 @@ Schedule a downtime to suppress monitor notifications during maintenance windows | Parameter | Type | Description | | --------- | ---- | ----------- | | `downtime` | object | The created downtime details | -| ↳ `id` | number | Downtime ID | +| ↳ `id` | string | Downtime UUID | | ↳ `scope` | array | Downtime scope | | ↳ `message` | string | Downtime message | | ↳ `start` | number | Start time \(Unix timestamp\) | | ↳ `end` | number | End time \(Unix timestamp\) | +| ↳ `timezone` | string | Display timezone for the downtime | | ↳ `active` | boolean | Whether downtime is currently active | +| ↳ `created` | number | Creation time \(Unix timestamp\) | +| ↳ `modified` | number | Last modification time \(Unix timestamp\) | ### Datadog List Downtimes @@ -318,7 +366,8 @@ List all scheduled downtimes in Datadog. | Parameter | Type | Required | Description | | --------- | ---- | -------- | ----------- | | `currentOnly` | boolean | No | Only return currently active downtimes | -| `monitorId` | string | No | Filter by monitor ID \(e.g., "12345678"\) | +| `limit` | number | No | Number of downtimes to return per page \(default: 30, max: 100\) | +| `offset` | number | No | Index of the first downtime to return \(e.g., 0, 30, 60\) | | `apiKey` | string | Yes | Datadog API key | | `applicationKey` | string | Yes | Datadog Application key | | `site` | string | No | Datadog site/region \(default: datadoghq.com\) | @@ -327,13 +376,17 @@ List all scheduled downtimes in Datadog. | Parameter | Type | Description | | --------- | ---- | ----------- | +| `totalCount` | number | Total number of downtimes matching the filter, across all pages | | `downtimes` | array | List of downtimes | -| ↳ `id` | number | Downtime ID | +| ↳ `id` | string | Downtime UUID | | ↳ `scope` | array | Downtime scope | | ↳ `message` | string | Downtime message | | ↳ `start` | number | Start time \(Unix timestamp\) | | ↳ `end` | number | End time \(Unix timestamp\) | +| ↳ `timezone` | string | Display timezone for the downtime | | ↳ `active` | boolean | Whether downtime is currently active | +| ↳ `created` | number | Creation time \(Unix timestamp\) | +| ↳ `modified` | number | Last modification time \(Unix timestamp\) | ### Datadog Cancel Downtime @@ -354,4 +407,872 @@ Cancel a scheduled downtime. | --------- | ---- | ----------- | | `success` | boolean | Whether the downtime was successfully canceled | +### Datadog List Incidents + +List incidents for the organization. Requires the Incident Management `incident_read` permission; the Incidents API is in public beta. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `include` | string | No | Comma-separated related resources to include: "users" and/or "attachments" | +| `pageSize` | number | No | Number of incidents to return per page \(default: 10, max: 100\) | +| `pageOffset` | number | No | Index of the first incident to return \(e.g., 0, 10, 20\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `incidents` | array | List of incidents | +| ↳ `id` | string | Incident UUID | +| ↳ `type` | string | Resource type \(incidents\) | +| ↳ `attributes` | object | Incident attributes | +| ↳ `title` | string | Incident title | +| ↳ `state` | string | Incident state | +| ↳ `severity` | string | Incident severity | +| ↳ `public_id` | number | Incremental public incident ID | +| ↳ `customer_impacted` | boolean | Whether customers were impacted | +| ↳ `created` | string | Creation timestamp | +| ↳ `modified` | string | Last modification timestamp | +| ↳ `resolved` | string | Resolution timestamp | +| `nextOffset` | number | Offset to use for the next page of results | + +### Datadog Get Incident + +Get the details of a single incident by ID. Requires the Incident Management `incident_read` permission; the Incidents API is in public beta. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `incidentId` | string | Yes | The UUID of the incident \(e.g., "00000000-0000-0000-1234-000000000000"\) | +| `include` | string | No | Comma-separated related resources to include \(e.g., "users", "attachments"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `incident` | object | The incident | +| ↳ `id` | string | Incident UUID | +| ↳ `type` | string | Resource type \(incidents\) | +| ↳ `attributes` | object | Incident attributes | +| ↳ `title` | string | Incident title | +| ↳ `state` | string | Incident state | +| ↳ `severity` | string | Incident severity | +| ↳ `public_id` | number | Incremental public incident ID | +| ↳ `customer_impacted` | boolean | Whether customers were impacted | +| ↳ `customer_impact_scope` | string | Summary of the customer impact | +| ↳ `created` | string | Creation timestamp | +| ↳ `modified` | string | Last modification timestamp | +| ↳ `resolved` | string | Resolution timestamp | +| ↳ `time_to_resolve` | number | Seconds from creation to resolution | + +### Datadog Create Incident + +Declare a new incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `title` | string | Yes | Title of the incident summarizing what happened | +| `customerImpacted` | boolean | Yes | Whether the incident caused customer impact | +| `severity` | string | No | Incident severity: UNKNOWN, SEV-0, SEV-1, SEV-2, SEV-3, SEV-4, or SEV-5 | +| `customerImpactScope` | string | No | Summary of the customer impact. Required when customerImpacted is true | +| `incidentTypeUuid` | string | No | UUID of the incident type. The default incident type is used when omitted | +| `isTest` | boolean | No | Whether this is a test incident | +| `fields` | string | No | JSON object of user-defined incident fields, e.g. \{"severity": \{"type": "dropdown", "value": "SEV-2"\}\} | +| `notificationHandles` | string | No | Comma-separated handles to notify on creation \(e.g., "@slack-incidents,@user@example.com"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `incident` | object | The created incident | +| ↳ `id` | string | Incident UUID | +| ↳ `type` | string | Resource type \(incidents\) | +| ↳ `attributes` | object | Incident attributes | +| ↳ `title` | string | Incident title | +| ↳ `public_id` | number | Incremental public incident ID | +| ↳ `customer_impacted` | boolean | Whether customers were impacted | +| ↳ `created` | string | Creation timestamp | +| ↳ `modified` | string | Last modification timestamp | + +### Datadog Update Incident + +Partially update an existing incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `incidentId` | string | Yes | The UUID of the incident to update | +| `title` | string | No | New title for the incident | +| `severity` | string | No | Incident severity: UNKNOWN, SEV-0, SEV-1, SEV-2, SEV-3, SEV-4, or SEV-5 | +| `customerImpacted` | boolean | No | Whether the incident caused customer impact | +| `customerImpactScope` | string | No | Summary of the customer impact | +| `customerImpactStart` | string | No | ISO-8601 timestamp when customers began being impacted | +| `customerImpactEnd` | string | No | ISO-8601 timestamp when customers were no longer impacted | +| `detected` | string | No | ISO-8601 timestamp when the incident was detected | +| `fields` | string | No | JSON object of user-defined incident fields to update, e.g. \{"state": \{"type": "dropdown", "value": "resolved"\}\} | +| `notificationHandles` | string | No | Comma-separated handles to notify about the update | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `incident` | object | The updated incident | +| ↳ `id` | string | Incident UUID | +| ↳ `type` | string | Resource type \(incidents\) | +| ↳ `attributes` | object | Incident attributes | +| ↳ `title` | string | Incident title | +| ↳ `state` | string | Incident state | +| ↳ `severity` | string | Incident severity | +| ↳ `modified` | string | Last modification timestamp | +| ↳ `resolved` | string | Resolution timestamp | + +### Datadog Add Incident Todo + +Add a follow-up task (todo) to an incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `incidentId` | string | Yes | The UUID of the incident the todo belongs to | +| `content` | string | Yes | The follow-up task content \(e.g., "Restore lost data"\) | +| `assignees` | string | Yes | Comma-separated assignee handles \(e.g., "@jane@example.com,@on-call"\). Datadog requires at least one assignee | +| `dueDate` | string | No | ISO-8601 timestamp for when the todo should be completed | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `todo` | object | The created incident todo | +| ↳ `id` | string | Todo UUID | +| ↳ `type` | string | Resource type \(incident_todos\) | +| ↳ `attributes` | object | Todo attributes | +| ↳ `content` | string | Task content | +| ↳ `assignees` | array | Assignee handles | +| ↳ `due_date` | string | Due date | +| ↳ `completed` | string | Completion timestamp | +| ↳ `incident_id` | string | UUID of the parent incident | + +### Datadog List SLOs + +List service level objectives, optionally filtered by IDs, name, tags, or underlying metrics query. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `ids` | string | No | Comma-separated SLO IDs to fetch \(e.g., "id1,id2"\) | +| `query` | string | No | Filter results by SLO name \(e.g., "checkout latency"\) | +| `tagsQuery` | string | No | Filter results by a single SLO tag \(e.g., "env:prod"\) | +| `metricsQuery` | string | No | Filter results by SLO numerator and denominator \(e.g., "aws.elb.request_count"\) | +| `limit` | number | No | Number of SLOs to return \(default: 1000\) | +| `offset` | number | No | Offset of the first SLO returned \(e.g., 0, 50\) | +| `isDeleted` | boolean | No | Return only deleted SLOs | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `slos` | array | List of service level objectives | +| ↳ `id` | string | SLO ID | +| ↳ `name` | string | SLO name | +| ↳ `type` | string | SLO type: metric, monitor, or time_slice | +| ↳ `description` | string | SLO description | +| ↳ `tags` | array | SLO tags | +| ↳ `thresholds` | array | Timeframe targets and warnings | +| ↳ `target_threshold` | number | Primary target threshold | +| ↳ `warning_threshold` | number | Primary warning threshold | +| ↳ `timeframe` | string | Primary timeframe | +| ↳ `monitor_ids` | array | Monitor IDs for monitor-based SLOs | +| ↳ `created_at` | number | Creation timestamp \(Unix seconds\) | +| ↳ `modified_at` | number | Modification timestamp \(Unix seconds\) | + +### Datadog Get SLO + +Get the configuration of a single service level objective by ID. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `sloId` | string | Yes | The ID of the service level objective | +| `withConfiguredAlertIds` | boolean | No | Include the IDs of SLO monitors that reference this SLO | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `slo` | object | The service level objective | +| ↳ `id` | string | SLO ID | +| ↳ `name` | string | SLO name | +| ↳ `type` | string | SLO type: metric, monitor, or time_slice | +| ↳ `description` | string | SLO description | +| ↳ `tags` | array | SLO tags | +| ↳ `thresholds` | array | Timeframe targets and warnings | +| ↳ `target_threshold` | number | Primary target threshold | +| ↳ `warning_threshold` | number | Primary warning threshold | +| ↳ `timeframe` | string | Primary timeframe | +| ↳ `monitor_ids` | array | Monitor IDs for monitor-based SLOs | +| ↳ `groups` | array | Monitor groups narrowing the SLO scope | +| ↳ `configured_alert_ids` | array | SLO monitor IDs referencing this SLO | +| ↳ `created_at` | number | Creation timestamp \(Unix seconds\) | +| ↳ `modified_at` | number | Modification timestamp \(Unix seconds\) | + +### Datadog Create SLO + +Create a service level objective from a metric query, monitors, or a time-slice condition. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `name` | string | Yes | Name of the SLO \(e.g., "Checkout API availability"\) | +| `type` | string | Yes | SLO type: "metric" \(supply query\) or "monitor" \(supply monitorIds\). Time-slice SLOs are not supported here because they need an SLI specification this tool does not send. | +| `thresholds` | string | Yes | JSON array of thresholds, e.g. \[\{"timeframe": "30d", "target": 99.9, "warning": 99.95\}\] | +| `description` | string | No | Description of the SLO | +| `tags` | string | No | Comma-separated tags \(e.g., "env:prod,team:core"\) | +| `query` | string | No | For metric SLOs, JSON with numerator and denominator, e.g. \{"numerator": "sum:requests\{status:ok\}.as_count\(\)", "denominator": "sum:requests\{*\}.as_count\(\)"\} | +| `monitorIds` | string | No | For monitor SLOs, comma-separated monitor IDs \(e.g., "123,456"\) | +| `groups` | string | No | For monitor SLOs with a single monitor, comma-separated monitor groups \(e.g., "env:prod,role:mysql"\) | +| `targetThreshold` | number | No | Primary target threshold \(e.g., 99.9\) | +| `warningThreshold` | number | No | Primary warning threshold, must be greater than the target \(e.g., 99.95\) | +| `timeframe` | string | No | Primary timeframe: "7d", "30d", or "90d" | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `slo` | object | The created service level objective | +| ↳ `id` | string | SLO ID | +| ↳ `name` | string | SLO name | +| ↳ `type` | string | SLO type | +| ↳ `description` | string | SLO description | +| ↳ `tags` | array | SLO tags | +| ↳ `thresholds` | array | Timeframe targets and warnings | +| ↳ `created_at` | number | Creation timestamp \(Unix seconds\) | +| ↳ `modified_at` | number | Modification timestamp \(Unix seconds\) | + +### Datadog Update SLO + +Update a service level objective. Reads the current SLO first and applies only the fields you supply, so anything left blank keeps its stored value. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `sloId` | string | Yes | The ID of the service level objective to update | +| `name` | string | No | New name for the SLO. Leave blank to keep the current name. | +| `type` | string | No | SLO type: "metric" or "monitor". Leave blank to keep the current type. Changing type requires supplying the matching query or monitorIds. | +| `thresholds` | string | No | JSON array of thresholds replacing the stored ones, e.g. \[\{"timeframe": "30d", "target": 99.9, "warning": 99.95\}\]. Leave blank to keep the current thresholds. | +| `description` | string | No | Description of the SLO | +| `tags` | string | No | Comma-separated tags \(e.g., "env:prod,team:core"\) | +| `query` | string | No | For metric SLOs, JSON with numerator and denominator, e.g. \{"numerator": "sum:requests\{status:ok\}.as_count\(\)", "denominator": "sum:requests\{*\}.as_count\(\)"\} | +| `monitorIds` | string | No | For monitor SLOs, comma-separated monitor IDs \(e.g., "123,456"\) | +| `groups` | string | No | Comma-separated monitor groups \(e.g., "env:prod,role:mysql"\) | +| `targetThreshold` | number | No | Primary target threshold \(e.g., 99.9\) | +| `warningThreshold` | number | No | Primary warning threshold, must be greater than the target \(e.g., 99.95\) | +| `timeframe` | string | No | Primary timeframe: "7d", "30d", or "90d" | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `slo` | object | The updated service level objective | +| ↳ `id` | string | SLO ID | +| ↳ `name` | string | SLO name | +| ↳ `type` | string | SLO type | +| ↳ `description` | string | SLO description | +| ↳ `tags` | array | SLO tags | +| ↳ `thresholds` | array | Timeframe targets and warnings | +| ↳ `modified_at` | number | Modification timestamp \(Unix seconds\) | + +### Datadog Delete SLO + +Permanently delete a service level objective. Datadog returns a conflict when the SLO is still referenced by a dashboard. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `sloId` | string | Yes | The ID of the service level objective to delete | +| `force` | boolean | No | Delete even when the SLO is referenced by other resources | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `success` | boolean | Whether the SLO was deleted | +| `deletedIds` | array | IDs of the deleted service level objectives | + +### Datadog Get SLO History + +Get an SLO’s history over a time window, including the overall SLI value and remaining error budget. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `sloId` | string | Yes | The ID of the service level objective | +| `fromTs` | number | Yes | Start of the query window as a Unix timestamp in seconds | +| `toTs` | number | Yes | End of the query window as a Unix timestamp in seconds | +| `target` | number | No | SLO target between 0 and 100. When supplied, the response includes the remaining error budget for a custom timeframe | +| `applyCorrection` | boolean | No | Whether to apply SLO corrections \(defaults to true\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `history` | object | SLO history for the requested window | +| ↳ `from_ts` | number | Window start \(Unix seconds\) | +| ↳ `to_ts` | number | Window end \(Unix seconds\) | +| ↳ `type` | string | SLO type | +| ↳ `overall` | object | Overall SLI data for the window | +| ↳ `sli_value` | number | SLI value over the window | +| ↳ `span_precision` | number | Decimal precision of the SLI value | +| ↳ `error_budget_remaining` | object | Remaining error budget keyed by timeframe | +| ↳ `groups` | array | Per-group SLI data for grouped SLOs | +| ↳ `monitors` | array | Per-monitor SLI data for multi-monitor SLOs | +| ↳ `thresholds` | object | Thresholds keyed by timeframe | +| `sliValue` | number | Overall SLI value over the window | + +### Datadog List Dashboards + +List custom created or cloned dashboards. Datadog preset dashboards are not returned. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `filterShared` | boolean | No | Return only shared dashboards | +| `filterDeleted` | boolean | No | Return only deleted dashboards. Incompatible with filterShared | +| `count` | number | No | Maximum number of dashboards to return \(default: 100\) | +| `start` | number | No | Offset of the first dashboard returned \(e.g., 0, 100\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `dashboards` | array | List of dashboard summaries | +| ↳ `id` | string | Dashboard ID | +| ↳ `title` | string | Dashboard title | +| ↳ `description` | string | Dashboard description | +| ↳ `layout_type` | string | Layout type: ordered or free | +| ↳ `url` | string | Dashboard URL path | +| ↳ `author_handle` | string | Handle of the dashboard author | +| ↳ `created_at` | string | Creation timestamp | +| ↳ `modified_at` | string | Modification timestamp | +| ↳ `is_read_only` | boolean | Whether the dashboard is read-only | + +### Datadog Get Dashboard + +Get the full definition of a dashboard, including its widgets. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `dashboardId` | string | Yes | The ID of the dashboard \(e.g., "abc-def-ghi"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `dashboard` | object | The dashboard definition | +| ↳ `id` | string | Dashboard ID | +| ↳ `title` | string | Dashboard title | +| ↳ `description` | string | Dashboard description | +| ↳ `layout_type` | string | Layout type: ordered or free | +| ↳ `url` | string | Dashboard URL path | +| ↳ `author_handle` | string | Handle of the dashboard author | +| ↳ `author_name` | string | Name of the dashboard author | +| ↳ `created_at` | string | Creation timestamp | +| ↳ `modified_at` | string | Modification timestamp | +| ↳ `tags` | array | Dashboard tags | +| ↳ `notify_list` | array | Handles notified on dashboard changes | +| ↳ `template_variables` | array | Template variable definitions | +| ↳ `widgets` | array | Widget definitions | + +### Datadog Create Dashboard + +Create a dashboard from a title, layout type, and widget definitions. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `title` | string | Yes | Title of the dashboard | +| `layoutType` | string | Yes | Layout type: "ordered" or "free" | +| `widgets` | string | Yes | JSON array of widget definitions, e.g. \[\{"definition": \{"type": "timeseries", "requests": \[\{"q": "avg:system.cpu.user\{*\}"\}\]\}\}\] | +| `description` | string | No | Description of the dashboard | +| `notifyList` | string | No | Comma-separated user handles to notify on dashboard changes | +| `templateVariables` | string | No | JSON array of template variable definitions, e.g. \[\{"name": "env", "prefix": "env", "available_values": \["prod"\]\}\] | +| `tags` | string | No | Comma-separated dashboard tags in the form "team:<name>" \(max 5\) | +| `reflowType` | string | No | Reflow type for ordered layouts: "auto" or "fixed" | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `dashboard` | object | The created dashboard | +| ↳ `id` | string | Dashboard ID | +| ↳ `title` | string | Dashboard title | +| ↳ `layout_type` | string | Layout type: ordered or free | +| ↳ `url` | string | Dashboard URL path | +| ↳ `author_handle` | string | Handle of the dashboard author | +| ↳ `created_at` | string | Creation timestamp | +| ↳ `modified_at` | string | Modification timestamp | +| ↳ `widgets` | array | Widget definitions | + +### Datadog Delete Dashboard + +Delete a dashboard by ID. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `dashboardId` | string | Yes | The ID of the dashboard to delete | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `success` | boolean | Whether the dashboard was deleted | +| `deletedDashboardId` | string | ID of the deleted dashboard | + +### Datadog List Synthetic Tests + +List all Synthetic tests (API, browser, and mobile) with their current status. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `pageSize` | number | No | Number of tests returned per page \(default: 100\) | +| `pageNumber` | number | No | Page to retrieve, starting at zero | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `tests` | array | List of Synthetic tests | +| ↳ `public_id` | string | Public ID of the test | +| ↳ `name` | string | Test name | +| ↳ `status` | string | Pause status: live or paused | +| ↳ `type` | string | Test type: api, browser, mobile, or network | +| ↳ `subtype` | string | Test subtype, such as http or ssl | +| ↳ `message` | string | Notification message | +| ↳ `monitor_id` | number | Associated monitor ID | +| ↳ `tags` | array | Tags attached to the test | +| ↳ `locations` | array | Locations the test runs from | + +### Datadog Get Synthetic Test + +Get the configuration of a Synthetic test by public ID. Browser test steps are not included by this type-agnostic endpoint. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `publicId` | string | Yes | The public ID of the Synthetic test \(e.g., "abc-def-ghi"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `test` | object | The Synthetic test configuration | +| ↳ `public_id` | string | Public ID of the test | +| ↳ `name` | string | Test name | +| ↳ `status` | string | Pause status: live or paused | +| ↳ `type` | string | Test type: api, browser, mobile, or network | +| ↳ `subtype` | string | Test subtype, such as http or ssl | +| ↳ `message` | string | Notification message | +| ↳ `monitor_id` | number | Associated monitor ID | +| ↳ `tags` | array | Tags attached to the test | +| ↳ `locations` | array | Locations the test runs from | +| ↳ `config` | object | Test request, assertions, and variables | +| ↳ `options` | object | Scheduling, retry, and monitor options | +| ↳ `creator` | object | User who created the test | + +### Datadog Get Synthetic Test Results + +Get the latest result summaries (up to the last 150 runs) for a Synthetic API test. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `publicId` | string | Yes | The public ID of the Synthetic API test | +| `fromTs` | number | No | Timestamp in milliseconds from which to start querying results | +| `toTs` | number | No | Timestamp in milliseconds up to which to query results | +| `probeDc` | string | No | Comma-separated locations to query results for \(e.g., "aws:eu-west-3"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `results` | array | Latest test result summaries | +| ↳ `result_id` | string | ID of the test result | +| ↳ `check_time` | number | Time the test ran | +| ↳ `probe_dc` | string | Location the test ran from | +| ↳ `status` | number | Monitor status: 0 not triggered, 1 triggered, 2 no data | +| ↳ `result` | object | Run outcome | +| ↳ `passed` | boolean | Whether the run passed | +| ↳ `timings` | object | Request timing breakdown | +| `lastTimestampFetched` | number | Timestamp of the latest test run | + +### Datadog Get Browser Synthetic Test Results + +Get the latest result summaries (up to the last 150 runs) for a Synthetic browser test, including step counts and errors. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `publicId` | string | Yes | The public ID of the Synthetic browser test | +| `fromTs` | number | No | Timestamp in milliseconds from which to start querying results | +| `toTs` | number | No | Timestamp in milliseconds up to which to query results | +| `probeDc` | string | No | Comma-separated locations to query results for \(e.g., "aws:eu-west-3"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `results` | array | Latest browser test result summaries | +| ↳ `result_id` | string | ID of the browser test result | +| ↳ `check_time` | number | Time the browser test ran | +| ↳ `probe_dc` | string | Location the browser test ran from | +| ↳ `status` | number | Monitor status: 0 not triggered, 1 triggered, 2 no data | +| ↳ `result` | object | Run outcome | +| ↳ `duration` | number | Length of the run in milliseconds | +| ↳ `errorCount` | number | Number of errors collected in the run | +| ↳ `stepCountCompleted` | number | Steps completed before failing | +| ↳ `stepCountTotal` | number | Total number of steps | +| ↳ `device` | object | Device the run was performed on | +| `lastTimestampFetched` | number | Timestamp of the latest browser test run | + +### Datadog Trigger Synthetic Tests + +Trigger an immediate run of one or more Synthetic tests by public ID. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `publicIds` | string | Yes | Comma-separated public IDs of the Synthetic tests to trigger | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `batchId` | string | Public ID of the triggered batch | +| `triggeredCheckIds` | array | Public IDs of the triggered Synthetic tests | +| `results` | array | Information about each triggered test run | +| ↳ `public_id` | string | Public ID of the test | +| ↳ `result_id` | string | ID of the run result | +| ↳ `location` | number | Location ID of the run | +| ↳ `device` | string | Device ID used for browser tests | +| `locations` | array | Locations the tests were triggered from | +| ↳ `id` | number | Location ID | +| ↳ `name` | string | Location name | + +### Datadog Pause Or Start Synthetic Test + +Pause or resume a Synthetic test by setting its status to "paused" or "live". + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `publicId` | string | Yes | The public ID of the Synthetic test to update | +| `newStatus` | string | Yes | New status: "live" to start the test or "paused" to pause it | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `success` | boolean | Whether Datadog reported the status update as successful | +| `status` | string | The status that was requested: live or paused | + +### Datadog List Security Signals + +Search Cloud SIEM security signals by query and time range. Requires the `security_monitoring_signals_read` permission. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `query` | string | No | Signal search query \(e.g., "security:attack status:high"\) | +| `from` | string | No | Minimum timestamp as an ISO-8601 date-time \(e.g., "2026-01-02T09:42:36.320Z"\). Signal search does not accept relative expressions like "now-1h". | +| `to` | string | No | Maximum timestamp as an ISO-8601 date-time \(e.g., "2026-01-03T09:42:36.320Z"\). Signal search does not accept relative expressions like "now". | +| `sort` | string | No | Sort order: "timestamp" for oldest first, "-timestamp" for newest first | +| `cursor` | string | No | Pagination cursor returned as nextCursor by a previous call | +| `limit` | number | No | Maximum number of signals to return \(default: 10, max: 1000\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `signals` | array | List of security signals | +| ↳ `id` | string | Signal ID | +| ↳ `type` | string | Resource type \(signal\) | +| ↳ `attributes` | object | Signal attributes | +| ↳ `message` | string | Message from the detection rule | +| ↳ `timestamp` | string | Signal timestamp | +| ↳ `tags` | array | Tags on the signal | +| ↳ `custom` | object | Signal-specific attributes | +| `nextCursor` | string | Cursor for the next page of signals | + +### Datadog Get Security Signal + +Get the details of a single Cloud SIEM security signal. Requires the `security_monitoring_signals_read` permission. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `signalId` | string | Yes | The ID of the security signal | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `signal` | object | The security signal | +| ↳ `id` | string | Signal ID | +| ↳ `type` | string | Resource type \(signal\) | +| ↳ `attributes` | object | Signal attributes | +| ↳ `message` | string | Message from the detection rule | +| ↳ `timestamp` | string | Signal timestamp | +| ↳ `tags` | array | Tags on the signal | +| ↳ `custom` | object | Signal-specific attributes | + +### Datadog Update Security Signal State + +Change the triage state of a Cloud SIEM security signal to open, under_review, or archived. Requires the `security_monitoring_signals_write` permission. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `signalId` | string | Yes | The ID of the security signal | +| `state` | string | Yes | New triage state: "open", "under_review", or "archived" | +| `archiveReason` | string | No | Reason when archiving: none, false_positive, testing_or_maintenance, remediated, investigated_case_opened, true_positive_benign, true_positive_malicious, or other | +| `archiveComment` | string | No | Comment explaining why the signal was archived | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `signal` | object | The updated signal triage data | +| ↳ `id` | string | Signal ID | +| ↳ `type` | string | Resource type of the signal | +| ↳ `state` | string | Current triage state | +| ↳ `assignee` | object | User the signal is assigned to | +| ↳ `incidentIds` | array | IDs of incidents linked to the signal | +| ↳ `archiveReason` | string | Archive reason, when archived | +| ↳ `archiveComment` | string | Archive comment, when archived | +| ↳ `stateUpdateTimestamp` | number | Timestamp of the last state update | + +### Datadog Assign Security Signal + +Assign a Cloud SIEM security signal to a Datadog user by UUID. Requires the `security_monitoring_signals_write` permission. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `signalId` | string | Yes | The ID of the security signal | +| `assigneeUuid` | string | Yes | UUID of the Datadog user to assign the signal to \(e.g., "773b045d-ccf8-4808-bd3b-955ef6a8c940"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `signal` | object | The updated signal triage data | +| ↳ `id` | string | Signal ID | +| ↳ `type` | string | Resource type of the signal | +| ↳ `state` | string | Current triage state | +| ↳ `assignee` | object | User the signal is assigned to | +| ↳ `incidentIds` | array | IDs of incidents linked to the signal | +| ↳ `archiveReason` | string | Archive reason, when archived | +| ↳ `archiveComment` | string | Archive comment, when archived | +| ↳ `stateUpdateTimestamp` | number | Timestamp of the last state update | + +### Datadog List Security Rules + +List Cloud SIEM detection rules. Requires the `security_monitoring_rules_read` permission. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `query` | string | No | Search query filtering rules by attributes such as type, source, or tags \(e.g., "type:log_detection source:cloudtrail"\) | +| `sort` | string | No | Sort attribute, prefix with "-" for descending: name, creation_date, update_date, enabled, type, highest_severity, or source | +| `pageSize` | number | No | Number of rules per page \(default: 10, max: 100\) | +| `pageNumber` | number | No | Page to retrieve, starting at zero | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `rules` | array | List of detection rules | +| ↳ `id` | string | Rule ID | +| ↳ `name` | string | Rule name | +| ↳ `type` | string | Rule type | +| ↳ `message` | string | Message attached to generated signals | +| ↳ `tags` | array | Rule tags | +| ↳ `isEnabled` | boolean | Whether the rule is enabled | +| ↳ `isDefault` | boolean | Whether the rule is a Datadog default rule | +| ↳ `createdAt` | number | Creation timestamp in milliseconds | +| ↳ `version` | number | Rule version | + +### Datadog Search Spans + +Search indexed APM spans using the span query syntax, with cursor pagination. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `query` | string | No | Span search query \(e.g., "service:web* AND @http.status_code:\[500 TO 599\]"\). Defaults to "*" | +| `from` | string | No | Minimum time, ISO-8601, date math, or milliseconds \(default: "now-15m"\) | +| `to` | string | No | Maximum time, ISO-8601, date math, or milliseconds \(default: "now"\) | +| `sort` | string | No | Sort order: "timestamp" for oldest first, "-timestamp" for newest first | +| `cursor` | string | No | Pagination cursor returned as nextCursor by a previous call | +| `limit` | number | No | Maximum number of spans to return \(default: 10, max: 1000\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `spans` | array | List of matching spans | +| ↳ `id` | string | Unique span event ID | +| ↳ `type` | string | Resource type \(spans\) | +| ↳ `attributes` | object | Span attributes | +| ↳ `service` | string | Service that emitted the span | +| ↳ `resource_name` | string | Resource name | +| ↳ `env` | string | Environment | +| ↳ `host` | string | Host that emitted the span | +| ↳ `type` | string | Span type, such as web or db | +| ↳ `trace_id` | string | Trace ID | +| ↳ `span_id` | string | Span ID | +| ↳ `parent_id` | string | Parent span ID | +| ↳ `start_timestamp` | string | Span start timestamp | +| ↳ `end_timestamp` | string | Span end timestamp | +| ↳ `tags` | array | Tags on the span | +| ↳ `custom` | object | Custom span data | +| `nextCursor` | string | Cursor for the next page of spans | +| `elapsed` | number | Query time in milliseconds | + +### Datadog List Services + +List service definitions from the Datadog Service Catalog. Requires the `apm_service_catalog_read` permission. + +#### Input + +| Parameter | Type | Required | Description | +| --------- | ---- | -------- | ----------- | +| `pageSize` | number | No | Number of service definitions per page \(default: 10, max: 100\) | +| `pageNumber` | number | No | Page to retrieve, starting at zero | +| `schemaVersion` | string | No | Schema version to return \(e.g., "v2", "v2.1", "v2.2"\) | +| `apiKey` | string | Yes | Datadog API key | +| `applicationKey` | string | Yes | Datadog Application key | +| `site` | string | No | Datadog site/region \(default: datadoghq.com\) | + +#### Output + +| Parameter | Type | Description | +| --------- | ---- | ----------- | +| `services` | array | List of service definitions | +| ↳ `id` | string | Service definition ID | +| ↳ `type` | string | Resource type \(service_definitions\) | +| ↳ `schema` | object | The service definition schema. Its shape depends on the requested schema version | +| ↳ `meta` | object | Ingestion metadata such as origin and last modified time | + diff --git a/apps/sim/blocks/blocks/datadog.ts b/apps/sim/blocks/blocks/datadog.ts index 96e090aa26..da94bfc558 100644 --- a/apps/sim/blocks/blocks/datadog.ts +++ b/apps/sim/blocks/blocks/datadog.ts @@ -3,6 +3,18 @@ import type { BlockConfig, BlockMeta } from '@/blocks/types' import { AuthMode, IntegrationType } from '@/blocks/types' import type { DatadogResponse } from '@/tools/datadog/types' +/** + * Normalizes a `switch` sub-block value. Switches serialize their state as the + * strings `'true'`/`'false'`, so `Boolean(value)` would read `'false'` as true. + * Returns `undefined` when the switch was never set so the tool falls back to + * Datadog's own default. + */ +function toSwitchBoolean(value: unknown): boolean | undefined { + if (value === true || value === 'true') return true + if (value === false || value === 'false') return false + return undefined +} + export const DatadogBlock: BlockConfig = { type: 'datadog', name: 'Datadog', @@ -44,6 +56,10 @@ export const DatadogBlock: BlockConfig = { { text: ', for scope', field: 'scope' }, { text: ', until', field: 'end' }, ], + datadog_unmute_monitor: [ + { text: 'Unmute monitor', field: 'muteMonitorId', core: true }, + { text: ', for scope', field: 'scope' }, + ], datadog_query_logs: [ { text: 'Search logs matching', field: 'logQuery', core: true }, { text: ', since', field: 'logFrom' }, @@ -55,6 +71,87 @@ export const DatadogBlock: BlockConfig = { ], datadog_list_downtimes: ['List scheduled downtimes'], datadog_cancel_downtime: [{ text: 'Cancel downtime', field: 'downtimeId', core: true }], + datadog_list_incidents: ['List incidents'], + datadog_get_incident: [{ text: 'Read incident', field: 'incidentId', core: true }], + datadog_create_incident: [ + { text: 'Declare incident', field: 'incidentTitle', core: true }, + { text: ', at severity', field: 'incidentSeverity' }, + ], + datadog_update_incident: [ + { text: 'Update incident', field: 'incidentId', core: true }, + { text: ', to severity', field: 'incidentSeverity' }, + ], + datadog_add_incident_todo: [ + { text: 'Add follow-up task to incident', field: 'incidentId', core: true }, + { text: ', assigned to', field: 'todoAssignees' }, + ], + datadog_list_slos: [ + 'List SLOs', + { text: ', named like', field: 'sloQuery' }, + { text: ', tagged', field: 'sloTagsQuery' }, + ], + datadog_get_slo: [{ text: 'Read SLO', field: 'sloId', core: true }], + datadog_create_slo: [ + { text: 'Create SLO', field: 'sloName', core: true }, + { text: ', of type', field: 'sloType' }, + ], + datadog_update_slo: [{ text: 'Update SLO', field: 'sloId', core: true }], + datadog_delete_slo: [{ text: 'Delete SLO', field: 'sloId', core: true }], + datadog_get_slo_history: [ + { text: 'Read SLO history for', field: 'sloId', core: true }, + { text: ', since', field: 'sloFromTs' }, + ], + datadog_list_dashboards: ['List dashboards'], + datadog_get_dashboard: [{ text: 'Read dashboard', field: 'dashboardId', core: true }], + datadog_create_dashboard: [ + { text: 'Create dashboard', field: 'dashboardTitle', core: true }, + ], + datadog_delete_dashboard: [{ text: 'Delete dashboard', field: 'dashboardId', core: true }], + datadog_list_synthetics_tests: ['List Synthetic tests'], + datadog_get_synthetics_test: [ + { text: 'Read Synthetic test', field: 'syntheticsPublicId', core: true }, + ], + datadog_get_synthetics_results: [ + { text: 'Read results for Synthetic test', field: 'syntheticsPublicId', core: true }, + ], + datadog_get_browser_synthetics_results: [ + { + text: 'Read results for browser Synthetic test', + field: 'syntheticsPublicId', + core: true, + }, + ], + datadog_trigger_synthetics_tests: [ + { text: 'Trigger Synthetic tests', field: 'syntheticsPublicIds', core: true }, + ], + datadog_update_synthetics_status: [ + { text: 'Set Synthetic test', field: 'syntheticsPublicId', core: true }, + { text: 'to', field: 'syntheticsNewStatus' }, + ], + datadog_list_security_signals: [ + { text: 'Search security signals matching', field: 'signalQuery', core: true }, + { text: ', since', field: 'signalFrom' }, + ], + datadog_get_security_signal: [ + { text: 'Read security signal', field: 'signalId', core: true }, + ], + datadog_update_security_signal_state: [ + { text: 'Set security signal', field: 'signalId', core: true }, + { text: 'to state', field: 'signalState' }, + ], + datadog_update_security_signal_assignee: [ + { text: 'Assign security signal', field: 'signalId', core: true }, + { text: ', to', field: 'signalAssigneeUuid' }, + ], + datadog_list_security_rules: [ + 'List detection rules', + { text: ', matching', field: 'ruleQuery' }, + ], + datadog_search_spans: [ + { text: 'Search APM spans matching', field: 'spanQuery', core: true }, + { text: ', since', field: 'spanFrom' }, + ], + datadog_list_services: ['List services in the catalog'], }, }, }, @@ -72,11 +169,43 @@ export const DatadogBlock: BlockConfig = { { label: 'Get Monitor', id: 'datadog_get_monitor' }, { label: 'List Monitors', id: 'datadog_list_monitors' }, { label: 'Mute Monitor', id: 'datadog_mute_monitor' }, + { label: 'Unmute Monitor', id: 'datadog_unmute_monitor' }, { label: 'Query Logs', id: 'datadog_query_logs' }, { label: 'Send Logs', id: 'datadog_send_logs' }, { label: 'Create Downtime', id: 'datadog_create_downtime' }, { label: 'List Downtimes', id: 'datadog_list_downtimes' }, { label: 'Cancel Downtime', id: 'datadog_cancel_downtime' }, + { label: 'List Incidents', id: 'datadog_list_incidents' }, + { label: 'Get Incident', id: 'datadog_get_incident' }, + { label: 'Create Incident', id: 'datadog_create_incident' }, + { label: 'Update Incident', id: 'datadog_update_incident' }, + { label: 'Add Incident Todo', id: 'datadog_add_incident_todo' }, + { label: 'List SLOs', id: 'datadog_list_slos' }, + { label: 'Get SLO', id: 'datadog_get_slo' }, + { label: 'Create SLO', id: 'datadog_create_slo' }, + { label: 'Update SLO', id: 'datadog_update_slo' }, + { label: 'Delete SLO', id: 'datadog_delete_slo' }, + { label: 'Get SLO History', id: 'datadog_get_slo_history' }, + { label: 'List Dashboards', id: 'datadog_list_dashboards' }, + { label: 'Get Dashboard', id: 'datadog_get_dashboard' }, + { label: 'Create Dashboard', id: 'datadog_create_dashboard' }, + { label: 'Delete Dashboard', id: 'datadog_delete_dashboard' }, + { label: 'List Synthetic Tests', id: 'datadog_list_synthetics_tests' }, + { label: 'Get Synthetic Test', id: 'datadog_get_synthetics_test' }, + { label: 'Get Synthetic Test Results', id: 'datadog_get_synthetics_results' }, + { + label: 'Get Browser Synthetic Test Results', + id: 'datadog_get_browser_synthetics_results', + }, + { label: 'Trigger Synthetic Tests', id: 'datadog_trigger_synthetics_tests' }, + { label: 'Pause Or Start Synthetic Test', id: 'datadog_update_synthetics_status' }, + { label: 'List Security Signals', id: 'datadog_list_security_signals' }, + { label: 'Get Security Signal', id: 'datadog_get_security_signal' }, + { label: 'Update Security Signal State', id: 'datadog_update_security_signal_state' }, + { label: 'Assign Security Signal', id: 'datadog_update_security_signal_assignee' }, + { label: 'List Security Rules', id: 'datadog_list_security_rules' }, + { label: 'Search Spans', id: 'datadog_search_spans' }, + { label: 'List Services', id: 'datadog_list_services' }, ], value: () => 'datadog_submit_metrics', }, @@ -386,43 +515,43 @@ Return ONLY valid JSON - no explanations, no markdown code blocks.`, mode: 'advanced', }, - // Mute Monitor inputs + // Mute / Unmute Monitor inputs { id: 'muteMonitorId', title: 'Monitor ID', type: 'short-input', placeholder: '12345678', - condition: { field: 'operation', value: 'datadog_mute_monitor' }, - required: true, + condition: { + field: 'operation', + value: ['datadog_mute_monitor', 'datadog_unmute_monitor'], + }, + required: { field: 'operation', value: ['datadog_mute_monitor', 'datadog_unmute_monitor'] }, }, { id: 'scope', title: 'Scope', type: 'short-input', - placeholder: 'host:myhost (optional)', - condition: { field: 'operation', value: 'datadog_mute_monitor' }, + placeholder: 'host:myhost (leave blank for all scopes)', + condition: { + field: 'operation', + value: ['datadog_mute_monitor', 'datadog_unmute_monitor'], + }, mode: 'advanced', }, { id: 'end', - title: 'End Time (Unix Timestamp)', + title: 'Mute Until (Unix Timestamp)', type: 'short-input', - placeholder: 'Leave empty for indefinite', + placeholder: 'Leave empty to mute until unmuted', condition: { field: 'operation', value: 'datadog_mute_monitor' }, mode: 'advanced', - wandConfig: { - enabled: true, - prompt: `Generate a Unix timestamp (seconds since epoch) based on the user's description. -The timestamp should be a number representing seconds since January 1, 1970 UTC. -Examples: -- "in 1 hour" -> Calculate current time plus 3600 seconds -- "tomorrow morning" -> Calculate tomorrow at 09:00:00 UTC as Unix timestamp -- "end of day" -> Calculate today at 23:59:59 UTC as Unix timestamp - -Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, - placeholder: 'Describe when mute should end (e.g., "in 1 hour", "tomorrow")...', - generationType: 'timestamp', - }, + }, + { + id: 'unmuteAllScopes', + title: 'Clear All Scopes', + type: 'switch', + condition: { field: 'operation', value: 'datadog_unmute_monitor' }, + mode: 'advanced', }, // Query Logs inputs @@ -497,6 +626,14 @@ Return ONLY the relative time string - no explanations, no quotes, no extra text condition: { field: 'operation', value: 'datadog_query_logs' }, mode: 'advanced', }, + { + id: 'logCursor', + title: 'Cursor', + type: 'short-input', + placeholder: 'Cursor returned by a previous call', + condition: { field: 'operation', value: 'datadog_query_logs' }, + mode: 'advanced', + }, // Send Logs inputs { @@ -605,6 +742,38 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, condition: { field: 'operation', value: 'datadog_create_downtime' }, mode: 'advanced', }, + { + id: 'downtimeMonitorTags', + title: 'Monitor Tags', + type: 'short-input', + placeholder: 'team:backend,priority:high', + condition: { field: 'operation', value: 'datadog_create_downtime' }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: `Generate a comma-separated list of Datadog monitor tags based on the user's description. +Each tag uses the "key:value" form. +Examples: "team:backend,priority:high", "env:production", "service:checkout" + +Return ONLY the comma-separated tag list - no explanations, no extra text.`, + placeholder: 'Describe which monitors to target...', + }, + }, + { + id: 'downtimeTimezone', + title: 'Timezone', + type: 'short-input', + placeholder: 'UTC or America/New_York', + condition: { field: 'operation', value: 'datadog_create_downtime' }, + mode: 'advanced', + }, + { + id: 'downtimeMuteFirstRecovery', + title: 'Mute First Recovery Notification', + type: 'switch', + condition: { field: 'operation', value: 'datadog_create_downtime' }, + mode: 'advanced', + }, // List Downtimes inputs { @@ -614,6 +783,22 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, condition: { field: 'operation', value: 'datadog_list_downtimes' }, mode: 'advanced', }, + { + id: 'downtimeLimit', + title: 'Limit', + type: 'short-input', + placeholder: '30', + condition: { field: 'operation', value: 'datadog_list_downtimes' }, + mode: 'advanced', + }, + { + id: 'downtimeOffset', + title: 'Offset', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_downtimes' }, + mode: 'advanced', + }, // Cancel Downtime inputs { @@ -625,6 +810,1010 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, required: true, }, + // Incidents inputs + { + id: 'incidentId', + title: 'Incident ID', + type: 'short-input', + placeholder: '00000000-0000-0000-1234-000000000000', + condition: { + field: 'operation', + value: ['datadog_get_incident', 'datadog_update_incident', 'datadog_add_incident_todo'], + }, + required: { + field: 'operation', + value: ['datadog_get_incident', 'datadog_update_incident', 'datadog_add_incident_todo'], + }, + }, + { + id: 'incidentTitle', + title: 'Incident Title', + type: 'short-input', + placeholder: 'Checkout API returning 500s', + condition: { + field: 'operation', + value: ['datadog_create_incident', 'datadog_update_incident'], + }, + required: { field: 'operation', value: 'datadog_create_incident' }, + }, + { + id: 'incidentCustomerImpacted', + title: 'Customer Impacted', + type: 'switch', + condition: { + field: 'operation', + value: ['datadog_create_incident', 'datadog_update_incident'], + }, + }, + { + id: 'incidentSeverity', + title: 'Severity', + type: 'dropdown', + options: [ + { label: 'SEV-0', id: 'SEV-0' }, + { label: 'SEV-1', id: 'SEV-1' }, + { label: 'SEV-2', id: 'SEV-2' }, + { label: 'SEV-3', id: 'SEV-3' }, + { label: 'SEV-4', id: 'SEV-4' }, + { label: 'SEV-5', id: 'SEV-5' }, + { label: 'Unknown', id: 'UNKNOWN' }, + ], + condition: { + field: 'operation', + value: ['datadog_create_incident', 'datadog_update_incident'], + }, + }, + { + id: 'incidentCustomerImpactScope', + title: 'Customer Impact Scope', + type: 'long-input', + placeholder: 'Checkout unavailable for EU customers', + condition: { + field: 'operation', + value: ['datadog_create_incident', 'datadog_update_incident'], + }, + mode: 'advanced', + }, + { + id: 'incidentTypeUuid', + title: 'Incident Type UUID', + type: 'short-input', + placeholder: 'Leave empty to use the default incident type', + condition: { field: 'operation', value: 'datadog_create_incident' }, + mode: 'advanced', + }, + { + id: 'incidentIsTest', + title: 'Test Incident', + type: 'switch', + condition: { field: 'operation', value: 'datadog_create_incident' }, + mode: 'advanced', + }, + { + id: 'incidentCustomerImpactStart', + title: 'Customer Impact Start', + type: 'short-input', + placeholder: '2026-01-02T09:42:36Z', + condition: { field: 'operation', value: 'datadog_update_incident' }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: + 'Generate an ISO 8601 timestamp for when customer impact began. Return ONLY the timestamp string.', + placeholder: 'Describe when customer impact started...', + generationType: 'timestamp', + }, + }, + { + id: 'incidentCustomerImpactEnd', + title: 'Customer Impact End', + type: 'short-input', + placeholder: '2026-01-02T10:15:00Z', + condition: { field: 'operation', value: 'datadog_update_incident' }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: + 'Generate an ISO 8601 timestamp for when customer impact ended. Return ONLY the timestamp string.', + placeholder: 'Describe when customer impact ended...', + generationType: 'timestamp', + }, + }, + { + id: 'incidentDetected', + title: 'Detected At', + type: 'short-input', + placeholder: '2026-01-02T09:40:00Z', + condition: { field: 'operation', value: 'datadog_update_incident' }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: + 'Generate an ISO 8601 timestamp for when the incident was detected. Return ONLY the timestamp string.', + placeholder: 'Describe when the incident was detected...', + generationType: 'timestamp', + }, + }, + { + id: 'incidentFields', + title: 'Fields (JSON)', + type: 'code', + placeholder: '{"state": {"type": "dropdown", "value": "resolved"}}', + condition: { + field: 'operation', + value: ['datadog_create_incident', 'datadog_update_incident'], + }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: `Generate a Datadog incident fields object based on the user's description. +Each key is a field name and each value is an object with "type" and "value". +Examples: +- {"severity": {"type": "dropdown", "value": "SEV-2"}} +- {"state": {"type": "dropdown", "value": "resolved"}} +- {"services": {"type": "multiselect", "value": ["checkout", "payments"]}} + +Return ONLY valid JSON - no explanations, no markdown code blocks.`, + placeholder: 'Describe the incident fields to set...', + generationType: 'json-object', + }, + }, + { + id: 'incidentNotificationHandles', + title: 'Notification Handles', + type: 'short-input', + placeholder: '@slack-incidents, @oncall@example.com', + condition: { + field: 'operation', + value: ['datadog_create_incident', 'datadog_update_incident'], + }, + mode: 'advanced', + }, + { + id: 'incidentInclude', + title: 'Include Related Resources', + type: 'short-input', + placeholder: 'users, attachments', + condition: { + field: 'operation', + value: ['datadog_list_incidents', 'datadog_get_incident'], + }, + mode: 'advanced', + }, + { + id: 'incidentPageSize', + title: 'Page Size', + type: 'short-input', + placeholder: '10', + condition: { field: 'operation', value: 'datadog_list_incidents' }, + mode: 'advanced', + }, + { + id: 'incidentPageOffset', + title: 'Page Offset', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_incidents' }, + mode: 'advanced', + }, + { + id: 'todoContent', + title: 'Task Content', + type: 'long-input', + placeholder: 'Restore lost data', + condition: { field: 'operation', value: 'datadog_add_incident_todo' }, + required: true, + }, + { + id: 'todoAssignees', + title: 'Assignees', + type: 'short-input', + placeholder: '@jane@example.com, @oncall', + condition: { field: 'operation', value: 'datadog_add_incident_todo' }, + required: true, + }, + { + id: 'todoDueDate', + title: 'Due Date', + type: 'short-input', + placeholder: '2026-01-10T05:00:00Z', + condition: { field: 'operation', value: 'datadog_add_incident_todo' }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: + 'Generate an ISO 8601 timestamp for when the task is due. Return ONLY the timestamp string.', + placeholder: 'Describe when the task is due...', + generationType: 'timestamp', + }, + }, + + // SLO inputs + { + id: 'sloId', + title: 'SLO ID', + type: 'short-input', + placeholder: 'e6ce9c47b6c04d3d9dbfbb1cb4b7a8a3', + condition: { + field: 'operation', + value: [ + 'datadog_get_slo', + 'datadog_update_slo', + 'datadog_delete_slo', + 'datadog_get_slo_history', + ], + }, + required: { + field: 'operation', + value: [ + 'datadog_get_slo', + 'datadog_update_slo', + 'datadog_delete_slo', + 'datadog_get_slo_history', + ], + }, + }, + { + id: 'sloName', + title: 'SLO Name', + type: 'short-input', + placeholder: 'Checkout API availability', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + required: { field: 'operation', value: ['datadog_create_slo'] }, + }, + { + id: 'sloType', + title: 'SLO Type', + type: 'dropdown', + options: [ + { label: 'Metric', id: 'metric' }, + { label: 'Monitor', id: 'monitor' }, + ], + value: () => 'metric', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + required: { field: 'operation', value: ['datadog_create_slo'] }, + }, + { + id: 'sloThresholds', + title: 'Thresholds (JSON)', + type: 'code', + placeholder: '[{"timeframe": "30d", "target": 99.9, "warning": 99.95}]', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + required: { field: 'operation', value: ['datadog_create_slo'] }, + wandConfig: { + enabled: true, + prompt: `Generate a JSON array of Datadog SLO thresholds based on the user's description. +Each threshold object has: +- "timeframe": one of "7d", "30d", or "90d" +- "target": the target percentage (e.g., 99.9) +- "warning": optional warning percentage, must be greater than the target + +Return ONLY valid JSON - no explanations, no markdown code blocks.`, + placeholder: 'Describe the SLO targets...', + generationType: 'json-object', + }, + }, + { + id: 'sloMetricQuery', + title: 'Metric Query (JSON)', + type: 'code', + placeholder: + '{"numerator": "sum:requests{status:ok}.as_count()", "denominator": "sum:requests{*}.as_count()"}', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + wandConfig: { + enabled: true, + prompt: `Generate a Datadog metric SLO query object based on the user's description. +The object has: +- "numerator": the query counting good events +- "denominator": the query counting all events + +Return ONLY valid JSON - no explanations, no markdown code blocks.`, + placeholder: 'Describe the good events and total events...', + generationType: 'json-object', + }, + }, + { + id: 'sloMonitorIds', + title: 'Monitor IDs', + type: 'short-input', + placeholder: '12345678, 23456789', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloGroups', + title: 'Monitor Groups', + type: 'short-input', + placeholder: 'env:prod, role:mysql', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloDescription', + title: 'Description', + type: 'long-input', + placeholder: 'Availability of the checkout API', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloTags', + title: 'Tags', + type: 'short-input', + placeholder: 'env:prod, team:core', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloTargetThreshold', + title: 'Target Threshold', + type: 'short-input', + placeholder: '99.9', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloWarningThreshold', + title: 'Warning Threshold', + type: 'short-input', + placeholder: '99.95', + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloTimeframe', + title: 'Timeframe', + type: 'dropdown', + options: [ + { label: '7 days', id: '7d' }, + { label: '30 days', id: '30d' }, + { label: '90 days', id: '90d' }, + ], + condition: { field: 'operation', value: ['datadog_create_slo', 'datadog_update_slo'] }, + mode: 'advanced', + }, + { + id: 'sloIds', + title: 'Filter by IDs', + type: 'short-input', + placeholder: 'id1, id2', + condition: { field: 'operation', value: 'datadog_list_slos' }, + mode: 'advanced', + }, + { + id: 'sloQuery', + title: 'Filter by Name', + type: 'short-input', + placeholder: 'checkout', + condition: { field: 'operation', value: 'datadog_list_slos' }, + mode: 'advanced', + }, + { + id: 'sloTagsQuery', + title: 'Filter by Tag', + type: 'short-input', + placeholder: 'env:prod', + condition: { field: 'operation', value: 'datadog_list_slos' }, + mode: 'advanced', + }, + { + id: 'sloMetricsQuery', + title: 'Filter by Metrics Query', + type: 'short-input', + placeholder: 'aws.elb.request_count', + condition: { field: 'operation', value: 'datadog_list_slos' }, + mode: 'advanced', + }, + { + id: 'sloLimit', + title: 'Limit', + type: 'short-input', + placeholder: '100', + condition: { field: 'operation', value: 'datadog_list_slos' }, + mode: 'advanced', + }, + { + id: 'sloOffset', + title: 'Offset', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_slos' }, + mode: 'advanced', + }, + { + id: 'sloWithConfiguredAlertIds', + title: 'Include SLO Monitor IDs', + type: 'switch', + condition: { field: 'operation', value: 'datadog_get_slo' }, + mode: 'advanced', + }, + { + id: 'sloForce', + title: 'Force Delete', + type: 'switch', + condition: { field: 'operation', value: 'datadog_delete_slo' }, + mode: 'advanced', + }, + { + id: 'sloFromTs', + title: 'From (Unix Timestamp)', + type: 'short-input', + placeholder: 'e.g., 1701360000', + condition: { field: 'operation', value: 'datadog_get_slo_history' }, + required: true, + wandConfig: { + enabled: true, + prompt: + 'Generate a Unix timestamp in seconds for the start of the window. Return ONLY the numeric timestamp.', + placeholder: 'Describe the start time (e.g., "7 days ago")...', + generationType: 'timestamp', + }, + }, + { + id: 'sloToTs', + title: 'To (Unix Timestamp)', + type: 'short-input', + placeholder: 'e.g., 1701446400', + condition: { field: 'operation', value: 'datadog_get_slo_history' }, + required: true, + wandConfig: { + enabled: true, + prompt: + 'Generate a Unix timestamp in seconds for the end of the window. Return ONLY the numeric timestamp.', + placeholder: 'Describe the end time (e.g., "now")...', + generationType: 'timestamp', + }, + }, + { + id: 'sloTarget', + title: 'Target', + type: 'short-input', + placeholder: '99.9', + condition: { field: 'operation', value: 'datadog_get_slo_history' }, + mode: 'advanced', + }, + { + id: 'sloApplyCorrection', + title: 'Apply Corrections', + type: 'switch', + value: () => 'true', + condition: { field: 'operation', value: 'datadog_get_slo_history' }, + mode: 'advanced', + }, + + // Dashboard inputs + { + id: 'dashboardId', + title: 'Dashboard ID', + type: 'short-input', + placeholder: 'abc-def-ghi', + condition: { + field: 'operation', + value: ['datadog_get_dashboard', 'datadog_delete_dashboard'], + }, + required: { + field: 'operation', + value: ['datadog_get_dashboard', 'datadog_delete_dashboard'], + }, + }, + { + id: 'dashboardTitle', + title: 'Dashboard Title', + type: 'short-input', + placeholder: 'Checkout service overview', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + required: true, + }, + { + id: 'dashboardLayoutType', + title: 'Layout Type', + type: 'dropdown', + options: [ + { label: 'Ordered', id: 'ordered' }, + { label: 'Free', id: 'free' }, + ], + value: () => 'ordered', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + required: true, + }, + { + id: 'dashboardWidgets', + title: 'Widgets (JSON)', + type: 'code', + placeholder: + '[{"definition": {"type": "timeseries", "title": "CPU", "requests": [{"q": "avg:system.cpu.user{*}"}]}}]', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + required: true, + wandConfig: { + enabled: true, + prompt: `Generate a JSON array of Datadog dashboard widgets based on the user's description. +Each widget has a "definition" object with at least a "type" (e.g., "timeseries", "query_value", "toplist"), +a "title", and the widget's "requests" array. + +Return ONLY valid JSON - no explanations, no markdown code blocks.`, + placeholder: 'Describe the widgets you want on the dashboard...', + generationType: 'json-object', + }, + }, + { + id: 'dashboardDescription', + title: 'Description', + type: 'long-input', + placeholder: 'Latency, errors, and saturation for checkout', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + mode: 'advanced', + }, + { + id: 'dashboardTags', + title: 'Tags', + type: 'short-input', + placeholder: 'team:core', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + mode: 'advanced', + }, + { + id: 'dashboardNotifyList', + title: 'Notify List', + type: 'short-input', + placeholder: 'jane@example.com, john@example.com', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + mode: 'advanced', + }, + { + id: 'dashboardTemplateVariables', + title: 'Template Variables (JSON)', + type: 'code', + placeholder: '[{"name": "env", "prefix": "env", "available_values": ["prod", "staging"]}]', + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: `Generate a JSON array of Datadog dashboard template variables based on the user's description. +Each variable has a "name", an optional "prefix" (the tag key), and optional "available_values". + +Return ONLY valid JSON - no explanations, no markdown code blocks.`, + placeholder: 'Describe the template variables...', + generationType: 'json-object', + }, + }, + { + id: 'dashboardReflowType', + title: 'Reflow Type', + type: 'dropdown', + options: [ + { label: 'Auto', id: 'auto' }, + { label: 'Fixed', id: 'fixed' }, + ], + condition: { field: 'operation', value: 'datadog_create_dashboard' }, + mode: 'advanced', + }, + { + id: 'dashboardFilterShared', + title: 'Shared Only', + type: 'switch', + condition: { field: 'operation', value: 'datadog_list_dashboards' }, + mode: 'advanced', + }, + { + id: 'dashboardFilterDeleted', + title: 'Deleted Only', + type: 'switch', + condition: { field: 'operation', value: 'datadog_list_dashboards' }, + mode: 'advanced', + }, + { + id: 'dashboardCount', + title: 'Count', + type: 'short-input', + placeholder: '100', + condition: { field: 'operation', value: 'datadog_list_dashboards' }, + mode: 'advanced', + }, + { + id: 'dashboardStart', + title: 'Start Offset', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_dashboards' }, + mode: 'advanced', + }, + + // Synthetics inputs + { + id: 'syntheticsPublicId', + title: 'Test Public ID', + type: 'short-input', + placeholder: 'abc-def-ghi', + condition: { + field: 'operation', + value: [ + 'datadog_get_synthetics_test', + 'datadog_get_synthetics_results', + 'datadog_get_browser_synthetics_results', + 'datadog_update_synthetics_status', + ], + }, + required: { + field: 'operation', + value: [ + 'datadog_get_synthetics_test', + 'datadog_get_synthetics_results', + 'datadog_get_browser_synthetics_results', + 'datadog_update_synthetics_status', + ], + }, + }, + { + id: 'syntheticsNewStatus', + title: 'New Status', + type: 'dropdown', + options: [ + { label: 'Live', id: 'live' }, + { label: 'Paused', id: 'paused' }, + ], + value: () => 'live', + condition: { field: 'operation', value: 'datadog_update_synthetics_status' }, + required: true, + }, + { + id: 'syntheticsPublicIds', + title: 'Test Public IDs', + type: 'short-input', + placeholder: 'abc-def-ghi, jkl-mno-pqr', + condition: { field: 'operation', value: 'datadog_trigger_synthetics_tests' }, + required: true, + }, + { + id: 'syntheticsFromTs', + title: 'From (Unix Milliseconds)', + type: 'short-input', + placeholder: 'e.g., 1701360000000', + condition: { + field: 'operation', + value: ['datadog_get_synthetics_results', 'datadog_get_browser_synthetics_results'], + }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: + 'Generate a Unix timestamp in MILLISECONDS for the start of the window. Return ONLY the numeric timestamp.', + placeholder: 'Describe the start time (e.g., "1 hour ago")...', + generationType: 'timestamp', + }, + }, + { + id: 'syntheticsToTs', + title: 'To (Unix Milliseconds)', + type: 'short-input', + placeholder: 'e.g., 1701446400000', + condition: { + field: 'operation', + value: ['datadog_get_synthetics_results', 'datadog_get_browser_synthetics_results'], + }, + mode: 'advanced', + wandConfig: { + enabled: true, + prompt: + 'Generate a Unix timestamp in MILLISECONDS for the end of the window. Return ONLY the numeric timestamp.', + placeholder: 'Describe the end time (e.g., "now")...', + generationType: 'timestamp', + }, + }, + { + id: 'syntheticsProbeDc', + title: 'Locations', + type: 'short-input', + placeholder: 'aws:eu-west-3, aws:us-east-1', + condition: { + field: 'operation', + value: ['datadog_get_synthetics_results', 'datadog_get_browser_synthetics_results'], + }, + mode: 'advanced', + }, + { + id: 'syntheticsPageSize', + title: 'Page Size', + type: 'short-input', + placeholder: '100', + condition: { field: 'operation', value: 'datadog_list_synthetics_tests' }, + mode: 'advanced', + }, + { + id: 'syntheticsPageNumber', + title: 'Page Number', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_synthetics_tests' }, + mode: 'advanced', + }, + + // Security monitoring inputs + { + id: 'signalId', + title: 'Signal ID', + type: 'short-input', + placeholder: 'AAAAAWgN8Xwgr1vKDQAAAABBV2dOOFh3ZzZobm1mWXJFYTR0OA', + condition: { + field: 'operation', + value: [ + 'datadog_get_security_signal', + 'datadog_update_security_signal_state', + 'datadog_update_security_signal_assignee', + ], + }, + required: { + field: 'operation', + value: [ + 'datadog_get_security_signal', + 'datadog_update_security_signal_state', + 'datadog_update_security_signal_assignee', + ], + }, + }, + { + id: 'signalState', + title: 'Triage State', + type: 'dropdown', + options: [ + { label: 'Open', id: 'open' }, + { label: 'Under Review', id: 'under_review' }, + { label: 'Archived', id: 'archived' }, + ], + value: () => 'open', + condition: { field: 'operation', value: 'datadog_update_security_signal_state' }, + required: true, + }, + { + id: 'signalArchiveReason', + title: 'Archive Reason', + type: 'dropdown', + options: [ + { label: 'None', id: 'none' }, + { label: 'False Positive', id: 'false_positive' }, + { label: 'Testing Or Maintenance', id: 'testing_or_maintenance' }, + { label: 'Remediated', id: 'remediated' }, + { label: 'Investigated, Case Opened', id: 'investigated_case_opened' }, + { label: 'True Positive - Benign', id: 'true_positive_benign' }, + { label: 'True Positive - Malicious', id: 'true_positive_malicious' }, + { label: 'Other', id: 'other' }, + ], + condition: { field: 'operation', value: 'datadog_update_security_signal_state' }, + mode: 'advanced', + }, + { + id: 'signalArchiveComment', + title: 'Archive Comment', + type: 'long-input', + placeholder: 'Known scanner traffic from the security team', + condition: { field: 'operation', value: 'datadog_update_security_signal_state' }, + mode: 'advanced', + }, + { + id: 'signalAssigneeUuid', + title: 'Assignee UUID', + type: 'short-input', + placeholder: '773b045d-ccf8-4808-bd3b-955ef6a8c940', + condition: { field: 'operation', value: 'datadog_update_security_signal_assignee' }, + required: true, + }, + { + id: 'signalQuery', + title: 'Search Query', + type: 'long-input', + placeholder: 'security:attack status:high', + condition: { field: 'operation', value: 'datadog_list_security_signals' }, + wandConfig: { + enabled: true, + prompt: `Generate a Datadog security signal search query based on the user's description. +The query uses facet syntax: facet:value +Examples: +- "security:attack status:high" - High severity attack signals +- "@workflow.rule.name:\"Brute Force\"" - Signals from a specific rule +- "source:cloudtrail status:critical" - Critical CloudTrail signals + +Return ONLY the search query string - no explanations.`, + placeholder: 'Describe the signals you want to find...', + }, + }, + { + id: 'signalFrom', + title: 'From', + type: 'short-input', + placeholder: '2026-01-02T09:42:36.320Z', + condition: { field: 'operation', value: 'datadog_list_security_signals' }, + wandConfig: { + enabled: true, + prompt: + 'Convert the described start time into an absolute ISO-8601 UTC date-time, e.g. 2026-01-02T09:42:36.320Z. Datadog signal search rejects relative expressions such as "now-1h", so always resolve them against the current date. Return ONLY the timestamp.', + placeholder: 'Describe the start time (e.g., "1 hour ago")...', + generationType: 'timestamp', + }, + }, + { + id: 'signalTo', + title: 'To', + type: 'short-input', + placeholder: '2026-01-03T09:42:36.320Z', + condition: { field: 'operation', value: 'datadog_list_security_signals' }, + wandConfig: { + enabled: true, + prompt: + 'Convert the described end time into an absolute ISO-8601 UTC date-time, e.g. 2026-01-03T09:42:36.320Z. Datadog signal search rejects relative expressions such as "now", so always resolve them against the current date. Return ONLY the timestamp.', + placeholder: 'Describe the end time (e.g., "now")...', + generationType: 'timestamp', + }, + }, + { + id: 'signalSort', + title: 'Sort', + type: 'dropdown', + options: [ + { label: 'Newest First', id: '-timestamp' }, + { label: 'Oldest First', id: 'timestamp' }, + ], + condition: { field: 'operation', value: 'datadog_list_security_signals' }, + mode: 'advanced', + }, + { + id: 'signalLimit', + title: 'Limit', + type: 'short-input', + placeholder: '25', + condition: { field: 'operation', value: 'datadog_list_security_signals' }, + mode: 'advanced', + }, + { + id: 'signalCursor', + title: 'Cursor', + type: 'short-input', + placeholder: 'Cursor returned by a previous call', + condition: { field: 'operation', value: 'datadog_list_security_signals' }, + mode: 'advanced', + }, + { + id: 'ruleQuery', + title: 'Search Query', + type: 'short-input', + placeholder: 'type:log_detection source:cloudtrail', + condition: { field: 'operation', value: 'datadog_list_security_rules' }, + mode: 'advanced', + }, + { + id: 'ruleSort', + title: 'Sort', + type: 'dropdown', + options: [ + { label: 'Name', id: 'name' }, + { label: 'Name (descending)', id: '-name' }, + { label: 'Creation Date', id: 'creation_date' }, + { label: 'Creation Date (descending)', id: '-creation_date' }, + { label: 'Update Date', id: 'update_date' }, + { label: 'Update Date (descending)', id: '-update_date' }, + ], + condition: { field: 'operation', value: 'datadog_list_security_rules' }, + mode: 'advanced', + }, + { + id: 'rulePageSize', + title: 'Page Size', + type: 'short-input', + placeholder: '25', + condition: { field: 'operation', value: 'datadog_list_security_rules' }, + mode: 'advanced', + }, + { + id: 'rulePageNumber', + title: 'Page Number', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_security_rules' }, + mode: 'advanced', + }, + + // APM inputs + { + id: 'spanQuery', + title: 'Span Query', + type: 'long-input', + placeholder: 'service:checkout AND @http.status_code:[500 TO 599]', + condition: { field: 'operation', value: 'datadog_search_spans' }, + wandConfig: { + enabled: true, + prompt: `Generate a Datadog span search query based on the user's description. +The query uses facet syntax: facet:value +Examples: +- "service:checkout AND @http.status_code:[500 TO 599]" - Server errors in checkout +- "env:prod resource_name:\"GET /cart\"" - Spans for a specific endpoint +- "@duration:>1000000000" - Spans slower than one second (duration is in nanoseconds) + +Return ONLY the search query string - no explanations.`, + placeholder: 'Describe the spans you want to find...', + }, + }, + { + id: 'spanFrom', + title: 'From', + type: 'short-input', + placeholder: 'now-15m', + condition: { field: 'operation', value: 'datadog_search_spans' }, + wandConfig: { + enabled: true, + prompt: + 'Generate a Datadog relative time string such as now-15m, now-1h, or now-1d. Return ONLY the string.', + placeholder: 'Describe the start time (e.g., "15 minutes ago")...', + generationType: 'timestamp', + }, + }, + { + id: 'spanTo', + title: 'To', + type: 'short-input', + placeholder: 'now', + condition: { field: 'operation', value: 'datadog_search_spans' }, + wandConfig: { + enabled: true, + prompt: + 'Generate a Datadog relative time string such as now or now-5m. Return ONLY the string.', + placeholder: 'Describe the end time (e.g., "now")...', + generationType: 'timestamp', + }, + }, + { + id: 'spanSort', + title: 'Sort', + type: 'dropdown', + options: [ + { label: 'Newest First', id: '-timestamp' }, + { label: 'Oldest First', id: 'timestamp' }, + ], + condition: { field: 'operation', value: 'datadog_search_spans' }, + mode: 'advanced', + }, + { + id: 'spanLimit', + title: 'Limit', + type: 'short-input', + placeholder: '25', + condition: { field: 'operation', value: 'datadog_search_spans' }, + mode: 'advanced', + }, + { + id: 'spanCursor', + title: 'Cursor', + type: 'short-input', + placeholder: 'Cursor returned by a previous call', + condition: { field: 'operation', value: 'datadog_search_spans' }, + mode: 'advanced', + }, + { + id: 'servicePageSize', + title: 'Page Size', + type: 'short-input', + placeholder: '25', + condition: { field: 'operation', value: 'datadog_list_services' }, + mode: 'advanced', + }, + { + id: 'servicePageNumber', + title: 'Page Number', + type: 'short-input', + placeholder: '0', + condition: { field: 'operation', value: 'datadog_list_services' }, + mode: 'advanced', + }, + { + id: 'serviceSchemaVersion', + title: 'Schema Version', + type: 'dropdown', + options: [ + { label: 'v2', id: 'v2' }, + { label: 'v2.1', id: 'v2.1' }, + { label: 'v2.2', id: 'v2.2' }, + ], + condition: { field: 'operation', value: 'datadog_list_services' }, + mode: 'advanced', + }, + // Authentication (common) { id: 'apiKey', @@ -649,10 +1838,39 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, 'datadog_get_monitor', 'datadog_list_monitors', 'datadog_mute_monitor', + 'datadog_unmute_monitor', 'datadog_query_logs', 'datadog_create_downtime', 'datadog_list_downtimes', 'datadog_cancel_downtime', + 'datadog_list_incidents', + 'datadog_get_incident', + 'datadog_create_incident', + 'datadog_update_incident', + 'datadog_add_incident_todo', + 'datadog_list_slos', + 'datadog_get_slo', + 'datadog_create_slo', + 'datadog_update_slo', + 'datadog_delete_slo', + 'datadog_get_slo_history', + 'datadog_list_dashboards', + 'datadog_get_dashboard', + 'datadog_create_dashboard', + 'datadog_delete_dashboard', + 'datadog_list_synthetics_tests', + 'datadog_get_synthetics_test', + 'datadog_get_synthetics_results', + 'datadog_get_browser_synthetics_results', + 'datadog_trigger_synthetics_tests', + 'datadog_update_synthetics_status', + 'datadog_list_security_signals', + 'datadog_get_security_signal', + 'datadog_update_security_signal_state', + 'datadog_update_security_signal_assignee', + 'datadog_list_security_rules', + 'datadog_search_spans', + 'datadog_list_services', ], }, required: true, @@ -667,7 +1885,10 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, { label: 'US5 (us5.datadoghq.com)', id: 'us5.datadoghq.com' }, { label: 'EU (datadoghq.eu)', id: 'datadoghq.eu' }, { label: 'AP1 (ap1.datadoghq.com)', id: 'ap1.datadoghq.com' }, + { label: 'AP2 (ap2.datadoghq.com)', id: 'ap2.datadoghq.com' }, + { label: 'UK1 (uk1.datadoghq.com)', id: 'uk1.datadoghq.com' }, { label: 'US1-FED (ddog-gov.com)', id: 'ddog-gov.com' }, + { label: 'US2-FED (us2.ddog-gov.com)', id: 'us2.ddog-gov.com' }, ], value: () => 'datadoghq.com', mode: 'advanced', @@ -682,23 +1903,50 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, 'datadog_get_monitor', 'datadog_list_monitors', 'datadog_mute_monitor', + 'datadog_unmute_monitor', 'datadog_query_logs', 'datadog_send_logs', 'datadog_create_downtime', 'datadog_list_downtimes', 'datadog_cancel_downtime', + 'datadog_list_incidents', + 'datadog_get_incident', + 'datadog_create_incident', + 'datadog_update_incident', + 'datadog_add_incident_todo', + 'datadog_list_slos', + 'datadog_get_slo', + 'datadog_create_slo', + 'datadog_update_slo', + 'datadog_delete_slo', + 'datadog_get_slo_history', + 'datadog_list_dashboards', + 'datadog_get_dashboard', + 'datadog_create_dashboard', + 'datadog_delete_dashboard', + 'datadog_list_synthetics_tests', + 'datadog_get_synthetics_test', + 'datadog_get_synthetics_results', + 'datadog_get_browser_synthetics_results', + 'datadog_trigger_synthetics_tests', + 'datadog_update_synthetics_status', + 'datadog_list_security_signals', + 'datadog_get_security_signal', + 'datadog_update_security_signal_state', + 'datadog_update_security_signal_assignee', + 'datadog_list_security_rules', + 'datadog_search_spans', + 'datadog_list_services', ], config: { tool: (params) => params.operation, params: (params) => { - // Base params that are always needed - const baseParams: Record = { + const baseParams: { apiKey: string; applicationKey: string; site: string } = { apiKey: params.apiKey, applicationKey: params.applicationKey, site: params.site, } - // Only include params relevant to each operation switch (params.operation) { case 'datadog_submit_metrics': return { ...baseParams, series: params.series } @@ -747,10 +1995,18 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, return { ...baseParams, monitorId: params.muteMonitorId, - scope: params.scope, + scope: params.scope || undefined, end: params.end ? Number(params.end) : undefined, } + case 'datadog_unmute_monitor': + return { + ...baseParams, + monitorId: params.muteMonitorId, + scope: params.scope || undefined, + allScopes: toSwitchBoolean(params.unmuteAllScopes), + } + case 'datadog_query_logs': return { ...baseParams, @@ -758,6 +2014,7 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, from: params.logFrom, to: params.logTo, limit: params.logLimit ? Number(params.logLimit) : undefined, + cursor: params.logCursor || undefined, } case 'datadog_send_logs': @@ -771,14 +2028,268 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, start: params.downtimeStart ? Number(params.downtimeStart) : undefined, end: params.downtimeEnd ? Number(params.downtimeEnd) : undefined, monitorId: params.downtimeMonitorId, + monitorTags: params.downtimeMonitorTags || undefined, + timezone: params.downtimeTimezone || undefined, + muteFirstRecoveryNotification: toSwitchBoolean(params.downtimeMuteFirstRecovery), } case 'datadog_list_downtimes': - return { ...baseParams, currentOnly: params.currentOnly } + return { + ...baseParams, + currentOnly: toSwitchBoolean(params.currentOnly), + limit: params.downtimeLimit ? Number(params.downtimeLimit) : undefined, + offset: params.downtimeOffset ? Number(params.downtimeOffset) : undefined, + } case 'datadog_cancel_downtime': return { ...baseParams, downtimeId: params.downtimeId } + case 'datadog_list_incidents': + return { + ...baseParams, + include: params.incidentInclude || undefined, + pageSize: params.incidentPageSize ? Number(params.incidentPageSize) : undefined, + pageOffset: params.incidentPageOffset ? Number(params.incidentPageOffset) : undefined, + } + + case 'datadog_get_incident': + return { + ...baseParams, + incidentId: params.incidentId, + include: params.incidentInclude || undefined, + } + + case 'datadog_create_incident': + return { + ...baseParams, + title: params.incidentTitle, + customerImpacted: toSwitchBoolean(params.incidentCustomerImpacted) ?? false, + severity: params.incidentSeverity || undefined, + customerImpactScope: params.incidentCustomerImpactScope || undefined, + incidentTypeUuid: params.incidentTypeUuid || undefined, + isTest: toSwitchBoolean(params.incidentIsTest), + fields: params.incidentFields || undefined, + notificationHandles: params.incidentNotificationHandles || undefined, + } + + case 'datadog_update_incident': + return { + ...baseParams, + incidentId: params.incidentId, + title: params.incidentTitle || undefined, + severity: params.incidentSeverity || undefined, + customerImpacted: toSwitchBoolean(params.incidentCustomerImpacted), + customerImpactScope: params.incidentCustomerImpactScope || undefined, + customerImpactStart: params.incidentCustomerImpactStart || undefined, + customerImpactEnd: params.incidentCustomerImpactEnd || undefined, + detected: params.incidentDetected || undefined, + fields: params.incidentFields || undefined, + notificationHandles: params.incidentNotificationHandles || undefined, + } + + case 'datadog_add_incident_todo': + return { + ...baseParams, + incidentId: params.incidentId, + content: params.todoContent, + assignees: params.todoAssignees, + dueDate: params.todoDueDate || undefined, + } + + case 'datadog_list_slos': + return { + ...baseParams, + ids: params.sloIds || undefined, + query: params.sloQuery || undefined, + tagsQuery: params.sloTagsQuery || undefined, + metricsQuery: params.sloMetricsQuery || undefined, + limit: params.sloLimit ? Number(params.sloLimit) : undefined, + offset: params.sloOffset ? Number(params.sloOffset) : undefined, + } + + case 'datadog_get_slo': + return { + ...baseParams, + sloId: params.sloId, + withConfiguredAlertIds: toSwitchBoolean(params.sloWithConfiguredAlertIds), + } + + case 'datadog_create_slo': + return { + ...baseParams, + name: params.sloName, + type: params.sloType, + thresholds: params.sloThresholds, + description: params.sloDescription || undefined, + tags: params.sloTags || undefined, + query: params.sloMetricQuery || undefined, + monitorIds: params.sloMonitorIds || undefined, + groups: params.sloGroups || undefined, + targetThreshold: params.sloTargetThreshold + ? Number(params.sloTargetThreshold) + : undefined, + warningThreshold: params.sloWarningThreshold + ? Number(params.sloWarningThreshold) + : undefined, + timeframe: params.sloTimeframe || undefined, + } + + case 'datadog_update_slo': + return { + ...baseParams, + sloId: params.sloId, + name: params.sloName || undefined, + type: params.sloType || undefined, + thresholds: params.sloThresholds || undefined, + description: params.sloDescription || undefined, + tags: params.sloTags || undefined, + query: params.sloMetricQuery || undefined, + monitorIds: params.sloMonitorIds || undefined, + groups: params.sloGroups || undefined, + targetThreshold: params.sloTargetThreshold + ? Number(params.sloTargetThreshold) + : undefined, + warningThreshold: params.sloWarningThreshold + ? Number(params.sloWarningThreshold) + : undefined, + timeframe: params.sloTimeframe || undefined, + } + + case 'datadog_delete_slo': + return { + ...baseParams, + sloId: params.sloId, + force: toSwitchBoolean(params.sloForce), + } + + case 'datadog_get_slo_history': + return { + ...baseParams, + sloId: params.sloId, + fromTs: params.sloFromTs ? Number(params.sloFromTs) : undefined, + toTs: params.sloToTs ? Number(params.sloToTs) : undefined, + target: params.sloTarget ? Number(params.sloTarget) : undefined, + applyCorrection: toSwitchBoolean(params.sloApplyCorrection), + } + + case 'datadog_list_dashboards': + return { + ...baseParams, + filterShared: toSwitchBoolean(params.dashboardFilterShared), + filterDeleted: toSwitchBoolean(params.dashboardFilterDeleted), + count: params.dashboardCount ? Number(params.dashboardCount) : undefined, + start: params.dashboardStart ? Number(params.dashboardStart) : undefined, + } + + case 'datadog_get_dashboard': + return { ...baseParams, dashboardId: params.dashboardId } + + case 'datadog_create_dashboard': + return { + ...baseParams, + title: params.dashboardTitle, + layoutType: params.dashboardLayoutType, + widgets: params.dashboardWidgets, + description: params.dashboardDescription || undefined, + notifyList: params.dashboardNotifyList || undefined, + templateVariables: params.dashboardTemplateVariables || undefined, + tags: params.dashboardTags || undefined, + reflowType: params.dashboardReflowType || undefined, + } + + case 'datadog_delete_dashboard': + return { ...baseParams, dashboardId: params.dashboardId } + + case 'datadog_list_synthetics_tests': + return { + ...baseParams, + pageSize: params.syntheticsPageSize ? Number(params.syntheticsPageSize) : undefined, + pageNumber: params.syntheticsPageNumber + ? Number(params.syntheticsPageNumber) + : undefined, + } + + case 'datadog_get_synthetics_test': + return { ...baseParams, publicId: params.syntheticsPublicId } + + case 'datadog_get_synthetics_results': + case 'datadog_get_browser_synthetics_results': + return { + ...baseParams, + publicId: params.syntheticsPublicId, + fromTs: params.syntheticsFromTs ? Number(params.syntheticsFromTs) : undefined, + toTs: params.syntheticsToTs ? Number(params.syntheticsToTs) : undefined, + probeDc: params.syntheticsProbeDc || undefined, + } + + case 'datadog_trigger_synthetics_tests': + return { ...baseParams, publicIds: params.syntheticsPublicIds } + + case 'datadog_update_synthetics_status': + return { + ...baseParams, + publicId: params.syntheticsPublicId, + newStatus: params.syntheticsNewStatus, + } + + case 'datadog_list_security_signals': + return { + ...baseParams, + query: params.signalQuery || undefined, + from: params.signalFrom || undefined, + to: params.signalTo || undefined, + sort: params.signalSort || undefined, + cursor: params.signalCursor || undefined, + limit: params.signalLimit ? Number(params.signalLimit) : undefined, + } + + case 'datadog_get_security_signal': + return { ...baseParams, signalId: params.signalId } + + case 'datadog_update_security_signal_state': + return { + ...baseParams, + signalId: params.signalId, + state: params.signalState, + archiveReason: params.signalArchiveReason || undefined, + archiveComment: params.signalArchiveComment || undefined, + } + + case 'datadog_update_security_signal_assignee': + return { + ...baseParams, + signalId: params.signalId, + assigneeUuid: params.signalAssigneeUuid, + } + + case 'datadog_list_security_rules': + return { + ...baseParams, + query: params.ruleQuery || undefined, + sort: params.ruleSort || undefined, + pageSize: params.rulePageSize ? Number(params.rulePageSize) : undefined, + pageNumber: params.rulePageNumber ? Number(params.rulePageNumber) : undefined, + } + + case 'datadog_search_spans': + return { + ...baseParams, + query: params.spanQuery || undefined, + from: params.spanFrom || undefined, + to: params.spanTo || undefined, + sort: params.spanSort || undefined, + cursor: params.spanCursor || undefined, + limit: params.spanLimit ? Number(params.spanLimit) : undefined, + } + + case 'datadog_list_services': + return { + ...baseParams, + pageSize: params.servicePageSize ? Number(params.servicePageSize) : undefined, + pageNumber: params.servicePageNumber ? Number(params.servicePageNumber) : undefined, + schemaVersion: params.serviceSchemaVersion || undefined, + } + default: return baseParams } @@ -810,10 +2321,11 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, monitorPriority: { type: 'number', description: 'Monitor priority (1-5)' }, options: { type: 'json', description: 'Monitor options' }, monitorId: { type: 'string', description: 'Monitor ID' }, - muteMonitorId: { type: 'string', description: 'Monitor ID to mute' }, - scope: { type: 'string', description: 'Scope for muting' }, - end: { type: 'number', description: 'End time for mute' }, // Logs + muteMonitorId: { type: 'string', description: 'Monitor ID to mute or unmute' }, + scope: { type: 'string', description: 'Scope to mute or unmute' }, + end: { type: 'number', description: 'Unix timestamp when the mute ends' }, + unmuteAllScopes: { type: 'boolean', description: 'Clear mute settings for every scope' }, logQuery: { type: 'string', description: 'Log search query' }, logFrom: { type: 'string', description: 'Log start time' }, logTo: { type: 'string', description: 'Log end time' }, @@ -825,10 +2337,115 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, downtimeStart: { type: 'number', description: 'Downtime start time' }, downtimeEnd: { type: 'number', description: 'Downtime end time' }, downtimeMonitorId: { type: 'string', description: 'Monitor ID for downtime' }, + downtimeMonitorTags: { + type: 'string', + description: 'Comma-separated monitor tags to target', + }, + downtimeTimezone: { type: 'string', description: 'Display timezone for the downtime' }, + downtimeLimit: { type: 'number', description: 'Downtimes to return per page' }, + downtimeOffset: { type: 'number', description: 'Index of the first downtime to return' }, + downtimeMuteFirstRecovery: { + type: 'boolean', + description: 'Mute the first recovery notification', + }, currentOnly: { type: 'boolean', description: 'Filter to current downtimes' }, downtimeId: { type: 'string', description: 'Downtime ID to cancel' }, listMonitorName: { type: 'string', description: 'Filter monitors by name' }, listMonitorTags: { type: 'string', description: 'Filter monitors by tags' }, + // Incidents + incidentId: { type: 'string', description: 'Incident UUID' }, + incidentTitle: { type: 'string', description: 'Incident title' }, + incidentCustomerImpacted: { type: 'boolean', description: 'Whether customers were impacted' }, + incidentSeverity: { type: 'string', description: 'Incident severity' }, + incidentCustomerImpactScope: { type: 'string', description: 'Summary of the customer impact' }, + incidentCustomerImpactStart: { type: 'string', description: 'Customer impact start timestamp' }, + incidentCustomerImpactEnd: { type: 'string', description: 'Customer impact end timestamp' }, + incidentDetected: { type: 'string', description: 'Detection timestamp' }, + incidentTypeUuid: { type: 'string', description: 'Incident type UUID' }, + incidentIsTest: { type: 'boolean', description: 'Whether the incident is a test' }, + incidentFields: { type: 'json', description: 'User-defined incident fields' }, + incidentNotificationHandles: { type: 'string', description: 'Handles to notify' }, + incidentInclude: { type: 'string', description: 'Related resources to include' }, + incidentPageSize: { type: 'number', description: 'Incidents per page' }, + incidentPageOffset: { type: 'number', description: 'Incident page offset' }, + todoContent: { type: 'string', description: 'Follow-up task content' }, + todoAssignees: { type: 'string', description: 'Follow-up task assignees' }, + todoDueDate: { type: 'string', description: 'Follow-up task due date' }, + // SLOs + sloId: { type: 'string', description: 'SLO ID' }, + sloName: { type: 'string', description: 'SLO name' }, + sloType: { type: 'string', description: 'SLO type' }, + sloThresholds: { type: 'json', description: 'SLO thresholds' }, + sloDescription: { type: 'string', description: 'SLO description' }, + sloTags: { type: 'string', description: 'SLO tags' }, + sloMetricQuery: { type: 'json', description: 'Metric SLO numerator and denominator' }, + sloMonitorIds: { type: 'string', description: 'Monitor IDs for monitor SLOs' }, + sloGroups: { type: 'string', description: 'Monitor groups for monitor SLOs' }, + sloTargetThreshold: { type: 'number', description: 'Primary target threshold' }, + sloWarningThreshold: { type: 'number', description: 'Primary warning threshold' }, + sloTimeframe: { type: 'string', description: 'Primary timeframe' }, + sloIds: { type: 'string', description: 'Filter SLOs by IDs' }, + sloQuery: { type: 'string', description: 'Filter SLOs by name' }, + sloTagsQuery: { type: 'string', description: 'Filter SLOs by tag' }, + sloMetricsQuery: { type: 'string', description: 'Filter SLOs by metrics query' }, + sloLimit: { type: 'number', description: 'Max SLOs to return' }, + sloOffset: { type: 'number', description: 'SLO list offset' }, + sloWithConfiguredAlertIds: { type: 'boolean', description: 'Include SLO monitor IDs' }, + sloForce: { type: 'boolean', description: 'Force SLO deletion' }, + sloFromTs: { type: 'number', description: 'SLO history window start (Unix seconds)' }, + sloToTs: { type: 'number', description: 'SLO history window end (Unix seconds)' }, + sloTarget: { type: 'number', description: 'SLO target for history queries' }, + sloApplyCorrection: { type: 'boolean', description: 'Apply SLO corrections' }, + // Dashboards + dashboardId: { type: 'string', description: 'Dashboard ID' }, + dashboardTitle: { type: 'string', description: 'Dashboard title' }, + dashboardLayoutType: { type: 'string', description: 'Dashboard layout type' }, + dashboardWidgets: { type: 'json', description: 'Dashboard widget definitions' }, + dashboardDescription: { type: 'string', description: 'Dashboard description' }, + dashboardTags: { type: 'string', description: 'Dashboard tags' }, + dashboardNotifyList: { type: 'string', description: 'Handles notified on changes' }, + dashboardTemplateVariables: { type: 'json', description: 'Template variable definitions' }, + dashboardReflowType: { type: 'string', description: 'Dashboard reflow type' }, + dashboardFilterShared: { type: 'boolean', description: 'Return only shared dashboards' }, + dashboardFilterDeleted: { type: 'boolean', description: 'Return only deleted dashboards' }, + dashboardCount: { type: 'number', description: 'Max dashboards to return' }, + dashboardStart: { type: 'number', description: 'Dashboard list offset' }, + // Synthetics + syntheticsPublicId: { type: 'string', description: 'Synthetic test public ID' }, + syntheticsPublicIds: { type: 'string', description: 'Synthetic test public IDs to trigger' }, + syntheticsNewStatus: { type: 'string', description: 'New Synthetic test status' }, + syntheticsFromTs: { type: 'number', description: 'Results window start (Unix milliseconds)' }, + syntheticsToTs: { type: 'number', description: 'Results window end (Unix milliseconds)' }, + syntheticsProbeDc: { type: 'string', description: 'Locations to query results for' }, + syntheticsPageSize: { type: 'number', description: 'Synthetic tests per page' }, + syntheticsPageNumber: { type: 'number', description: 'Synthetic tests page number' }, + // Security monitoring + signalId: { type: 'string', description: 'Security signal ID' }, + signalState: { type: 'string', description: 'Security signal triage state' }, + signalArchiveReason: { type: 'string', description: 'Archive reason' }, + signalArchiveComment: { type: 'string', description: 'Archive comment' }, + signalAssigneeUuid: { type: 'string', description: 'UUID of the assignee' }, + signalQuery: { type: 'string', description: 'Security signal search query' }, + signalFrom: { type: 'string', description: 'Signal search window start' }, + signalTo: { type: 'string', description: 'Signal search window end' }, + signalSort: { type: 'string', description: 'Signal sort order' }, + signalLimit: { type: 'number', description: 'Max signals to return' }, + signalCursor: { type: 'string', description: 'Signal pagination cursor' }, + ruleQuery: { type: 'string', description: 'Detection rule search query' }, + ruleSort: { type: 'string', description: 'Detection rule sort order' }, + rulePageSize: { type: 'number', description: 'Detection rules per page' }, + rulePageNumber: { type: 'number', description: 'Detection rules page number' }, + // APM + spanQuery: { type: 'string', description: 'Span search query' }, + spanFrom: { type: 'string', description: 'Span search window start' }, + spanTo: { type: 'string', description: 'Span search window end' }, + spanSort: { type: 'string', description: 'Span sort order' }, + spanLimit: { type: 'number', description: 'Max spans to return' }, + spanCursor: { type: 'string', description: 'Span pagination cursor' }, + logCursor: { type: 'string', description: 'Log search pagination cursor' }, + servicePageSize: { type: 'number', description: 'Service definitions per page' }, + servicePageNumber: { type: 'number', description: 'Service definitions page number' }, + serviceSchemaVersion: { type: 'string', description: 'Service definition schema version' }, }, outputs: { success: { type: 'boolean', description: 'Whether the operation succeeded' }, @@ -847,6 +2464,39 @@ Return ONLY the numeric timestamp - no explanations, no quotes, no extra text.`, // Downtimes downtime: { type: 'json', description: 'Downtime data' }, downtimes: { type: 'json', description: 'List of downtimes' }, + totalCount: { type: 'number', description: 'Total downtimes matching the filter' }, + // Incidents + incident: { type: 'json', description: 'Incident data' }, + incidents: { type: 'json', description: 'List of incidents' }, + nextOffset: { type: 'number', description: 'Offset for the next page of incidents' }, + todo: { type: 'json', description: 'Incident follow-up task' }, + // SLOs + slo: { type: 'json', description: 'Service level objective' }, + slos: { type: 'json', description: 'List of service level objectives' }, + history: { type: 'json', description: 'SLO history for the requested window' }, + sliValue: { type: 'number', description: 'Overall SLI value over the window' }, + deletedIds: { type: 'json', description: 'IDs of deleted service level objectives' }, + // Dashboards + dashboard: { type: 'json', description: 'Dashboard definition' }, + dashboards: { type: 'json', description: 'List of dashboard summaries' }, + deletedDashboardId: { type: 'string', description: 'ID of the deleted dashboard' }, + // Synthetics + test: { type: 'json', description: 'Synthetic test configuration' }, + tests: { type: 'json', description: 'List of Synthetic tests' }, + results: { type: 'json', description: 'Synthetic test run results' }, + lastTimestampFetched: { type: 'number', description: 'Timestamp of the latest test run' }, + batchId: { type: 'string', description: 'Public ID of the triggered batch' }, + triggeredCheckIds: { type: 'json', description: 'Public IDs of triggered tests' }, + locations: { type: 'json', description: 'Locations the tests ran from' }, + // Security monitoring + signal: { type: 'json', description: 'Security signal' }, + signals: { type: 'json', description: 'List of security signals' }, + rules: { type: 'json', description: 'List of detection rules' }, + nextCursor: { type: 'string', description: 'Cursor for the next page of results' }, + // APM + spans: { type: 'json', description: 'List of APM spans' }, + elapsed: { type: 'number', description: 'Query time in milliseconds' }, + services: { type: 'json', description: 'List of service definitions' }, }, } diff --git a/apps/sim/lib/integrations/integrations.json b/apps/sim/lib/integrations/integrations.json index 6908e2840d..283a744769 100644 --- a/apps/sim/lib/integrations/integrations.json +++ b/apps/sim/lib/integrations/integrations.json @@ -4933,7 +4933,11 @@ }, { "name": "Mute Monitor", - "description": "Mute a monitor to temporarily suppress notifications." + "description": "Mute a monitor to temporarily suppress its notifications. Use Unmute Monitor to reverse it, or schedule a downtime instead when you want a planned, auditable maintenance window." + }, + { + "name": "Unmute Monitor", + "description": "Unmute a monitor so it resumes sending notifications. Reverses Mute Monitor, either for one scope or for every scope at once." }, { "name": "Query Logs", @@ -4954,9 +4958,121 @@ { "name": "Cancel Downtime", "description": "Cancel a scheduled downtime." + }, + { + "name": "List Incidents", + "description": "List incidents for the organization. Requires the Incident Management `incident_read` permission; the Incidents API is in public beta." + }, + { + "name": "Get Incident", + "description": "Get the details of a single incident by ID. Requires the Incident Management `incident_read` permission; the Incidents API is in public beta." + }, + { + "name": "Create Incident", + "description": "Declare a new incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta." + }, + { + "name": "Update Incident", + "description": "Partially update an existing incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta." + }, + { + "name": "Add Incident Todo", + "description": "Add a follow-up task (todo) to an incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta." + }, + { + "name": "List SLOs", + "description": "List service level objectives, optionally filtered by IDs, name, tags, or underlying metrics query." + }, + { + "name": "Get SLO", + "description": "Get the configuration of a single service level objective by ID." + }, + { + "name": "Create SLO", + "description": "Create a service level objective from a metric query, monitors, or a time-slice condition." + }, + { + "name": "Update SLO", + "description": "Update a service level objective. Reads the current SLO first and applies only the fields you supply, so anything left blank keeps its stored value." + }, + { + "name": "Delete SLO", + "description": "Permanently delete a service level objective. Datadog returns a conflict when the SLO is still referenced by a dashboard." + }, + { + "name": "Get SLO History", + "description": "Get an SLO’s history over a time window, including the overall SLI value and remaining error budget." + }, + { + "name": "List Dashboards", + "description": "List custom created or cloned dashboards. Datadog preset dashboards are not returned." + }, + { + "name": "Get Dashboard", + "description": "Get the full definition of a dashboard, including its widgets." + }, + { + "name": "Create Dashboard", + "description": "Create a dashboard from a title, layout type, and widget definitions." + }, + { + "name": "Delete Dashboard", + "description": "Delete a dashboard by ID." + }, + { + "name": "List Synthetic Tests", + "description": "List all Synthetic tests (API, browser, and mobile) with their current status." + }, + { + "name": "Get Synthetic Test", + "description": "Get the configuration of a Synthetic test by public ID. Browser test steps are not included by this type-agnostic endpoint." + }, + { + "name": "Get Synthetic Test Results", + "description": "Get the latest result summaries (up to the last 150 runs) for a Synthetic API test." + }, + { + "name": "Get Browser Synthetic Test Results", + "description": "Get the latest result summaries (up to the last 150 runs) for a Synthetic browser test, including step counts and errors." + }, + { + "name": "Trigger Synthetic Tests", + "description": "Trigger an immediate run of one or more Synthetic tests by public ID." + }, + { + "name": "Pause Or Start Synthetic Test", + "description": "Pause or resume a Synthetic test by setting its status to \"paused\" or \"live\"." + }, + { + "name": "List Security Signals", + "description": "Search Cloud SIEM security signals by query and time range. Requires the `security_monitoring_signals_read` permission." + }, + { + "name": "Get Security Signal", + "description": "Get the details of a single Cloud SIEM security signal. Requires the `security_monitoring_signals_read` permission." + }, + { + "name": "Update Security Signal State", + "description": "Change the triage state of a Cloud SIEM security signal to open, under_review, or archived. Requires the `security_monitoring_signals_write` permission." + }, + { + "name": "Assign Security Signal", + "description": "Assign a Cloud SIEM security signal to a Datadog user by UUID. Requires the `security_monitoring_signals_write` permission." + }, + { + "name": "List Security Rules", + "description": "List Cloud SIEM detection rules. Requires the `security_monitoring_rules_read` permission." + }, + { + "name": "Search Spans", + "description": "Search indexed APM spans using the span query syntax, with cursor pagination." + }, + { + "name": "List Services", + "description": "List service definitions from the Datadog Service Catalog. Requires the `apm_service_catalog_read` permission." } ], - "operationCount": 12, + "operationCount": 41, "triggers": [], "triggerCount": 0, "authType": "api-key", diff --git a/apps/sim/tools/datadog/add_incident_todo.ts b/apps/sim/tools/datadog/add_incident_todo.ts new file mode 100644 index 0000000000..c82dc16b63 --- /dev/null +++ b/apps/sim/tools/datadog/add_incident_todo.ts @@ -0,0 +1,127 @@ +import type { AddIncidentTodoParams, AddIncidentTodoResponse } from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const addIncidentTodoTool: ToolConfig = { + id: 'datadog_add_incident_todo', + name: 'Datadog Add Incident Todo', + description: + 'Add a follow-up task (todo) to an incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta.', + version: '1.0.0', + + params: { + incidentId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The UUID of the incident the todo belongs to', + }, + content: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The follow-up task content (e.g., "Restore lost data")', + }, + assignees: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: + 'Comma-separated assignee handles (e.g., "@jane@example.com,@on-call"). Datadog requires at least one assignee', + }, + dueDate: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'ISO-8601 timestamp for when the todo should be completed', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl( + params.site, + `/api/v2/incidents/${encodeURIComponent(params.incidentId)}/relationships/todos` + ), + method: 'POST', + headers: datadogHeaders, + body: (params) => { + const attributes: Record = { + content: params.content, + assignees: splitCommaList(params.assignees) ?? [], + incident_id: params.incidentId, + } + if (params.dueDate) attributes.due_date = params.dueDate + + return { data: { type: 'incident_todos', attributes } } + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { todo: { attributes: {} } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + todo: { + id: data.data?.id, + type: data.data?.type, + attributes: data.data?.attributes ?? {}, + }, + }, + } + }, + + outputs: { + todo: { + type: 'object', + description: 'The created incident todo', + properties: { + id: { type: 'string', description: 'Todo UUID' }, + type: { type: 'string', description: 'Resource type (incident_todos)' }, + attributes: { + type: 'object', + description: 'Todo attributes', + properties: { + content: { type: 'string', description: 'Task content' }, + assignees: { type: 'array', description: 'Assignee handles' }, + due_date: { type: 'string', description: 'Due date' }, + completed: { type: 'string', description: 'Completion timestamp' }, + incident_id: { type: 'string', description: 'UUID of the parent incident' }, + }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/cancel_downtime.ts b/apps/sim/tools/datadog/cancel_downtime.ts index 89b701fa96..7c99ba9b3f 100644 --- a/apps/sim/tools/datadog/cancel_downtime.ts +++ b/apps/sim/tools/datadog/cancel_downtime.ts @@ -1,4 +1,5 @@ import type { CancelDowntimeParams, CancelDowntimeResponse } from '@/tools/datadog/types' +import { datadogErrorMessage } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const cancelDowntimeTool: ToolConfig = { @@ -49,13 +50,13 @@ export const cancelDowntimeTool: ToolConfig { if (!response.ok && response.status !== 204) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { success: false, }, - error: errorData.errors?.[0]?.detail || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } diff --git a/apps/sim/tools/datadog/create_dashboard.ts b/apps/sim/tools/datadog/create_dashboard.ts new file mode 100644 index 0000000000..bf0951cb2d --- /dev/null +++ b/apps/sim/tools/datadog/create_dashboard.ts @@ -0,0 +1,149 @@ +import type { CreateDashboardParams, CreateDashboardResponse } from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + parseJsonParam, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const createDashboardTool: ToolConfig = { + id: 'datadog_create_dashboard', + name: 'Datadog Create Dashboard', + description: 'Create a dashboard from a title, layout type, and widget definitions.', + version: '1.0.0', + + params: { + title: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'Title of the dashboard', + }, + layoutType: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'Layout type: "ordered" or "free"', + }, + widgets: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: + 'JSON array of widget definitions, e.g. [{"definition": {"type": "timeseries", "requests": [{"q": "avg:system.cpu.user{*}"}]}}]', + }, + description: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Description of the dashboard', + }, + notifyList: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated user handles to notify on dashboard changes', + }, + templateVariables: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'JSON array of template variable definitions, e.g. [{"name": "env", "prefix": "env", "available_values": ["prod"]}]', + }, + tags: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated dashboard tags in the form "team:" (max 5)', + }, + reflowType: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Reflow type for ordered layouts: "auto" or "fixed"', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, '/api/v1/dashboard'), + method: 'POST', + headers: datadogHeaders, + body: (params) => { + const body: Record = { + title: params.title, + layout_type: params.layoutType, + widgets: parseJsonParam(params.widgets, 'widgets parameter') ?? [], + } + + if (params.description) body.description = params.description + if (params.reflowType) body.reflow_type = params.reflowType + + const notifyList = splitCommaList(params.notifyList) + if (notifyList) body.notify_list = notifyList + + const tags = splitCommaList(params.tags) + if (tags) body.tags = tags + + const templateVariables = parseJsonParam( + params.templateVariables, + 'templateVariables parameter' + ) + if (templateVariables) body.template_variables = templateVariables + + return body + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { dashboard: {} }, + error: await datadogErrorMessage(response), + } + } + + return { + success: true, + output: { dashboard: await response.json() }, + } + }, + + outputs: { + dashboard: { + type: 'object', + description: 'The created dashboard', + properties: { + id: { type: 'string', description: 'Dashboard ID' }, + title: { type: 'string', description: 'Dashboard title' }, + layout_type: { type: 'string', description: 'Layout type: ordered or free' }, + url: { type: 'string', description: 'Dashboard URL path' }, + author_handle: { type: 'string', description: 'Handle of the dashboard author' }, + created_at: { type: 'string', description: 'Creation timestamp' }, + modified_at: { type: 'string', description: 'Modification timestamp' }, + widgets: { type: 'array', description: 'Widget definitions' }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/create_downtime.ts b/apps/sim/tools/datadog/create_downtime.ts index 56f5334939..4d9f235d79 100644 --- a/apps/sim/tools/datadog/create_downtime.ts +++ b/apps/sim/tools/datadog/create_downtime.ts @@ -1,4 +1,9 @@ -import type { CreateDowntimeParams, CreateDowntimeResponse } from '@/tools/datadog/types' +import type { + CreateDowntimeParams, + CreateDowntimeResponse, + DowntimeAttributes, +} from '@/tools/datadog/types' +import { datadogErrorMessage, parseMonitorIds, splitCommaList } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const createDowntimeTool: ToolConfig = { @@ -90,57 +95,62 @@ export const createDowntimeTool: ToolConfig { - const schedule: Record = {} + // A one-time schedule accepts only `start` and `end` (`additionalProperties: false`); + // the timezone is a display-only attribute on the downtime itself. + const schedule: { start?: string; end?: string } = {} if (params.start) schedule.start = new Date(params.start * 1000).toISOString() if (params.end) schedule.end = new Date(params.end * 1000).toISOString() - if (params.timezone) schedule.timezone = params.timezone - const body: Record = { - data: { - type: 'downtime', - attributes: { - scope: params.scope, - schedule: Object.keys(schedule).length > 0 ? schedule : undefined, - }, - }, + const monitorTags = splitCommaList(params.monitorTags) + const monitorId = parseMonitorIds(params.monitorId)?.[0] + + /** + * `monitor_identifier` is required and is a `oneOf`: a downtime targets either a + * single monitor or a tag set, never both. Accepting both silently would drop one + * of them and mute a different set of monitors than the caller asked for. Both + * sides are compared after parsing so a blank or whitespace-only input, which is + * how an untouched field arrives, does not read as a chosen target. + */ + if (monitorId !== undefined && monitorTags) { + throw new Error( + 'Supply either a monitor ID or monitor tags, not both — a downtime targets one or the other' + ) } - if (params.message) body.data.attributes.message = params.message + // Datadog expresses "every monitor in scope" as the `*` monitor tag, which is the + // fallback when no monitor is named. + const monitorIdentifier = + monitorId !== undefined ? { monitor_id: monitorId } : { monitor_tags: monitorTags ?? ['*'] } + + const attributes: Record = { + scope: params.scope, + monitor_identifier: monitorIdentifier, + } + if (Object.keys(schedule).length > 0) attributes.schedule = schedule + if (params.timezone) attributes.display_timezone = params.timezone + if (params.message) attributes.message = params.message if (params.muteFirstRecoveryNotification !== undefined) { - body.data.attributes.mute_first_recovery_notification = params.muteFirstRecoveryNotification + attributes.mute_first_recovery_notification = params.muteFirstRecoveryNotification } - if (params.monitorId) { - body.data.attributes.monitor_identifier = { - monitor_id: Number.parseInt(params.monitorId, 10), - } - } else if (params.monitorTags) { - body.data.attributes.monitor_identifier = { - monitor_tags: params.monitorTags - .split(',') - .map((t: string) => t.trim()) - .filter((t: string) => t.length > 0), - } - } - - return body + return { data: { type: 'downtime', attributes } } }, }, transformResponse: async (response: Response) => { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { - downtime: {} as any, + downtime: { scope: [] }, }, - error: errorData.errors?.[0]?.detail || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } const data = await response.json() - const attrs = data.data?.attributes || {} + const attrs: DowntimeAttributes = data.data?.attributes || {} return { success: true, output: { @@ -152,8 +162,7 @@ export const createDowntimeTool: ToolConfig = { @@ -91,7 +97,17 @@ export const createEventTool: ToolConfig 'DD-API-KEY': params.apiKey, }), body: (params) => { - const body: Record = { + const body: { + title: string + text: string + alert_type?: EventAlertType + priority?: EventPriority + host?: string + aggregation_key?: string + source_type_name?: string + date_happened?: number + tags?: string[] + } = { title: params.title, text: params.text, } @@ -116,13 +132,13 @@ export const createEventTool: ToolConfig transformResponse: async (response: Response) => { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { - event: {} as any, + event: {}, }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } diff --git a/apps/sim/tools/datadog/create_incident.ts b/apps/sim/tools/datadog/create_incident.ts new file mode 100644 index 0000000000..5e6a2d7114 --- /dev/null +++ b/apps/sim/tools/datadog/create_incident.ts @@ -0,0 +1,162 @@ +import type { CreateIncidentParams, CreateIncidentResponse } from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + parseJsonParam, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const createIncidentTool: ToolConfig = { + id: 'datadog_create_incident', + name: 'Datadog Create Incident', + description: + 'Declare a new incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta.', + version: '1.0.0', + + params: { + title: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'Title of the incident summarizing what happened', + }, + customerImpacted: { + type: 'boolean', + required: true, + visibility: 'user-or-llm', + description: 'Whether the incident caused customer impact', + }, + severity: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Incident severity: UNKNOWN, SEV-0, SEV-1, SEV-2, SEV-3, SEV-4, or SEV-5', + }, + customerImpactScope: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Summary of the customer impact. Required when customerImpacted is true', + }, + incidentTypeUuid: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'UUID of the incident type. The default incident type is used when omitted', + }, + isTest: { + type: 'boolean', + required: false, + visibility: 'user-or-llm', + description: 'Whether this is a test incident', + }, + fields: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'JSON object of user-defined incident fields, e.g. {"severity": {"type": "dropdown", "value": "SEV-2"}}', + }, + notificationHandles: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Comma-separated handles to notify on creation (e.g., "@slack-incidents,@user@example.com")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, '/api/v2/incidents'), + method: 'POST', + headers: datadogHeaders, + body: (params) => { + const fields = + parseJsonParam>(params.fields, 'fields parameter') ?? {} + if (params.severity) { + fields.severity = { type: 'dropdown', value: params.severity } + } + + const attributes: Record = { + title: params.title, + customer_impacted: params.customerImpacted, + } + if (params.customerImpactScope) attributes.customer_impact_scope = params.customerImpactScope + if (params.incidentTypeUuid) attributes.incident_type_uuid = params.incidentTypeUuid + if (params.isTest !== undefined) attributes.is_test = params.isTest + if (Object.keys(fields).length > 0) attributes.fields = fields + + const handles = splitCommaList(params.notificationHandles) + if (handles) { + attributes.notification_handles = handles.map((handle) => ({ handle })) + } + + return { data: { type: 'incidents', attributes } } + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { incident: { id: '', attributes: {} } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + incident: { + id: data.data?.id, + type: data.data?.type, + attributes: data.data?.attributes ?? {}, + }, + }, + } + }, + + outputs: { + incident: { + type: 'object', + description: 'The created incident', + properties: { + id: { type: 'string', description: 'Incident UUID' }, + type: { type: 'string', description: 'Resource type (incidents)' }, + attributes: { + type: 'object', + description: 'Incident attributes', + properties: { + title: { type: 'string', description: 'Incident title' }, + public_id: { type: 'number', description: 'Incremental public incident ID' }, + customer_impacted: { type: 'boolean', description: 'Whether customers were impacted' }, + created: { type: 'string', description: 'Creation timestamp' }, + modified: { type: 'string', description: 'Last modification timestamp' }, + }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/create_monitor.ts b/apps/sim/tools/datadog/create_monitor.ts index d08da95eae..d2d99e3882 100644 --- a/apps/sim/tools/datadog/create_monitor.ts +++ b/apps/sim/tools/datadog/create_monitor.ts @@ -1,4 +1,5 @@ -import type { CreateMonitorParams, CreateMonitorResponse } from '@/tools/datadog/types' +import type { CreateMonitorParams, CreateMonitorResponse, MonitorType } from '@/tools/datadog/types' +import { datadogErrorMessage, parseJsonParam } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const createMonitorTool: ToolConfig = { @@ -86,7 +87,15 @@ export const createMonitorTool: ToolConfig { - const body: Record = { + const body: { + name: string + type: MonitorType + query: string + message?: string + priority?: number + tags?: string[] + options?: unknown + } = { name: params.name, type: params.type, query: params.query, @@ -102,14 +111,8 @@ export const createMonitorTool: ToolConfig t.length > 0) } - if (params.options) { - try { - body.options = - typeof params.options === 'string' ? JSON.parse(params.options) : params.options - } catch { - // If options parsing fails, skip it - } - } + const options = parseJsonParam>(params.options, 'options parameter') + if (options) body.options = options return body }, @@ -117,13 +120,13 @@ export const createMonitorTool: ToolConfig { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { - monitor: {} as any, + monitor: {}, }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } @@ -164,6 +167,11 @@ export const createMonitorTool: ToolConfig = { + id: 'datadog_create_slo', + name: 'Datadog Create SLO', + description: + 'Create a service level objective from a metric query, monitors, or a time-slice condition.', + version: '1.0.0', + + params: { + name: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'Name of the SLO (e.g., "Checkout API availability")', + }, + type: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: + 'SLO type: "metric" (supply query) or "monitor" (supply monitorIds). Time-slice SLOs are not supported here because they need an SLI specification this tool does not send.', + }, + thresholds: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: + 'JSON array of thresholds, e.g. [{"timeframe": "30d", "target": 99.9, "warning": 99.95}]', + }, + description: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Description of the SLO', + }, + tags: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated tags (e.g., "env:prod,team:core")', + }, + query: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'For metric SLOs, JSON with numerator and denominator, e.g. {"numerator": "sum:requests{status:ok}.as_count()", "denominator": "sum:requests{*}.as_count()"}', + }, + monitorIds: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'For monitor SLOs, comma-separated monitor IDs (e.g., "123,456")', + }, + groups: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'For monitor SLOs with a single monitor, comma-separated monitor groups (e.g., "env:prod,role:mysql")', + }, + targetThreshold: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Primary target threshold (e.g., 99.9)', + }, + warningThreshold: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Primary warning threshold, must be greater than the target (e.g., 99.95)', + }, + timeframe: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Primary timeframe: "7d", "30d", or "90d"', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, '/api/v1/slo'), + method: 'POST', + headers: datadogHeaders, + body: buildSloPayload, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { slo: { id: '', name: '', type: '' } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { slo: data.data?.[0] ?? { id: '', name: '', type: '' } }, + } + }, + + outputs: { + slo: { + type: 'object', + description: 'The created service level objective', + properties: { + id: { type: 'string', description: 'SLO ID' }, + name: { type: 'string', description: 'SLO name' }, + type: { type: 'string', description: 'SLO type' }, + description: { type: 'string', description: 'SLO description' }, + tags: { type: 'array', description: 'SLO tags' }, + thresholds: { type: 'array', description: 'Timeframe targets and warnings' }, + created_at: { type: 'number', description: 'Creation timestamp (Unix seconds)' }, + modified_at: { type: 'number', description: 'Modification timestamp (Unix seconds)' }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/datadog.test.ts b/apps/sim/tools/datadog/datadog.test.ts new file mode 100644 index 0000000000..72d9ba14ae --- /dev/null +++ b/apps/sim/tools/datadog/datadog.test.ts @@ -0,0 +1,456 @@ +/** + * @vitest-environment node + */ +import { beforeEach, describe, expect, it, vi } from 'vitest' +import { createDowntimeTool } from '@/tools/datadog/create_downtime' +import { createEventTool } from '@/tools/datadog/create_event' +import { createMonitorTool } from '@/tools/datadog/create_monitor' +import { getIncidentTool } from '@/tools/datadog/get_incident' +import { listDowntimesTool } from '@/tools/datadog/list_downtimes' +import { listIncidentsTool } from '@/tools/datadog/list_incidents' +import { muteMonitorTool } from '@/tools/datadog/mute_monitor' +import { queryLogsTool } from '@/tools/datadog/query_logs' +import { queryTimeseriesTool } from '@/tools/datadog/query_timeseries' +import { sendLogsTool } from '@/tools/datadog/send_logs' +import { submitMetricsTool } from '@/tools/datadog/submit_metrics' +import { unmuteMonitorTool } from '@/tools/datadog/unmute_monitor' +import { updateIncidentTool } from '@/tools/datadog/update_incident' +import { updateSloTool } from '@/tools/datadog/update_slo' +import { + buildSloPayload, + datadogErrorMessage, + mergeSloUpdatePayload, + splitCommaList, +} from '@/tools/datadog/utils' + +const auth = { apiKey: 'key', applicationKey: 'app-key' } as const + +function jsonResponse(body: unknown, init?: { status?: number; statusText?: string }): Response { + return new Response(JSON.stringify(body), { + status: init?.status ?? 200, + statusText: init?.statusText ?? 'OK', + headers: { 'Content-Type': 'application/json' }, + }) +} + +function callBody( + tool: { request: { body?: (params: TParams) => unknown } }, + params: TParams +): any { + return tool.request.body?.(params) +} + +function callUrl(tool: { request: { url: unknown } }, params: TParams): string { + const url = tool.request.url + return typeof url === 'function' ? url(params) : (url as string) +} + +describe('submit_metrics metric intake types', () => { + /** + * Datadog `MetricIntakeType` is 0 unspecified, 1 count, 2 rate, 3 gauge. Swapping + * these silently changes how Datadog aggregates the series. + */ + it.each([ + ['count', 1], + ['rate', 2], + ['gauge', 3], + ])('encodes %s as %i', (type, code) => { + const body = callBody(submitMetricsTool, { + ...auth, + series: JSON.stringify([{ metric: 'm', type, points: [{ timestamp: 1, value: 2 }] }]), + } as any) + expect(body.series[0].type).toBe(code) + }) + + it('omits type when the caller did not supply one', () => { + const body = callBody(submitMetricsTool, { + ...auth, + series: JSON.stringify([{ metric: 'm', points: [{ timestamp: 1, value: 2 }] }]), + } as any) + expect(body.series[0]).not.toHaveProperty('type') + }) + + it('does not invent a resources entry', () => { + const body = callBody(submitMetricsTool, { + ...auth, + series: JSON.stringify([{ metric: 'm', points: [{ timestamp: 1, value: 2 }] }]), + } as any) + expect(body.series[0]).not.toHaveProperty('resources') + }) + + it('forwards interval, which Datadog requires for count and rate metrics', () => { + const body = callBody(submitMetricsTool, { + ...auth, + series: JSON.stringify([ + { metric: 'm', type: 'count', interval: 20, points: [{ timestamp: 1, value: 2 }] }, + ]), + } as any) + expect(body.series[0].interval).toBe(20) + }) +}) + +describe('SLO payloads', () => { + it('rejects blank thresholds instead of sending an empty array', () => { + expect(() => + buildSloPayload({ ...auth, name: 'n', type: 'metric', thresholds: '' } as any) + ).toThrow(/thresholds must be a non-empty JSON array/) + }) + + it('rejects a non-numeric monitor id instead of sending null', () => { + expect(() => + buildSloPayload({ + ...auth, + name: 'n', + type: 'monitor', + thresholds: '[{"timeframe":"30d","target":99.9}]', + monitorIds: '123,abc', + } as any) + ).toThrow(/monitorIds must be a comma-separated list of whole numbers/) + }) + + /** + * `PUT /api/v1/slo/{slo_id}` is a full replacement, so every stored field the user + * did not edit has to be replayed or Datadog erases it. + */ + it('preserves stored fields the caller left blank', () => { + const stored = { + id: 'slo-1', + created_at: 1, + modified_at: 2, + creator: { email: 'a@b.c' }, + monitor_tags: ['env:prod'], + name: 'Old name', + type: 'monitor', + thresholds: [{ timeframe: '30d', target: 99.9 }], + description: 'keep me', + tags: ['team:core'], + monitor_ids: [123], + groups: ['env:prod'], + target_threshold: 99.9, + timeframe: '30d', + } + + const body = mergeSloUpdatePayload(stored, { ...auth, sloId: 'slo-1', name: 'New name' } as any) + + expect(body.name).toBe('New name') + expect(body.description).toBe('keep me') + expect(body.tags).toEqual(['team:core']) + expect(body.monitor_ids).toEqual([123]) + expect(body.groups).toEqual(['env:prod']) + expect(body.thresholds).toEqual([{ timeframe: '30d', target: 99.9 }]) + expect(body.target_threshold).toBe(99.9) + expect(body.timeframe).toBe('30d') + }) + + it('strips fields Datadog computes and rejects on update', () => { + const body = mergeSloUpdatePayload( + { id: 'slo-1', created_at: 1, modified_at: 2, creator: {}, monitor_tags: [], name: 'n' }, + { ...auth, sloId: 'slo-1' } as any + ) + for (const field of ['id', 'created_at', 'modified_at', 'creator', 'monitor_tags']) { + expect(body).not.toHaveProperty(field) + } + }) +}) + +describe('update_slo read-modify-write', () => { + beforeEach(() => vi.restoreAllMocks()) + + it('reads the stored SLO before replacing it', async () => { + const fetchMock = vi + .spyOn(globalThis, 'fetch') + .mockResolvedValueOnce( + jsonResponse({ data: { id: 'slo-1', name: 'Old', type: 'metric', description: 'keep' } }) + ) + .mockResolvedValueOnce(jsonResponse({ data: [{ id: 'slo-1', name: 'New' }] })) + + const result = await updateSloTool.directExecution!( + { ...auth, sloId: 'slo-1', name: 'New' } as any, + undefined + ) + + expect(result.success).toBe(true) + expect(fetchMock).toHaveBeenCalledTimes(2) + expect(fetchMock.mock.calls[0][1]?.method).toBe('GET') + + const putBody = JSON.parse(String(fetchMock.mock.calls[1][1]?.body)) + expect(putBody.name).toBe('New') + expect(putBody.description).toBe('keep') + }) + + it('does not write when the stored SLO cannot be read', async () => { + const fetchMock = vi + .spyOn(globalThis, 'fetch') + .mockResolvedValueOnce(jsonResponse({ errors: ['SLO not found'] }, { status: 404 })) + + const result = await updateSloTool.directExecution!( + { ...auth, sloId: 'missing', name: 'New' } as any, + undefined + ) + + expect(result.success).toBe(false) + expect(result.error).toContain('SLO not found') + expect(fetchMock).toHaveBeenCalledTimes(1) + }) +}) + +describe('datadogErrorMessage', () => { + it('reads v1 string errors', async () => { + await expect( + datadogErrorMessage(jsonResponse({ errors: ['bad query'] }, { status: 400 })) + ).resolves.toBe('bad query') + }) + + it('reads v2 JSON:API error objects', async () => { + await expect( + datadogErrorMessage(jsonResponse({ errors: [{ detail: 'forbidden' }] }, { status: 403 })) + ).resolves.toBe('forbidden') + }) + + /** The SLO delete conflict returns errors as a map of resource id to reason. */ + it('reads dictionary-shaped errors', async () => { + await expect( + datadogErrorMessage( + jsonResponse({ errors: { 'slo-1': 'still referenced by a dashboard' } }, { status: 409 }) + ) + ).resolves.toBe('still referenced by a dashboard') + }) + + it('falls back to the status line when no message is present', async () => { + await expect( + datadogErrorMessage(jsonResponse({}, { status: 500, statusText: 'Server Error' })) + ).resolves.toBe('HTTP 500: Server Error') + }) +}) + +describe('send_logs', () => { + /** Datadog treats unrecognized keys as the log's structured attributes. */ + it('preserves custom attributes', () => { + const body = callBody(sendLogsTool, { + ...auth, + logs: JSON.stringify([{ message: 'boom', status: 'error', orderId: 42 }]), + } as any) + expect(body[0].status).toBe('error') + expect(body[0].orderId).toBe(42) + }) + + it('does not pad absent optional fields with empty strings', () => { + const body = callBody(sendLogsTool, { + ...auth, + logs: JSON.stringify([{ message: 'boom' }]), + } as any) + expect(body[0]).not.toHaveProperty('hostname') + expect(body[0]).not.toHaveProperty('service') + expect(body[0]).not.toHaveProperty('ddtags') + }) +}) + +describe('incident include parameter', () => { + /** The spec enum is exact, so a space from a comma-separated input 400s. */ + it('trims spaces in get_incident', () => { + const url = callUrl(getIncidentTool, { + ...auth, + incidentId: 'abc', + include: 'users, attachments', + } as any) + expect(url).toContain('include=users%2Cattachments') + expect(url).not.toContain('%20') + }) + + it('trims spaces in list_incidents', () => { + const url = callUrl(listIncidentsTool, { ...auth, include: 'users, attachments' } as any) + expect(url).toContain('include=users%2Cattachments') + expect(url).not.toContain('%20') + }) +}) + +describe('update_incident blank handling', () => { + /** A blank input must not blank the stored incident under a partial update. */ + it('omits empty strings rather than overwriting stored values', () => { + const body = callBody(updateIncidentTool, { + ...auth, + incidentId: 'abc', + title: '', + customerImpactScope: '', + detected: '', + } as any) + expect(body.data.attributes).not.toHaveProperty('title') + expect(body.data.attributes).not.toHaveProperty('customer_impact_scope') + expect(body.data.attributes).not.toHaveProperty('detected') + }) + + it('still sends supplied values', () => { + const body = callBody(updateIncidentTool, { + ...auth, + incidentId: 'abc', + title: 'Real title', + } as any) + expect(body.data.id).toBe('abc') + expect(body.data.type).toBe('incidents') + expect(body.data.attributes.title).toBe('Real title') + }) +}) + +describe('create_monitor options', () => { + /** Silently dropping malformed options created monitors with no thresholds. */ + it('fails loudly on malformed options JSON', () => { + expect(() => + callBody(createMonitorTool, { + ...auth, + name: 'n', + type: 'metric alert', + query: 'q', + options: '{not json', + } as any) + ).toThrow(/options parameter must be valid JSON/) + }) +}) + +describe('query_timeseries', () => { + /** Datadog reports query failures with a 200 and a non-ok status. */ + it('surfaces a non-ok status as a failure', async () => { + const result = await queryTimeseriesTool.transformResponse!( + jsonResponse({ status: 'error', error: 'invalid query', series: [] }) + ) + expect(result.success).toBe(false) + expect(result.error).toContain('invalid query') + }) + + it('passes through a successful query', async () => { + const result = await queryTimeseriesTool.transformResponse!( + jsonResponse({ status: 'ok', series: [{ metric: 'm', tag_set: [], pointlist: [[1000, 5]] }] }) + ) + expect(result.success).toBe(true) + expect(result.output.series[0].points[0]).toEqual({ timestamp: 1, value: 5 }) + }) +}) + +describe('pagination wiring', () => { + it('sends downtime page params', () => { + const url = callUrl(listDowntimesTool, { ...auth, limit: 50, offset: 100 } as any) + expect(url).toContain('page%5Blimit%5D=50') + expect(url).toContain('page%5Boffset%5D=100') + }) + + it('feeds a log search cursor back into the request', () => { + const body = callBody(queryLogsTool, { + ...auth, + query: '*', + from: 'now-1h', + to: 'now', + cursor: 'abc123', + } as any) + expect(body.page.cursor).toBe('abc123') + }) +}) + +describe('monitor mute and unmute', () => { + it('mutes with the scope and end datadogpy documents', () => { + const body = callBody(muteMonitorTool, { + ...auth, + monitorId: '123', + scope: 'host:web-1', + end: 1705323600, + } as any) + expect(body).toEqual({ scope: 'host:web-1', end: 1705323600 }) + expect(callUrl(muteMonitorTool, { ...auth, monitorId: '123' } as any)).toContain( + '/api/v1/monitor/123/mute' + ) + }) + + /** An indefinite mute sends no `end`, so the monitor stays muted until unmuted. */ + it('omits end when the caller wants an indefinite mute', () => { + const body = callBody(muteMonitorTool, { ...auth, monitorId: '123' } as any) + expect(body).not.toHaveProperty('end') + }) + + /** Muting is only safe to ship because it can be reversed from Sim. */ + it('ships an unmute counterpart that can clear every scope', () => { + const body = callBody(unmuteMonitorTool, { + ...auth, + monitorId: '123', + allScopes: true, + } as any) + expect(body).toEqual({ all_scopes: true }) + expect(callUrl(unmuteMonitorTool, { ...auth, monitorId: '123' } as any)).toContain( + '/api/v1/monitor/123/unmute' + ) + }) +}) + +describe('create_downtime monitor targeting', () => { + /** monitor_identifier is a oneOf, so accepting both would silently drop one. */ + it('rejects a monitor ID and monitor tags together', () => { + expect(() => + callBody(createDowntimeTool, { + ...auth, + scope: '*', + monitorId: '123', + monitorTags: 'team:backend', + } as any) + ).toThrow(/either a monitor ID or monitor tags, not both/) + }) + + it('rejects a non-numeric monitor ID instead of sending null', () => { + expect(() => + callBody(createDowntimeTool, { ...auth, scope: '*', monitorId: 'abc' } as any) + ).toThrow(/monitorIds must be a comma-separated list of whole numbers/) + }) + + it('falls back to the wildcard monitor tag when no monitor is named', () => { + const body = callBody(createDowntimeTool, { ...auth, scope: '*' } as any) + expect(body.data.attributes.monitor_identifier).toEqual({ monitor_tags: ['*'] }) + }) + + it('targets a single monitor by numeric id', () => { + const body = callBody(createDowntimeTool, { ...auth, scope: '*', monitorId: '123' } as any) + expect(body.data.attributes.monitor_identifier).toEqual({ monitor_id: 123 }) + }) + + /** + * A `` reference to get_monitor resolves to a number, and an LLM tool + * call can pass one too, so the parser must not assume a string. + */ + it('accepts a monitor id that arrives as a number', () => { + const body = callBody(createDowntimeTool, { ...auth, scope: '*', monitorId: 123 } as any) + expect(body.data.attributes.monitor_identifier).toEqual({ monitor_id: 123 }) + }) + + /** A blank monitor ID is how an untouched field arrives; it is not a chosen target. */ + it('does not treat a whitespace-only monitor id as a conflicting target', () => { + const body = callBody(createDowntimeTool, { + ...auth, + scope: '*', + monitorId: ' ', + monitorTags: 'team:backend', + } as any) + expect(body.data.attributes.monitor_identifier).toEqual({ monitor_tags: ['team:backend'] }) + }) + + it('accepts monitor tags that arrive as an array', () => { + const body = callBody(createDowntimeTool, { + ...auth, + scope: '*', + monitorTags: ['team:backend', 'priority:high'], + } as any) + expect(body.data.attributes.monitor_identifier).toEqual({ + monitor_tags: ['team:backend', 'priority:high'], + }) + }) +}) + +describe('splitCommaList input tolerance', () => { + it('handles strings, numbers, and arrays without throwing', () => { + expect(splitCommaList('a, b')).toEqual(['a', 'b']) + expect(splitCommaList(123)).toEqual(['123']) + expect(splitCommaList([1, 2])).toEqual(['1', '2']) + expect(splitCommaList(undefined)).toBeUndefined() + expect(splitCommaList('')).toBeUndefined() + }) +}) + +describe('registry surface', () => { + it('keeps create_event on api-key-only auth', () => { + expect(createEventTool.params.applicationKey).toBeUndefined() + }) +}) diff --git a/apps/sim/tools/datadog/delete_dashboard.ts b/apps/sim/tools/datadog/delete_dashboard.ts new file mode 100644 index 0000000000..1d9411d69d --- /dev/null +++ b/apps/sim/tools/datadog/delete_dashboard.ts @@ -0,0 +1,76 @@ +import type { DeleteDashboardParams, DeleteDashboardResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const deleteDashboardTool: ToolConfig = { + id: 'datadog_delete_dashboard', + name: 'Datadog Delete Dashboard', + description: 'Delete a dashboard by ID.', + version: '1.0.0', + + params: { + dashboardId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the dashboard to delete', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl(params.site, `/api/v1/dashboard/${encodeURIComponent(params.dashboardId)}`), + method: 'DELETE', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { success: false }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json().catch(() => ({})) + + return { + success: true, + output: { + success: true, + deletedDashboardId: data.deleted_dashboard_id, + }, + } + }, + + outputs: { + success: { + type: 'boolean', + description: 'Whether the dashboard was deleted', + }, + deletedDashboardId: { + type: 'string', + description: 'ID of the deleted dashboard', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/delete_slo.ts b/apps/sim/tools/datadog/delete_slo.ts new file mode 100644 index 0000000000..f0c9b672a4 --- /dev/null +++ b/apps/sim/tools/datadog/delete_slo.ts @@ -0,0 +1,88 @@ +import type { DeleteSloParams, DeleteSloResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const deleteSloTool: ToolConfig = { + id: 'datadog_delete_slo', + name: 'Datadog Delete SLO', + description: + 'Permanently delete a service level objective. Datadog returns a conflict when the SLO is still referenced by a dashboard.', + version: '1.0.0', + + params: { + sloId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the service level objective to delete', + }, + force: { + type: 'boolean', + required: false, + visibility: 'user-only', + description: 'Delete even when the SLO is referenced by other resources', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryString = params.force ? '?force=true' : '' + return datadogApiUrl( + params.site, + `/api/v1/slo/${encodeURIComponent(params.sloId)}${queryString}` + ) + }, + method: 'DELETE', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { success: false, deletedIds: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json().catch(() => ({})) + + return { + success: true, + output: { + success: true, + deletedIds: data.data ?? [], + }, + } + }, + + outputs: { + success: { + type: 'boolean', + description: 'Whether the SLO was deleted', + }, + deletedIds: { + type: 'array', + description: 'IDs of the deleted service level objectives', + items: { type: 'string' }, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_browser_synthetics_results.ts b/apps/sim/tools/datadog/get_browser_synthetics_results.ts new file mode 100644 index 0000000000..d4986798ca --- /dev/null +++ b/apps/sim/tools/datadog/get_browser_synthetics_results.ts @@ -0,0 +1,145 @@ +import type { + GetBrowserSyntheticsResultsParams, + GetBrowserSyntheticsResultsResponse, +} from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getBrowserSyntheticsResultsTool: ToolConfig< + GetBrowserSyntheticsResultsParams, + GetBrowserSyntheticsResultsResponse +> = { + id: 'datadog_get_browser_synthetics_results', + name: 'Datadog Get Browser Synthetic Test Results', + description: + 'Get the latest result summaries (up to the last 150 runs) for a Synthetic browser test, including step counts and errors.', + version: '1.0.0', + + params: { + publicId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The public ID of the Synthetic browser test', + }, + fromTs: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Timestamp in milliseconds from which to start querying results', + }, + toTs: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Timestamp in milliseconds up to which to query results', + }, + probeDc: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated locations to query results for (e.g., "aws:eu-west-3")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.fromTs !== undefined) queryParams.set('from_ts', String(params.fromTs)) + if (params.toTs !== undefined) queryParams.set('to_ts', String(params.toTs)) + for (const location of splitCommaList(params.probeDc) ?? []) { + queryParams.append('probe_dc', location) + } + const queryString = queryParams.toString() + return datadogApiUrl( + params.site, + `/api/v1/synthetics/tests/browser/${encodeURIComponent(params.publicId)}/results${ + queryString ? `?${queryString}` : '' + }` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { results: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + results: data.results ?? [], + lastTimestampFetched: data.last_timestamp_fetched, + }, + } + }, + + outputs: { + results: { + type: 'array', + description: 'Latest browser test result summaries', + items: { + type: 'object', + properties: { + result_id: { type: 'string', description: 'ID of the browser test result' }, + check_time: { type: 'number', description: 'Time the browser test ran' }, + probe_dc: { type: 'string', description: 'Location the browser test ran from' }, + status: { + type: 'number', + description: 'Monitor status: 0 not triggered, 1 triggered, 2 no data', + }, + result: { + type: 'object', + description: 'Run outcome', + properties: { + duration: { type: 'number', description: 'Length of the run in milliseconds' }, + errorCount: { type: 'number', description: 'Number of errors collected in the run' }, + stepCountCompleted: { + type: 'number', + description: 'Steps completed before failing', + }, + stepCountTotal: { type: 'number', description: 'Total number of steps' }, + device: { type: 'object', description: 'Device the run was performed on' }, + }, + }, + }, + }, + }, + lastTimestampFetched: { + type: 'number', + description: 'Timestamp of the latest browser test run', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_dashboard.ts b/apps/sim/tools/datadog/get_dashboard.ts new file mode 100644 index 0000000000..b3eb9c4ad3 --- /dev/null +++ b/apps/sim/tools/datadog/get_dashboard.ts @@ -0,0 +1,81 @@ +import type { GetDashboardParams, GetDashboardResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getDashboardTool: ToolConfig = { + id: 'datadog_get_dashboard', + name: 'Datadog Get Dashboard', + description: 'Get the full definition of a dashboard, including its widgets.', + version: '1.0.0', + + params: { + dashboardId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the dashboard (e.g., "abc-def-ghi")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl(params.site, `/api/v1/dashboard/${encodeURIComponent(params.dashboardId)}`), + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { dashboard: {} }, + error: await datadogErrorMessage(response), + } + } + + return { + success: true, + output: { dashboard: await response.json() }, + } + }, + + outputs: { + dashboard: { + type: 'object', + description: 'The dashboard definition', + properties: { + id: { type: 'string', description: 'Dashboard ID' }, + title: { type: 'string', description: 'Dashboard title' }, + description: { type: 'string', description: 'Dashboard description' }, + layout_type: { type: 'string', description: 'Layout type: ordered or free' }, + url: { type: 'string', description: 'Dashboard URL path' }, + author_handle: { type: 'string', description: 'Handle of the dashboard author' }, + author_name: { type: 'string', description: 'Name of the dashboard author' }, + created_at: { type: 'string', description: 'Creation timestamp' }, + modified_at: { type: 'string', description: 'Modification timestamp' }, + tags: { type: 'array', description: 'Dashboard tags' }, + notify_list: { type: 'array', description: 'Handles notified on dashboard changes' }, + template_variables: { type: 'array', description: 'Template variable definitions' }, + widgets: { type: 'array', description: 'Widget definitions' }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_incident.ts b/apps/sim/tools/datadog/get_incident.ts new file mode 100644 index 0000000000..8574c6438c --- /dev/null +++ b/apps/sim/tools/datadog/get_incident.ts @@ -0,0 +1,115 @@ +import type { GetIncidentParams, GetIncidentResponse } from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getIncidentTool: ToolConfig = { + id: 'datadog_get_incident', + name: 'Datadog Get Incident', + description: + 'Get the details of a single incident by ID. Requires the Incident Management `incident_read` permission; the Incidents API is in public beta.', + version: '1.0.0', + + params: { + incidentId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The UUID of the incident (e.g., "00000000-0000-0000-1234-000000000000")', + }, + include: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated related resources to include (e.g., "users", "attachments")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const include = splitCommaList(params.include)?.join(',') + const queryString = include ? `?${new URLSearchParams({ include }).toString()}` : '' + return datadogApiUrl( + params.site, + `/api/v2/incidents/${encodeURIComponent(params.incidentId)}${queryString}` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { incident: { id: '', attributes: {} } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + incident: { + id: data.data?.id, + type: data.data?.type, + attributes: data.data?.attributes ?? {}, + }, + }, + } + }, + + outputs: { + incident: { + type: 'object', + description: 'The incident', + properties: { + id: { type: 'string', description: 'Incident UUID' }, + type: { type: 'string', description: 'Resource type (incidents)' }, + attributes: { + type: 'object', + description: 'Incident attributes', + properties: { + title: { type: 'string', description: 'Incident title' }, + state: { type: 'string', description: 'Incident state' }, + severity: { type: 'string', description: 'Incident severity' }, + public_id: { type: 'number', description: 'Incremental public incident ID' }, + customer_impacted: { type: 'boolean', description: 'Whether customers were impacted' }, + customer_impact_scope: { + type: 'string', + description: 'Summary of the customer impact', + }, + created: { type: 'string', description: 'Creation timestamp' }, + modified: { type: 'string', description: 'Last modification timestamp' }, + resolved: { type: 'string', description: 'Resolution timestamp' }, + time_to_resolve: { type: 'number', description: 'Seconds from creation to resolution' }, + }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_monitor.ts b/apps/sim/tools/datadog/get_monitor.ts index 0a65208fc8..441b1d4797 100644 --- a/apps/sim/tools/datadog/get_monitor.ts +++ b/apps/sim/tools/datadog/get_monitor.ts @@ -1,4 +1,5 @@ import type { GetMonitorParams, GetMonitorResponse } from '@/tools/datadog/types' +import { datadogErrorMessage } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const getMonitorTool: ToolConfig = { @@ -19,7 +20,7 @@ export const getMonitorTool: ToolConfig = required: false, visibility: 'user-or-llm', description: - 'Comma-separated group states to include (e.g., "alert,warn", "alert,warn,no data,ok")', + 'Comma-separated group states to include. Valid values are "all", "alert", "warn", and "no data" (e.g., "alert,warn").', }, withDowntimes: { type: 'boolean', @@ -68,13 +69,13 @@ export const getMonitorTool: ToolConfig = transformResponse: async (response: Response) => { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { - monitor: {} as any, + monitor: {}, }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } @@ -115,6 +116,11 @@ export const getMonitorTool: ToolConfig = overall_state: { type: 'string', description: 'Current monitor state' }, created: { type: 'string', description: 'Creation timestamp' }, modified: { type: 'string', description: 'Last modification timestamp' }, + options: { + type: 'json', + description: 'Monitor options (thresholds, notification settings)', + }, + creator: { type: 'json', description: 'Monitor creator (email, handle, name)' }, }, }, }, diff --git a/apps/sim/tools/datadog/get_security_signal.ts b/apps/sim/tools/datadog/get_security_signal.ts new file mode 100644 index 0000000000..d5eee359db --- /dev/null +++ b/apps/sim/tools/datadog/get_security_signal.ts @@ -0,0 +1,93 @@ +import type { GetSecuritySignalParams, GetSecuritySignalResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getSecuritySignalTool: ToolConfig = + { + id: 'datadog_get_security_signal', + name: 'Datadog Get Security Signal', + description: + 'Get the details of a single Cloud SIEM security signal. Requires the `security_monitoring_signals_read` permission.', + version: '1.0.0', + + params: { + signalId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the security signal', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl( + params.site, + `/api/v2/security_monitoring/signals/${encodeURIComponent(params.signalId)}` + ), + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { signal: { attributes: {} } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + signal: { + id: data.data?.id, + type: data.data?.type, + attributes: data.data?.attributes ?? {}, + }, + }, + } + }, + + outputs: { + signal: { + type: 'object', + description: 'The security signal', + properties: { + id: { type: 'string', description: 'Signal ID' }, + type: { type: 'string', description: 'Resource type (signal)' }, + attributes: { + type: 'object', + description: 'Signal attributes', + properties: { + message: { type: 'string', description: 'Message from the detection rule' }, + timestamp: { type: 'string', description: 'Signal timestamp' }, + tags: { type: 'array', description: 'Tags on the signal' }, + custom: { type: 'object', description: 'Signal-specific attributes' }, + }, + }, + }, + }, + }, + } diff --git a/apps/sim/tools/datadog/get_slo.ts b/apps/sim/tools/datadog/get_slo.ts new file mode 100644 index 0000000000..f902b503ca --- /dev/null +++ b/apps/sim/tools/datadog/get_slo.ts @@ -0,0 +1,99 @@ +import type { GetSloParams, GetSloResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getSloTool: ToolConfig = { + id: 'datadog_get_slo', + name: 'Datadog Get SLO', + description: 'Get the configuration of a single service level objective by ID.', + version: '1.0.0', + + params: { + sloId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the service level objective', + }, + withConfiguredAlertIds: { + type: 'boolean', + required: false, + visibility: 'user-or-llm', + description: 'Include the IDs of SLO monitors that reference this SLO', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryString = params.withConfiguredAlertIds ? '?with_configured_alert_ids=true' : '' + return datadogApiUrl( + params.site, + `/api/v1/slo/${encodeURIComponent(params.sloId)}${queryString}` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { slo: { id: '', name: '', type: '' } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { slo: data.data ?? { id: '', name: '', type: '' } }, + } + }, + + outputs: { + slo: { + type: 'object', + description: 'The service level objective', + properties: { + id: { type: 'string', description: 'SLO ID' }, + name: { type: 'string', description: 'SLO name' }, + type: { type: 'string', description: 'SLO type: metric, monitor, or time_slice' }, + description: { type: 'string', description: 'SLO description' }, + tags: { type: 'array', description: 'SLO tags' }, + thresholds: { type: 'array', description: 'Timeframe targets and warnings' }, + target_threshold: { type: 'number', description: 'Primary target threshold' }, + warning_threshold: { type: 'number', description: 'Primary warning threshold' }, + timeframe: { type: 'string', description: 'Primary timeframe' }, + monitor_ids: { type: 'array', description: 'Monitor IDs for monitor-based SLOs' }, + groups: { type: 'array', description: 'Monitor groups narrowing the SLO scope' }, + configured_alert_ids: { + type: 'array', + description: 'SLO monitor IDs referencing this SLO', + optional: true, + }, + created_at: { type: 'number', description: 'Creation timestamp (Unix seconds)' }, + modified_at: { type: 'number', description: 'Modification timestamp (Unix seconds)' }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_slo_history.ts b/apps/sim/tools/datadog/get_slo_history.ts new file mode 100644 index 0000000000..01199c0322 --- /dev/null +++ b/apps/sim/tools/datadog/get_slo_history.ts @@ -0,0 +1,134 @@ +import type { GetSloHistoryParams, GetSloHistoryResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getSloHistoryTool: ToolConfig = { + id: 'datadog_get_slo_history', + name: 'Datadog Get SLO History', + description: + 'Get an SLO’s history over a time window, including the overall SLI value and remaining error budget.', + version: '1.0.0', + + params: { + sloId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the service level objective', + }, + fromTs: { + type: 'number', + required: true, + visibility: 'user-or-llm', + description: 'Start of the query window as a Unix timestamp in seconds', + }, + toTs: { + type: 'number', + required: true, + visibility: 'user-or-llm', + description: 'End of the query window as a Unix timestamp in seconds', + }, + target: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: + 'SLO target between 0 and 100. When supplied, the response includes the remaining error budget for a custom timeframe', + }, + applyCorrection: { + type: 'boolean', + required: false, + visibility: 'user-only', + description: 'Whether to apply SLO corrections (defaults to true)', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams({ + from_ts: String(params.fromTs), + to_ts: String(params.toTs), + }) + if (params.target !== undefined) queryParams.set('target', String(params.target)) + if (params.applyCorrection !== undefined) + queryParams.set('apply_correction', String(params.applyCorrection)) + return datadogApiUrl( + params.site, + `/api/v1/slo/${encodeURIComponent(params.sloId)}/history?${queryParams.toString()}` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { history: {} }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + const history = data.data ?? {} + + return { + success: true, + output: { + history, + sliValue: history.overall?.sli_value ?? null, + }, + } + }, + + outputs: { + history: { + type: 'object', + description: 'SLO history for the requested window', + properties: { + from_ts: { type: 'number', description: 'Window start (Unix seconds)' }, + to_ts: { type: 'number', description: 'Window end (Unix seconds)' }, + type: { type: 'string', description: 'SLO type' }, + overall: { + type: 'object', + description: 'Overall SLI data for the window', + properties: { + sli_value: { type: 'number', description: 'SLI value over the window' }, + span_precision: { type: 'number', description: 'Decimal precision of the SLI value' }, + error_budget_remaining: { + type: 'object', + description: 'Remaining error budget keyed by timeframe', + }, + }, + }, + groups: { type: 'array', description: 'Per-group SLI data for grouped SLOs' }, + monitors: { type: 'array', description: 'Per-monitor SLI data for multi-monitor SLOs' }, + thresholds: { type: 'object', description: 'Thresholds keyed by timeframe' }, + }, + }, + sliValue: { + type: 'number', + description: 'Overall SLI value over the window', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_synthetics_results.ts b/apps/sim/tools/datadog/get_synthetics_results.ts new file mode 100644 index 0000000000..4b16db8f9e --- /dev/null +++ b/apps/sim/tools/datadog/get_synthetics_results.ts @@ -0,0 +1,139 @@ +import type { + GetSyntheticsResultsParams, + GetSyntheticsResultsResponse, +} from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getSyntheticsResultsTool: ToolConfig< + GetSyntheticsResultsParams, + GetSyntheticsResultsResponse +> = { + id: 'datadog_get_synthetics_results', + name: 'Datadog Get Synthetic Test Results', + description: + 'Get the latest result summaries (up to the last 150 runs) for a Synthetic API test.', + version: '1.0.0', + + params: { + publicId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The public ID of the Synthetic API test', + }, + fromTs: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Timestamp in milliseconds from which to start querying results', + }, + toTs: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Timestamp in milliseconds up to which to query results', + }, + probeDc: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated locations to query results for (e.g., "aws:eu-west-3")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.fromTs !== undefined) queryParams.set('from_ts', String(params.fromTs)) + if (params.toTs !== undefined) queryParams.set('to_ts', String(params.toTs)) + for (const location of splitCommaList(params.probeDc) ?? []) { + queryParams.append('probe_dc', location) + } + const queryString = queryParams.toString() + return datadogApiUrl( + params.site, + `/api/v1/synthetics/tests/${encodeURIComponent(params.publicId)}/results${ + queryString ? `?${queryString}` : '' + }` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { results: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + results: data.results ?? [], + lastTimestampFetched: data.last_timestamp_fetched, + }, + } + }, + + outputs: { + results: { + type: 'array', + description: 'Latest test result summaries', + items: { + type: 'object', + properties: { + result_id: { type: 'string', description: 'ID of the test result' }, + check_time: { type: 'number', description: 'Time the test ran' }, + probe_dc: { type: 'string', description: 'Location the test ran from' }, + status: { + type: 'number', + description: 'Monitor status: 0 not triggered, 1 triggered, 2 no data', + }, + result: { + type: 'object', + description: 'Run outcome', + properties: { + passed: { type: 'boolean', description: 'Whether the run passed' }, + timings: { type: 'object', description: 'Request timing breakdown' }, + }, + }, + }, + }, + }, + lastTimestampFetched: { + type: 'number', + description: 'Timestamp of the latest test run', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/get_synthetics_test.ts b/apps/sim/tools/datadog/get_synthetics_test.ts new file mode 100644 index 0000000000..3dc59815c0 --- /dev/null +++ b/apps/sim/tools/datadog/get_synthetics_test.ts @@ -0,0 +1,85 @@ +import type { GetSyntheticsTestParams, GetSyntheticsTestResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const getSyntheticsTestTool: ToolConfig = + { + id: 'datadog_get_synthetics_test', + name: 'Datadog Get Synthetic Test', + description: + 'Get the configuration of a Synthetic test by public ID. Browser test steps are not included by this type-agnostic endpoint.', + version: '1.0.0', + + params: { + publicId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The public ID of the Synthetic test (e.g., "abc-def-ghi")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl( + params.site, + `/api/v1/synthetics/tests/${encodeURIComponent(params.publicId)}` + ), + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { test: {} }, + error: await datadogErrorMessage(response), + } + } + + return { + success: true, + output: { test: await response.json() }, + } + }, + + outputs: { + test: { + type: 'object', + description: 'The Synthetic test configuration', + properties: { + public_id: { type: 'string', description: 'Public ID of the test' }, + name: { type: 'string', description: 'Test name' }, + status: { type: 'string', description: 'Pause status: live or paused' }, + type: { type: 'string', description: 'Test type: api, browser, mobile, or network' }, + subtype: { type: 'string', description: 'Test subtype, such as http or ssl' }, + message: { type: 'string', description: 'Notification message' }, + monitor_id: { type: 'number', description: 'Associated monitor ID' }, + tags: { type: 'array', description: 'Tags attached to the test' }, + locations: { type: 'array', description: 'Locations the test runs from' }, + config: { type: 'object', description: 'Test request, assertions, and variables' }, + options: { type: 'object', description: 'Scheduling, retry, and monitor options' }, + creator: { type: 'object', description: 'User who created the test' }, + }, + }, + }, + } diff --git a/apps/sim/tools/datadog/index.ts b/apps/sim/tools/datadog/index.ts index 2568a9bb3e..e00b7a65af 100644 --- a/apps/sim/tools/datadog/index.ts +++ b/apps/sim/tools/datadog/index.ts @@ -1,15 +1,44 @@ +import { addIncidentTodoTool } from '@/tools/datadog/add_incident_todo' import { cancelDowntimeTool } from '@/tools/datadog/cancel_downtime' +import { createDashboardTool } from '@/tools/datadog/create_dashboard' import { createDowntimeTool } from '@/tools/datadog/create_downtime' import { createEventTool } from '@/tools/datadog/create_event' +import { createIncidentTool } from '@/tools/datadog/create_incident' import { createMonitorTool } from '@/tools/datadog/create_monitor' +import { createSloTool } from '@/tools/datadog/create_slo' +import { deleteDashboardTool } from '@/tools/datadog/delete_dashboard' +import { deleteSloTool } from '@/tools/datadog/delete_slo' +import { getBrowserSyntheticsResultsTool } from '@/tools/datadog/get_browser_synthetics_results' +import { getDashboardTool } from '@/tools/datadog/get_dashboard' +import { getIncidentTool } from '@/tools/datadog/get_incident' import { getMonitorTool } from '@/tools/datadog/get_monitor' +import { getSecuritySignalTool } from '@/tools/datadog/get_security_signal' +import { getSloTool } from '@/tools/datadog/get_slo' +import { getSloHistoryTool } from '@/tools/datadog/get_slo_history' +import { getSyntheticsResultsTool } from '@/tools/datadog/get_synthetics_results' +import { getSyntheticsTestTool } from '@/tools/datadog/get_synthetics_test' +import { listDashboardsTool } from '@/tools/datadog/list_dashboards' import { listDowntimesTool } from '@/tools/datadog/list_downtimes' +import { listIncidentsTool } from '@/tools/datadog/list_incidents' import { listMonitorsTool } from '@/tools/datadog/list_monitors' +import { listSecurityRulesTool } from '@/tools/datadog/list_security_rules' +import { listSecuritySignalsTool } from '@/tools/datadog/list_security_signals' +import { listServicesTool } from '@/tools/datadog/list_services' +import { listSlosTool } from '@/tools/datadog/list_slos' +import { listSyntheticsTestsTool } from '@/tools/datadog/list_synthetics_tests' import { muteMonitorTool } from '@/tools/datadog/mute_monitor' import { queryLogsTool } from '@/tools/datadog/query_logs' import { queryTimeseriesTool } from '@/tools/datadog/query_timeseries' +import { searchSpansTool } from '@/tools/datadog/search_spans' import { sendLogsTool } from '@/tools/datadog/send_logs' import { submitMetricsTool } from '@/tools/datadog/submit_metrics' +import { triggerSyntheticsTestsTool } from '@/tools/datadog/trigger_synthetics_tests' +import { unmuteMonitorTool } from '@/tools/datadog/unmute_monitor' +import { updateIncidentTool } from '@/tools/datadog/update_incident' +import { updateSecuritySignalAssigneeTool } from '@/tools/datadog/update_security_signal_assignee' +import { updateSecuritySignalStateTool } from '@/tools/datadog/update_security_signal_state' +import { updateSloTool } from '@/tools/datadog/update_slo' +import { updateSyntheticsStatusTool } from '@/tools/datadog/update_synthetics_status' export const datadogSubmitMetricsTool = submitMetricsTool export const datadogQueryTimeseriesTool = queryTimeseriesTool @@ -18,8 +47,37 @@ export const datadogCreateMonitorTool = createMonitorTool export const datadogGetMonitorTool = getMonitorTool export const datadogListMonitorsTool = listMonitorsTool export const datadogMuteMonitorTool = muteMonitorTool +export const datadogUnmuteMonitorTool = unmuteMonitorTool export const datadogQueryLogsTool = queryLogsTool export const datadogSendLogsTool = sendLogsTool export const datadogCreateDowntimeTool = createDowntimeTool export const datadogListDowntimesTool = listDowntimesTool export const datadogCancelDowntimeTool = cancelDowntimeTool +export const datadogListIncidentsTool = listIncidentsTool +export const datadogGetIncidentTool = getIncidentTool +export const datadogCreateIncidentTool = createIncidentTool +export const datadogUpdateIncidentTool = updateIncidentTool +export const datadogAddIncidentTodoTool = addIncidentTodoTool +export const datadogListSlosTool = listSlosTool +export const datadogGetSloTool = getSloTool +export const datadogCreateSloTool = createSloTool +export const datadogUpdateSloTool = updateSloTool +export const datadogDeleteSloTool = deleteSloTool +export const datadogGetSloHistoryTool = getSloHistoryTool +export const datadogListDashboardsTool = listDashboardsTool +export const datadogGetDashboardTool = getDashboardTool +export const datadogCreateDashboardTool = createDashboardTool +export const datadogDeleteDashboardTool = deleteDashboardTool +export const datadogListSyntheticsTestsTool = listSyntheticsTestsTool +export const datadogGetSyntheticsTestTool = getSyntheticsTestTool +export const datadogGetSyntheticsResultsTool = getSyntheticsResultsTool +export const datadogGetBrowserSyntheticsResultsTool = getBrowserSyntheticsResultsTool +export const datadogTriggerSyntheticsTestsTool = triggerSyntheticsTestsTool +export const datadogUpdateSyntheticsStatusTool = updateSyntheticsStatusTool +export const datadogListSecuritySignalsTool = listSecuritySignalsTool +export const datadogGetSecuritySignalTool = getSecuritySignalTool +export const datadogUpdateSecuritySignalStateTool = updateSecuritySignalStateTool +export const datadogUpdateSecuritySignalAssigneeTool = updateSecuritySignalAssigneeTool +export const datadogListSecurityRulesTool = listSecurityRulesTool +export const datadogSearchSpansTool = searchSpansTool +export const datadogListServicesTool = listServicesTool diff --git a/apps/sim/tools/datadog/list_dashboards.ts b/apps/sim/tools/datadog/list_dashboards.ts new file mode 100644 index 0000000000..642058113c --- /dev/null +++ b/apps/sim/tools/datadog/list_dashboards.ts @@ -0,0 +1,110 @@ +import type { ListDashboardsParams, ListDashboardsResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const listDashboardsTool: ToolConfig = { + id: 'datadog_list_dashboards', + name: 'Datadog List Dashboards', + description: + 'List custom created or cloned dashboards. Datadog preset dashboards are not returned.', + version: '1.0.0', + + params: { + filterShared: { + type: 'boolean', + required: false, + visibility: 'user-or-llm', + description: 'Return only shared dashboards', + }, + filterDeleted: { + type: 'boolean', + required: false, + visibility: 'user-or-llm', + description: 'Return only deleted dashboards. Incompatible with filterShared', + }, + count: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Maximum number of dashboards to return (default: 100)', + }, + start: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Offset of the first dashboard returned (e.g., 0, 100)', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.filterShared !== undefined) + queryParams.set('filter[shared]', String(params.filterShared)) + if (params.filterDeleted !== undefined) + queryParams.set('filter[deleted]', String(params.filterDeleted)) + if (params.count !== undefined) queryParams.set('count', String(params.count)) + if (params.start !== undefined) queryParams.set('start', String(params.start)) + const queryString = queryParams.toString() + return datadogApiUrl(params.site, `/api/v1/dashboard${queryString ? `?${queryString}` : ''}`) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { dashboards: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { dashboards: data.dashboards ?? [] }, + } + }, + + outputs: { + dashboards: { + type: 'array', + description: 'List of dashboard summaries', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'Dashboard ID' }, + title: { type: 'string', description: 'Dashboard title' }, + description: { type: 'string', description: 'Dashboard description' }, + layout_type: { type: 'string', description: 'Layout type: ordered or free' }, + url: { type: 'string', description: 'Dashboard URL path' }, + author_handle: { type: 'string', description: 'Handle of the dashboard author' }, + created_at: { type: 'string', description: 'Creation timestamp' }, + modified_at: { type: 'string', description: 'Modification timestamp' }, + is_read_only: { type: 'boolean', description: 'Whether the dashboard is read-only' }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/list_downtimes.ts b/apps/sim/tools/datadog/list_downtimes.ts index 430f439e6e..c690ea7f9d 100644 --- a/apps/sim/tools/datadog/list_downtimes.ts +++ b/apps/sim/tools/datadog/list_downtimes.ts @@ -1,4 +1,10 @@ -import type { ListDowntimesParams, ListDowntimesResponse } from '@/tools/datadog/types' +import type { + DatadogV2Resource, + DowntimeAttributes, + ListDowntimesParams, + ListDowntimesResponse, +} from '@/tools/datadog/types' +import { datadogErrorMessage } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const listDowntimesTool: ToolConfig = { @@ -14,11 +20,17 @@ export const listDowntimesTool: ToolConfig { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { downtimes: [], }, - error: errorData.errors?.[0]?.detail || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } const data = await response.json() - const downtimes = (data.data || []).map((d: any) => { - const attrs = d.attributes || {} + const downtimes = (data.data || []).map((d: DatadogV2Resource) => { + const attrs: DowntimeAttributes = d.attributes || {} return { id: d.id, scope: attrs.scope ? [attrs.scope] : [], message: attrs.message, start: attrs.schedule?.start ? new Date(attrs.schedule.start).getTime() / 1000 : undefined, end: attrs.schedule?.end ? new Date(attrs.schedule.end).getTime() / 1000 : undefined, - timezone: attrs.schedule?.timezone, - disabled: attrs.disabled, + timezone: attrs.display_timezone ?? undefined, active: attrs.status === 'active', created: attrs.created ? new Date(attrs.created).getTime() / 1000 : undefined, modified: attrs.modified ? new Date(attrs.modified).getTime() / 1000 : undefined, @@ -92,23 +104,32 @@ export const listDowntimesTool: ToolConfig = { + id: 'datadog_list_incidents', + name: 'Datadog List Incidents', + description: + 'List incidents for the organization. Requires the Incident Management `incident_read` permission; the Incidents API is in public beta.', + version: '1.0.0', + + params: { + include: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated related resources to include: "users" and/or "attachments"', + }, + pageSize: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Number of incidents to return per page (default: 10, max: 100)', + }, + pageOffset: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Index of the first incident to return (e.g., 0, 10, 20)', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + const include = splitCommaList(params.include)?.join(',') + if (include) queryParams.set('include', include) + if (params.pageSize !== undefined) queryParams.set('page[size]', String(params.pageSize)) + if (params.pageOffset !== undefined) + queryParams.set('page[offset]', String(params.pageOffset)) + const queryString = queryParams.toString() + return datadogApiUrl(params.site, `/api/v2/incidents${queryString ? `?${queryString}` : ''}`) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { incidents: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + incidents: (data.data ?? []).map((incident: DatadogV2Resource) => ({ + id: incident.id, + type: incident.type, + attributes: incident.attributes ?? {}, + })), + nextOffset: data.meta?.pagination?.next_offset, + }, + } + }, + + outputs: { + incidents: { + type: 'array', + description: 'List of incidents', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'Incident UUID' }, + type: { type: 'string', description: 'Resource type (incidents)' }, + attributes: { + type: 'object', + description: 'Incident attributes', + properties: { + title: { type: 'string', description: 'Incident title' }, + state: { type: 'string', description: 'Incident state' }, + severity: { type: 'string', description: 'Incident severity' }, + public_id: { type: 'number', description: 'Incremental public incident ID' }, + customer_impacted: { + type: 'boolean', + description: 'Whether customers were impacted', + }, + created: { type: 'string', description: 'Creation timestamp' }, + modified: { type: 'string', description: 'Last modification timestamp' }, + resolved: { type: 'string', description: 'Resolution timestamp' }, + }, + }, + }, + }, + }, + nextOffset: { + type: 'number', + description: 'Offset to use for the next page of results', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/list_monitors.ts b/apps/sim/tools/datadog/list_monitors.ts index eaf2449360..f910ab3eac 100644 --- a/apps/sim/tools/datadog/list_monitors.ts +++ b/apps/sim/tools/datadog/list_monitors.ts @@ -1,9 +1,7 @@ -import { createLogger } from '@sim/logger' -import type { ListMonitorsParams, ListMonitorsResponse } from '@/tools/datadog/types' +import type { ListMonitorsParams, ListMonitorsResponse, MonitorData } from '@/tools/datadog/types' +import { datadogErrorMessage } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' -const logger = createLogger('DatadogListMonitors') - export const listMonitorsTool: ToolConfig = { id: 'datadog_list_monitors', name: 'Datadog List Monitors', @@ -16,7 +14,7 @@ export const listMonitorsTool: ToolConfig ({ @@ -112,18 +99,18 @@ export const listMonitorsTool: ToolConfig { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { monitors: [], }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } const text = await response.text() - let data: any + let data: unknown try { data = JSON.parse(text) } catch (e) { @@ -142,7 +129,7 @@ export const listMonitorsTool: ToolConfig ({ + const monitors = (data as MonitorData[]).map((m) => ({ id: m.id, name: m.name, type: m.type, @@ -176,8 +163,17 @@ export const listMonitorsTool: ToolConfig = + { + id: 'datadog_list_security_rules', + name: 'Datadog List Security Rules', + description: + 'List Cloud SIEM detection rules. Requires the `security_monitoring_rules_read` permission.', + version: '1.0.0', + + params: { + query: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Search query filtering rules by attributes such as type, source, or tags (e.g., "type:log_detection source:cloudtrail")', + }, + sort: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Sort attribute, prefix with "-" for descending: name, creation_date, update_date, enabled, type, highest_severity, or source', + }, + pageSize: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Number of rules per page (default: 10, max: 100)', + }, + pageNumber: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Page to retrieve, starting at zero', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.query) queryParams.set('query', params.query) + if (params.sort) queryParams.set('sort', params.sort) + if (params.pageSize !== undefined) queryParams.set('page[size]', String(params.pageSize)) + if (params.pageNumber !== undefined) + queryParams.set('page[number]', String(params.pageNumber)) + const queryString = queryParams.toString() + return datadogApiUrl( + params.site, + `/api/v2/security_monitoring/rules${queryString ? `?${queryString}` : ''}` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { rules: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + rules: (data.data ?? []).map((rule: SecurityRuleData) => ({ + id: rule.id, + name: rule.name, + type: rule.type, + message: rule.message, + tags: rule.tags ?? [], + isEnabled: rule.isEnabled, + isDefault: rule.isDefault, + createdAt: rule.createdAt, + version: rule.version, + })), + }, + } + }, + + outputs: { + rules: { + type: 'array', + description: 'List of detection rules', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'Rule ID' }, + name: { type: 'string', description: 'Rule name' }, + type: { type: 'string', description: 'Rule type' }, + message: { type: 'string', description: 'Message attached to generated signals' }, + tags: { type: 'array', description: 'Rule tags' }, + isEnabled: { type: 'boolean', description: 'Whether the rule is enabled' }, + isDefault: { + type: 'boolean', + description: 'Whether the rule is a Datadog default rule', + }, + createdAt: { type: 'number', description: 'Creation timestamp in milliseconds' }, + version: { type: 'number', description: 'Rule version' }, + }, + }, + }, + }, + } diff --git a/apps/sim/tools/datadog/list_security_signals.ts b/apps/sim/tools/datadog/list_security_signals.ts new file mode 100644 index 0000000000..22b09bafd8 --- /dev/null +++ b/apps/sim/tools/datadog/list_security_signals.ts @@ -0,0 +1,154 @@ +import type { + DatadogV2Resource, + ListSecuritySignalsParams, + ListSecuritySignalsResponse, + SecuritySignalAttributes, +} from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const listSecuritySignalsTool: ToolConfig< + ListSecuritySignalsParams, + ListSecuritySignalsResponse +> = { + id: 'datadog_list_security_signals', + name: 'Datadog List Security Signals', + description: + 'Search Cloud SIEM security signals by query and time range. Requires the `security_monitoring_signals_read` permission.', + version: '1.0.0', + + params: { + query: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Signal search query (e.g., "security:attack status:high")', + }, + from: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Minimum timestamp as an ISO-8601 date-time (e.g., "2026-01-02T09:42:36.320Z"). Signal search does not accept relative expressions like "now-1h".', + }, + to: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Maximum timestamp as an ISO-8601 date-time (e.g., "2026-01-03T09:42:36.320Z"). Signal search does not accept relative expressions like "now".', + }, + sort: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Sort order: "timestamp" for oldest first, "-timestamp" for newest first', + }, + cursor: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Pagination cursor returned as nextCursor by a previous call', + }, + limit: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Maximum number of signals to return (default: 10, max: 1000)', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, '/api/v2/security_monitoring/signals/search'), + method: 'POST', + headers: datadogHeaders, + body: (params) => { + const filter: Record = {} + if (params.query) filter.query = params.query + if (params.from) filter.from = params.from + if (params.to) filter.to = params.to + + const page: Record = {} + if (params.cursor) page.cursor = params.cursor + if (params.limit !== undefined) page.limit = params.limit + + const body: Record = {} + if (Object.keys(filter).length > 0) body.filter = filter + if (Object.keys(page).length > 0) body.page = page + if (params.sort) body.sort = params.sort + + return body + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { signals: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + signals: (data.data ?? []).map((signal: DatadogV2Resource) => ({ + id: signal.id, + type: signal.type, + attributes: signal.attributes ?? {}, + })), + nextCursor: data.meta?.page?.after, + }, + } + }, + + outputs: { + signals: { + type: 'array', + description: 'List of security signals', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'Signal ID' }, + type: { type: 'string', description: 'Resource type (signal)' }, + attributes: { + type: 'object', + description: 'Signal attributes', + properties: { + message: { type: 'string', description: 'Message from the detection rule' }, + timestamp: { type: 'string', description: 'Signal timestamp' }, + tags: { type: 'array', description: 'Tags on the signal' }, + custom: { type: 'object', description: 'Signal-specific attributes' }, + }, + }, + }, + }, + }, + nextCursor: { + type: 'string', + description: 'Cursor for the next page of signals', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/list_services.ts b/apps/sim/tools/datadog/list_services.ts new file mode 100644 index 0000000000..4081e6440e --- /dev/null +++ b/apps/sim/tools/datadog/list_services.ts @@ -0,0 +1,121 @@ +import type { + DatadogV2Resource, + ListServicesParams, + ListServicesResponse, + ServiceDefinitionAttributes, +} from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const listServicesTool: ToolConfig = { + id: 'datadog_list_services', + name: 'Datadog List Services', + description: + 'List service definitions from the Datadog Service Catalog. Requires the `apm_service_catalog_read` permission.', + version: '1.0.0', + + params: { + pageSize: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Number of service definitions per page (default: 10, max: 100)', + }, + pageNumber: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Page to retrieve, starting at zero', + }, + schemaVersion: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Schema version to return (e.g., "v2", "v2.1", "v2.2")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.pageSize !== undefined) queryParams.set('page[size]', String(params.pageSize)) + if (params.pageNumber !== undefined) + queryParams.set('page[number]', String(params.pageNumber)) + if (params.schemaVersion) queryParams.set('schema_version', params.schemaVersion) + const queryString = queryParams.toString() + return datadogApiUrl( + params.site, + `/api/v2/services/definitions${queryString ? `?${queryString}` : ''}` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { services: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + services: (data.data ?? []).map( + (service: DatadogV2Resource) => ({ + id: service.id, + type: service.type, + schema: service.attributes?.schema ?? {}, + meta: service.attributes?.meta ?? {}, + }) + ), + }, + } + }, + + outputs: { + services: { + type: 'array', + description: 'List of service definitions', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'Service definition ID' }, + type: { type: 'string', description: 'Resource type (service_definitions)' }, + schema: { + type: 'object', + description: + 'The service definition schema. Its shape depends on the requested schema version', + }, + meta: { + type: 'object', + description: 'Ingestion metadata such as origin and last modified time', + }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/list_slos.ts b/apps/sim/tools/datadog/list_slos.ts new file mode 100644 index 0000000000..bbf6fdb96d --- /dev/null +++ b/apps/sim/tools/datadog/list_slos.ts @@ -0,0 +1,135 @@ +import type { ListSlosParams, ListSlosResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const listSlosTool: ToolConfig = { + id: 'datadog_list_slos', + name: 'Datadog List SLOs', + description: + 'List service level objectives, optionally filtered by IDs, name, tags, or underlying metrics query.', + version: '1.0.0', + + params: { + ids: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated SLO IDs to fetch (e.g., "id1,id2")', + }, + query: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Filter results by SLO name (e.g., "checkout latency")', + }, + tagsQuery: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Filter results by a single SLO tag (e.g., "env:prod")', + }, + metricsQuery: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Filter results by SLO numerator and denominator (e.g., "aws.elb.request_count")', + }, + limit: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Number of SLOs to return (default: 1000)', + }, + offset: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Offset of the first SLO returned (e.g., 0, 50)', + }, + isDeleted: { + type: 'boolean', + required: false, + visibility: 'user-only', + description: 'Return only deleted SLOs', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.ids) queryParams.set('ids', params.ids) + if (params.query) queryParams.set('query', params.query) + if (params.tagsQuery) queryParams.set('tags_query', params.tagsQuery) + if (params.metricsQuery) queryParams.set('metrics_query', params.metricsQuery) + if (params.limit !== undefined) queryParams.set('limit', String(params.limit)) + if (params.offset !== undefined) queryParams.set('offset', String(params.offset)) + if (params.isDeleted) queryParams.set('is_deleted', 'true') + const queryString = queryParams.toString() + return datadogApiUrl(params.site, `/api/v1/slo${queryString ? `?${queryString}` : ''}`) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { slos: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + slos: data.data ?? [], + }, + } + }, + + outputs: { + slos: { + type: 'array', + description: 'List of service level objectives', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'SLO ID' }, + name: { type: 'string', description: 'SLO name' }, + type: { type: 'string', description: 'SLO type: metric, monitor, or time_slice' }, + description: { type: 'string', description: 'SLO description' }, + tags: { type: 'array', description: 'SLO tags' }, + thresholds: { type: 'array', description: 'Timeframe targets and warnings' }, + target_threshold: { type: 'number', description: 'Primary target threshold' }, + warning_threshold: { type: 'number', description: 'Primary warning threshold' }, + timeframe: { type: 'string', description: 'Primary timeframe' }, + monitor_ids: { type: 'array', description: 'Monitor IDs for monitor-based SLOs' }, + created_at: { type: 'number', description: 'Creation timestamp (Unix seconds)' }, + modified_at: { type: 'number', description: 'Modification timestamp (Unix seconds)' }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/list_synthetics_tests.ts b/apps/sim/tools/datadog/list_synthetics_tests.ts new file mode 100644 index 0000000000..fef037aef2 --- /dev/null +++ b/apps/sim/tools/datadog/list_synthetics_tests.ts @@ -0,0 +1,115 @@ +import type { + ListSyntheticsTestsParams, + ListSyntheticsTestsResponse, + SyntheticsTestData, +} from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const listSyntheticsTestsTool: ToolConfig< + ListSyntheticsTestsParams, + ListSyntheticsTestsResponse +> = { + id: 'datadog_list_synthetics_tests', + name: 'Datadog List Synthetic Tests', + description: 'List all Synthetic tests (API, browser, and mobile) with their current status.', + version: '1.0.0', + + params: { + pageSize: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Number of tests returned per page (default: 100)', + }, + pageNumber: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Page to retrieve, starting at zero', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => { + const queryParams = new URLSearchParams() + if (params.pageSize !== undefined) queryParams.set('page_size', String(params.pageSize)) + if (params.pageNumber !== undefined) queryParams.set('page_number', String(params.pageNumber)) + const queryString = queryParams.toString() + return datadogApiUrl( + params.site, + `/api/v1/synthetics/tests${queryString ? `?${queryString}` : ''}` + ) + }, + method: 'GET', + headers: datadogHeaders, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { tests: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + tests: (data.tests ?? []).map((test: SyntheticsTestData) => ({ + public_id: test.public_id, + name: test.name, + status: test.status, + type: test.type, + subtype: test.subtype, + message: test.message, + monitor_id: test.monitor_id, + tags: test.tags ?? [], + locations: test.locations ?? [], + })), + }, + } + }, + + outputs: { + tests: { + type: 'array', + description: 'List of Synthetic tests', + items: { + type: 'object', + properties: { + public_id: { type: 'string', description: 'Public ID of the test' }, + name: { type: 'string', description: 'Test name' }, + status: { type: 'string', description: 'Pause status: live or paused' }, + type: { type: 'string', description: 'Test type: api, browser, mobile, or network' }, + subtype: { type: 'string', description: 'Test subtype, such as http or ssl' }, + message: { type: 'string', description: 'Notification message' }, + monitor_id: { type: 'number', description: 'Associated monitor ID' }, + tags: { type: 'array', description: 'Tags attached to the test' }, + locations: { type: 'array', description: 'Locations the test runs from' }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/mute_monitor.ts b/apps/sim/tools/datadog/mute_monitor.ts index 5d64185388..708d3d0e88 100644 --- a/apps/sim/tools/datadog/mute_monitor.ts +++ b/apps/sim/tools/datadog/mute_monitor.ts @@ -1,10 +1,12 @@ import type { MuteMonitorParams, MuteMonitorResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const muteMonitorTool: ToolConfig = { id: 'datadog_mute_monitor', name: 'Datadog Mute Monitor', - description: 'Mute a monitor to temporarily suppress notifications.', + description: + 'Mute a monitor to temporarily suppress its notifications. Use Unmute Monitor to reverse it, or schedule a downtime instead when you want a planned, auditable maintenance window.', version: '1.0.0', params: { @@ -26,7 +28,7 @@ export const muteMonitorTool: ToolConfig required: false, visibility: 'user-or-llm', description: - 'Unix timestamp in seconds when the mute should end (e.g., 1705323600). If not specified, mutes indefinitely.', + 'Unix timestamp in seconds when the mute should end (e.g., 1705323600). If not specified, the monitor stays muted until it is unmuted.', }, apiKey: { type: 'string', @@ -49,40 +51,36 @@ export const muteMonitorTool: ToolConfig }, request: { - url: (params) => { - const site = params.site || 'datadoghq.com' - return `https://api.${site}/api/v1/monitor/${params.monitorId}/mute` - }, + url: (params) => + datadogApiUrl(params.site, `/api/v1/monitor/${encodeURIComponent(params.monitorId)}/mute`), method: 'POST', - headers: (params) => ({ - 'Content-Type': 'application/json', - 'DD-API-KEY': params.apiKey, - 'DD-APPLICATION-KEY': params.applicationKey, - }), + headers: datadogHeaders, body: (params) => { - const body: Record = {} + const body: { scope?: string; end?: number } = {} if (params.scope) body.scope = params.scope - if (params.end) body.end = params.end + if (params.end !== undefined) body.end = params.end return body }, }, transformResponse: async (response: Response) => { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) return { success: false, - output: { - success: false, - }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + output: { success: false }, + error: await datadogErrorMessage(response), } } + const data = await response.json().catch(() => ({})) + return { success: true, output: { success: true, + monitorId: data.id, + name: data.name, + overallState: data.overall_state, }, } }, @@ -92,5 +90,20 @@ export const muteMonitorTool: ToolConfig type: 'boolean', description: 'Whether the monitor was successfully muted', }, + monitorId: { + type: 'number', + description: 'ID of the muted monitor', + optional: true, + }, + name: { + type: 'string', + description: 'Name of the muted monitor', + optional: true, + }, + overallState: { + type: 'string', + description: 'Monitor state after muting', + optional: true, + }, }, } diff --git a/apps/sim/tools/datadog/query_logs.ts b/apps/sim/tools/datadog/query_logs.ts index 1443c8077f..c668820efb 100644 --- a/apps/sim/tools/datadog/query_logs.ts +++ b/apps/sim/tools/datadog/query_logs.ts @@ -1,4 +1,10 @@ -import type { QueryLogsParams, QueryLogsResponse } from '@/tools/datadog/types' +import type { + DatadogV2Resource, + LogAttributes, + QueryLogsParams, + QueryLogsResponse, +} from '@/tools/datadog/types' +import { datadogErrorMessage } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const queryLogsTool: ToolConfig = { @@ -36,6 +42,13 @@ export const queryLogsTool: ToolConfig = { visibility: 'user-or-llm', description: 'Maximum number of logs to return (e.g., 50, 100, max: 1000)', }, + cursor: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Pagination cursor from a previous call, taken from its nextLogId output. Omit for the first page.', + }, sort: { type: 'string', required: false, @@ -80,7 +93,11 @@ export const queryLogsTool: ToolConfig = { 'DD-APPLICATION-KEY': params.applicationKey, }), body: (params) => { - const body: Record = { + const body: { + filter: { query: string; from: string; to: string; indexes?: string[] } + page: { limit: number; cursor?: string } + sort?: 'timestamp' | '-timestamp' + } = { filter: { query: params.query, from: params.from, @@ -91,6 +108,10 @@ export const queryLogsTool: ToolConfig = { }, } + if (params.cursor) { + body.page.cursor = params.cursor + } + if (params.sort) { body.sort = params.sort } @@ -108,18 +129,18 @@ export const queryLogsTool: ToolConfig = { transformResponse: async (response: Response) => { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { logs: [], }, - error: errorData.errors?.[0]?.detail || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } const data = await response.json() - const logs = (data.data || []).map((log: any) => ({ + const logs = (data.data || []).map((log: DatadogV2Resource) => ({ id: log.id, content: { timestamp: log.attributes?.timestamp, @@ -158,6 +179,8 @@ export const queryLogsTool: ToolConfig = { service: { type: 'string', description: 'Service name' }, message: { type: 'string', description: 'Log message' }, status: { type: 'string', description: 'Log status/level' }, + attributes: { type: 'json', description: 'Free-form log attributes' }, + tags: { type: 'array', description: 'Log tags' }, }, }, }, diff --git a/apps/sim/tools/datadog/query_timeseries.ts b/apps/sim/tools/datadog/query_timeseries.ts index abae9e4a3e..ee4be02dfc 100644 --- a/apps/sim/tools/datadog/query_timeseries.ts +++ b/apps/sim/tools/datadog/query_timeseries.ts @@ -1,4 +1,9 @@ -import type { QueryTimeseriesParams, QueryTimeseriesResponse } from '@/tools/datadog/types' +import type { + MetricsQuerySeries, + QueryTimeseriesParams, + QueryTimeseriesResponse, +} from '@/tools/datadog/types' +import { datadogErrorMessage } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const queryTimeseriesTool: ToolConfig = { @@ -68,19 +73,33 @@ export const queryTimeseriesTool: ToolConfig { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { series: [], status: 'error', }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } const data = await response.json() - const series = (data.series || []).map((s: any) => ({ + + /** + * A failed metrics query still returns 200; Datadog signals it with a non-`ok` + * `status` and puts the reason in `error`. Without this the caller gets an empty + * series and no indication anything went wrong. + */ + if (data.status && data.status !== 'ok') { + return { + success: false, + output: { series: [], status: data.status }, + error: data.error || `Datadog returned query status "${data.status}"`, + } + } + + const series = (data.series || []).map((s: MetricsQuerySeries) => ({ metric: s.metric || s.expression, tags: s.tag_set || [], points: (s.pointlist || []).map((p: [number, number]) => ({ @@ -93,7 +112,7 @@ export const queryTimeseriesTool: ToolConfig = { + id: 'datadog_search_spans', + name: 'Datadog Search Spans', + description: 'Search indexed APM spans using the span query syntax, with cursor pagination.', + version: '1.0.0', + + params: { + query: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Span search query (e.g., "service:web* AND @http.status_code:[500 TO 599]"). Defaults to "*"', + }, + from: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Minimum time, ISO-8601, date math, or milliseconds (default: "now-15m")', + }, + to: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Maximum time, ISO-8601, date math, or milliseconds (default: "now")', + }, + sort: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Sort order: "timestamp" for oldest first, "-timestamp" for newest first', + }, + cursor: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Pagination cursor returned as nextCursor by a previous call', + }, + limit: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Maximum number of spans to return (default: 10, max: 1000)', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, '/api/v2/spans/events/search'), + method: 'POST', + headers: datadogHeaders, + body: (params) => { + const filter: Record = {} + if (params.query) filter.query = params.query + if (params.from) filter.from = params.from + if (params.to) filter.to = params.to + + const page: Record = {} + if (params.cursor) page.cursor = params.cursor + if (params.limit !== undefined) page.limit = params.limit + + const attributes: Record = {} + if (Object.keys(filter).length > 0) attributes.filter = filter + if (Object.keys(page).length > 0) attributes.page = page + if (params.sort) attributes.sort = params.sort + + return { data: { type: 'search_request', attributes } } + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { spans: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + spans: (data.data ?? []).map((span: DatadogV2Resource) => ({ + id: span.id, + type: span.type, + attributes: span.attributes ?? {}, + })), + nextCursor: data.meta?.page?.after, + elapsed: data.meta?.elapsed, + }, + } + }, + + outputs: { + spans: { + type: 'array', + description: 'List of matching spans', + items: { + type: 'object', + properties: { + id: { type: 'string', description: 'Unique span event ID' }, + type: { type: 'string', description: 'Resource type (spans)' }, + attributes: { + type: 'object', + description: 'Span attributes', + properties: { + service: { type: 'string', description: 'Service that emitted the span' }, + resource_name: { type: 'string', description: 'Resource name' }, + env: { type: 'string', description: 'Environment' }, + host: { type: 'string', description: 'Host that emitted the span' }, + type: { type: 'string', description: 'Span type, such as web or db' }, + trace_id: { type: 'string', description: 'Trace ID' }, + span_id: { type: 'string', description: 'Span ID' }, + parent_id: { type: 'string', description: 'Parent span ID' }, + start_timestamp: { type: 'string', description: 'Span start timestamp' }, + end_timestamp: { type: 'string', description: 'Span end timestamp' }, + tags: { type: 'array', description: 'Tags on the span' }, + custom: { type: 'object', description: 'Custom span data' }, + }, + }, + }, + }, + }, + nextCursor: { + type: 'string', + description: 'Cursor for the next page of spans', + optional: true, + }, + elapsed: { + type: 'number', + description: 'Query time in milliseconds', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/send_logs.ts b/apps/sim/tools/datadog/send_logs.ts index 1dd5055675..39f0a41ae0 100644 --- a/apps/sim/tools/datadog/send_logs.ts +++ b/apps/sim/tools/datadog/send_logs.ts @@ -1,4 +1,6 @@ -import type { SendLogsParams, SendLogsResponse } from '@/tools/datadog/types' +import { filterUndefined } from '@sim/utils/object' +import type { LogEntry, SendLogsParams, SendLogsResponse } from '@/tools/datadog/types' +import { datadogErrorMessage, parseJsonParam } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' export const sendLogsTool: ToolConfig = { @@ -47,33 +49,31 @@ export const sendLogsTool: ToolConfig = { 'DD-API-KEY': params.apiKey, }), body: (params) => { - let logs: any[] - try { - logs = typeof params.logs === 'string' ? JSON.parse(params.logs) : params.logs - } catch { - throw new Error('Invalid JSON in logs parameter') + const logs = parseJsonParam(params.logs, 'logs parameter') + if (!Array.isArray(logs) || logs.length === 0) { + throw new Error('logs must be a non-empty JSON array of log entries') } - // Ensure each log entry has the required format - return logs.map((log: any) => ({ - ddsource: log.ddsource || 'custom', - ddtags: log.ddtags || '', - hostname: log.hostname || '', - message: log.message, - service: log.service || '', - })) + /** + * Every extra key is preserved: Datadog's log intake accepts arbitrary + * additional properties as the log's structured attributes, so rebuilding each + * entry from a fixed field list would silently discard them. Empty optional + * fields are dropped rather than sent blank, which would otherwise suppress + * Datadog's own host inference and write an empty reserved `service` attribute. + */ + return logs.map((log) => filterUndefined({ ...log, ddsource: log.ddsource || 'custom' })) }, }, transformResponse: async (response: Response) => { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, output: { success: false, }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + error: message, } } diff --git a/apps/sim/tools/datadog/submit_metrics.ts b/apps/sim/tools/datadog/submit_metrics.ts index 7b4df3cf99..7b0155f2e0 100644 --- a/apps/sim/tools/datadog/submit_metrics.ts +++ b/apps/sim/tools/datadog/submit_metrics.ts @@ -1,6 +1,23 @@ -import type { SubmitMetricsParams, SubmitMetricsResponse } from '@/tools/datadog/types' +import { filterUndefined } from '@sim/utils/object' +import type { + MetricSeries, + SubmitMetricsParams, + SubmitMetricsResponse, +} from '@/tools/datadog/types' +import { datadogErrorMessage, parseJsonParam } from '@/tools/datadog/utils' import type { ToolConfig } from '@/tools/types' +/** + * Datadog `MetricIntakeType` codes: 0 unspecified, 1 count, 2 rate, 3 gauge. + * A metric with no recognized type is submitted without a `type`, letting Datadog + * infer it rather than silently mislabeling the series. + */ +const METRIC_INTAKE_TYPE = { + count: 1, + rate: 2, + gauge: 3, +} as const + export const submitMetricsTool: ToolConfig = { id: 'datadog_submit_metrics', name: 'Datadog Submit Metrics', @@ -14,7 +31,7 @@ export const submitMetricsTool: ToolConfig { - let series: any[] - try { - series = typeof params.series === 'string' ? JSON.parse(params.series) : params.series - } catch { - throw new Error('Invalid JSON in series parameter') + const series = parseJsonParam(params.series, 'series parameter') + if (!Array.isArray(series) || series.length === 0) { + throw new Error('series must be a non-empty JSON array of metric series') } - // Transform to Datadog API v2 format - const formattedSeries = series.map((s: any) => ({ - metric: s.metric, - type: s.type === 'gauge' ? 0 : s.type === 'rate' ? 1 : s.type === 'count' ? 2 : 3, - points: s.points.map((p: any) => ({ - timestamp: p.timestamp, - value: p.value, - })), - tags: s.tags || [], - unit: s.unit, - resources: s.resources || [{ name: 'host', type: 'host' }], - })) + const formattedSeries = series.map((s) => + filterUndefined({ + metric: s.metric, + type: METRIC_INTAKE_TYPE[s.type as keyof typeof METRIC_INTAKE_TYPE], + points: s.points?.map((p) => ({ timestamp: p.timestamp, value: p.value })), + tags: s.tags, + unit: s.unit, + interval: s.interval, + source_type_name: s.sourceTypeName, + resources: s.resources, + }) + ) return { series: formattedSeries } }, @@ -67,14 +82,11 @@ export const submitMetricsTool: ToolConfig { if (!response.ok) { - const errorData = await response.json().catch(() => ({})) + const message = await datadogErrorMessage(response) return { success: false, - output: { - success: false, - errors: [errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`], - }, - error: errorData.errors?.[0] || `HTTP ${response.status}: ${response.statusText}`, + output: { success: false, errors: [message] }, + error: message, } } diff --git a/apps/sim/tools/datadog/trigger_synthetics_tests.ts b/apps/sim/tools/datadog/trigger_synthetics_tests.ts new file mode 100644 index 0000000000..e7ce5a7f23 --- /dev/null +++ b/apps/sim/tools/datadog/trigger_synthetics_tests.ts @@ -0,0 +1,118 @@ +import type { + TriggerSyntheticsTestsParams, + TriggerSyntheticsTestsResponse, +} from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const triggerSyntheticsTestsTool: ToolConfig< + TriggerSyntheticsTestsParams, + TriggerSyntheticsTestsResponse +> = { + id: 'datadog_trigger_synthetics_tests', + name: 'Datadog Trigger Synthetic Tests', + description: 'Trigger an immediate run of one or more Synthetic tests by public ID.', + version: '1.0.0', + + params: { + publicIds: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'Comma-separated public IDs of the Synthetic tests to trigger', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, '/api/v1/synthetics/tests/trigger'), + method: 'POST', + headers: datadogHeaders, + body: (params) => ({ + tests: (splitCommaList(params.publicIds) ?? []).map((publicId) => ({ + public_id: publicId, + })), + }), + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { triggeredCheckIds: [], results: [], locations: [] }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + batchId: data.batch_id, + triggeredCheckIds: data.triggered_check_ids ?? [], + results: data.results ?? [], + locations: data.locations ?? [], + }, + } + }, + + outputs: { + batchId: { + type: 'string', + description: 'Public ID of the triggered batch', + optional: true, + }, + triggeredCheckIds: { + type: 'array', + description: 'Public IDs of the triggered Synthetic tests', + items: { type: 'string' }, + }, + results: { + type: 'array', + description: 'Information about each triggered test run', + items: { + type: 'object', + properties: { + public_id: { type: 'string', description: 'Public ID of the test' }, + result_id: { type: 'string', description: 'ID of the run result' }, + location: { type: 'number', description: 'Location ID of the run' }, + device: { type: 'string', description: 'Device ID used for browser tests' }, + }, + }, + }, + locations: { + type: 'array', + description: 'Locations the tests were triggered from', + items: { + type: 'object', + properties: { + id: { type: 'number', description: 'Location ID' }, + name: { type: 'string', description: 'Location name' }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/types.ts b/apps/sim/tools/datadog/types.ts index fc6e0f62ee..9932f83835 100644 --- a/apps/sim/tools/datadog/types.ts +++ b/apps/sim/tools/datadog/types.ts @@ -2,13 +2,17 @@ import type { ToolResponse } from '@/tools/types' // Datadog Site/Region options +/** Regional sites Datadog serves the API from, per the `site` server variable enum. */ export type DatadogSite = | 'datadoghq.com' | 'us3.datadoghq.com' | 'us5.datadoghq.com' | 'datadoghq.eu' | 'ap1.datadoghq.com' + | 'ap2.datadoghq.com' + | 'uk1.datadoghq.com' | 'ddog-gov.com' + | 'us2.ddog-gov.com' // Base parameters for write-only operations (only need API key) interface DatadogWriteOnlyParams { @@ -21,21 +25,34 @@ interface DatadogBaseParams extends DatadogWriteOnlyParams { applicationKey: string } +/** + * A JSON:API resource object as returned by Datadog v2 endpoints. v1 endpoints + * return flat objects instead, so this wrapper is only used for v2 payloads. + */ +export interface DatadogV2Resource { + id?: string + type?: string + attributes?: TAttributes +} + // METRICS TYPES export type MetricType = 'gauge' | 'rate' | 'count' | 'distribution' -interface MetricPoint { +export interface MetricPoint { timestamp: number value: number } -interface MetricSeries { +export interface MetricSeries { metric: string type?: MetricType points: MetricPoint[] tags?: string[] unit?: string + /** Required by Datadog when `type` is `rate` or `count`, in seconds. */ + interval?: number + sourceTypeName?: string resources?: { name: string; type: string }[] } @@ -63,6 +80,18 @@ interface TimeseriesPoint { value: number } +/** + * One series of a v1 metrics query response (`MetricsQueryMetadata`). Datadog + * returns the metric under `metric` for plain queries and `expression` for + * arithmetic/function queries. + */ +export interface MetricsQuerySeries { + metric?: string + expression?: string + tag_set?: string[] + pointlist?: [number, number][] +} + interface TimeseriesResult { metric: string tags: string[] @@ -71,48 +100,13 @@ interface TimeseriesResult { interface QueryTimeseriesOutput { series: TimeseriesResult[] - status: string + status?: string } export interface QueryTimeseriesResponse extends ToolResponse { output: QueryTimeseriesOutput } -interface ListMetricsParams extends DatadogBaseParams { - from?: number // Unix timestamp - only return metrics active since this time - host?: string // Filter by host name - tags?: string // Filter by tags (comma-separated) -} - -interface ListMetricsOutput { - metrics: string[] -} - -interface ListMetricsResponse extends ToolResponse { - output: ListMetricsOutput -} - -interface GetMetricMetadataParams extends DatadogBaseParams { - metricName: string -} - -interface MetricMetadata { - description?: string - short_name?: string - unit?: string - per_unit?: string - type?: string - integration?: string -} - -interface GetMetricMetadataOutput { - metadata: MetricMetadata -} - -interface GetMetricMetadataResponse extends ToolResponse { - output: GetMetricMetadataOutput -} - // EVENTS TYPES export type EventAlertType = @@ -137,13 +131,13 @@ export interface CreateEventParams extends DatadogWriteOnlyParams { dateHappened?: number // Unix timestamp } -interface EventData { - id: number - title: string - text: string - date_happened: number - priority: string - alert_type: string +export interface EventData { + id?: number + title?: string + text?: string + date_happened?: number + priority?: string + alert_type?: string host?: string tags?: string[] url?: string @@ -157,37 +151,6 @@ export interface CreateEventResponse extends ToolResponse { output: CreateEventOutput } -interface GetEventParams extends DatadogBaseParams { - eventId: string -} - -interface GetEventOutput { - event: EventData -} - -interface GetEventResponse extends ToolResponse { - output: GetEventOutput -} - -interface QueryEventsParams extends DatadogBaseParams { - start: number // Unix timestamp - end: number // Unix timestamp - priority?: EventPriority - sources?: string // Comma-separated source names - tags?: string // Comma-separated tags - unaggregated?: boolean - excludeAggregate?: boolean - page?: number -} - -interface QueryEventsOutput { - events: EventData[] -} - -interface QueryEventsResponse extends ToolResponse { - output: QueryEventsOutput -} - // MONITORS TYPES export type MonitorType = @@ -235,11 +198,11 @@ export interface CreateMonitorParams extends DatadogBaseParams { options?: string // JSON string of MonitorOptions } -interface MonitorData { - id: number - name: string - type: string - query: string +export interface MonitorData { + id?: number + name?: string + type?: string + query?: string message?: string tags?: string[] priority?: number @@ -272,37 +235,6 @@ export interface GetMonitorResponse extends ToolResponse { output: GetMonitorOutput } -interface UpdateMonitorParams extends DatadogBaseParams { - monitorId: string - name?: string - query?: string - message?: string - tags?: string // Comma-separated tags - priority?: number - options?: string // JSON string of MonitorOptions -} - -interface UpdateMonitorOutput { - monitor: MonitorData -} - -interface UpdateMonitorResponse extends ToolResponse { - output: UpdateMonitorOutput -} - -interface DeleteMonitorParams extends DatadogBaseParams { - monitorId: string - force?: boolean -} - -interface DeleteMonitorOutput { - deleted_monitor_id: number -} - -interface DeleteMonitorResponse extends ToolResponse { - output: DeleteMonitorOutput -} - export interface ListMonitorsParams extends DatadogBaseParams { groupStates?: string // Comma-separated states name?: string // Filter by name @@ -322,42 +254,52 @@ export interface ListMonitorsResponse extends ToolResponse { output: ListMonitorsOutput } +/** + * Mute/unmute monitor are served by `POST /api/v1/monitor/{monitor_id}/mute` and + * `/unmute`. They are absent from the datadog-api-client-go generator spec but are + * still implemented by Datadog's official Python client (`datadogpy` Monitor.mute / + * Monitor.unmute), which is the source for these request shapes. + */ export interface MuteMonitorParams extends DatadogBaseParams { monitorId: string - scope?: string // Scope to mute (e.g., "host:myhost") - end?: number // Unix timestamp when mute ends + scope?: string + end?: number } -interface MuteMonitorOutput { - success: boolean -} - -export interface MuteMonitorResponse extends ToolResponse { - output: MuteMonitorOutput -} - -interface UnmuteMonitorParams extends DatadogBaseParams { +export interface UnmuteMonitorParams extends DatadogBaseParams { monitorId: string scope?: string allScopes?: boolean } -interface UnmuteMonitorOutput { +interface MonitorMuteOutput { success: boolean + monitorId?: number + name?: string + overallState?: string } -interface UnmuteMonitorResponse extends ToolResponse { - output: UnmuteMonitorOutput +export interface MuteMonitorResponse extends ToolResponse { + output: MonitorMuteOutput +} + +export interface UnmuteMonitorResponse extends ToolResponse { + output: MonitorMuteOutput } // LOGS TYPES -interface LogEntry { +/** + * One entry for the Datadog log intake. Datadog treats any key beyond the reserved + * ones as a structured log attribute, so extra properties are carried through. + */ +export interface LogEntry { ddsource?: string ddtags?: string hostname?: string message: string service?: string + [attribute: string]: unknown } export interface SendLogsParams extends DatadogWriteOnlyParams { @@ -377,21 +319,25 @@ export interface QueryLogsParams extends DatadogBaseParams { from: string // ISO-8601 or relative (now-1h) to: string // ISO-8601 or relative (now) limit?: number + cursor?: string sort?: 'timestamp' | '-timestamp' indexes?: string // Comma-separated index names } +/** Attributes of a v2 log event (`LogAttributes` in the Datadog v2 schema). */ +export interface LogAttributes { + timestamp?: string + host?: string + service?: string + message?: string + status?: string + attributes?: Record + tags?: string[] +} + interface LogData { - id: string - content: { - timestamp: string - host?: string - service?: string - message: string - status?: string - attributes?: Record - tags?: string[] - } + id?: string + content: LogAttributes } interface QueryLogsOutput { @@ -414,25 +360,32 @@ export interface CreateDowntimeParams extends DatadogBaseParams { monitorId?: string // Monitor ID to mute monitorTags?: string // Comma-separated tags to match monitors muteFirstRecoveryNotification?: boolean - notifyEndTypes?: string // Comma-separated: "canceled", "expired" - recurrence?: string // JSON string of recurrence config +} + +/** + * Attributes of a v2 downtime (`DowntimeResponseAttributes`). `scope` is a single + * query string, and every timestamp is an ISO-8601 string rather than epoch seconds. + */ +export interface DowntimeAttributes { + scope?: string + message?: string + schedule?: { start?: string | null; end?: string | null; timezone?: string } + status?: string + display_timezone?: string | null + created?: string + modified?: string + canceled?: string | null } interface DowntimeData { - id: number + id?: string scope: string[] message?: string start?: number end?: number timezone?: string - monitor_id?: number - monitor_tags?: string[] - mute_first_recovery_notification?: boolean - disabled?: boolean created?: number modified?: number - creator_id?: number - canceled?: number active?: boolean } @@ -446,12 +399,13 @@ export interface CreateDowntimeResponse extends ToolResponse { export interface ListDowntimesParams extends DatadogBaseParams { currentOnly?: boolean - withCreator?: boolean - monitorId?: string + limit?: number + offset?: number } interface ListDowntimesOutput { downtimes: DowntimeData[] + totalCount?: number } export interface ListDowntimesResponse extends ToolResponse { @@ -469,82 +423,158 @@ interface CancelDowntimeOutput { export interface CancelDowntimeResponse extends ToolResponse { output: CancelDowntimeOutput } - // SLO TYPES export type SloType = 'metric' | 'monitor' | 'time_slice' +export type SloTimeframe = '7d' | '30d' | '90d' | 'custom' + interface SloThreshold { - timeframe: '7d' | '30d' | '90d' | 'custom' - target: number // Target percentage (e.g., 99.9) + timeframe: SloTimeframe + target: number target_display?: string warning?: number warning_display?: string } -interface CreateSloParams extends DatadogBaseParams { - name: string - type: SloType - description?: string - tags?: string // Comma-separated tags - thresholds: string // JSON string of SloThreshold[] - // For metric-based SLO - query?: string // JSON string of { numerator: string, denominator: string } - // For monitor-based SLO - monitorIds?: string // Comma-separated monitor IDs - groups?: string // Comma-separated group names -} - interface SloData { id: string name: string type: string - description?: string + description?: string | null tags?: string[] - thresholds: SloThreshold[] - creator?: { email: string; handle: string; name: string } + thresholds?: SloThreshold[] + target_threshold?: number + warning_threshold?: number + timeframe?: string + monitor_ids?: number[] + monitor_tags?: string[] + groups?: string[] + query?: { numerator: string; denominator: string } | null + creator?: { email?: string; handle?: string; name?: string | null } | null created_at?: number modified_at?: number + configured_alert_ids?: number[] +} + +export interface ListSlosParams extends DatadogBaseParams { + ids?: string + query?: string + tagsQuery?: string + metricsQuery?: string + limit?: number + offset?: number + isDeleted?: boolean +} + +interface ListSlosOutput { + slos: SloData[] +} + +export interface ListSlosResponse extends ToolResponse { + output: ListSlosOutput +} + +export interface GetSloParams extends DatadogBaseParams { + sloId: string + withConfiguredAlertIds?: boolean +} + +interface GetSloOutput { + slo: SloData +} + +export interface GetSloResponse extends ToolResponse { + output: GetSloOutput +} + +export interface CreateSloParams extends DatadogBaseParams { + name: string + type: SloType + description?: string + tags?: string + thresholds: string + query?: string + monitorIds?: string + groups?: string + targetThreshold?: number + warningThreshold?: number + timeframe?: SloTimeframe } interface CreateSloOutput { slo: SloData } -interface CreateSloResponse extends ToolResponse { +export interface CreateSloResponse extends ToolResponse { output: CreateSloOutput } -interface GetSloHistoryParams extends DatadogBaseParams { +export interface UpdateSloParams extends CreateSloParams { sloId: string - fromTs: number // Unix timestamp - toTs: number // Unix timestamp - target?: number // Target SLO percentage +} + +interface UpdateSloOutput { + slo: SloData +} + +export interface UpdateSloResponse extends ToolResponse { + output: UpdateSloOutput +} + +export interface DeleteSloParams extends DatadogBaseParams { + sloId: string + force?: boolean +} + +interface DeleteSloOutput { + success: boolean + deletedIds: string[] +} + +export interface DeleteSloResponse extends ToolResponse { + output: DeleteSloOutput +} + +export interface GetSloHistoryParams extends DatadogBaseParams { + sloId: string + fromTs: number + toTs: number + target?: number + applyCorrection?: boolean +} + +interface SloHistorySliData { + name?: string + group?: string + sli_value?: number | null + span_precision?: number + precision?: Record + error_budget_remaining?: Record + monitor_type?: string + monitor_modified?: number + preview?: boolean + history?: number[][] } interface SloHistoryData { - from_ts: number - to_ts: number - type: string - type_id: number - sli_value?: number - overall: { - name: string - sli_value: number - span_precision: number - precision: { [key: string]: number } - } - series?: { - times: number[] - values: number[] - } + from_ts?: number + to_ts?: number + type?: string + type_id?: number + group_by?: string[] + overall?: SloHistorySliData + groups?: SloHistorySliData[] + monitors?: SloHistorySliData[] + thresholds?: Record } interface GetSloHistoryOutput { history: SloHistoryData + sliValue?: number | null } -interface GetSloHistoryResponse extends ToolResponse { +export interface GetSloHistoryResponse extends ToolResponse { output: GetSloHistoryOutput } @@ -552,39 +582,53 @@ interface GetSloHistoryResponse extends ToolResponse { export type DashboardLayoutType = 'ordered' | 'free' -interface CreateDashboardParams extends DatadogBaseParams { - title: string - layoutType: DashboardLayoutType - description?: string - widgets?: string // JSON string of widget definitions - isReadOnly?: boolean - notifyList?: string // Comma-separated user handles to notify - templateVariables?: string // JSON string of template variable definitions - tags?: string // Comma-separated tags +interface DashboardData { + id?: string + title?: string + layout_type?: string + description?: string | null + url?: string + author_handle?: string + author_name?: string | null + created_at?: string + modified_at?: string + is_read_only?: boolean + reflow_type?: string + tags?: string[] | null + notify_list?: string[] | null + restricted_roles?: string[] + template_variables?: unknown[] | null + widgets?: unknown[] } -interface DashboardData { - id: string - title: string - layout_type: string - description?: string +interface DashboardSummaryData { + id?: string + title?: string + description?: string | null + layout_type?: string url?: string author_handle?: string created_at?: string modified_at?: string is_read_only?: boolean - tags?: string[] } -interface CreateDashboardOutput { - dashboard: DashboardData +export interface ListDashboardsParams extends DatadogBaseParams { + filterShared?: boolean + filterDeleted?: boolean + count?: number + start?: number } -interface CreateDashboardResponse extends ToolResponse { - output: CreateDashboardOutput +interface ListDashboardsOutput { + dashboards: DashboardSummaryData[] } -interface GetDashboardParams extends DatadogBaseParams { +export interface ListDashboardsResponse extends ToolResponse { + output: ListDashboardsOutput +} + +export interface GetDashboardParams extends DatadogBaseParams { dashboardId: string } @@ -592,160 +636,525 @@ interface GetDashboardOutput { dashboard: DashboardData } -interface GetDashboardResponse extends ToolResponse { +export interface GetDashboardResponse extends ToolResponse { output: GetDashboardOutput } -interface ListDashboardsParams extends DatadogBaseParams { - filterShared?: boolean - filterDeleted?: boolean - count?: number - start?: number -} - -interface DashboardSummary { - id: string +export interface CreateDashboardParams extends DatadogBaseParams { title: string + layoutType: DashboardLayoutType + widgets: string description?: string - layout_type: string - url?: string - author_handle?: string - created_at?: string - modified_at?: string - is_read_only?: boolean - popularity?: number + notifyList?: string + templateVariables?: string + tags?: string + reflowType?: 'auto' | 'fixed' } -interface ListDashboardsOutput { - dashboards: DashboardSummary[] - total?: number +interface CreateDashboardOutput { + dashboard: DashboardData } -interface ListDashboardsResponse extends ToolResponse { - output: ListDashboardsOutput +export interface CreateDashboardResponse extends ToolResponse { + output: CreateDashboardOutput } -// HOSTS TYPES - -interface ListHostsParams extends DatadogBaseParams { - filter?: string // Filter hosts by name, alias, or tag - sortField?: string // Field to sort by - sortDir?: 'asc' | 'desc' - start?: number // Starting offset - count?: number // Max hosts to return - from?: number // Unix timestamp - hosts seen in last N seconds - includeMutedHostsData?: boolean - includeHostsMetadata?: boolean +export interface DeleteDashboardParams extends DatadogBaseParams { + dashboardId: string } -interface HostData { - name: string - id: number - aliases?: string[] - apps?: string[] - aws_name?: string - host_name?: string - is_muted?: boolean - last_reported_time?: number - meta?: { - agent_version?: string - cpu_cores?: number - gohai?: string - machine?: string - platform?: string +interface DeleteDashboardOutput { + success: boolean + deletedDashboardId?: string +} + +export interface DeleteDashboardResponse extends ToolResponse { + output: DeleteDashboardOutput +} + +// SYNTHETICS TYPES + +export type SyntheticsTestPauseStatus = 'live' | 'paused' + +export interface SyntheticsTestData { + public_id?: string + name?: string + status?: string + type?: string + subtype?: string + message?: string + monitor_id?: number + tags?: string[] + locations?: string[] + config?: unknown + options?: unknown + creator?: { email?: string; handle?: string; name?: string | null } | null +} + +export interface ListSyntheticsTestsParams extends DatadogBaseParams { + pageSize?: number + pageNumber?: number +} + +interface ListSyntheticsTestsOutput { + tests: SyntheticsTestData[] +} + +export interface ListSyntheticsTestsResponse extends ToolResponse { + output: ListSyntheticsTestsOutput +} + +export interface GetSyntheticsTestParams extends DatadogBaseParams { + publicId: string +} + +interface GetSyntheticsTestOutput { + test: SyntheticsTestData +} + +export interface GetSyntheticsTestResponse extends ToolResponse { + output: GetSyntheticsTestOutput +} + +export interface GetSyntheticsResultsParams extends DatadogBaseParams { + publicId: string + fromTs?: number + toTs?: number + probeDc?: string +} + +interface SyntheticsResultData { + result_id?: string + check_time?: number + probe_dc?: string + status?: number + result?: { passed?: boolean; timings?: Record } +} + +interface GetSyntheticsResultsOutput { + results: SyntheticsResultData[] + lastTimestampFetched?: number +} + +export interface GetSyntheticsResultsResponse extends ToolResponse { + output: GetSyntheticsResultsOutput +} + +export interface GetBrowserSyntheticsResultsParams extends DatadogBaseParams { + publicId: string + fromTs?: number + toTs?: number + probeDc?: string +} + +/** + * Result of a single browser test run (`SyntheticsBrowserTestResultShortResult`). + * Unlike the API-test result shape, these fields are camelCase. + */ +interface SyntheticsBrowserResultData { + result_id?: string + check_time?: number + probe_dc?: string + status?: number + result?: { + duration?: number + errorCount?: number + stepCountCompleted?: number + stepCountTotal?: number + device?: Record } - metrics?: { - cpu?: number - iowait?: number - load?: number - } - mute_timeout?: number - sources?: string[] - tags_by_source?: Record - up?: boolean } -interface ListHostsOutput { - hosts: HostData[] - total_matching?: number - total_returned?: number +interface GetBrowserSyntheticsResultsOutput { + results: SyntheticsBrowserResultData[] + lastTimestampFetched?: number } -interface ListHostsResponse extends ToolResponse { - output: ListHostsOutput +export interface GetBrowserSyntheticsResultsResponse extends ToolResponse { + output: GetBrowserSyntheticsResultsOutput +} + +export interface TriggerSyntheticsTestsParams extends DatadogBaseParams { + publicIds: string +} + +interface TriggerSyntheticsTestsOutput { + batchId?: string | null + triggeredCheckIds: string[] + results: { + public_id?: string + result_id?: string + location?: number + device?: string + }[] + locations: { id?: number; name?: string }[] +} + +export interface TriggerSyntheticsTestsResponse extends ToolResponse { + output: TriggerSyntheticsTestsOutput +} + +export interface UpdateSyntheticsStatusParams extends DatadogBaseParams { + publicId: string + newStatus: SyntheticsTestPauseStatus +} + +interface UpdateSyntheticsStatusOutput { + success: boolean + status?: SyntheticsTestPauseStatus +} + +export interface UpdateSyntheticsStatusResponse extends ToolResponse { + output: UpdateSyntheticsStatusOutput +} + +// SECURITY MONITORING TYPES + +export type SecuritySignalState = 'open' | 'archived' | 'under_review' + +export type SecuritySignalArchiveReason = + | 'none' + | 'false_positive' + | 'testing_or_maintenance' + | 'remediated' + | 'investigated_case_opened' + | 'true_positive_benign' + | 'true_positive_malicious' + | 'other' + +/** Attributes of a Cloud SIEM signal (`SecurityMonitoringSignalAttributes`). */ +export interface SecuritySignalAttributes { + message?: string + timestamp?: string + tags?: string[] + custom?: Record +} + +interface SecuritySignalData { + id?: string + type?: string + attributes: SecuritySignalAttributes +} + +export interface ListSecuritySignalsParams extends DatadogBaseParams { + query?: string + from?: string + to?: string + sort?: 'timestamp' | '-timestamp' + cursor?: string + limit?: number +} + +interface ListSecuritySignalsOutput { + signals: SecuritySignalData[] + nextCursor?: string +} + +export interface ListSecuritySignalsResponse extends ToolResponse { + output: ListSecuritySignalsOutput +} + +export interface GetSecuritySignalParams extends DatadogBaseParams { + signalId: string +} + +interface GetSecuritySignalOutput { + signal: SecuritySignalData +} + +export interface GetSecuritySignalResponse extends ToolResponse { + output: GetSecuritySignalOutput +} + +export interface SecuritySignalTriageData { + id?: string + type?: string + state?: string + assignee?: { uuid?: string; handle?: string; name?: string | null; id?: number } + incidentIds?: number[] + archiveReason?: string + archiveComment?: string + stateUpdateTimestamp?: number +} + +export interface UpdateSecuritySignalStateParams extends DatadogBaseParams { + signalId: string + state: SecuritySignalState + archiveReason?: SecuritySignalArchiveReason + archiveComment?: string +} + +interface UpdateSecuritySignalStateOutput { + signal: SecuritySignalTriageData +} + +export interface UpdateSecuritySignalStateResponse extends ToolResponse { + output: UpdateSecuritySignalStateOutput +} + +export interface UpdateSecuritySignalAssigneeParams extends DatadogBaseParams { + signalId: string + assigneeUuid: string +} + +interface UpdateSecuritySignalAssigneeOutput { + signal: SecuritySignalTriageData +} + +export interface UpdateSecuritySignalAssigneeResponse extends ToolResponse { + output: UpdateSecuritySignalAssigneeOutput +} + +export interface ListSecurityRulesParams extends DatadogBaseParams { + query?: string + sort?: string + pageSize?: number + pageNumber?: number +} + +export interface SecurityRuleData { + id?: string + name?: string + type?: string + message?: string + tags?: string[] + isEnabled?: boolean + isDefault?: boolean + createdAt?: number + version?: number +} + +interface ListSecurityRulesOutput { + rules: SecurityRuleData[] +} + +export interface ListSecurityRulesResponse extends ToolResponse { + output: ListSecurityRulesOutput +} + +// APM / SPANS TYPES + +export interface SearchSpansParams extends DatadogBaseParams { + query?: string + from?: string + to?: string + sort?: 'timestamp' | '-timestamp' + cursor?: string + limit?: number +} + +/** Attributes of an indexed APM span (`SpansAttributes`). */ +export interface SpanAttributes { + service?: string + resource_name?: string + env?: string + host?: string + type?: string + trace_id?: string + span_id?: string + parent_id?: string + start_timestamp?: string + end_timestamp?: string + ingestion_reason?: string + retained_by?: string + single_span?: boolean + tags?: string[] + custom?: Record + attributes?: Record +} + +interface SpanData { + id?: string + type?: string + attributes: SpanAttributes +} + +interface SearchSpansOutput { + spans: SpanData[] + nextCursor?: string + elapsed?: number +} + +export interface SearchSpansResponse extends ToolResponse { + output: SearchSpansOutput +} + +export interface ListServicesParams extends DatadogBaseParams { + pageSize?: number + pageNumber?: number + schemaVersion?: string +} + +/** + * Attributes of a service definition (`ServiceDefinitionDataAttributes`). `schema` + * is a union of the v2, v2.1 and v2.2 schema versions, so it stays opaque. + */ +export interface ServiceDefinitionAttributes { + schema?: unknown + meta?: Record +} + +interface ServiceDefinitionData { + id?: string + type?: string + schema?: unknown + meta?: Record +} + +interface ListServicesOutput { + services: ServiceDefinitionData[] +} + +export interface ListServicesResponse extends ToolResponse { + output: ListServicesOutput } // INCIDENTS TYPES -export type IncidentSeverity = 'SEV-1' | 'SEV-2' | 'SEV-3' | 'SEV-4' | 'SEV-5' | 'UNKNOWN' -export type IncidentState = 'active' | 'stable' | 'resolved' +export type IncidentSeverity = 'UNKNOWN' | 'SEV-0' | 'SEV-1' | 'SEV-2' | 'SEV-3' | 'SEV-4' | 'SEV-5' -interface CreateIncidentParams extends DatadogBaseParams { - title: string - customerImpacted: boolean - severity?: IncidentSeverity - fields?: string // JSON string of additional fields +interface IncidentFieldValue { + type?: string + value?: string | string[] | null +} + +/** Attributes of an incident (`IncidentResponseAttributes`). */ +export interface IncidentAttributes { + title?: string + state?: string | null + severity?: string + visibility?: string | null + customer_impacted?: boolean + customer_impact_scope?: string | null + customer_impact_start?: string | null + customer_impact_end?: string | null + customer_impact_duration?: number + fields?: Record + incident_type_uuid?: string + is_test?: boolean + public_id?: number + created?: string + modified?: string + declared?: string + detected?: string | null + resolved?: string | null + archived?: string | null + time_to_detect?: number + time_to_internal_response?: number + time_to_repair?: number + time_to_resolve?: number } interface IncidentData { - id: string - type: string - attributes: { - title: string - customer_impacted: boolean - severity?: IncidentSeverity - state?: IncidentState - created?: string - modified?: string - resolved?: string - detected?: string - customer_impact_scope?: string - customer_impact_start?: string - customer_impact_end?: string - public_id?: number - time_to_detect?: number - time_to_internal_response?: number - time_to_repair?: number - time_to_resolve?: number - } + id?: string + type?: string + attributes: IncidentAttributes +} + +export interface ListIncidentsParams extends DatadogBaseParams { + include?: string + pageSize?: number + pageOffset?: number +} + +interface ListIncidentsOutput { + incidents: IncidentData[] + nextOffset?: number +} + +export interface ListIncidentsResponse extends ToolResponse { + output: ListIncidentsOutput +} + +export interface GetIncidentParams extends DatadogBaseParams { + incidentId: string + include?: string +} + +interface GetIncidentOutput { + incident: IncidentData +} + +export interface GetIncidentResponse extends ToolResponse { + output: GetIncidentOutput +} + +export interface CreateIncidentParams extends DatadogBaseParams { + title: string + customerImpacted: boolean + severity?: IncidentSeverity + customerImpactScope?: string + incidentTypeUuid?: string + isTest?: boolean + fields?: string + notificationHandles?: string } interface CreateIncidentOutput { incident: IncidentData } -interface CreateIncidentResponse extends ToolResponse { +export interface CreateIncidentResponse extends ToolResponse { output: CreateIncidentOutput } -interface ListIncidentsParams extends DatadogBaseParams { - query?: string - pageSize?: number - pageOffset?: number - include?: string // Comma-separated: users, attachments +export interface UpdateIncidentParams extends DatadogBaseParams { + incidentId: string + title?: string + severity?: IncidentSeverity + customerImpacted?: boolean + customerImpactScope?: string + customerImpactStart?: string + customerImpactEnd?: string + detected?: string + fields?: string + notificationHandles?: string } -interface ListIncidentsOutput { - incidents: IncidentData[] +interface UpdateIncidentOutput { + incident: IncidentData } -interface ListIncidentsResponse extends ToolResponse { - output: ListIncidentsOutput +export interface UpdateIncidentResponse extends ToolResponse { + output: UpdateIncidentOutput +} + +export interface AddIncidentTodoParams extends DatadogBaseParams { + incidentId: string + content: string + assignees: string + dueDate?: string +} + +interface IncidentTodoData { + id?: string + type?: string + attributes: { + content?: string + assignees?: string[] + completed?: string | null + due_date?: string | null + incident_id?: string + created?: string + modified?: string + } +} + +interface AddIncidentTodoOutput { + todo: IncidentTodoData +} + +export interface AddIncidentTodoResponse extends ToolResponse { + output: AddIncidentTodoOutput } // Union type for all Datadog responses export type DatadogResponse = | SubmitMetricsResponse | QueryTimeseriesResponse - | ListMetricsResponse - | GetMetricMetadataResponse | CreateEventResponse - | GetEventResponse - | QueryEventsResponse | CreateMonitorResponse | GetMonitorResponse - | UpdateMonitorResponse - | DeleteMonitorResponse | ListMonitorsResponse | MuteMonitorResponse | UnmuteMonitorResponse @@ -754,11 +1163,31 @@ export type DatadogResponse = | CreateDowntimeResponse | ListDowntimesResponse | CancelDowntimeResponse + | ListSlosResponse + | GetSloResponse | CreateSloResponse + | UpdateSloResponse + | DeleteSloResponse | GetSloHistoryResponse - | CreateDashboardResponse - | GetDashboardResponse | ListDashboardsResponse - | ListHostsResponse - | CreateIncidentResponse + | GetDashboardResponse + | CreateDashboardResponse + | DeleteDashboardResponse + | ListSyntheticsTestsResponse + | GetSyntheticsTestResponse + | GetSyntheticsResultsResponse + | GetBrowserSyntheticsResultsResponse + | TriggerSyntheticsTestsResponse + | UpdateSyntheticsStatusResponse + | ListSecuritySignalsResponse + | GetSecuritySignalResponse + | UpdateSecuritySignalStateResponse + | UpdateSecuritySignalAssigneeResponse + | ListSecurityRulesResponse + | SearchSpansResponse + | ListServicesResponse | ListIncidentsResponse + | GetIncidentResponse + | CreateIncidentResponse + | UpdateIncidentResponse + | AddIncidentTodoResponse diff --git a/apps/sim/tools/datadog/unmute_monitor.ts b/apps/sim/tools/datadog/unmute_monitor.ts new file mode 100644 index 0000000000..5fc48af2b5 --- /dev/null +++ b/apps/sim/tools/datadog/unmute_monitor.ts @@ -0,0 +1,108 @@ +import type { UnmuteMonitorParams, UnmuteMonitorResponse } from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const unmuteMonitorTool: ToolConfig = { + id: 'datadog_unmute_monitor', + name: 'Datadog Unmute Monitor', + description: + 'Unmute a monitor so it resumes sending notifications. Reverses Mute Monitor, either for one scope or for every scope at once.', + version: '1.0.0', + + params: { + monitorId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the monitor to unmute (e.g., "12345678")', + }, + scope: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Scope to unmute (e.g., "host:myhost"). Leave blank to unmute the monitor itself rather than a single scope.', + }, + allScopes: { + type: 'boolean', + required: false, + visibility: 'user-or-llm', + description: 'Clear the mute settings for every scope on this monitor', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl(params.site, `/api/v1/monitor/${encodeURIComponent(params.monitorId)}/unmute`), + method: 'POST', + headers: datadogHeaders, + body: (params) => { + const body: { scope?: string; all_scopes?: boolean } = {} + if (params.scope) body.scope = params.scope + if (params.allScopes !== undefined) body.all_scopes = params.allScopes + return body + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { success: false }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json().catch(() => ({})) + + return { + success: true, + output: { + success: true, + monitorId: data.id, + name: data.name, + overallState: data.overall_state, + }, + } + }, + + outputs: { + success: { + type: 'boolean', + description: 'Whether the monitor was successfully unmuted', + }, + monitorId: { + type: 'number', + description: 'ID of the unmuted monitor', + optional: true, + }, + name: { + type: 'string', + description: 'Name of the unmuted monitor', + optional: true, + }, + overallState: { + type: 'string', + description: 'Monitor state after unmuting', + optional: true, + }, + }, +} diff --git a/apps/sim/tools/datadog/update_incident.ts b/apps/sim/tools/datadog/update_incident.ts new file mode 100644 index 0000000000..7be32b485c --- /dev/null +++ b/apps/sim/tools/datadog/update_incident.ts @@ -0,0 +1,180 @@ +import type { UpdateIncidentParams, UpdateIncidentResponse } from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + parseJsonParam, + splitCommaList, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const updateIncidentTool: ToolConfig = { + id: 'datadog_update_incident', + name: 'Datadog Update Incident', + description: + 'Partially update an existing incident. Requires the Incident Management `incident_write` permission; the Incidents API is in public beta.', + version: '1.0.0', + + params: { + incidentId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The UUID of the incident to update', + }, + title: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'New title for the incident', + }, + severity: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Incident severity: UNKNOWN, SEV-0, SEV-1, SEV-2, SEV-3, SEV-4, or SEV-5', + }, + customerImpacted: { + type: 'boolean', + required: false, + visibility: 'user-or-llm', + description: 'Whether the incident caused customer impact', + }, + customerImpactScope: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Summary of the customer impact', + }, + customerImpactStart: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'ISO-8601 timestamp when customers began being impacted', + }, + customerImpactEnd: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'ISO-8601 timestamp when customers were no longer impacted', + }, + detected: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'ISO-8601 timestamp when the incident was detected', + }, + fields: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'JSON object of user-defined incident fields to update, e.g. {"state": {"type": "dropdown", "value": "resolved"}}', + }, + notificationHandles: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated handles to notify about the update', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl(params.site, `/api/v2/incidents/${encodeURIComponent(params.incidentId)}`), + method: 'PATCH', + headers: datadogHeaders, + body: (params) => { + const fields = + parseJsonParam>(params.fields, 'fields parameter') ?? {} + if (params.severity) { + fields.severity = { type: 'dropdown', value: params.severity } + } + + /** + * Only non-empty values are sent. An empty string is how an untouched input + * arrives, and Datadog would take it literally — blanking the stored title or + * rejecting the request as an invalid `date-time`. + */ + const attributes: Record = {} + if (params.title) attributes.title = params.title + if (params.customerImpacted !== undefined) + attributes.customer_impacted = params.customerImpacted + if (params.customerImpactScope) attributes.customer_impact_scope = params.customerImpactScope + if (params.customerImpactStart) attributes.customer_impact_start = params.customerImpactStart + if (params.customerImpactEnd) attributes.customer_impact_end = params.customerImpactEnd + if (params.detected) attributes.detected = params.detected + if (Object.keys(fields).length > 0) attributes.fields = fields + + const handles = splitCommaList(params.notificationHandles) + if (handles) { + attributes.notification_handles = handles.map((handle) => ({ handle })) + } + + return { data: { type: 'incidents', id: params.incidentId, attributes } } + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { incident: { id: '', attributes: {} } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { + incident: { + id: data.data?.id, + type: data.data?.type, + attributes: data.data?.attributes ?? {}, + }, + }, + } + }, + + outputs: { + incident: { + type: 'object', + description: 'The updated incident', + properties: { + id: { type: 'string', description: 'Incident UUID' }, + type: { type: 'string', description: 'Resource type (incidents)' }, + attributes: { + type: 'object', + description: 'Incident attributes', + properties: { + title: { type: 'string', description: 'Incident title' }, + state: { type: 'string', description: 'Incident state' }, + severity: { type: 'string', description: 'Incident severity' }, + modified: { type: 'string', description: 'Last modification timestamp' }, + resolved: { type: 'string', description: 'Resolution timestamp' }, + }, + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/update_security_signal_assignee.ts b/apps/sim/tools/datadog/update_security_signal_assignee.ts new file mode 100644 index 0000000000..00a41db112 --- /dev/null +++ b/apps/sim/tools/datadog/update_security_signal_assignee.ts @@ -0,0 +1,104 @@ +import type { + UpdateSecuritySignalAssigneeParams, + UpdateSecuritySignalAssigneeResponse, +} from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + mapSignalTriageData, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const updateSecuritySignalAssigneeTool: ToolConfig< + UpdateSecuritySignalAssigneeParams, + UpdateSecuritySignalAssigneeResponse +> = { + id: 'datadog_update_security_signal_assignee', + name: 'Datadog Assign Security Signal', + description: + 'Assign a Cloud SIEM security signal to a Datadog user by UUID. Requires the `security_monitoring_signals_write` permission.', + version: '1.0.0', + + params: { + signalId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the security signal', + }, + assigneeUuid: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: + 'UUID of the Datadog user to assign the signal to (e.g., "773b045d-ccf8-4808-bd3b-955ef6a8c940")', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl( + params.site, + `/api/v2/security_monitoring/signals/${encodeURIComponent(params.signalId)}/assignee` + ), + method: 'PATCH', + headers: datadogHeaders, + body: (params) => ({ + data: { attributes: { assignee: { uuid: params.assigneeUuid } } }, + }), + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { signal: {} }, + error: await datadogErrorMessage(response), + } + } + + return { + success: true, + output: { signal: mapSignalTriageData(await response.json()) }, + } + }, + + outputs: { + signal: { + type: 'object', + description: 'The updated signal triage data', + properties: { + id: { type: 'string', description: 'Signal ID' }, + type: { type: 'string', description: 'Resource type of the signal' }, + state: { type: 'string', description: 'Current triage state' }, + assignee: { type: 'object', description: 'User the signal is assigned to' }, + incidentIds: { type: 'array', description: 'IDs of incidents linked to the signal' }, + archiveReason: { type: 'string', description: 'Archive reason, when archived' }, + archiveComment: { type: 'string', description: 'Archive comment, when archived' }, + stateUpdateTimestamp: { + type: 'number', + description: 'Timestamp of the last state update', + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/update_security_signal_state.ts b/apps/sim/tools/datadog/update_security_signal_state.ts new file mode 100644 index 0000000000..78a87fb082 --- /dev/null +++ b/apps/sim/tools/datadog/update_security_signal_state.ts @@ -0,0 +1,119 @@ +import type { + UpdateSecuritySignalStateParams, + UpdateSecuritySignalStateResponse, +} from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + mapSignalTriageData, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const updateSecuritySignalStateTool: ToolConfig< + UpdateSecuritySignalStateParams, + UpdateSecuritySignalStateResponse +> = { + id: 'datadog_update_security_signal_state', + name: 'Datadog Update Security Signal State', + description: + 'Change the triage state of a Cloud SIEM security signal to open, under_review, or archived. Requires the `security_monitoring_signals_write` permission.', + version: '1.0.0', + + params: { + signalId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the security signal', + }, + state: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'New triage state: "open", "under_review", or "archived"', + }, + archiveReason: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'Reason when archiving: none, false_positive, testing_or_maintenance, remediated, investigated_case_opened, true_positive_benign, true_positive_malicious, or other', + }, + archiveComment: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comment explaining why the signal was archived', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl( + params.site, + `/api/v2/security_monitoring/signals/${encodeURIComponent(params.signalId)}/state` + ), + method: 'PATCH', + headers: datadogHeaders, + body: (params) => { + const attributes: Record = { state: params.state } + if (params.archiveReason) attributes.archive_reason = params.archiveReason + if (params.archiveComment) attributes.archive_comment = params.archiveComment + return { data: { attributes } } + }, + }, + + transformResponse: async (response: Response) => { + if (!response.ok) { + return { + success: false, + output: { signal: {} }, + error: await datadogErrorMessage(response), + } + } + + return { + success: true, + output: { signal: mapSignalTriageData(await response.json()) }, + } + }, + + outputs: { + signal: { + type: 'object', + description: 'The updated signal triage data', + properties: { + id: { type: 'string', description: 'Signal ID' }, + type: { type: 'string', description: 'Resource type of the signal' }, + state: { type: 'string', description: 'Current triage state' }, + assignee: { type: 'object', description: 'User the signal is assigned to' }, + incidentIds: { type: 'array', description: 'IDs of incidents linked to the signal' }, + archiveReason: { type: 'string', description: 'Archive reason, when archived' }, + archiveComment: { type: 'string', description: 'Archive comment, when archived' }, + stateUpdateTimestamp: { + type: 'number', + description: 'Timestamp of the last state update', + }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/update_slo.ts b/apps/sim/tools/datadog/update_slo.ts new file mode 100644 index 0000000000..9d01b1da86 --- /dev/null +++ b/apps/sim/tools/datadog/update_slo.ts @@ -0,0 +1,185 @@ +import type { UpdateSloParams, UpdateSloResponse } from '@/tools/datadog/types' +import { + datadogApiUrl, + datadogErrorMessage, + datadogHeaders, + mergeSloUpdatePayload, +} from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const updateSloTool: ToolConfig = { + id: 'datadog_update_slo', + name: 'Datadog Update SLO', + description: + 'Update a service level objective. Reads the current SLO first and applies only the fields you supply, so anything left blank keeps its stored value.', + version: '1.0.0', + + params: { + sloId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The ID of the service level objective to update', + }, + name: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'New name for the SLO. Leave blank to keep the current name.', + }, + type: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'SLO type: "metric" or "monitor". Leave blank to keep the current type. Changing type requires supplying the matching query or monitorIds.', + }, + thresholds: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'JSON array of thresholds replacing the stored ones, e.g. [{"timeframe": "30d", "target": 99.9, "warning": 99.95}]. Leave blank to keep the current thresholds.', + }, + description: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Description of the SLO', + }, + tags: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated tags (e.g., "env:prod,team:core")', + }, + query: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: + 'For metric SLOs, JSON with numerator and denominator, e.g. {"numerator": "sum:requests{status:ok}.as_count()", "denominator": "sum:requests{*}.as_count()"}', + }, + monitorIds: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'For monitor SLOs, comma-separated monitor IDs (e.g., "123,456")', + }, + groups: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Comma-separated monitor groups (e.g., "env:prod,role:mysql")', + }, + targetThreshold: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Primary target threshold (e.g., 99.9)', + }, + warningThreshold: { + type: 'number', + required: false, + visibility: 'user-or-llm', + description: 'Primary warning threshold, must be greater than the target (e.g., 99.95)', + }, + timeframe: { + type: 'string', + required: false, + visibility: 'user-or-llm', + description: 'Primary timeframe: "7d", "30d", or "90d"', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => datadogApiUrl(params.site, `/api/v1/slo/${encodeURIComponent(params.sloId)}`), + method: 'PUT', + headers: datadogHeaders, + }, + + /** + * Datadog's SLO update is a full replacement, so the stored SLO is read first and + * the supplied edits are overlaid onto it. Sending only the filled-in fields would + * erase every field the caller left blank. + */ + directExecution: async (params, signal) => { + const url = datadogApiUrl(params.site, `/api/v1/slo/${encodeURIComponent(params.sloId)}`) + const headers = datadogHeaders(params) + + const existingResponse = await fetch(url, { method: 'GET', headers, signal }) + if (!existingResponse.ok) { + return { + success: false, + output: { slo: { id: '', name: '', type: '' } }, + error: `Could not load SLO ${params.sloId} before updating it: ${await datadogErrorMessage(existingResponse)}`, + } + } + + const existing = await existingResponse.json() + const stored = existing.data + if (!stored || typeof stored !== 'object') { + return { + success: false, + output: { slo: { id: '', name: '', type: '' } }, + error: `Datadog returned no SLO for id ${params.sloId}`, + } + } + + const response = await fetch(url, { + method: 'PUT', + headers, + body: JSON.stringify(mergeSloUpdatePayload(stored, params)), + signal, + }) + + if (!response.ok) { + return { + success: false, + output: { slo: { id: '', name: '', type: '' } }, + error: await datadogErrorMessage(response), + } + } + + const data = await response.json() + + return { + success: true, + output: { slo: data.data?.[0] ?? { id: '', name: '', type: '' } }, + } + }, + + outputs: { + slo: { + type: 'object', + description: 'The updated service level objective', + properties: { + id: { type: 'string', description: 'SLO ID' }, + name: { type: 'string', description: 'SLO name' }, + type: { type: 'string', description: 'SLO type' }, + description: { type: 'string', description: 'SLO description' }, + tags: { type: 'array', description: 'SLO tags' }, + thresholds: { type: 'array', description: 'Timeframe targets and warnings' }, + modified_at: { type: 'number', description: 'Modification timestamp (Unix seconds)' }, + }, + }, + }, +} diff --git a/apps/sim/tools/datadog/update_synthetics_status.ts b/apps/sim/tools/datadog/update_synthetics_status.ts new file mode 100644 index 0000000000..d504dc3422 --- /dev/null +++ b/apps/sim/tools/datadog/update_synthetics_status.ts @@ -0,0 +1,93 @@ +import type { + UpdateSyntheticsStatusParams, + UpdateSyntheticsStatusResponse, +} from '@/tools/datadog/types' +import { datadogApiUrl, datadogErrorMessage, datadogHeaders } from '@/tools/datadog/utils' +import type { ToolConfig } from '@/tools/types' + +export const updateSyntheticsStatusTool: ToolConfig< + UpdateSyntheticsStatusParams, + UpdateSyntheticsStatusResponse +> = { + id: 'datadog_update_synthetics_status', + name: 'Datadog Pause Or Start Synthetic Test', + description: 'Pause or resume a Synthetic test by setting its status to "paused" or "live".', + version: '1.0.0', + + params: { + publicId: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'The public ID of the Synthetic test to update', + }, + newStatus: { + type: 'string', + required: true, + visibility: 'user-or-llm', + description: 'New status: "live" to start the test or "paused" to pause it', + }, + apiKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog API key', + }, + applicationKey: { + type: 'string', + required: true, + visibility: 'user-only', + description: 'Datadog Application key', + }, + site: { + type: 'string', + required: false, + visibility: 'user-only', + description: 'Datadog site/region (default: datadoghq.com)', + }, + }, + + request: { + url: (params) => + datadogApiUrl( + params.site, + `/api/v1/synthetics/tests/${encodeURIComponent(params.publicId)}/status` + ), + method: 'PUT', + headers: datadogHeaders, + body: (params) => ({ new_status: params.newStatus }), + }, + + transformResponse: async (response: Response, params) => { + const status = params?.newStatus + + if (!response.ok) { + return { + success: false, + output: { success: false, status }, + error: await datadogErrorMessage(response), + } + } + + const updated = await response.json().catch(() => false) + + return { + success: true, + output: { + success: updated === true, + status, + }, + } + }, + + outputs: { + success: { + type: 'boolean', + description: 'Whether Datadog reported the status update as successful', + }, + status: { + type: 'string', + description: 'The status that was requested: live or paused', + }, + }, +} diff --git a/apps/sim/tools/datadog/utils.ts b/apps/sim/tools/datadog/utils.ts new file mode 100644 index 0000000000..45d744a78a --- /dev/null +++ b/apps/sim/tools/datadog/utils.ts @@ -0,0 +1,235 @@ +import type { + CreateSloParams, + DatadogSite, + SecuritySignalTriageData, + UpdateSloParams, +} from '@/tools/datadog/types' + +/** + * Builds a fully-qualified Datadog API URL for the caller's site/region. + * Datadog serves each region from its own host (`datadoghq.com`, `datadoghq.eu`, + * `ddog-gov.com`, ...), so every request must be built from the configured site. + */ +export function datadogApiUrl(site: DatadogSite | undefined, path: string): string { + return `https://api.${site || 'datadoghq.com'}${path}` +} + +/** Standard Datadog authentication headers for API + application key auth. */ +export function datadogHeaders(params: { + apiKey: string + applicationKey: string +}): Record { + return { + 'Content-Type': 'application/json', + 'DD-API-KEY': params.apiKey, + 'DD-APPLICATION-KEY': params.applicationKey, + } +} + +/** Reads one Datadog error entry, which is a plain string (v1) or a JSON:API object (v2). */ +function errorEntryMessage(entry: unknown): string | null { + if (typeof entry === 'string') return entry + if (entry && typeof entry === 'object') { + const record = entry as { detail?: unknown; title?: unknown } + if (typeof record.detail === 'string') return record.detail + if (typeof record.title === 'string') return record.title + } + return null +} + +/** + * Extracts a human-readable message from a failed Datadog response. + * + * Datadog returns `{ errors: ... }` in three shapes: an array of plain strings (v1), + * an array of JSON:API error objects carrying `detail`/`title` (v2), and — on the SLO + * delete conflict — a dictionary keyed by resource ID whose values are the reasons. + */ +export async function datadogErrorMessage(response: Response): Promise { + const fallback = `HTTP ${response.status}: ${response.statusText}` + const body = await response.json().catch(() => null) + const errors = (body as { errors?: unknown })?.errors + + const entries = Array.isArray(errors) + ? errors + : errors && typeof errors === 'object' + ? Object.values(errors as Record) + : [] + + const messages = entries + .map(errorEntryMessage) + .filter((message): message is string => Boolean(message)) + + return messages.length > 0 ? messages.join('; ') : fallback +} + +/** + * Splits a comma-separated user input into a trimmed, non-empty list. + * + * Accepts `unknown` because a `` reference can resolve to a non-string: + * a monitor ID read from `get_monitor` arrives as a number, and an LLM tool call can + * pass an array. Calling `.split` on those would throw before the request is built. + */ +export function splitCommaList(value: unknown): string[] | undefined { + if (value === undefined || value === null || value === '') return undefined + const items = (Array.isArray(value) ? value : String(value).split(',')) + .map((item) => String(item).trim()) + .filter((item) => item.length > 0) + return items.length > 0 ? items : undefined +} + +/** + * Parses a JSON param, throwing a descriptive error when it is malformed. + * Block inputs arrive as strings, but an upstream block reference can resolve to + * an already-parsed object, so both shapes are accepted. + */ +export function parseJsonParam(value: unknown, fieldName: string): T | undefined { + if (value === undefined || value === null || value === '') return undefined + if (typeof value !== 'string') return value as T + try { + return JSON.parse(value) as T + } catch { + throw new Error(`${fieldName} must be valid JSON`) + } +} + +/** + * Parses a comma-separated monitor ID list into the integers Datadog expects. + * `Number('abc')` yields `NaN`, which `JSON.stringify` writes as `null` and Datadog + * rejects with a message that names nothing the user typed, so bad input is rejected here. + */ +export function parseMonitorIds(value: unknown): number[] | undefined { + const items = splitCommaList(value) + if (!items) return undefined + return items.map((id) => { + const parsed = Number(id) + if (!Number.isInteger(parsed)) { + throw new Error(`monitorIds must be a comma-separated list of whole numbers (got "${id}")`) + } + return parsed + }) +} + +/** + * Builds the `ServiceLevelObjective` request body for SLO creation. + */ +export function buildSloPayload(params: CreateSloParams): Record { + const thresholds = parseJsonParam(params.thresholds, 'thresholds parameter') + if (!Array.isArray(thresholds) || thresholds.length === 0) { + throw new Error('thresholds must be a non-empty JSON array') + } + + const body: Record = { + name: params.name, + type: params.type, + thresholds, + } + + if (params.description) body.description = params.description + + const tags = splitCommaList(params.tags) + if (tags) body.tags = tags + + const query = parseJsonParam>(params.query, 'query parameter') + if (query) body.query = query + + const monitorIds = parseMonitorIds(params.monitorIds) + if (monitorIds) body.monitor_ids = monitorIds + + const groups = splitCommaList(params.groups) + if (groups) body.groups = groups + + if (params.targetThreshold !== undefined) body.target_threshold = params.targetThreshold + if (params.warningThreshold !== undefined) body.warning_threshold = params.warningThreshold + if (params.timeframe) body.timeframe = params.timeframe + + return body +} + +/** + * Fields Datadog computes and rejects or ignores on an SLO update request. + * They must be stripped from a stored SLO before it is replayed into `PUT /api/v1/slo/{slo_id}`. + */ +const SLO_READ_ONLY_FIELDS = ['id', 'created_at', 'modified_at', 'creator', 'monitor_tags'] as const + +/** + * Merges user-supplied SLO edits onto the SLO Datadog currently stores. + * + * `PUT /api/v1/slo/{slo_id}` is a full replacement, not a patch, so a request built + * only from the fields the user filled in silently erases every field they left + * blank. Reading the stored SLO first and overlaying only the supplied fields keeps + * an edit to one field from destroying the rest. + */ +export function mergeSloUpdatePayload( + stored: Record, + params: UpdateSloParams +): Record { + const body: Record = { ...stored } + for (const field of SLO_READ_ONLY_FIELDS) delete body[field] + + const thresholds = parseJsonParam(params.thresholds, 'thresholds parameter') + if (thresholds !== undefined) { + if (!Array.isArray(thresholds) || thresholds.length === 0) { + throw new Error('thresholds must be a non-empty JSON array') + } + body.thresholds = thresholds + } + + if (params.name) body.name = params.name + if (params.type) body.type = params.type + if (params.description !== undefined && params.description !== '') { + body.description = params.description + } + + const tags = splitCommaList(params.tags) + if (tags) body.tags = tags + + const query = parseJsonParam>(params.query, 'query parameter') + if (query) body.query = query + + const monitorIds = parseMonitorIds(params.monitorIds) + if (monitorIds) body.monitor_ids = monitorIds + + const groups = splitCommaList(params.groups) + if (groups) body.groups = groups + + if (params.targetThreshold !== undefined) body.target_threshold = params.targetThreshold + if (params.warningThreshold !== undefined) body.warning_threshold = params.warningThreshold + if (params.timeframe) body.timeframe = params.timeframe + + return body +} + +/** + * Projects a security signal triage response (`PATCH .../state` and `.../assignee` + * both return `SecurityMonitoringSignalTriageUpdateResponse`) onto a flat shape. + */ +export function mapSignalTriageData(data: unknown): SecuritySignalTriageData { + const payload = + ( + data as { + data?: { + id?: string + type?: string + attributes?: { + state?: string + assignee?: SecuritySignalTriageData['assignee'] + incident_ids?: number[] + archive_reason?: string + archive_comment?: string + state_update_timestamp?: number + } + } + } + )?.data ?? {} + const attributes = payload.attributes ?? {} + return { + id: payload.id, + type: payload.type, + state: attributes.state, + assignee: attributes.assignee, + incidentIds: attributes.incident_ids, + archiveReason: attributes.archive_reason, + archiveComment: attributes.archive_comment, + stateUpdateTimestamp: attributes.state_update_timestamp, + } +} diff --git a/apps/sim/tools/generated/tool-ids.ts b/apps/sim/tools/generated/tool-ids.ts index dcc50f9e1d..c14c7474cd 100644 --- a/apps/sim/tools/generated/tool-ids.ts +++ b/apps/sim/tools/generated/tool-ids.ts @@ -3,7 +3,7 @@ /** Every registered tool id, including versioned variants. */ const toolIds: string[] = JSON.parse( - '["a2a_cancel_task","a2a_get_agent_card","a2a_get_task","a2a_send_message","agentmail_create_draft","agentmail_create_inbox","agentmail_delete_draft","agentmail_delete_inbox","agentmail_delete_thread","agentmail_forward_message","agentmail_get_draft","agentmail_get_inbox","agentmail_get_message","agentmail_get_thread","agentmail_list_drafts","agentmail_list_inboxes","agentmail_list_messages","agentmail_list_threads","agentmail_reply_message","agentmail_send_draft","agentmail_send_message","agentmail_update_draft","agentmail_update_inbox","agentmail_update_message","agentmail_update_thread","agentphone_create_call","agentphone_create_contact","agentphone_create_number","agentphone_delete_contact","agentphone_get_call","agentphone_get_call_transcript","agentphone_get_contact","agentphone_get_conversation","agentphone_get_conversation_messages","agentphone_get_number_messages","agentphone_get_usage","agentphone_get_usage_daily","agentphone_get_usage_monthly","agentphone_list_calls","agentphone_list_contacts","agentphone_list_conversations","agentphone_list_numbers","agentphone_react_to_message","agentphone_release_number","agentphone_send_message","agentphone_update_contact","agentphone_update_conversation","agiloft_async_status","agiloft_attach_file","agiloft_attachment_info","agiloft_create_record","agiloft_delete_record","agiloft_get_choice_line_id","agiloft_list_tables","agiloft_lock_record","agiloft_nlp_search","agiloft_read_record","agiloft_remove_attachment","agiloft_retrieve_attachment","agiloft_run_action_button","agiloft_saved_search","agiloft_search_records","agiloft_select_records","agiloft_update_record","agiloft_upsert_record","ahrefs_anchors","ahrefs_backlinks","ahrefs_backlinks_stats","ahrefs_batch_analysis","ahrefs_broken_backlinks","ahrefs_domain_rating","ahrefs_domain_rating_history","ahrefs_keyword_overview","ahrefs_keywords_history","ahrefs_metrics","ahrefs_metrics_history","ahrefs_organic_competitors","ahrefs_organic_keywords","ahrefs_paid_pages","ahrefs_rank_tracker_competitors_overview","ahrefs_rank_tracker_competitors_stats","ahrefs_rank_tracker_overview","ahrefs_rank_tracker_serp_overview","ahrefs_refdomains_history","ahrefs_referring_domains","ahrefs_related_terms","ahrefs_site_audit_page_explorer","ahrefs_top_pages","airtable_create_records","airtable_delete_records","airtable_get_base_schema","airtable_get_record","airtable_list_bases","airtable_list_records","airtable_list_tables","airtable_update_multiple_records","airtable_update_record","airtable_upsert_records","airweave_search","algolia_add_record","algolia_batch_operations","algolia_browse_records","algolia_clear_records","algolia_copy_move_index","algolia_delete_by_filter","algolia_delete_index","algolia_delete_record","algolia_get_record","algolia_get_records","algolia_get_settings","algolia_get_task_status","algolia_list_indices","algolia_partial_update_record","algolia_search","algolia_update_settings","amplitude_event_segmentation","amplitude_funnels","amplitude_get_active_users","amplitude_get_revenue","amplitude_group_identify","amplitude_identify_user","amplitude_list_events","amplitude_realtime_active_users","amplitude_retention","amplitude_send_event","amplitude_user_activity","amplitude_user_profile","amplitude_user_search","apify_get_dataset_items","apify_get_run","apify_run_actor_async","apify_run_actor_sync","apify_run_task","apollo_account_bulk_create","apollo_account_bulk_update","apollo_account_create","apollo_account_search","apollo_account_update","apollo_contact_bulk_create","apollo_contact_bulk_update","apollo_contact_create","apollo_contact_search","apollo_contact_update","apollo_email_accounts","apollo_opportunity_create","apollo_opportunity_get","apollo_opportunity_search","apollo_opportunity_update","apollo_organization_bulk_enrich","apollo_organization_enrich","apollo_organization_search","apollo_people_bulk_enrich","apollo_people_enrich","apollo_people_search","apollo_sequence_add_contacts","apollo_sequence_search","apollo_task_create","apollo_task_search","appconfig_create_application","appconfig_create_configuration_profile","appconfig_create_environment","appconfig_create_hosted_configuration_version","appconfig_delete_application","appconfig_delete_configuration_profile","appconfig_delete_environment","appconfig_delete_hosted_configuration_version","appconfig_get_application","appconfig_get_configuration","appconfig_get_configuration_profile","appconfig_get_deployment","appconfig_get_environment","appconfig_get_hosted_configuration_version","appconfig_list_applications","appconfig_list_configuration_profiles","appconfig_list_deployment_strategies","appconfig_list_deployments","appconfig_list_environments","appconfig_list_hosted_configuration_versions","appconfig_start_deployment","appconfig_stop_deployment","appconfig_update_application","appconfig_update_configuration_profile","appconfig_update_environment","arxiv_get_author_papers","arxiv_get_paper","arxiv_search","asana_add_comment","asana_add_followers","asana_create_project","asana_create_section","asana_create_subtask","asana_create_task","asana_delete_task","asana_get_project","asana_get_projects","asana_get_task","asana_list_sections","asana_list_workspaces","asana_search_tasks","asana_update_task","ashby_add_candidate_tag","ashby_anonymize_candidate","ashby_change_application_source","ashby_change_application_stage","ashby_create_application","ashby_create_candidate","ashby_create_note","ashby_delete_application","ashby_get_application","ashby_get_candidate","ashby_get_job","ashby_get_job_posting","ashby_get_offer","ashby_list_applications","ashby_list_archive_reasons","ashby_list_candidate_tags","ashby_list_candidates","ashby_list_custom_fields","ashby_list_departments","ashby_list_interviews","ashby_list_job_postings","ashby_list_jobs","ashby_list_locations","ashby_list_notes","ashby_list_offers","ashby_list_openings","ashby_list_sources","ashby_list_users","ashby_remove_candidate_tag","ashby_search_candidates","ashby_set_custom_field_value","ashby_set_custom_field_values","ashby_update_candidate","athena_batch_get_query_execution","athena_create_named_query","athena_delete_named_query","athena_get_named_query","athena_get_query_execution","athena_get_query_results","athena_list_databases","athena_list_named_queries","athena_list_query_executions","athena_list_table_metadata","athena_start_query","athena_stop_query","attio_assert_record","attio_create_attribute","attio_create_comment","attio_create_list","attio_create_list_entry","attio_create_note","attio_create_object","attio_create_record","attio_create_task","attio_create_webhook","attio_delete_comment","attio_delete_list_entry","attio_delete_note","attio_delete_record","attio_delete_task","attio_delete_webhook","attio_get_attribute","attio_get_comment","attio_get_list","attio_get_list_entry","attio_get_member","attio_get_note","attio_get_object","attio_get_record","attio_get_task","attio_get_thread","attio_get_webhook","attio_list_attributes","attio_list_lists","attio_list_members","attio_list_notes","attio_list_objects","attio_list_records","attio_list_tasks","attio_list_threads","attio_list_webhooks","attio_query_list_entries","attio_search_records","attio_update_attribute","attio_update_list","attio_update_list_entry","attio_update_object","attio_update_record","attio_update_task","attio_update_webhook","azure_data_explorer_create_table","azure_data_explorer_drop_table","azure_data_explorer_ingest_from_query","azure_data_explorer_ingest_inline","azure_data_explorer_list_databases","azure_data_explorer_list_functions","azure_data_explorer_list_tables","azure_data_explorer_management","azure_data_explorer_query","azure_data_explorer_show_database_schema","azure_data_explorer_show_ingestion_failures","azure_data_explorer_show_operations","azure_data_explorer_show_table_details","azure_data_explorer_show_table_schema","azure_devops_add_comment","azure_devops_create_work_item","azure_devops_get_build_log","azure_devops_get_build_timeline","azure_devops_get_comments","azure_devops_get_pipeline","azure_devops_get_pipeline_run","azure_devops_get_work_item","azure_devops_get_work_items_batch","azure_devops_get_work_items_between_builds","azure_devops_list_build_logs","azure_devops_list_builds","azure_devops_list_pipeline_runs","azure_devops_list_pipelines","azure_devops_query_work_items","azure_devops_update_work_item","box_copy_file","box_create_folder","box_delete_file","box_delete_folder","box_download_file","box_get_file_info","box_list_folder_items","box_search","box_sign_cancel_request","box_sign_create_request","box_sign_get_request","box_sign_list_requests","box_sign_resend_request","box_update_file","box_upload_file","brandfetch_get_brand","brandfetch_search","brex_archive_budget","brex_create_budget","brex_create_spend_limit","brex_create_transfer","brex_create_vendor","brex_get_budget","brex_get_cash_account","brex_get_company","brex_get_current_user","brex_get_expense","brex_get_spend_limit","brex_get_transfer","brex_get_user","brex_get_vendor","brex_list_budgets","brex_list_card_accounts","brex_list_card_statements","brex_list_card_transactions","brex_list_cards","brex_list_cash_accounts","brex_list_cash_statements","brex_list_cash_transactions","brex_list_departments","brex_list_expenses","brex_list_locations","brex_list_spend_limits","brex_list_titles","brex_list_transfers","brex_list_users","brex_list_vendors","brex_match_receipt","brex_update_expense","brex_update_vendor","brex_upload_receipt","brightdata_cancel_snapshot","brightdata_discover","brightdata_download_snapshot","brightdata_scrape_dataset","brightdata_scrape_url","brightdata_serp_search","brightdata_snapshot_status","brightdata_sync_scrape","browser_use_run_task","buffer_create_idea","buffer_create_post","buffer_delete_post","buffer_edit_post","buffer_get_account","buffer_get_channels","buffer_get_idea_groups","buffer_get_ideas","buffer_get_post","buffer_get_posts","calcom_cancel_booking","calcom_confirm_booking","calcom_create_booking","calcom_create_event_type","calcom_create_schedule","calcom_decline_booking","calcom_delete_event_type","calcom_delete_schedule","calcom_get_booking","calcom_get_default_schedule","calcom_get_event_type","calcom_get_schedule","calcom_get_slots","calcom_list_bookings","calcom_list_event_types","calcom_list_schedules","calcom_reschedule_booking","calcom_update_event_type","calcom_update_schedule","calendly_cancel_event","calendly_create_event_invitee","calendly_create_invitee_no_show","calendly_create_scheduling_link","calendly_create_webhook","calendly_delete_invitee_no_show","calendly_delete_webhook","calendly_get_current_user","calendly_get_event_invitee","calendly_get_event_type","calendly_get_scheduled_event","calendly_get_user","calendly_list_event_invitees","calendly_list_event_type_available_times","calendly_list_event_types","calendly_list_organization_memberships","calendly_list_routing_form_submissions","calendly_list_routing_forms","calendly_list_scheduled_events","calendly_list_user_availability_schedules","calendly_list_user_busy_times","calendly_list_webhooks","clay_populate","clerk_add_organization_member","clerk_ban_user","clerk_create_actor_token","clerk_create_allowlist_identifier","clerk_create_blocklist_identifier","clerk_create_organization","clerk_create_organization_invitation","clerk_create_user","clerk_delete_allowlist_identifier","clerk_delete_blocklist_identifier","clerk_delete_organization","clerk_delete_user","clerk_get_jwt_template","clerk_get_organization","clerk_get_session","clerk_get_user","clerk_get_user_oauth_token","clerk_list_allowlist_identifiers","clerk_list_blocklist_identifiers","clerk_list_jwt_templates","clerk_list_organization_invitations","clerk_list_organization_memberships","clerk_list_organizations","clerk_list_sessions","clerk_list_users","clerk_lock_user","clerk_remove_organization_member","clerk_revoke_actor_token","clerk_revoke_session","clerk_unban_user","clerk_unlock_user","clerk_update_organization","clerk_update_organization_membership","clerk_update_user","clickhouse_count_rows","clickhouse_create_database","clickhouse_create_table","clickhouse_delete","clickhouse_describe_table","clickhouse_drop_database","clickhouse_drop_partition","clickhouse_drop_table","clickhouse_execute","clickhouse_insert","clickhouse_insert_rows","clickhouse_introspect","clickhouse_kill_query","clickhouse_list_clusters","clickhouse_list_databases","clickhouse_list_mutations","clickhouse_list_partitions","clickhouse_list_running_queries","clickhouse_list_tables","clickhouse_optimize_table","clickhouse_query","clickhouse_rename_table","clickhouse_show_create_table","clickhouse_table_stats","clickhouse_truncate_table","clickhouse_update","clickup_add_tag_to_task","clickup_create_checklist","clickup_create_checklist_item","clickup_create_comment","clickup_create_folder","clickup_create_list","clickup_create_task","clickup_create_time_entry","clickup_delete_checklist","clickup_delete_checklist_item","clickup_delete_comment","clickup_delete_task","clickup_delete_time_entry","clickup_get_comments","clickup_get_custom_fields","clickup_get_folders","clickup_get_list_members","clickup_get_lists","clickup_get_running_timer","clickup_get_space_tags","clickup_get_spaces","clickup_get_task","clickup_get_task_members","clickup_get_tasks","clickup_get_time_entries","clickup_get_workspaces","clickup_remove_custom_field_value","clickup_remove_tag_from_task","clickup_search_tasks","clickup_set_custom_field_value","clickup_start_timer","clickup_stop_timer","clickup_update_checklist","clickup_update_checklist_item","clickup_update_comment","clickup_update_task","clickup_update_time_entry","clickup_upload_attachment","cloudflare_create_dns_record","cloudflare_create_zone","cloudflare_delete_dns_record","cloudflare_delete_zone","cloudflare_dns_analytics","cloudflare_get_zone","cloudflare_get_zone_settings","cloudflare_list_certificates","cloudflare_list_dns_records","cloudflare_list_zones","cloudflare_purge_cache","cloudflare_update_dns_record","cloudflare_update_zone_setting","cloudformation_cancel_update_stack","cloudformation_create_change_set","cloudformation_create_stack","cloudformation_delete_stack","cloudformation_describe_change_set","cloudformation_describe_stack_drift_detection_status","cloudformation_describe_stack_events","cloudformation_describe_stacks","cloudformation_detect_stack_drift","cloudformation_execute_change_set","cloudformation_get_template","cloudformation_get_template_summary","cloudformation_list_stack_resources","cloudformation_update_stack","cloudformation_validate_template","cloudwatch_describe_alarm_history","cloudwatch_describe_alarms","cloudwatch_describe_log_groups","cloudwatch_describe_log_streams","cloudwatch_filter_log_events","cloudwatch_get_log_events","cloudwatch_get_metric_statistics","cloudwatch_list_metrics","cloudwatch_mute_alarm","cloudwatch_put_log_group_retention","cloudwatch_put_metric_data","cloudwatch_query_logs","cloudwatch_unmute_alarm","codepipeline_disable_stage_transition","codepipeline_enable_stage_transition","codepipeline_get_pipeline","codepipeline_get_pipeline_execution","codepipeline_get_pipeline_state","codepipeline_list_action_executions","codepipeline_list_pipeline_executions","codepipeline_list_pipelines","codepipeline_put_approval_result","codepipeline_retry_stage_execution","codepipeline_start_execution","codepipeline_stop_execution","confluence_add_label","confluence_create_blogpost","confluence_create_comment","confluence_create_page","confluence_create_page_property","confluence_create_space","confluence_create_space_property","confluence_delete_attachment","confluence_delete_blogpost","confluence_delete_comment","confluence_delete_label","confluence_delete_page","confluence_delete_page_property","confluence_delete_space","confluence_delete_space_property","confluence_get_blogpost","confluence_get_page_ancestors","confluence_get_page_children","confluence_get_page_descendants","confluence_get_page_version","confluence_get_pages_by_label","confluence_get_space","confluence_get_task","confluence_get_user","confluence_list_attachments","confluence_list_blogposts","confluence_list_blogposts_in_space","confluence_list_comments","confluence_list_labels","confluence_list_page_properties","confluence_list_page_versions","confluence_list_pages_in_space","confluence_list_space_labels","confluence_list_space_permissions","confluence_list_space_properties","confluence_list_spaces","confluence_list_tasks","confluence_retrieve","confluence_search","confluence_search_in_space","confluence_update","confluence_update_blogpost","confluence_update_comment","confluence_update_space","confluence_update_task","confluence_upload_attachment","context_dev_classify_naics","context_dev_classify_sic","context_dev_crawl","context_dev_extract","context_dev_extract_product","context_dev_extract_products","context_dev_get_brand","context_dev_get_brand_by_email","context_dev_get_brand_by_name","context_dev_get_brand_by_ticker","context_dev_identify_transaction","context_dev_map","context_dev_scrape_fonts","context_dev_scrape_html","context_dev_scrape_images","context_dev_scrape_markdown","context_dev_scrape_styleguide","context_dev_screenshot","context_dev_search","convex_action","convex_document_deltas","convex_list_documents","convex_list_tables","convex_mutation","convex_query","convex_run_function","crowdstrike_create_indicators","crowdstrike_delete_indicators","crowdstrike_delete_rtr_session","crowdstrike_execute_rtr_command","crowdstrike_get_alert_details","crowdstrike_get_case_details","crowdstrike_get_host_group_details","crowdstrike_get_indicator_details","crowdstrike_get_rtr_command_status","crowdstrike_get_sensor_aggregates","crowdstrike_get_sensor_details","crowdstrike_get_vulnerability_details","crowdstrike_init_rtr_session","crowdstrike_perform_host_action","crowdstrike_perform_host_group_action","crowdstrike_query_alerts","crowdstrike_query_cases","crowdstrike_query_host_groups","crowdstrike_query_indicators","crowdstrike_query_sensors","crowdstrike_query_vulnerabilities","crowdstrike_update_alerts","crowdstrike_update_indicators","cursor_add_followup","cursor_add_followup_v2","cursor_delete_agent","cursor_delete_agent_v2","cursor_download_artifact","cursor_download_artifact_v2","cursor_get_agent","cursor_get_agent_v2","cursor_get_api_key_info","cursor_get_api_key_info_v2","cursor_get_conversation","cursor_get_conversation_v2","cursor_launch_agent","cursor_launch_agent_v2","cursor_list_agents","cursor_list_agents_v2","cursor_list_artifacts","cursor_list_artifacts_v2","cursor_list_models","cursor_list_models_v2","cursor_list_repositories","cursor_list_repositories_v2","cursor_stop_agent","cursor_stop_agent_v2","dagster_delete_run","dagster_get_asset","dagster_get_run","dagster_get_run_logs","dagster_launch_run","dagster_list_assets","dagster_list_jobs","dagster_list_runs","dagster_list_schedules","dagster_list_sensors","dagster_materialize_assets","dagster_reexecute_run","dagster_report_asset_materialization","dagster_start_schedule","dagster_start_sensor","dagster_stop_schedule","dagster_stop_sensor","dagster_terminate_run","dagster_wipe_asset","databricks_cancel_run","databricks_execute_sql","databricks_get_cluster","databricks_get_job","databricks_get_run","databricks_get_run_output","databricks_get_statement","databricks_list_clusters","databricks_list_jobs","databricks_list_runs","databricks_list_warehouses","databricks_run_job","datadog_cancel_downtime","datadog_create_downtime","datadog_create_event","datadog_create_monitor","datadog_get_monitor","datadog_list_downtimes","datadog_list_monitors","datadog_mute_monitor","datadog_query_logs","datadog_query_timeseries","datadog_send_logs","datadog_submit_metrics","datagma_enrich_company","datagma_enrich_person","datagma_find_email","datagma_find_phone","datagma_get_credits","daytona_create_sandbox","daytona_delete_sandbox","daytona_download_file","daytona_execute_command","daytona_get_sandbox","daytona_git_clone","daytona_list_files","daytona_list_sandboxes","daytona_run_code","daytona_start_sandbox","daytona_stop_sandbox","daytona_upload_file","deployed_block_executor","deployments_deploy","deployments_get_version","deployments_list_versions","deployments_promote","deployments_undeploy","devin_append_session_tags","devin_archive_session","devin_create_session","devin_get_session","devin_get_session_tags","devin_list_session_attachments","devin_list_session_messages","devin_list_sessions","devin_replace_session_tags","devin_send_message","devin_terminate_session","discord_add_reaction","discord_archive_thread","discord_assign_role","discord_ban_member","discord_bulk_delete_messages","discord_create_channel","discord_create_invite","discord_create_role","discord_create_thread","discord_create_webhook","discord_delete_channel","discord_delete_invite","discord_delete_message","discord_delete_role","discord_delete_webhook","discord_edit_message","discord_execute_webhook","discord_get_channel","discord_get_invite","discord_get_member","discord_get_messages","discord_get_pinned_messages","discord_get_server","discord_get_user","discord_get_webhook","discord_join_thread","discord_kick_member","discord_leave_thread","discord_list_channels","discord_list_roles","discord_pin_message","discord_remove_reaction","discord_remove_role","discord_send_message","discord_unban_member","discord_unpin_message","discord_update_channel","discord_update_member","discord_update_role","docusign_create_from_template","docusign_download_document","docusign_get_envelope","docusign_list_envelopes","docusign_list_recipients","docusign_list_templates","docusign_send_envelope","docusign_void_envelope","downdetector_get_company","downdetector_get_company_attribution","downdetector_get_company_baseline","downdetector_get_company_events","downdetector_get_company_incidents","downdetector_get_company_indicators","downdetector_get_company_last_15","downdetector_get_company_status","downdetector_get_provider","downdetector_get_reports","downdetector_get_site_companies","downdetector_list_categories","downdetector_list_incidents","downdetector_list_sites","downdetector_search_companies","dropbox_copy","dropbox_create_folder","dropbox_create_shared_link","dropbox_delete","dropbox_download","dropbox_get_metadata","dropbox_list_folder","dropbox_list_revisions","dropbox_list_shared_links","dropbox_move","dropbox_restore","dropbox_search","dropbox_upload","dropcontact_enrich_contact","dspy_chain_of_thought","dspy_predict","dspy_react","dub_bulk_create_links","dub_bulk_delete_links","dub_bulk_update_links","dub_create_link","dub_create_tag","dub_delete_link","dub_get_analytics","dub_get_events","dub_get_link","dub_get_links_count","dub_get_qr_code","dub_list_domains","dub_list_folders","dub_list_links","dub_list_tags","dub_update_link","dub_upsert_link","duckduckgo_search","dynamodb_delete","dynamodb_get","dynamodb_introspect","dynamodb_put","dynamodb_query","dynamodb_scan","dynamodb_update","dynatrace_add_problem_comment","dynatrace_add_tags","dynatrace_close_problem","dynatrace_create_settings_object","dynatrace_create_slo","dynatrace_delete_problem_comment","dynatrace_delete_settings_object","dynatrace_delete_slo","dynatrace_delete_tag","dynatrace_execute_synthetic_monitors","dynatrace_get_attack","dynatrace_get_audit_logs","dynatrace_get_entity","dynatrace_get_event","dynatrace_get_metric","dynatrace_get_problem","dynatrace_get_problem_comment","dynatrace_get_security_problem","dynatrace_get_settings_object","dynatrace_get_slo","dynatrace_get_synthetic_batch","dynatrace_ingest_event","dynatrace_ingest_logs","dynatrace_ingest_metrics","dynatrace_list_attacks","dynatrace_list_entities","dynatrace_list_entity_types","dynatrace_list_events","dynatrace_list_metrics","dynatrace_list_problem_comments","dynatrace_list_problems","dynatrace_list_remediation_items","dynatrace_list_security_problems","dynatrace_list_settings_objects","dynatrace_list_settings_schemas","dynatrace_list_slos","dynatrace_list_synthetic_monitors","dynatrace_list_tags","dynatrace_mute_security_problem","dynatrace_mute_security_problems","dynatrace_query_metrics","dynatrace_search_logs","dynatrace_unmute_security_problem","dynatrace_unmute_security_problems","dynatrace_update_problem_comment","dynatrace_update_settings_object","dynatrace_update_slo","elasticsearch_bulk","elasticsearch_cluster_health","elasticsearch_cluster_stats","elasticsearch_count","elasticsearch_create_index","elasticsearch_delete_document","elasticsearch_delete_index","elasticsearch_get_document","elasticsearch_get_index","elasticsearch_index_document","elasticsearch_list_indices","elasticsearch_search","elasticsearch_update_document","elevenlabs_audio_isolation","elevenlabs_edit_voice_settings","elevenlabs_get_user","elevenlabs_get_voice","elevenlabs_get_voice_settings","elevenlabs_list_models","elevenlabs_list_voices","elevenlabs_sound_effects","elevenlabs_speech_to_speech","elevenlabs_tts","emailbison_attach_leads_to_campaign","emailbison_attach_tags_to_leads","emailbison_create_campaign","emailbison_create_lead","emailbison_create_tag","emailbison_get_lead","emailbison_list_campaigns","emailbison_list_leads","emailbison_list_replies","emailbison_list_tags","emailbison_update_campaign","emailbison_update_campaign_status","emailbison_update_lead","embeddings_cohere","embeddings_gemini","embeddings_mistral","embeddings_openai","embeddings_openrouter","enrich_check_credits","enrich_company_funding","enrich_company_lookup","enrich_company_revenue","enrich_disposable_email_check","enrich_email_to_ip","enrich_email_to_person_lite","enrich_email_to_phone","enrich_email_to_profile","enrich_find_email","enrich_get_post_details","enrich_ip_to_company","enrich_linkedin_profile","enrich_linkedin_to_personal_email","enrich_linkedin_to_work_email","enrich_phone_finder","enrich_reverse_hash_lookup","enrich_sales_pointer_people","enrich_search_company","enrich_search_company_activities","enrich_search_company_employees","enrich_search_jobs","enrich_search_logo","enrich_search_people","enrich_search_people_activities","enrich_search_post_comments","enrich_search_post_comments_by_url","enrich_search_post_reactions","enrich_search_post_reactions_by_url","enrich_search_posts","enrich_search_similar_companies","enrich_verify_email","enrichment_run","enrow_find_email","enrow_verify_email","evernote_copy_note","evernote_create_note","evernote_create_notebook","evernote_create_tag","evernote_delete_note","evernote_get_note","evernote_get_notebook","evernote_list_notebooks","evernote_list_tags","evernote_search_notes","evernote_update_note","exa_agent","exa_answer","exa_find_similar_links","exa_get_contents","exa_search","extend_parser","extend_parser_v2","fathom_get_summary","fathom_get_transcript","fathom_list_meeting_types","fathom_list_meetings","fathom_list_team_members","fathom_list_teams","file_append","file_compress","file_decompress","file_fetch","file_get","file_get_content","file_manage_sharing","file_parser","file_parser_v2","file_parser_v3","file_read","file_write","findymail_find_email_from_linkedin","findymail_find_email_from_name","findymail_find_emails_by_domain","findymail_find_employees","findymail_find_phone","findymail_get_company","findymail_get_credits","findymail_lookup_technologies","findymail_reverse_email_lookup","findymail_search_technologies","findymail_verify_email","firecrawl_agent","firecrawl_batch_scrape","firecrawl_batch_scrape_status","firecrawl_cancel_crawl","firecrawl_crawl","firecrawl_crawl_status","firecrawl_credit_usage","firecrawl_extract","firecrawl_extract_status","firecrawl_map","firecrawl_parse","firecrawl_scrape","firecrawl_search","fireflies_add_to_live_meeting","fireflies_create_bite","fireflies_delete_transcript","fireflies_get_transcript","fireflies_get_user","fireflies_list_bites","fireflies_list_contacts","fireflies_list_transcripts","fireflies_list_users","fireflies_upload_audio","flint_create_task","flint_generate_pages","flint_get_task","function_execute","gamma_check_status","gamma_generate","gamma_generate_from_template","gamma_list_folders","gamma_list_themes","github_add_assignees","github_add_assignees_v2","github_add_labels","github_add_labels_v2","github_cancel_workflow_run","github_cancel_workflow_run_v2","github_check_star","github_check_star_v2","github_close_issue","github_close_issue_v2","github_close_pr","github_close_pr_v2","github_comment","github_comment_v2","github_compare_commits","github_compare_commits_v2","github_create_branch","github_create_branch_v2","github_create_comment_reaction","github_create_comment_reaction_v2","github_create_file","github_create_file_v2","github_create_gist","github_create_gist_v2","github_create_issue","github_create_issue_reaction","github_create_issue_reaction_v2","github_create_issue_v2","github_create_milestone","github_create_milestone_v2","github_create_pr","github_create_pr_review","github_create_pr_review_v2","github_create_pr_v2","github_create_project","github_create_project_v2","github_create_release","github_create_release_v2","github_delete_branch","github_delete_branch_v2","github_delete_comment","github_delete_comment_reaction","github_delete_comment_reaction_v2","github_delete_comment_v2","github_delete_file","github_delete_file_v2","github_delete_gist","github_delete_gist_v2","github_delete_issue_reaction","github_delete_issue_reaction_v2","github_delete_milestone","github_delete_milestone_v2","github_delete_project","github_delete_project_v2","github_delete_release","github_delete_release_v2","github_fork_gist","github_fork_gist_v2","github_fork_repo","github_fork_repo_v2","github_get_branch","github_get_branch_protection","github_get_branch_protection_v2","github_get_branch_v2","github_get_commit","github_get_commit_v2","github_get_file_content","github_get_file_content_v2","github_get_gist","github_get_gist_v2","github_get_issue","github_get_issue_v2","github_get_latest_release","github_get_latest_release_v2","github_get_milestone","github_get_milestone_v2","github_get_pr_files","github_get_pr_files_v2","github_get_project","github_get_project_v2","github_get_readme","github_get_readme_v2","github_get_release","github_get_release_v2","github_get_tree","github_get_tree_v2","github_get_workflow","github_get_workflow_run","github_get_workflow_run_v2","github_get_workflow_v2","github_issue_comment","github_issue_comment_v2","github_job_logs","github_latest_commit","github_latest_commit_v2","github_list_branches","github_list_branches_v2","github_list_commits","github_list_commits_v2","github_list_forks","github_list_forks_v2","github_list_gists","github_list_gists_v2","github_list_issue_comments","github_list_issue_comments_v2","github_list_issues","github_list_issues_v2","github_list_milestones","github_list_milestones_v2","github_list_pr_comments","github_list_pr_comments_v2","github_list_projects","github_list_projects_v2","github_list_prs","github_list_prs_v2","github_list_releases","github_list_releases_v2","github_list_review_threads","github_list_stargazers","github_list_stargazers_v2","github_list_tags","github_list_tags_v2","github_list_workflow_runs","github_list_workflow_runs_v2","github_list_workflows","github_list_workflows_v2","github_merge_pr","github_merge_pr_v2","github_pr","github_pr_v2","github_remove_label","github_remove_label_v2","github_reply_review_thread","github_repo_info","github_repo_info_v2","github_request_reviewers","github_request_reviewers_v2","github_rerun_workflow","github_rerun_workflow_v2","github_resolve_review_thread","github_search_code","github_search_code_v2","github_search_commits","github_search_commits_v2","github_search_issues","github_search_issues_v2","github_search_repos","github_search_repos_v2","github_search_users","github_search_users_v2","github_star_gist","github_star_gist_v2","github_star_repo","github_star_repo_v2","github_status_check_rollup","github_trigger_workflow","github_trigger_workflow_v2","github_unstar_gist","github_unstar_gist_v2","github_unstar_repo","github_unstar_repo_v2","github_update_branch_protection","github_update_branch_protection_v2","github_update_comment","github_update_comment_v2","github_update_file","github_update_file_v2","github_update_gist","github_update_gist_v2","github_update_issue","github_update_issue_v2","github_update_milestone","github_update_milestone_v2","github_update_pr","github_update_pr_v2","github_update_project","github_update_project_v2","github_update_release","github_update_release_v2","gitlab_activate_user","gitlab_add_member","gitlab_add_saml_group_link","gitlab_approve_access_request","gitlab_approve_merge_request","gitlab_approve_user","gitlab_ban_user","gitlab_block_user","gitlab_cancel_pipeline","gitlab_compare_branches","gitlab_create_branch","gitlab_create_file","gitlab_create_issue","gitlab_create_issue_note","gitlab_create_merge_request","gitlab_create_merge_request_note","gitlab_create_pipeline","gitlab_create_release","gitlab_create_user","gitlab_deactivate_user","gitlab_delete_branch","gitlab_delete_issue","gitlab_delete_saml_group_link","gitlab_delete_user","gitlab_delete_user_identity","gitlab_deny_access_request","gitlab_get_file","gitlab_get_group","gitlab_get_issue","gitlab_get_job_log","gitlab_get_merge_request","gitlab_get_merge_request_changes","gitlab_get_pipeline","gitlab_get_project","gitlab_invite_member","gitlab_list_access_requests","gitlab_list_branches","gitlab_list_commits","gitlab_list_groups","gitlab_list_invitations","gitlab_list_issues","gitlab_list_members","gitlab_list_merge_requests","gitlab_list_pipeline_jobs","gitlab_list_pipelines","gitlab_list_projects","gitlab_list_releases","gitlab_list_repository_tree","gitlab_list_saml_group_links","gitlab_list_user_memberships","gitlab_merge_merge_request","gitlab_play_job","gitlab_reject_user","gitlab_remove_member","gitlab_retry_pipeline","gitlab_revoke_invitation","gitlab_search_users","gitlab_unban_user","gitlab_unblock_user","gitlab_update_file","gitlab_update_invitation","gitlab_update_issue","gitlab_update_member","gitlab_update_merge_request","gitlab_update_user","gmail_add_label","gmail_add_label_v2","gmail_archive","gmail_archive_v2","gmail_create_label_v2","gmail_delete","gmail_delete_draft_v2","gmail_delete_label_v2","gmail_delete_v2","gmail_draft","gmail_draft_v2","gmail_edit_draft_v2","gmail_get_draft_v2","gmail_get_thread_v2","gmail_list_drafts_v2","gmail_list_labels_v2","gmail_list_threads_v2","gmail_mark_read","gmail_mark_read_v2","gmail_mark_unread","gmail_mark_unread_v2","gmail_move","gmail_move_v2","gmail_read","gmail_read_v2","gmail_remove_label","gmail_remove_label_v2","gmail_search","gmail_search_v2","gmail_send","gmail_send_v2","gmail_trash_thread_v2","gmail_unarchive","gmail_unarchive_v2","gmail_untrash_thread_v2","gmail_update_label_v2","gong_aggregate_activity","gong_aggregate_by_period","gong_answered_scorecards","gong_ask_anything","gong_assign_flow_prospects","gong_create_call","gong_day_by_day_activity","gong_get_brief","gong_get_call","gong_get_call_transcript","gong_get_coaching","gong_get_extensive_calls","gong_get_folder_content","gong_get_logs","gong_get_prospect_flows","gong_get_user","gong_interaction_stats","gong_list_calls","gong_list_flows","gong_list_library_folders","gong_list_scorecards","gong_list_trackers","gong_list_users","gong_list_workspaces","gong_lookup_email","gong_lookup_phone","gong_purge_email_address","gong_purge_phone_number","gong_unassign_flow_prospects","google_ads_ad_performance","google_ads_campaign_performance","google_ads_list_ad_groups","google_ads_list_campaigns","google_ads_list_customers","google_ads_search","google_appsheet_add_rows","google_appsheet_delete_rows","google_appsheet_edit_rows","google_appsheet_find_rows","google_bigquery_create_dataset","google_bigquery_create_table","google_bigquery_delete_dataset","google_bigquery_delete_table","google_bigquery_get_query_results","google_bigquery_get_table","google_bigquery_insert_rows","google_bigquery_list_datasets","google_bigquery_list_table_data","google_bigquery_list_tables","google_bigquery_query","google_books_volume_details","google_books_volume_search","google_calendar_create","google_calendar_create_calendar","google_calendar_create_calendar_v2","google_calendar_create_v2","google_calendar_delete","google_calendar_delete_calendar","google_calendar_delete_calendar_v2","google_calendar_delete_v2","google_calendar_freebusy","google_calendar_freebusy_v2","google_calendar_get","google_calendar_get_v2","google_calendar_instances","google_calendar_instances_v2","google_calendar_invite","google_calendar_invite_v2","google_calendar_list","google_calendar_list_acl","google_calendar_list_acl_v2","google_calendar_list_calendars","google_calendar_list_calendars_v2","google_calendar_list_v2","google_calendar_move","google_calendar_move_v2","google_calendar_quick_add","google_calendar_quick_add_v2","google_calendar_share_calendar","google_calendar_share_calendar_v2","google_calendar_unshare_calendar","google_calendar_unshare_calendar_v2","google_calendar_update","google_calendar_update_acl","google_calendar_update_acl_v2","google_calendar_update_calendar","google_calendar_update_calendar_v2","google_calendar_update_v2","google_contacts_create","google_contacts_delete","google_contacts_get","google_contacts_list","google_contacts_search","google_contacts_update","google_docs_create","google_docs_create_named_range","google_docs_create_paragraph_bullets","google_docs_delete_content_range","google_docs_delete_named_range","google_docs_delete_paragraph_bullets","google_docs_insert_image","google_docs_insert_page_break","google_docs_insert_table","google_docs_insert_text","google_docs_read","google_docs_replace_text","google_docs_update_paragraph_style","google_docs_update_text_style","google_docs_write","google_drive_copy","google_drive_create_comment","google_drive_create_folder","google_drive_delete","google_drive_delete_comment","google_drive_download","google_drive_export","google_drive_get_about","google_drive_get_content","google_drive_get_file","google_drive_get_revision","google_drive_list","google_drive_list_comments","google_drive_list_permissions","google_drive_list_revisions","google_drive_move","google_drive_search","google_drive_share","google_drive_trash","google_drive_unshare","google_drive_untrash","google_drive_update","google_drive_upload","google_forms_batch_update","google_forms_create_form","google_forms_create_watch","google_forms_delete_watch","google_forms_get_form","google_forms_get_responses","google_forms_list_watches","google_forms_renew_watch","google_forms_set_publish_settings","google_groups_add_alias","google_groups_add_member","google_groups_create_group","google_groups_delete_group","google_groups_get_group","google_groups_get_member","google_groups_get_settings","google_groups_has_member","google_groups_list_aliases","google_groups_list_groups","google_groups_list_members","google_groups_remove_alias","google_groups_remove_member","google_groups_update_group","google_groups_update_member","google_groups_update_settings","google_maps_air_quality","google_maps_directions","google_maps_distance_matrix","google_maps_elevation","google_maps_geocode","google_maps_geolocate","google_maps_place_details","google_maps_places_nearby","google_maps_places_search","google_maps_pollen","google_maps_reverse_geocode","google_maps_snap_to_roads","google_maps_solar","google_maps_speed_limits","google_maps_timezone","google_maps_validate_address","google_meet_create_space","google_meet_end_conference","google_meet_get_conference_record","google_meet_get_space","google_meet_list_conference_records","google_meet_list_participants","google_pagespeed_analyze","google_search","google_sheets_append","google_sheets_append_v2","google_sheets_batch_clear_v2","google_sheets_batch_get_v2","google_sheets_batch_update_v2","google_sheets_clear_v2","google_sheets_copy_sheet_v2","google_sheets_create_spreadsheet_v2","google_sheets_delete_rows_v2","google_sheets_delete_sheet_v2","google_sheets_delete_spreadsheet_v2","google_sheets_get_spreadsheet_v2","google_sheets_read","google_sheets_read_v2","google_sheets_update","google_sheets_update_v2","google_sheets_write","google_sheets_write_v2","google_slides_add_image","google_slides_add_slide","google_slides_batch_update","google_slides_copy_presentation","google_slides_create","google_slides_create_line","google_slides_create_paragraph_bullets","google_slides_create_shape","google_slides_create_sheets_chart","google_slides_create_table","google_slides_create_video","google_slides_delete_object","google_slides_delete_paragraph_bullets","google_slides_delete_table_column","google_slides_delete_table_row","google_slides_delete_text","google_slides_duplicate_object","google_slides_export_presentation","google_slides_get_page","google_slides_get_thumbnail","google_slides_group_objects","google_slides_insert_table_columns","google_slides_insert_table_rows","google_slides_insert_text","google_slides_merge_table_cells","google_slides_read","google_slides_refresh_sheets_chart","google_slides_replace_all_shapes_with_image","google_slides_replace_all_shapes_with_sheets_chart","google_slides_replace_all_text","google_slides_replace_image","google_slides_reroute_line","google_slides_ungroup_objects","google_slides_unmerge_table_cells","google_slides_update_image_properties","google_slides_update_line_category","google_slides_update_line_properties","google_slides_update_page_element_alt_text","google_slides_update_page_element_transform","google_slides_update_page_elements_z_order","google_slides_update_page_properties","google_slides_update_paragraph_style","google_slides_update_shape_properties","google_slides_update_slide_properties","google_slides_update_slides_position","google_slides_update_table_border_properties","google_slides_update_table_cell_properties","google_slides_update_table_column_properties","google_slides_update_table_row_properties","google_slides_update_text_style","google_slides_update_video_properties","google_slides_write","google_tasks_create","google_tasks_delete","google_tasks_get","google_tasks_list","google_tasks_list_task_lists","google_tasks_update","google_translate_detect","google_translate_text","google_vault_add_held_accounts","google_vault_add_matters_permissions","google_vault_close_matters","google_vault_create_matters","google_vault_create_matters_export","google_vault_create_matters_holds","google_vault_create_saved_query","google_vault_delete_matters","google_vault_delete_matters_export","google_vault_delete_matters_holds","google_vault_delete_saved_query","google_vault_download_export_file","google_vault_list_matters","google_vault_list_matters_export","google_vault_list_matters_holds","google_vault_list_saved_queries","google_vault_remove_held_accounts","google_vault_remove_matters_permissions","google_vault_reopen_matters","google_vault_undelete_matters","google_vault_update_matters","google_vault_update_matters_holds","grafana_check_data_source_health","grafana_create_alert_rule","grafana_create_annotation","grafana_create_contact_point","grafana_create_dashboard","grafana_create_folder","grafana_delete_alert_rule","grafana_delete_annotation","grafana_delete_contact_point","grafana_delete_dashboard","grafana_delete_folder","grafana_get_alert_rule","grafana_get_alert_rule_group","grafana_get_dashboard","grafana_get_data_source","grafana_get_folder","grafana_get_health","grafana_list_alert_rules","grafana_list_annotations","grafana_list_contact_points","grafana_list_dashboards","grafana_list_data_sources","grafana_list_folders","grafana_move_folder","grafana_query_data_source","grafana_update_alert_rule","grafana_update_annotation","grafana_update_contact_point","grafana_update_dashboard","grafana_update_folder","grain_create_hook","grain_create_hook_v2","grain_delete_hook","grain_delete_hook_v2","grain_get_recording","grain_get_transcript","grain_list_hooks","grain_list_hooks_v2","grain_list_meeting_types","grain_list_recordings","grain_list_teams","grain_list_views","granola_get_note","granola_list_folders","granola_list_notes","greenhouse_get_application","greenhouse_get_candidate","greenhouse_get_job","greenhouse_get_user","greenhouse_list_applications","greenhouse_list_candidates","greenhouse_list_departments","greenhouse_list_job_stages","greenhouse_list_jobs","greenhouse_list_offices","greenhouse_list_users","greptile_index_repo","greptile_query","greptile_search","greptile_status","guardrails_validate","hex_cancel_run","hex_create_collection","hex_create_group","hex_deactivate_user","hex_delete_group","hex_get_collection","hex_get_data_connection","hex_get_group","hex_get_project","hex_get_project_runs","hex_get_queried_tables","hex_get_run_status","hex_list_collections","hex_list_data_connections","hex_list_groups","hex_list_projects","hex_list_users","hex_run_project","hex_update_collection","hex_update_group","hex_update_project","http_request","hubspot_add_list_memberships","hubspot_create_appointment","hubspot_create_association","hubspot_create_company","hubspot_create_contact","hubspot_create_deal","hubspot_create_email","hubspot_create_line_item","hubspot_create_list","hubspot_create_note","hubspot_create_ticket","hubspot_delete_association","hubspot_delete_company","hubspot_delete_contact","hubspot_delete_deal","hubspot_delete_line_item","hubspot_delete_ticket","hubspot_get_appointment","hubspot_get_association_labels","hubspot_get_cart","hubspot_get_company","hubspot_get_contact","hubspot_get_deal","hubspot_get_email","hubspot_get_line_item","hubspot_get_list","hubspot_get_list_memberships","hubspot_get_marketing_event","hubspot_get_note","hubspot_get_properties","hubspot_get_quote","hubspot_get_ticket","hubspot_get_users","hubspot_list_appointments","hubspot_list_associations","hubspot_list_carts","hubspot_list_companies","hubspot_list_contacts","hubspot_list_deals","hubspot_list_emails","hubspot_list_line_items","hubspot_list_lists","hubspot_list_marketing_events","hubspot_list_notes","hubspot_list_owners","hubspot_list_quotes","hubspot_list_tickets","hubspot_remove_list_memberships","hubspot_search_companies","hubspot_search_contacts","hubspot_search_deals","hubspot_search_emails","hubspot_search_line_items","hubspot_search_notes","hubspot_search_quotes","hubspot_search_tickets","hubspot_update_appointment","hubspot_update_company","hubspot_update_contact","hubspot_update_deal","hubspot_update_line_item","hubspot_update_ticket","huggingface_chat","hunter_companies_find","hunter_discover","hunter_domain_search","hunter_email_count","hunter_email_finder","hunter_email_verifier","iam_add_user_to_group","iam_attach_role_policy","iam_attach_user_policy","iam_create_access_key","iam_create_role","iam_create_user","iam_delete_access_key","iam_delete_role","iam_delete_user","iam_detach_role_policy","iam_detach_user_policy","iam_get_role","iam_get_user","iam_list_attached_role_policies","iam_list_attached_user_policies","iam_list_groups","iam_list_policies","iam_list_roles","iam_list_users","iam_remove_user_from_group","iam_simulate_principal_policy","icypeas_find_email","icypeas_verify_email","identity_center_check_assignment_deletion_status","identity_center_check_assignment_status","identity_center_create_account_assignment","identity_center_delete_account_assignment","identity_center_describe_account","identity_center_get_group","identity_center_get_user","identity_center_list_account_assignments","identity_center_list_accounts","identity_center_list_groups","identity_center_list_instances","identity_center_list_permission_sets","image_generate","incidentio_actions_create","incidentio_actions_list","incidentio_actions_show","incidentio_actions_update","incidentio_alert_events_create","incidentio_alerts_list","incidentio_alerts_resolve","incidentio_alerts_show","incidentio_catalog_entries_list","incidentio_catalog_types_list","incidentio_custom_fields_create","incidentio_custom_fields_delete","incidentio_custom_fields_list","incidentio_custom_fields_show","incidentio_custom_fields_update","incidentio_escalation_paths_create","incidentio_escalation_paths_delete","incidentio_escalation_paths_list","incidentio_escalation_paths_show","incidentio_escalation_paths_update","incidentio_escalations_cancel","incidentio_escalations_create","incidentio_escalations_list","incidentio_escalations_show","incidentio_follow_ups_create","incidentio_follow_ups_list","incidentio_follow_ups_show","incidentio_follow_ups_update","incidentio_incident_alerts_list","incidentio_incident_memberships_create","incidentio_incident_memberships_revoke","incidentio_incident_participants_list","incidentio_incident_roles_create","incidentio_incident_roles_delete","incidentio_incident_roles_list","incidentio_incident_roles_show","incidentio_incident_roles_update","incidentio_incident_statuses_list","incidentio_incident_timestamps_list","incidentio_incident_timestamps_show","incidentio_incident_types_list","incidentio_incident_updates_list","incidentio_incidents_create","incidentio_incidents_list","incidentio_incidents_show","incidentio_incidents_update","incidentio_on_call_now","incidentio_schedule_entries_list","incidentio_schedule_overrides_create","incidentio_schedule_overrides_list","incidentio_schedules_create","incidentio_schedules_delete","incidentio_schedules_list","incidentio_schedules_show","incidentio_schedules_update","incidentio_severities_list","incidentio_teams_list","incidentio_teams_show","incidentio_users_list","incidentio_users_show","incidentio_workflows_create","incidentio_workflows_delete","incidentio_workflows_list","incidentio_workflows_show","incidentio_workflows_update","infisical_create_secret","infisical_delete_secret","infisical_get_secret","infisical_list_secrets","infisical_update_secret","instagram_delete_comment","instagram_download_media","instagram_get_account_insights","instagram_get_container_status","instagram_get_conversation_messages","instagram_get_media","instagram_get_media_insights","instagram_get_message","instagram_get_profile","instagram_get_publishing_limit","instagram_hide_comment","instagram_list_comments","instagram_list_conversations","instagram_list_media","instagram_list_stories","instagram_private_reply","instagram_publish_carousel","instagram_publish_image","instagram_publish_reel","instagram_publish_story","instagram_publish_video","instagram_reply_to_comment","instagram_send_text_message","instagram_set_comments_enabled","instantly_activate_campaign","instantly_create_campaign","instantly_create_lead","instantly_create_lead_list","instantly_delete_campaign","instantly_delete_leads","instantly_get_lead","instantly_list_campaigns","instantly_list_emails","instantly_list_lead_lists","instantly_list_leads","instantly_patch_campaign","instantly_patch_lead","instantly_pause_campaign","instantly_reply_to_email","instantly_update_lead_interest_status","intercom_assign_conversation_v2","intercom_attach_contact_to_company_v2","intercom_close_conversation_v2","intercom_create_company","intercom_create_company_v2","intercom_create_contact","intercom_create_contact_v2","intercom_create_event_v2","intercom_create_message","intercom_create_message_v2","intercom_create_note_v2","intercom_create_tag_v2","intercom_create_ticket","intercom_create_ticket_v2","intercom_delete_contact","intercom_delete_contact_v2","intercom_detach_contact_from_company_v2","intercom_get_company","intercom_get_company_v2","intercom_get_contact","intercom_get_contact_v2","intercom_get_conversation","intercom_get_conversation_v2","intercom_get_ticket","intercom_get_ticket_v2","intercom_list_admins_v2","intercom_list_companies","intercom_list_companies_v2","intercom_list_contacts","intercom_list_contacts_v2","intercom_list_conversations","intercom_list_conversations_v2","intercom_list_tags_v2","intercom_open_conversation_v2","intercom_reply_conversation","intercom_reply_conversation_v2","intercom_search_contacts","intercom_search_contacts_v2","intercom_search_conversations","intercom_search_conversations_v2","intercom_snooze_conversation_v2","intercom_tag_contact_v2","intercom_tag_conversation_v2","intercom_untag_contact_v2","intercom_update_contact","intercom_update_contact_v2","intercom_update_ticket_v2","jina_read_url","jina_search","jira_add_attachment","jira_add_comment","jira_add_watcher","jira_add_worklog","jira_assign_issue","jira_bulk_read","jira_create_issue_link","jira_delete_attachment","jira_delete_comment","jira_delete_issue","jira_delete_issue_link","jira_delete_worklog","jira_get_attachments","jira_get_comments","jira_get_fields","jira_get_project","jira_get_transitions","jira_get_users","jira_get_worklogs","jira_list_issue_types","jira_list_projects","jira_remove_watcher","jira_retrieve","jira_search_issues","jira_search_users","jira_transition_issue","jira_update","jira_update_comment","jira_update_worklog","jira_write","jsm_add_comment","jsm_add_customer","jsm_add_organization","jsm_add_participants","jsm_answer_approval","jsm_attach_form","jsm_copy_forms","jsm_create_object","jsm_create_organization","jsm_create_request","jsm_delete_form","jsm_delete_object","jsm_externalise_form","jsm_get_approvals","jsm_get_comments","jsm_get_customers","jsm_get_form","jsm_get_form_answers","jsm_get_form_structure","jsm_get_form_templates","jsm_get_issue_forms","jsm_get_object","jsm_get_object_schema","jsm_get_object_type_attributes","jsm_get_organizations","jsm_get_participants","jsm_get_queues","jsm_get_request","jsm_get_request_type_fields","jsm_get_request_types","jsm_get_requests","jsm_get_service_desks","jsm_get_sla","jsm_get_transitions","jsm_internalise_form","jsm_list_object_schemas","jsm_list_object_types","jsm_reopen_form","jsm_save_form_answers","jsm_search_objects_aql","jsm_submit_form","jsm_transition_request","jsm_update_object","jupyter_copy_content","jupyter_create_file","jupyter_create_session","jupyter_delete_content","jupyter_delete_session","jupyter_get_content","jupyter_interrupt_kernel","jupyter_list_contents","jupyter_list_kernels","jupyter_list_kernelspecs","jupyter_list_sessions","jupyter_rename_content","jupyter_restart_kernel","jupyter_start_kernel","jupyter_stop_kernel","jupyter_upload_file","kalshi_amend_order","kalshi_amend_order_v2","kalshi_cancel_order","kalshi_cancel_order_v2","kalshi_create_order","kalshi_create_order_v2","kalshi_get_balance","kalshi_get_balance_v2","kalshi_get_candlesticks","kalshi_get_candlesticks_v2","kalshi_get_event","kalshi_get_event_candlesticks","kalshi_get_event_candlesticks_v2","kalshi_get_event_v2","kalshi_get_events","kalshi_get_events_v2","kalshi_get_exchange_announcements","kalshi_get_exchange_announcements_v2","kalshi_get_exchange_schedule","kalshi_get_exchange_schedule_v2","kalshi_get_exchange_status","kalshi_get_exchange_status_v2","kalshi_get_fills","kalshi_get_fills_v2","kalshi_get_market","kalshi_get_market_v2","kalshi_get_markets","kalshi_get_markets_v2","kalshi_get_order","kalshi_get_order_v2","kalshi_get_orderbook","kalshi_get_orderbook_v2","kalshi_get_orders","kalshi_get_orders_v2","kalshi_get_positions","kalshi_get_positions_v2","kalshi_get_series_by_ticker","kalshi_get_series_by_ticker_v2","kalshi_get_series_list","kalshi_get_series_list_v2","kalshi_get_settlements","kalshi_get_settlements_v2","kalshi_get_trades","kalshi_get_trades_v2","ketch_get_consent","ketch_get_subscriptions","ketch_invoke_right","ketch_set_consent","ketch_set_subscriptions","knowledge_create_document","knowledge_delete_chunk","knowledge_delete_document","knowledge_get_connector","knowledge_get_document","knowledge_list_chunks","knowledge_list_connectors","knowledge_list_documents","knowledge_list_tags","knowledge_search","knowledge_trigger_sync","knowledge_update_chunk","knowledge_upload_chunk","knowledge_upsert_document","langsmith_create_feedback","langsmith_create_run","langsmith_create_runs_batch","langsmith_get_run","langsmith_update_run","latex_compile","latex_get_package","latex_list_fonts","latex_search_packages","launchdarkly_create_flag","launchdarkly_delete_flag","launchdarkly_get_audit_log","launchdarkly_get_flag","launchdarkly_get_flag_status","launchdarkly_list_environments","launchdarkly_list_flags","launchdarkly_list_members","launchdarkly_list_projects","launchdarkly_list_segments","launchdarkly_toggle_flag","launchdarkly_update_flag","leadmagic_company_search","leadmagic_email_to_profile","leadmagic_find_email","leadmagic_find_mobile","leadmagic_get_credits","leadmagic_profile_search","leadmagic_profile_to_email","leadmagic_role_finder","leadmagic_validate_email","lemlist_get_activities","lemlist_get_lead","lemlist_send_email","linear_add_label_to_issue","linear_add_label_to_project","linear_archive_issue","linear_archive_label","linear_archive_project","linear_create_attachment","linear_create_comment","linear_create_customer","linear_create_customer_request","linear_create_customer_status","linear_create_customer_tier","linear_create_cycle","linear_create_favorite","linear_create_issue","linear_create_issue_relation","linear_create_label","linear_create_project","linear_create_project_label","linear_create_project_milestone","linear_create_project_status","linear_create_project_update","linear_create_workflow_state","linear_delete_attachment","linear_delete_comment","linear_delete_customer","linear_delete_customer_status","linear_delete_customer_tier","linear_delete_issue","linear_delete_issue_relation","linear_delete_project","linear_delete_project_label","linear_delete_project_milestone","linear_delete_project_status","linear_get_active_cycle","linear_get_customer","linear_get_cycle","linear_get_issue","linear_get_project","linear_get_viewer","linear_list_attachments","linear_list_comments","linear_list_customer_requests","linear_list_customer_statuses","linear_list_customer_tiers","linear_list_customers","linear_list_cycles","linear_list_favorites","linear_list_issue_relations","linear_list_labels","linear_list_notifications","linear_list_project_labels","linear_list_project_milestones","linear_list_project_statuses","linear_list_project_updates","linear_list_projects","linear_list_teams","linear_list_users","linear_list_workflow_states","linear_merge_customers","linear_read_issues","linear_remove_label_from_issue","linear_remove_label_from_project","linear_search_issues","linear_unarchive_issue","linear_update_attachment","linear_update_comment","linear_update_customer","linear_update_customer_request","linear_update_customer_status","linear_update_customer_tier","linear_update_issue","linear_update_label","linear_update_notification","linear_update_project","linear_update_project_label","linear_update_project_milestone","linear_update_project_status","linear_update_workflow_state","linkedin_get_profile","linkedin_share_post","linkup_search","linq_add_participant","linq_check_imessage","linq_check_rcs","linq_create_attachment","linq_create_chat","linq_create_contact_card","linq_create_webhook_subscription","linq_delete_attachment","linq_delete_message","linq_delete_webhook_subscription","linq_edit_message","linq_get_attachment","linq_get_chat","linq_get_contact_card","linq_get_message","linq_get_webhook_subscription","linq_leave_chat","linq_list_chats","linq_list_messages","linq_list_phone_numbers","linq_list_thread","linq_list_webhook_events","linq_list_webhook_subscriptions","linq_mark_chat_read","linq_react_to_message","linq_remove_participant","linq_send_message","linq_send_voice_memo","linq_share_contact_card","linq_start_typing","linq_stop_typing","linq_update_chat","linq_update_contact_card","linq_update_webhook_subscription","llm_chat","logfire_get_token_info","logfire_get_trace","logfire_query","logfire_search_records","logrocket_create_release","logrocket_get_audit_logs","logrocket_get_highlights","logrocket_identify_user","logrocket_list_exported_sessions","logrocket_request_highlights","logs_get","logs_get_execution","logs_get_run_details","logs_query","logs_query_runs","loops_check_contact_suppression","loops_create_contact","loops_create_contact_property","loops_delete_contact","loops_find_contact","loops_get_transactional_email","loops_list_contact_properties","loops_list_mailing_lists","loops_list_transactional_emails","loops_remove_contact_suppression","loops_send_event","loops_send_transactional_email","loops_update_contact","luma_add_guests","luma_cancel_event","luma_create_event","luma_get_event","luma_get_guest","luma_get_guests","luma_list_events","luma_lookup_event","luma_send_invites","luma_update_event","luma_update_guest_status","mailchimp_add_member","mailchimp_add_member_tags","mailchimp_add_or_update_member","mailchimp_add_segment_member","mailchimp_add_subscriber_to_automation","mailchimp_archive_member","mailchimp_create_audience","mailchimp_create_batch_operation","mailchimp_create_campaign","mailchimp_create_interest","mailchimp_create_interest_category","mailchimp_create_landing_page","mailchimp_create_merge_field","mailchimp_create_segment","mailchimp_create_template","mailchimp_delete_audience","mailchimp_delete_batch_operation","mailchimp_delete_campaign","mailchimp_delete_interest","mailchimp_delete_interest_category","mailchimp_delete_landing_page","mailchimp_delete_member","mailchimp_delete_merge_field","mailchimp_delete_segment","mailchimp_delete_template","mailchimp_get_audience","mailchimp_get_audiences","mailchimp_get_automation","mailchimp_get_automations","mailchimp_get_batch_operation","mailchimp_get_batch_operations","mailchimp_get_campaign","mailchimp_get_campaign_content","mailchimp_get_campaign_report","mailchimp_get_campaign_reports","mailchimp_get_campaigns","mailchimp_get_interest","mailchimp_get_interest_categories","mailchimp_get_interest_category","mailchimp_get_interests","mailchimp_get_landing_page","mailchimp_get_landing_pages","mailchimp_get_member","mailchimp_get_member_tags","mailchimp_get_members","mailchimp_get_merge_field","mailchimp_get_merge_fields","mailchimp_get_segment","mailchimp_get_segment_members","mailchimp_get_segments","mailchimp_get_template","mailchimp_get_templates","mailchimp_pause_automation","mailchimp_publish_landing_page","mailchimp_remove_member_tags","mailchimp_remove_segment_member","mailchimp_replicate_campaign","mailchimp_schedule_campaign","mailchimp_send_campaign","mailchimp_set_campaign_content","mailchimp_start_automation","mailchimp_unarchive_member","mailchimp_unpublish_landing_page","mailchimp_unschedule_campaign","mailchimp_update_audience","mailchimp_update_campaign","mailchimp_update_interest","mailchimp_update_interest_category","mailchimp_update_landing_page","mailchimp_update_member","mailchimp_update_merge_field","mailchimp_update_segment","mailchimp_update_template","mailgun_add_list_member","mailgun_create_mailing_list","mailgun_get_domain","mailgun_get_mailing_list","mailgun_get_message","mailgun_list_domains","mailgun_list_messages","mailgun_send_message","managed_agent_archive_session","managed_agent_create_session","managed_agent_delete_session","managed_agent_get_session","managed_agent_interrupt_session","managed_agent_list_events","managed_agent_respond_custom_tool","managed_agent_respond_tool_confirmation","managed_agent_run_session","managed_agent_send_message","managed_agent_update_session","mem0_add_memories","mem0_get_memories","mem0_search_memories","memory_add","memory_delete","memory_get","memory_get_all","microsoft_ad_add_group_member","microsoft_ad_create_group","microsoft_ad_create_user","microsoft_ad_delete_group","microsoft_ad_delete_user","microsoft_ad_get_group","microsoft_ad_get_user","microsoft_ad_list_group_members","microsoft_ad_list_groups","microsoft_ad_list_users","microsoft_ad_remove_group_member","microsoft_ad_update_group","microsoft_ad_update_user","microsoft_dataverse_associate","microsoft_dataverse_create_multiple","microsoft_dataverse_create_record","microsoft_dataverse_delete_record","microsoft_dataverse_disassociate","microsoft_dataverse_download_file","microsoft_dataverse_execute_action","microsoft_dataverse_execute_function","microsoft_dataverse_fetchxml_query","microsoft_dataverse_get_entity_metadata","microsoft_dataverse_get_record","microsoft_dataverse_list_records","microsoft_dataverse_search","microsoft_dataverse_update_multiple","microsoft_dataverse_update_record","microsoft_dataverse_upload_file","microsoft_dataverse_upsert_record","microsoft_dataverse_whoami","microsoft_excel_clear_range","microsoft_excel_create_table","microsoft_excel_delete_worksheet","microsoft_excel_format_range","microsoft_excel_read","microsoft_excel_read_v2","microsoft_excel_sort_range","microsoft_excel_table_add","microsoft_excel_worksheet_add","microsoft_excel_write","microsoft_excel_write_v2","microsoft_planner_create_bucket","microsoft_planner_create_plan","microsoft_planner_create_task","microsoft_planner_delete_bucket","microsoft_planner_delete_plan","microsoft_planner_delete_task","microsoft_planner_get_plan_details","microsoft_planner_get_task_details","microsoft_planner_list_buckets","microsoft_planner_list_plans","microsoft_planner_read_bucket","microsoft_planner_read_plan","microsoft_planner_read_task","microsoft_planner_update_bucket","microsoft_planner_update_plan","microsoft_planner_update_plan_details","microsoft_planner_update_task","microsoft_planner_update_task_details","microsoft_teams_delete_channel_message","microsoft_teams_delete_chat_message","microsoft_teams_get_message","microsoft_teams_list_channel_members","microsoft_teams_list_channels","microsoft_teams_list_chat_members","microsoft_teams_list_chats","microsoft_teams_list_team_members","microsoft_teams_list_teams","microsoft_teams_read_channel","microsoft_teams_read_chat","microsoft_teams_reply_to_message","microsoft_teams_set_reaction","microsoft_teams_unset_reaction","microsoft_teams_update_channel_message","microsoft_teams_update_chat_message","microsoft_teams_write_channel","microsoft_teams_write_chat","millionverifier_get_credits","millionverifier_verify_email","mintlify_create_agent_job","mintlify_create_assistant_message","mintlify_detect_ai_prose","mintlify_get_agent_job","mintlify_get_assistant_caller_stats","mintlify_get_assistant_conversations","mintlify_get_feedback","mintlify_get_feedback_by_page","mintlify_get_page_content","mintlify_get_searches","mintlify_get_update_status","mintlify_get_views","mintlify_get_visitors","mintlify_search","mintlify_send_agent_message","mintlify_trigger_automation","mintlify_trigger_preview","mintlify_trigger_update","mistral_parser","mistral_parser_v2","mistral_parser_v3","monday_archive_item","monday_change_column_value","monday_create_board","monday_create_column","monday_create_group","monday_create_item","monday_create_subitem","monday_create_update","monday_delete_item","monday_duplicate_item","monday_get_board","monday_get_groups","monday_get_item","monday_get_items","monday_list_boards","monday_move_item_to_group","monday_search_items","monday_update_item","mongodb_delete","mongodb_execute","mongodb_insert","mongodb_introspect","mongodb_query","mongodb_update","mysql_delete","mysql_execute","mysql_insert","mysql_introspect","mysql_query","mysql_update","neo4j_create","neo4j_delete","neo4j_execute","neo4j_introspect","neo4j_merge","neo4j_query","neo4j_update","netsuite_attach_record","netsuite_batch_create_records","netsuite_batch_delete_records","netsuite_batch_get_records","netsuite_batch_update_records","netsuite_batch_upsert_records","netsuite_create_record","netsuite_delete_record","netsuite_detach_record","netsuite_execute_action","netsuite_execute_dataset","netsuite_execute_suiteql","netsuite_get_async_result","netsuite_get_async_status","netsuite_get_governance_limits","netsuite_get_record","netsuite_get_record_form","netsuite_get_record_metadata","netsuite_get_select_options","netsuite_get_server_time","netsuite_get_subresource","netsuite_list_datasets","netsuite_list_record_types","netsuite_list_records","netsuite_transform_record","netsuite_update_record","netsuite_upsert_record","neverbounce_get_credits","neverbounce_verify_email","new_relic_create_deployment_event","new_relic_get_entity","new_relic_nrql_query","new_relic_search_entities","notion_add_database_row","notion_add_database_row_v2","notion_append_blocks","notion_append_blocks_v2","notion_create_comment","notion_create_comment_v2","notion_create_database","notion_create_database_v2","notion_create_page","notion_create_page_v2","notion_delete_block","notion_delete_block_v2","notion_list_comments","notion_list_comments_v2","notion_list_users","notion_list_users_v2","notion_query_database","notion_query_database_v2","notion_read","notion_read_database","notion_read_database_v2","notion_read_v2","notion_retrieve_block","notion_retrieve_block_children","notion_retrieve_block_children_v2","notion_retrieve_block_v2","notion_retrieve_user","notion_retrieve_user_v2","notion_search","notion_search_v2","notion_update_block","notion_update_block_v2","notion_update_page","notion_update_page_v2","notion_write","notion_write_v2","obsidian_append_active","obsidian_append_note","obsidian_append_periodic_note","obsidian_create_note","obsidian_delete_note","obsidian_execute_command","obsidian_get_active","obsidian_get_note","obsidian_get_periodic_note","obsidian_list_commands","obsidian_list_files","obsidian_open_file","obsidian_patch_active","obsidian_patch_note","obsidian_search","okta_activate_group_rule","okta_activate_user","okta_add_user_to_group","okta_assign_group_to_app","okta_assign_user_role","okta_assign_user_to_app","okta_clear_user_sessions","okta_create_group","okta_create_group_rule","okta_create_user","okta_deactivate_group_rule","okta_deactivate_user","okta_delete_group","okta_delete_group_rule","okta_delete_user","okta_enroll_factor","okta_get_app","okta_get_factor","okta_get_group","okta_get_group_rule","okta_get_logs","okta_get_session","okta_get_user","okta_list_app_groups","okta_list_app_users","okta_list_apps","okta_list_factors","okta_list_group_members","okta_list_group_rules","okta_list_groups","okta_list_user_roles","okta_list_users","okta_remove_group_from_app","okta_remove_user_from_app","okta_remove_user_from_group","okta_remove_user_role","okta_reset_all_factors","okta_reset_factor","okta_reset_password","okta_revoke_session","okta_suspend_user","okta_unsuspend_user","okta_update_group","okta_update_user","onedrive_copy","onedrive_create_folder","onedrive_create_share_link","onedrive_delete","onedrive_download","onedrive_get_drive_info","onedrive_get_item","onedrive_list","onedrive_move","onedrive_search","onedrive_upload","onepassword_create_item","onepassword_delete_item","onepassword_get_item","onepassword_get_item_file","onepassword_get_vault","onepassword_list_items","onepassword_list_vaults","onepassword_replace_item","onepassword_resolve_secret","onepassword_update_item","openai_embeddings","openai_image","outlook_calendar_create_event","outlook_calendar_delete_event","outlook_calendar_get_event","outlook_calendar_list_events","outlook_calendar_respond","outlook_calendar_update_event","outlook_copy","outlook_create_folder","outlook_delete","outlook_draft","outlook_forward","outlook_get_attachment","outlook_list_attachments","outlook_list_folders","outlook_mark_read","outlook_mark_unread","outlook_move","outlook_read","outlook_reply","outlook_reply_all","outlook_search","outlook_send","outlook_update_message","pagerduty_add_note","pagerduty_create_incident","pagerduty_get_incident","pagerduty_get_service","pagerduty_list_escalation_policies","pagerduty_list_incident_alerts","pagerduty_list_incidents","pagerduty_list_oncalls","pagerduty_list_schedules","pagerduty_list_services","pagerduty_list_users","pagerduty_merge_incidents","pagerduty_send_event","pagerduty_snooze_incident","pagerduty_update_incident","parallel_deep_research","parallel_extract","parallel_search","pdl_autocomplete","pdl_bulk_company_enrich","pdl_bulk_person_enrich","pdl_clean_company","pdl_clean_location","pdl_clean_school","pdl_company_enrich","pdl_company_search","pdl_person_enrich","pdl_person_identify","pdl_person_search","perplexity_chat","perplexity_search","persona_approve_inquiry","persona_create_account","persona_create_inquiry","persona_create_report","persona_decline_inquiry","persona_expire_inquiry","persona_generate_inquiry_link","persona_get_account","persona_get_case","persona_get_document","persona_get_inquiry","persona_get_report","persona_get_verification","persona_import_accounts","persona_list_accounts","persona_list_cases","persona_list_inquiries","persona_list_inquiry_templates","persona_list_reports","persona_mark_inquiry_for_review","persona_print_inquiry_pdf","persona_redact_account","persona_redact_inquiry","persona_resume_inquiry","persona_update_account","persona_update_inquiry","pinecone_delete_vectors","pinecone_describe_index","pinecone_describe_index_stats","pinecone_fetch","pinecone_generate_embeddings","pinecone_list_indexes","pinecone_list_vector_ids","pinecone_search_text","pinecone_search_vector","pinecone_update_vector","pinecone_upsert_text","pipedrive_create_activity","pipedrive_create_deal","pipedrive_create_lead","pipedrive_create_project","pipedrive_delete_lead","pipedrive_get_activities","pipedrive_get_all_deals","pipedrive_get_deal","pipedrive_get_files","pipedrive_get_leads","pipedrive_get_mail_messages","pipedrive_get_mail_thread","pipedrive_get_pipeline_deals","pipedrive_get_pipelines","pipedrive_get_projects","pipedrive_update_activity","pipedrive_update_deal","pipedrive_update_lead","polymarket_get_activity","polymarket_get_event","polymarket_get_events","polymarket_get_holders","polymarket_get_last_trade_price","polymarket_get_leaderboard","polymarket_get_market","polymarket_get_markets","polymarket_get_midpoint","polymarket_get_orderbook","polymarket_get_positions","polymarket_get_price","polymarket_get_price_history","polymarket_get_series","polymarket_get_series_by_id","polymarket_get_spread","polymarket_get_tags","polymarket_get_tick_size","polymarket_get_trades","polymarket_search","postgresql_delete","postgresql_execute","postgresql_insert","postgresql_introspect","postgresql_query","postgresql_update","posthog_batch_events","posthog_capture_event","posthog_create_annotation","posthog_create_cohort","posthog_create_dashboard","posthog_create_experiment","posthog_create_feature_flag","posthog_create_insight","posthog_create_survey","posthog_delete_feature_flag","posthog_delete_person","posthog_delete_survey","posthog_evaluate_flags","posthog_get_cohort","posthog_get_dashboard","posthog_get_event_definition","posthog_get_experiment","posthog_get_feature_flag","posthog_get_insight","posthog_get_organization","posthog_get_person","posthog_get_project","posthog_get_property_definition","posthog_get_session_recording","posthog_get_survey","posthog_list_actions","posthog_list_annotations","posthog_list_cohorts","posthog_list_dashboards","posthog_list_event_definitions","posthog_list_experiments","posthog_list_feature_flags","posthog_list_insights","posthog_list_organizations","posthog_list_persons","posthog_list_projects","posthog_list_property_definitions","posthog_list_recording_playlists","posthog_list_session_recordings","posthog_list_surveys","posthog_query","posthog_update_cohort","posthog_update_event_definition","posthog_update_experiment","posthog_update_feature_flag","posthog_update_insight","posthog_update_property_definition","posthog_update_survey","profound_bot_logs","profound_bots_report","profound_category_assets","profound_category_personas","profound_category_prompts","profound_category_tags","profound_category_topics","profound_citation_prompts","profound_citations_report","profound_list_assets","profound_list_categories","profound_list_domains","profound_list_models","profound_list_optimizations","profound_list_personas","profound_list_regions","profound_optimization_analysis","profound_prompt_answers","profound_prompt_volume","profound_query_fanouts","profound_raw_logs","profound_referrals_report","profound_sentiment_report","profound_visibility_report","prospeo_account_information","prospeo_bulk_enrich_company","prospeo_bulk_enrich_person","prospeo_enrich_company","prospeo_enrich_person","prospeo_search_company","prospeo_search_person","prospeo_search_suggestions","pulse_parser","pulse_parser_v2","qdrant_fetch_points","qdrant_search_vector","qdrant_upsert_points","quartr_get_audio","quartr_get_company","quartr_get_event","quartr_get_event_summary","quartr_get_report","quartr_get_slide_deck","quartr_get_transcript","quartr_list_audio","quartr_list_companies","quartr_list_document_types","quartr_list_documents","quartr_list_event_types","quartr_list_events","quartr_list_live_events","quartr_list_reports","quartr_list_slide_decks","quartr_list_transcripts","quiver_image_to_svg","quiver_list_models","quiver_text_to_svg","rabbitmq_create_binding","rabbitmq_create_exchange","rabbitmq_create_policy","rabbitmq_create_queue","rabbitmq_delete_binding","rabbitmq_delete_exchange","rabbitmq_delete_policy","rabbitmq_delete_queue","rabbitmq_get_exchange","rabbitmq_get_messages","rabbitmq_get_overview","rabbitmq_get_queue","rabbitmq_health_check","rabbitmq_list_bindings","rabbitmq_list_channels","rabbitmq_list_connections","rabbitmq_list_consumers","rabbitmq_list_exchange_bindings","rabbitmq_list_exchanges","rabbitmq_list_nodes","rabbitmq_list_policies","rabbitmq_list_queues","rabbitmq_list_vhosts","rabbitmq_publish_message","rabbitmq_purge_queue","railway_create_environment","railway_create_project","railway_create_service","railway_delete_environment","railway_delete_project","railway_delete_service","railway_delete_variable","railway_deploy_service","railway_get_deployment","railway_get_deployment_logs","railway_get_project","railway_list_deployments","railway_list_project_members","railway_list_projects","railway_list_variables","railway_restart_deployment","railway_rollback_deployment","railway_transfer_project","railway_update_project","railway_upsert_variable","rb2b_credit_check","rb2b_email_to_activity","rb2b_hem_to_best_linkedin","rb2b_hem_to_business_profile","rb2b_hem_to_linkedin","rb2b_hem_to_maid","rb2b_ip_to_company","rb2b_ip_to_hem","rb2b_ip_to_maid","rb2b_linkedin_slug_search","rb2b_linkedin_to_best_personal_email","rb2b_linkedin_to_business_profile","rb2b_linkedin_to_hashed_emails","rb2b_linkedin_to_mobile_phone","rb2b_linkedin_to_personal_email","rds_delete","rds_execute","rds_insert","rds_introspect","rds_query","rds_update","reddit_delete","reddit_edit","reddit_get_comments","reddit_get_controversial","reddit_get_info","reddit_get_me","reddit_get_messages","reddit_get_posts","reddit_get_saved","reddit_get_subreddit_info","reddit_get_subreddit_rules","reddit_get_user","reddit_get_user_comments","reddit_get_user_posts","reddit_hide","reddit_hot_posts","reddit_list_my_subreddits","reddit_lock","reddit_mark_all_read","reddit_mark_read","reddit_marknsfw","reddit_mod_approve","reddit_mod_distinguish","reddit_mod_remove","reddit_mod_sticky","reddit_reply","reddit_report","reddit_save","reddit_search","reddit_search_subreddits","reddit_send_message","reddit_submit_post","reddit_subscribe","reddit_unhide","reddit_unlock","reddit_unmarknsfw","reddit_unsave","reddit_vote","redis_command","redis_delete","redis_exists","redis_expire","redis_get","redis_hdel","redis_hget","redis_hgetall","redis_hset","redis_incr","redis_incrby","redis_keys","redis_llen","redis_lpop","redis_lpush","redis_lrange","redis_persist","redis_rpop","redis_rpush","redis_set","redis_setnx","redis_ttl","reducto_parser","reducto_parser_v2","resend_cancel_email","resend_create_audience","resend_create_broadcast","resend_create_contact","resend_delete_audience","resend_delete_contact","resend_get_audience","resend_get_broadcast","resend_get_contact","resend_get_email","resend_list_audiences","resend_list_contacts","resend_list_domains","resend_send","resend_send_broadcast","resend_update_contact","revenuecat_create_purchase","revenuecat_defer_google_subscription","revenuecat_delete_customer","revenuecat_get_customer","revenuecat_grant_entitlement","revenuecat_list_offerings","revenuecat_refund_google_subscription","revenuecat_revoke_entitlement","revenuecat_revoke_google_subscription","revenuecat_update_subscriber_attributes","rippling_bulk_create_custom_object_records","rippling_bulk_delete_custom_object_records","rippling_bulk_update_custom_object_records","rippling_create_business_partner","rippling_create_business_partner_group","rippling_create_custom_app","rippling_create_custom_object","rippling_create_custom_object_field","rippling_create_custom_object_record","rippling_create_custom_page","rippling_create_custom_setting","rippling_create_department","rippling_create_draft_hires","rippling_create_object_category","rippling_create_title","rippling_create_work_location","rippling_delete_business_partner","rippling_delete_business_partner_group","rippling_delete_custom_app","rippling_delete_custom_object","rippling_delete_custom_object_field","rippling_delete_custom_object_record","rippling_delete_custom_page","rippling_delete_custom_setting","rippling_delete_object_category","rippling_delete_title","rippling_delete_work_location","rippling_get_business_partner","rippling_get_business_partner_group","rippling_get_current_user","rippling_get_custom_app","rippling_get_custom_object","rippling_get_custom_object_field","rippling_get_custom_object_record","rippling_get_custom_object_record_by_external_id","rippling_get_custom_page","rippling_get_custom_setting","rippling_get_department","rippling_get_employment_type","rippling_get_job_function","rippling_get_object_category","rippling_get_report_run","rippling_get_supergroup","rippling_get_team","rippling_get_title","rippling_get_user","rippling_get_work_location","rippling_get_worker","rippling_list_business_partner_groups","rippling_list_business_partners","rippling_list_companies","rippling_list_custom_apps","rippling_list_custom_fields","rippling_list_custom_object_fields","rippling_list_custom_object_records","rippling_list_custom_objects","rippling_list_custom_pages","rippling_list_custom_settings","rippling_list_departments","rippling_list_employment_types","rippling_list_entitlements","rippling_list_job_functions","rippling_list_object_categories","rippling_list_supergroup_exclusion_members","rippling_list_supergroup_inclusion_members","rippling_list_supergroup_members","rippling_list_supergroups","rippling_list_teams","rippling_list_titles","rippling_list_users","rippling_list_work_locations","rippling_list_workers","rippling_query_custom_object_records","rippling_trigger_report_run","rippling_update_custom_app","rippling_update_custom_object","rippling_update_custom_object_field","rippling_update_custom_object_record","rippling_update_custom_page","rippling_update_custom_setting","rippling_update_department","rippling_update_object_category","rippling_update_supergroup_exclusion_members","rippling_update_supergroup_inclusion_members","rippling_update_title","rippling_update_work_location","rocketlane_add_field_option","rocketlane_add_project_members","rocketlane_add_task_assignees","rocketlane_add_task_dependencies","rocketlane_add_task_followers","rocketlane_archive_project","rocketlane_assign_placeholders","rocketlane_create_field","rocketlane_create_phase","rocketlane_create_project","rocketlane_create_space","rocketlane_create_space_document","rocketlane_create_task","rocketlane_create_time_entry","rocketlane_create_time_off","rocketlane_delete_field","rocketlane_delete_phase","rocketlane_delete_project","rocketlane_delete_space","rocketlane_delete_space_document","rocketlane_delete_task","rocketlane_delete_time_entry","rocketlane_delete_time_off","rocketlane_get_field","rocketlane_get_invoice","rocketlane_get_invoice_line_items","rocketlane_get_invoice_payments","rocketlane_get_phase","rocketlane_get_project","rocketlane_get_space","rocketlane_get_space_document","rocketlane_get_task","rocketlane_get_time_entry","rocketlane_get_time_off","rocketlane_get_user","rocketlane_import_template","rocketlane_list_fields","rocketlane_list_invoices","rocketlane_list_phases","rocketlane_list_placeholders","rocketlane_list_projects","rocketlane_list_resource_allocations","rocketlane_list_space_documents","rocketlane_list_spaces","rocketlane_list_tasks","rocketlane_list_time_entries","rocketlane_list_time_entry_categories","rocketlane_list_time_offs","rocketlane_list_users","rocketlane_move_task_to_phase","rocketlane_remove_project_members","rocketlane_remove_task_assignees","rocketlane_remove_task_dependencies","rocketlane_remove_task_followers","rocketlane_search_time_entries","rocketlane_unassign_placeholders","rocketlane_update_field","rocketlane_update_field_option","rocketlane_update_phase","rocketlane_update_project","rocketlane_update_space","rocketlane_update_space_document","rocketlane_update_task","rocketlane_update_time_entry","rootly_acknowledge_alert","rootly_add_incident_event","rootly_add_subscribers","rootly_assign_incident_role","rootly_create_action_item","rootly_create_alert","rootly_create_incident","rootly_create_status_page_event","rootly_delete_action_item","rootly_delete_incident","rootly_escalate_alert","rootly_get_alert","rootly_get_incident","rootly_list_action_items","rootly_list_alerts","rootly_list_causes","rootly_list_environments","rootly_list_escalation_policies","rootly_list_functionalities","rootly_list_incident_events","rootly_list_incident_roles","rootly_list_incident_types","rootly_list_incidents","rootly_list_on_calls","rootly_list_playbooks","rootly_list_retrospectives","rootly_list_schedules","rootly_list_services","rootly_list_severities","rootly_list_teams","rootly_list_users","rootly_mitigate_incident","rootly_remove_subscribers","rootly_resolve_alert","rootly_resolve_incident","rootly_run_workflow","rootly_snooze_alert","rootly_unassign_incident_role","rootly_update_action_item","rootly_update_alert","rootly_update_incident","s3_copy_object","s3_create_bucket","s3_delete_bucket","s3_delete_object","s3_delete_objects","s3_get_object","s3_head_object","s3_list_buckets","s3_list_objects","s3_presigned_url","s3_put_object","salesforce_create_account","salesforce_create_case","salesforce_create_contact","salesforce_create_custom_field","salesforce_create_custom_object","salesforce_create_lead","salesforce_create_opportunity","salesforce_create_task","salesforce_delete_account","salesforce_delete_case","salesforce_delete_contact","salesforce_delete_custom_field","salesforce_delete_lead","salesforce_delete_opportunity","salesforce_delete_task","salesforce_describe_object","salesforce_get_accounts","salesforce_get_cases","salesforce_get_contacts","salesforce_get_dashboard","salesforce_get_leads","salesforce_get_opportunities","salesforce_get_report","salesforce_get_tasks","salesforce_list_dashboards","salesforce_list_objects","salesforce_list_report_types","salesforce_list_reports","salesforce_query","salesforce_query_more","salesforce_refresh_dashboard","salesforce_run_report","salesforce_tooling_query","salesforce_update_account","salesforce_update_case","salesforce_update_contact","salesforce_update_custom_field","salesforce_update_lead","salesforce_update_opportunity","salesforce_update_task","sap_concur_approve_expense_report","sap_concur_associate_attendees","sap_concur_create_cash_advance","sap_concur_create_expected_expense","sap_concur_create_expense_report","sap_concur_create_list_item","sap_concur_create_purchase_request","sap_concur_create_quick_expense","sap_concur_create_quick_expense_with_image","sap_concur_create_report_comment","sap_concur_create_travel_request","sap_concur_create_user","sap_concur_delete_expected_expense","sap_concur_delete_expense","sap_concur_delete_expense_report","sap_concur_delete_list_item","sap_concur_delete_travel_request","sap_concur_delete_user","sap_concur_get_allocation","sap_concur_get_budget","sap_concur_get_cash_advance","sap_concur_get_expected_expense","sap_concur_get_expense","sap_concur_get_expense_report","sap_concur_get_itemizations","sap_concur_get_itinerary","sap_concur_get_list","sap_concur_get_list_item","sap_concur_get_purchase_request","sap_concur_get_receipt","sap_concur_get_receipt_status","sap_concur_get_request_cash_advance","sap_concur_get_travel_profile","sap_concur_get_travel_request","sap_concur_get_user","sap_concur_issue_cash_advance","sap_concur_list_allocations","sap_concur_list_attendee_associations","sap_concur_list_budget_categories","sap_concur_list_budgets","sap_concur_list_exceptions","sap_concur_list_expected_expenses","sap_concur_list_expense_reports","sap_concur_list_expenses","sap_concur_list_itineraries","sap_concur_list_list_items","sap_concur_list_lists","sap_concur_list_receipts","sap_concur_list_report_comments","sap_concur_list_reports_to_approve","sap_concur_list_travel_profiles_summary","sap_concur_list_travel_request_comments","sap_concur_list_travel_requests","sap_concur_list_users","sap_concur_move_travel_request","sap_concur_recall_expense_report","sap_concur_remove_all_attendees","sap_concur_search_locations","sap_concur_search_users","sap_concur_send_back_expense_report","sap_concur_submit_expense_report","sap_concur_update_allocation","sap_concur_update_expected_expense","sap_concur_update_expense","sap_concur_update_expense_report","sap_concur_update_list_item","sap_concur_update_travel_request","sap_concur_update_user","sap_concur_upload_exchange_rates","sap_concur_upload_receipt_image","sap_s4hana_create_business_partner","sap_s4hana_create_purchase_order","sap_s4hana_create_purchase_requisition","sap_s4hana_create_sales_order","sap_s4hana_delete_sales_order","sap_s4hana_get_billing_document","sap_s4hana_get_business_partner","sap_s4hana_get_customer","sap_s4hana_get_inbound_delivery","sap_s4hana_get_material_document","sap_s4hana_get_outbound_delivery","sap_s4hana_get_product","sap_s4hana_get_purchase_order","sap_s4hana_get_purchase_requisition","sap_s4hana_get_sales_order","sap_s4hana_get_supplier","sap_s4hana_get_supplier_invoice","sap_s4hana_list_billing_documents","sap_s4hana_list_business_partners","sap_s4hana_list_customers","sap_s4hana_list_inbound_deliveries","sap_s4hana_list_material_documents","sap_s4hana_list_material_stock","sap_s4hana_list_outbound_deliveries","sap_s4hana_list_products","sap_s4hana_list_purchase_orders","sap_s4hana_list_purchase_requisitions","sap_s4hana_list_sales_orders","sap_s4hana_list_supplier_invoices","sap_s4hana_list_suppliers","sap_s4hana_odata_query","sap_s4hana_update_business_partner","sap_s4hana_update_customer","sap_s4hana_update_product","sap_s4hana_update_purchase_order","sap_s4hana_update_purchase_requisition","sap_s4hana_update_sales_order","sap_s4hana_update_supplier","search_tool","secrets_manager_create_secret","secrets_manager_delete_secret","secrets_manager_describe_secret","secrets_manager_get_secret","secrets_manager_list_secrets","secrets_manager_restore_secret","secrets_manager_rotate_secret","secrets_manager_tag_resource","secrets_manager_untag_resource","secrets_manager_update_secret","sendblue_evaluate_service","sendblue_get_message","sendblue_send_group_message","sendblue_send_message","sendblue_send_typing_indicator","sendgrid_add_contact","sendgrid_add_contacts_to_list","sendgrid_create_list","sendgrid_create_template","sendgrid_create_template_version","sendgrid_delete_contacts","sendgrid_delete_list","sendgrid_delete_template","sendgrid_get_contact","sendgrid_get_list","sendgrid_get_template","sendgrid_list_all_lists","sendgrid_list_templates","sendgrid_remove_contacts_from_list","sendgrid_search_contacts","sendgrid_send_mail","sentry_events_get","sentry_events_list","sentry_issues_get","sentry_issues_list","sentry_issues_update","sentry_projects_create","sentry_projects_get","sentry_projects_list","sentry_projects_update","sentry_releases_create","sentry_releases_deploy","sentry_releases_list","sentry_teams_list","serper_search","servicenow_add_incident_comment","servicenow_aggregate","servicenow_close_incident","servicenow_create_change_request","servicenow_create_incident","servicenow_create_record","servicenow_delete_record","servicenow_download_attachment","servicenow_find_user","servicenow_get_change_next_states","servicenow_get_change_request","servicenow_get_ci","servicenow_get_incident","servicenow_get_knowledge_article","servicenow_get_requested_item","servicenow_list_approvals","servicenow_list_attachments","servicenow_list_catalog_items","servicenow_list_change_requests","servicenow_list_change_tasks","servicenow_list_ci_relationships","servicenow_list_group_members","servicenow_list_incidents","servicenow_list_requested_items","servicenow_order_catalog_item","servicenow_read_record","servicenow_resolve_incident","servicenow_search_cis","servicenow_search_knowledge","servicenow_update_approval","servicenow_update_change_request","servicenow_update_change_state","servicenow_update_incident","servicenow_update_record","servicenow_upload_attachment","ses_create_configuration_set","ses_create_email_identity","ses_create_template","ses_delete_email_identity","ses_delete_suppressed_destination","ses_delete_template","ses_get_account","ses_get_email_identity","ses_get_suppressed_destination","ses_get_template","ses_list_identities","ses_list_suppressed_destinations","ses_list_templates","ses_put_suppressed_destination","ses_send_bulk_email","ses_send_custom_verification_email","ses_send_email","ses_send_templated_email","ses_update_template","sftp_delete","sftp_download","sftp_list","sftp_mkdir","sftp_upload","sharepoint_add_list_items","sharepoint_create_list","sharepoint_create_page","sharepoint_delete_file","sharepoint_delete_list_item","sharepoint_delete_page","sharepoint_download_file","sharepoint_get_drive_item","sharepoint_get_list","sharepoint_get_list_item","sharepoint_list_sites","sharepoint_publish_page","sharepoint_read_page","sharepoint_update_list","sharepoint_update_page","sharepoint_upload_file","shopify_adjust_inventory","shopify_cancel_order","shopify_create_customer","shopify_create_fulfillment","shopify_create_product","shopify_delete_customer","shopify_delete_product","shopify_get_collection","shopify_get_customer","shopify_get_inventory_level","shopify_get_order","shopify_get_product","shopify_list_collections","shopify_list_customers","shopify_list_inventory_items","shopify_list_locations","shopify_list_orders","shopify_list_products","shopify_update_customer","shopify_update_order","shopify_update_product","similarweb_bounce_rate","similarweb_page_views","similarweb_pages_per_visit","similarweb_traffic_visits","similarweb_visit_duration","similarweb_website_overview","sixtyfour_enrich_company","sixtyfour_enrich_lead","sixtyfour_find_email","sixtyfour_find_phone","slack_add_reaction","slack_archive_conversation","slack_canvas","slack_create_channel_canvas","slack_create_conversation","slack_delete_canvas","slack_delete_message","slack_delete_scheduled_message","slack_download","slack_edit_canvas","slack_ephemeral_message","slack_get_canvas","slack_get_channel_history","slack_get_channel_info","slack_get_message","slack_get_permalink","slack_get_thread","slack_get_thread_replies","slack_get_user","slack_get_user_presence","slack_invite_to_conversation","slack_list_canvases","slack_list_channels","slack_list_members","slack_list_scheduled_messages","slack_list_users","slack_lookup_canvas_sections","slack_message","slack_message_reader","slack_open_view","slack_publish_view","slack_push_view","slack_remove_reaction","slack_rename_conversation","slack_schedule_message","slack_set_conversation_purpose","slack_set_conversation_topic","slack_set_status","slack_set_suggested_prompts","slack_set_title","slack_update_message","slack_update_view","smartlead_add_email_accounts_to_campaign","smartlead_add_leads_to_campaign","smartlead_create_campaign","smartlead_create_lead_list","smartlead_delete_campaign","smartlead_delete_campaign_webhook","smartlead_delete_lead_from_campaign","smartlead_delete_lead_list","smartlead_duplicate_campaign","smartlead_export_campaign_leads","smartlead_get_campaign","smartlead_get_campaign_analytics","smartlead_get_campaign_analytics_by_date","smartlead_get_campaign_lead_statistics","smartlead_get_campaign_mailbox_statistics","smartlead_get_campaign_sequences","smartlead_get_campaign_statistics","smartlead_get_campaign_top_level_analytics_by_date","smartlead_get_campaign_webhook_summary","smartlead_get_lead_by_email","smartlead_get_lead_by_id","smartlead_get_lead_list","smartlead_get_lead_message_history","smartlead_list_campaign_email_accounts","smartlead_list_campaign_leads","smartlead_list_campaign_webhooks","smartlead_list_campaigns","smartlead_list_clients","smartlead_list_email_accounts","smartlead_list_inbox_replies","smartlead_list_lead_activities","smartlead_list_lead_categories","smartlead_list_lead_lists","smartlead_mark_lead_complete","smartlead_pause_lead","smartlead_remove_email_accounts_from_campaign","smartlead_resume_lead","smartlead_save_campaign_sequences","smartlead_unsubscribe_lead_from_campaign","smartlead_unsubscribe_lead_globally","smartlead_update_campaign_schedule","smartlead_update_campaign_settings","smartlead_update_campaign_status","smartlead_update_lead","smartlead_update_lead_category","smartlead_update_lead_list","smartlead_upsert_campaign_webhook","sms_send","smtp_send_mail","snowflake_alter_warehouse","snowflake_call_procedure","snowflake_cancel_statement","snowflake_cancel_task_run","snowflake_delete_rows","snowflake_execute_sql","snowflake_get_statement","snowflake_get_task","snowflake_get_task_run","snowflake_get_task_run_output","snowflake_get_warehouse","snowflake_insert_rows","snowflake_introspect_schema","snowflake_list_copy_history","snowflake_list_databases","snowflake_list_query_history","snowflake_list_schemas","snowflake_list_tables","snowflake_list_task_runs","snowflake_list_tasks","snowflake_list_warehouses","snowflake_load_data","snowflake_resume_task","snowflake_resume_warehouse","snowflake_run_task","snowflake_suspend_task","snowflake_suspend_warehouse","snowflake_unload_data","snowflake_update_rows","snowflake_upsert_rows","splunk_cancel_search_job","splunk_create_search_job","splunk_dispatch_saved_search","splunk_get_fired_alerts","splunk_get_saved_search","splunk_get_search_job","splunk_get_search_results","splunk_list_apps","splunk_list_fired_alerts","splunk_list_indexes","splunk_list_saved_searches","splunk_run_search","sportmonks_core_get_cities","sportmonks_core_get_city","sportmonks_core_get_continent","sportmonks_core_get_continents","sportmonks_core_get_countries","sportmonks_core_get_country","sportmonks_core_get_entity_filters","sportmonks_core_get_my_usage","sportmonks_core_get_region","sportmonks_core_get_regions","sportmonks_core_get_timezones","sportmonks_core_get_type","sportmonks_core_get_type_by_entity","sportmonks_core_get_types","sportmonks_core_search_cities","sportmonks_core_search_countries","sportmonks_core_search_regions","sportmonks_football_expected_by_player","sportmonks_football_expected_by_team","sportmonks_football_get_all_commentaries","sportmonks_football_get_all_fixtures","sportmonks_football_get_all_players","sportmonks_football_get_all_rivals","sportmonks_football_get_all_teams","sportmonks_football_get_all_transfer_rumours","sportmonks_football_get_all_transfers","sportmonks_football_get_brackets_by_season","sportmonks_football_get_coach","sportmonks_football_get_coaches","sportmonks_football_get_coaches_by_country","sportmonks_football_get_commentaries_by_fixture","sportmonks_football_get_current_leagues_by_team","sportmonks_football_get_expected_lineups_by_player","sportmonks_football_get_expected_lineups_by_team","sportmonks_football_get_extended_team_squad","sportmonks_football_get_fixture","sportmonks_football_get_fixtures_by_date","sportmonks_football_get_fixtures_by_date_range","sportmonks_football_get_fixtures_by_date_range_for_team","sportmonks_football_get_fixtures_by_ids","sportmonks_football_get_grouped_standings_by_round","sportmonks_football_get_head_to_head","sportmonks_football_get_inplay_livescores","sportmonks_football_get_latest_coaches","sportmonks_football_get_latest_fixtures","sportmonks_football_get_latest_livescores","sportmonks_football_get_latest_players","sportmonks_football_get_latest_totw","sportmonks_football_get_latest_transfers","sportmonks_football_get_league","sportmonks_football_get_leagues","sportmonks_football_get_leagues_by_country","sportmonks_football_get_leagues_by_date","sportmonks_football_get_leagues_by_team","sportmonks_football_get_live_leagues","sportmonks_football_get_live_probabilities","sportmonks_football_get_live_probabilities_by_fixture","sportmonks_football_get_live_standings_by_league","sportmonks_football_get_livescores","sportmonks_football_get_match_facts","sportmonks_football_get_match_facts_by_date_range","sportmonks_football_get_match_facts_by_fixture","sportmonks_football_get_match_facts_by_league","sportmonks_football_get_past_fixtures_by_tv_station","sportmonks_football_get_player","sportmonks_football_get_players_by_country","sportmonks_football_get_postmatch_news","sportmonks_football_get_postmatch_news_by_season","sportmonks_football_get_predictability_by_league","sportmonks_football_get_prematch_news","sportmonks_football_get_prematch_news_by_season","sportmonks_football_get_prematch_news_upcoming","sportmonks_football_get_probabilities","sportmonks_football_get_probabilities_by_fixture","sportmonks_football_get_referee","sportmonks_football_get_referees","sportmonks_football_get_referees_by_country","sportmonks_football_get_referees_by_season","sportmonks_football_get_rivals_by_team","sportmonks_football_get_round","sportmonks_football_get_round_statistics","sportmonks_football_get_rounds","sportmonks_football_get_rounds_by_season","sportmonks_football_get_schedules_by_season","sportmonks_football_get_schedules_by_season_and_team","sportmonks_football_get_schedules_by_team","sportmonks_football_get_season","sportmonks_football_get_seasons","sportmonks_football_get_seasons_by_team","sportmonks_football_get_stage","sportmonks_football_get_stage_statistics","sportmonks_football_get_stages","sportmonks_football_get_stages_by_season","sportmonks_football_get_standing_corrections_by_season","sportmonks_football_get_standings","sportmonks_football_get_standings_by_round","sportmonks_football_get_standings_by_season","sportmonks_football_get_state","sportmonks_football_get_states","sportmonks_football_get_team","sportmonks_football_get_team_rankings","sportmonks_football_get_team_rankings_by_date","sportmonks_football_get_team_rankings_by_team","sportmonks_football_get_team_squad","sportmonks_football_get_team_squad_by_season","sportmonks_football_get_teams_by_country","sportmonks_football_get_teams_by_season","sportmonks_football_get_topscorers_by_season","sportmonks_football_get_topscorers_by_stage","sportmonks_football_get_totw","sportmonks_football_get_totw_by_round","sportmonks_football_get_transfer","sportmonks_football_get_transfer_rumour","sportmonks_football_get_transfer_rumours_between_dates","sportmonks_football_get_transfer_rumours_by_player","sportmonks_football_get_transfer_rumours_by_team","sportmonks_football_get_transfers_between_dates","sportmonks_football_get_transfers_by_player","sportmonks_football_get_transfers_by_team","sportmonks_football_get_tv_station","sportmonks_football_get_tv_stations","sportmonks_football_get_tv_stations_by_fixture","sportmonks_football_get_upcoming_fixtures_by_market","sportmonks_football_get_upcoming_fixtures_by_tv_station","sportmonks_football_get_value_bets","sportmonks_football_get_value_bets_by_fixture","sportmonks_football_get_venue","sportmonks_football_get_venues","sportmonks_football_get_venues_by_season","sportmonks_football_search_coaches","sportmonks_football_search_fixtures","sportmonks_football_search_leagues","sportmonks_football_search_players","sportmonks_football_search_referees","sportmonks_football_search_rounds","sportmonks_football_search_seasons","sportmonks_football_search_stages","sportmonks_football_search_teams","sportmonks_football_search_venues","sportmonks_motorsport_get_all_fixtures","sportmonks_motorsport_get_current_leagues_by_team","sportmonks_motorsport_get_driver","sportmonks_motorsport_get_driver_standings","sportmonks_motorsport_get_driver_standings_by_season","sportmonks_motorsport_get_drivers","sportmonks_motorsport_get_drivers_by_country","sportmonks_motorsport_get_drivers_by_season","sportmonks_motorsport_get_fixture","sportmonks_motorsport_get_fixtures_by_date","sportmonks_motorsport_get_fixtures_by_date_range","sportmonks_motorsport_get_fixtures_by_ids","sportmonks_motorsport_get_laps_by_fixture","sportmonks_motorsport_get_laps_by_fixture_and_driver","sportmonks_motorsport_get_laps_by_fixture_and_lap","sportmonks_motorsport_get_latest_laps_by_fixture","sportmonks_motorsport_get_latest_pitstops_by_fixture","sportmonks_motorsport_get_latest_stints_by_fixture","sportmonks_motorsport_get_latest_updated_drivers","sportmonks_motorsport_get_latest_updated_fixtures","sportmonks_motorsport_get_league","sportmonks_motorsport_get_leagues","sportmonks_motorsport_get_leagues_by_country","sportmonks_motorsport_get_leagues_by_date","sportmonks_motorsport_get_leagues_by_live","sportmonks_motorsport_get_leagues_by_team","sportmonks_motorsport_get_livescores","sportmonks_motorsport_get_pitstops_by_fixture","sportmonks_motorsport_get_pitstops_by_fixture_and_driver","sportmonks_motorsport_get_pitstops_by_fixture_and_lap","sportmonks_motorsport_get_race_results_by_season_and_driver","sportmonks_motorsport_get_race_results_by_season_and_team","sportmonks_motorsport_get_schedules_by_season","sportmonks_motorsport_get_season","sportmonks_motorsport_get_seasons","sportmonks_motorsport_get_stage","sportmonks_motorsport_get_stages","sportmonks_motorsport_get_stages_by_season","sportmonks_motorsport_get_state","sportmonks_motorsport_get_states","sportmonks_motorsport_get_stints_by_fixture","sportmonks_motorsport_get_stints_by_fixture_and_driver","sportmonks_motorsport_get_stints_by_fixture_and_stint","sportmonks_motorsport_get_team","sportmonks_motorsport_get_team_standings","sportmonks_motorsport_get_team_standings_by_season","sportmonks_motorsport_get_teams","sportmonks_motorsport_get_teams_by_country","sportmonks_motorsport_get_teams_by_season","sportmonks_motorsport_get_venue","sportmonks_motorsport_get_venues","sportmonks_motorsport_get_venues_by_season","sportmonks_motorsport_search_drivers","sportmonks_motorsport_search_leagues","sportmonks_motorsport_search_stages","sportmonks_motorsport_search_teams","sportmonks_motorsport_search_venues","sportmonks_odds_get_all_historical_odds","sportmonks_odds_get_all_inplay_odds","sportmonks_odds_get_all_pre_match_odds","sportmonks_odds_get_all_premium_odds","sportmonks_odds_get_bookmaker","sportmonks_odds_get_bookmaker_event_ids_by_fixture","sportmonks_odds_get_bookmakers","sportmonks_odds_get_bookmakers_by_fixture","sportmonks_odds_get_inplay_odds_by_fixture","sportmonks_odds_get_inplay_odds_by_fixture_and_bookmaker","sportmonks_odds_get_inplay_odds_by_fixture_and_market","sportmonks_odds_get_last_updated_inplay_odds","sportmonks_odds_get_last_updated_pre_match_odds","sportmonks_odds_get_market","sportmonks_odds_get_markets","sportmonks_odds_get_pre_match_odds_by_fixture","sportmonks_odds_get_pre_match_odds_by_fixture_and_bookmaker","sportmonks_odds_get_pre_match_odds_by_fixture_and_market","sportmonks_odds_get_premium_odds_by_fixture","sportmonks_odds_get_premium_odds_by_fixture_and_bookmaker","sportmonks_odds_get_premium_odds_by_fixture_and_market","sportmonks_odds_get_updated_historical_odds_between","sportmonks_odds_get_updated_premium_odds_between","sportmonks_odds_search_bookmakers","sportmonks_odds_search_markets","spotify_add_playlist_cover","spotify_add_to_queue","spotify_add_tracks_to_playlist","spotify_check_following","spotify_check_playlist_followers","spotify_check_saved_albums","spotify_check_saved_audiobooks","spotify_check_saved_episodes","spotify_check_saved_shows","spotify_check_saved_tracks","spotify_create_playlist","spotify_follow_artists","spotify_follow_playlist","spotify_get_album","spotify_get_album_tracks","spotify_get_albums","spotify_get_artist","spotify_get_artist_albums","spotify_get_artist_top_tracks","spotify_get_artists","spotify_get_audiobook","spotify_get_audiobook_chapters","spotify_get_audiobooks","spotify_get_categories","spotify_get_current_user","spotify_get_currently_playing","spotify_get_devices","spotify_get_episode","spotify_get_episodes","spotify_get_followed_artists","spotify_get_markets","spotify_get_new_releases","spotify_get_playback_state","spotify_get_playlist","spotify_get_playlist_cover","spotify_get_playlist_tracks","spotify_get_queue","spotify_get_recently_played","spotify_get_saved_albums","spotify_get_saved_audiobooks","spotify_get_saved_episodes","spotify_get_saved_shows","spotify_get_saved_tracks","spotify_get_show","spotify_get_show_episodes","spotify_get_shows","spotify_get_top_artists","spotify_get_top_tracks","spotify_get_track","spotify_get_tracks","spotify_get_user_playlists","spotify_get_user_profile","spotify_pause","spotify_play","spotify_remove_saved_albums","spotify_remove_saved_audiobooks","spotify_remove_saved_episodes","spotify_remove_saved_shows","spotify_remove_saved_tracks","spotify_remove_tracks_from_playlist","spotify_reorder_playlist_items","spotify_replace_playlist_items","spotify_save_albums","spotify_save_audiobooks","spotify_save_episodes","spotify_save_shows","spotify_save_tracks","spotify_search","spotify_seek","spotify_set_repeat","spotify_set_shuffle","spotify_set_volume","spotify_skip_next","spotify_skip_previous","spotify_transfer_playback","spotify_unfollow_artists","spotify_unfollow_playlist","spotify_update_playlist","sqs_send","square_batch_retrieve_inventory_counts","square_cancel_invoice","square_cancel_payment","square_complete_payment","square_create_catalog_image","square_create_customer","square_create_invoice","square_create_order","square_create_payment","square_delete_catalog_object","square_delete_customer","square_delete_invoice","square_get_catalog_object","square_get_customer","square_get_invoice","square_get_location","square_get_order","square_get_payment","square_get_refund","square_list_catalog","square_list_customers","square_list_invoices","square_list_locations","square_list_payments","square_list_refunds","square_pay_order","square_publish_invoice","square_refund_payment","square_search_catalog_objects","square_search_customers","square_search_invoices","square_search_orders","square_update_customer","square_upsert_catalog_object","ssh_check_command_exists","ssh_check_file_exists","ssh_create_directory","ssh_delete_file","ssh_download_file","ssh_execute_command","ssh_execute_script","ssh_get_system_info","ssh_list_directory","ssh_move_rename","ssh_read_file_content","ssh_upload_file","ssh_write_file_content","stagehand_agent","stagehand_extract","stripe_cancel_payment_intent","stripe_cancel_subscription","stripe_capture_charge","stripe_capture_payment_intent","stripe_confirm_payment_intent","stripe_create_charge","stripe_create_customer","stripe_create_invoice","stripe_create_payment_intent","stripe_create_price","stripe_create_product","stripe_create_subscription","stripe_delete_customer","stripe_delete_invoice","stripe_delete_product","stripe_finalize_invoice","stripe_list_charges","stripe_list_customers","stripe_list_events","stripe_list_invoices","stripe_list_payment_intents","stripe_list_prices","stripe_list_products","stripe_list_subscriptions","stripe_pay_invoice","stripe_resume_subscription","stripe_retrieve_charge","stripe_retrieve_customer","stripe_retrieve_event","stripe_retrieve_invoice","stripe_retrieve_payment_intent","stripe_retrieve_price","stripe_retrieve_product","stripe_retrieve_subscription","stripe_search_charges","stripe_search_customers","stripe_search_invoices","stripe_search_payment_intents","stripe_search_prices","stripe_search_products","stripe_search_subscriptions","stripe_send_invoice","stripe_update_charge","stripe_update_customer","stripe_update_invoice","stripe_update_payment_intent","stripe_update_price","stripe_update_product","stripe_update_subscription","stripe_void_invoice","sts_assume_role","sts_assume_role_with_saml","sts_assume_role_with_web_identity","sts_get_access_key_info","sts_get_caller_identity","sts_get_session_token","stt_assemblyai","stt_assemblyai_v2","stt_deepgram","stt_deepgram_v2","stt_elevenlabs","stt_elevenlabs_v2","stt_gemini","stt_gemini_v2","stt_whisper","stt_whisper_v2","supabase_count","supabase_delete","supabase_get_row","supabase_insert","supabase_introspect","supabase_invoke_function","supabase_query","supabase_rpc","supabase_storage_copy","supabase_storage_create_bucket","supabase_storage_create_signed_upload_url","supabase_storage_create_signed_url","supabase_storage_delete","supabase_storage_delete_bucket","supabase_storage_download","supabase_storage_empty_bucket","supabase_storage_get_public_url","supabase_storage_list","supabase_storage_list_buckets","supabase_storage_move","supabase_storage_update_bucket","supabase_storage_upload","supabase_text_search","supabase_update","supabase_upsert","supabase_vector_search","table_batch_insert_rows","table_create","table_delete_row","table_delete_rows_by_filter","table_get_row","table_get_schema","table_insert_row","table_list","table_query_rows","table_query_rows_v2","table_update_row","table_update_rows_by_filter","table_upsert_row","tailscale_authorize_device","tailscale_create_auth_key","tailscale_delete_auth_key","tailscale_delete_device","tailscale_delete_user","tailscale_expire_device_key","tailscale_get_acl","tailscale_get_auth_key","tailscale_get_device","tailscale_get_device_routes","tailscale_get_dns_preferences","tailscale_get_dns_searchpaths","tailscale_list_auth_keys","tailscale_list_devices","tailscale_list_dns_nameservers","tailscale_list_users","tailscale_set_acl","tailscale_set_device_routes","tailscale_set_device_tags","tailscale_set_dns_nameservers","tailscale_set_dns_preferences","tailscale_set_dns_searchpaths","tailscale_suspend_user","tailscale_update_device_key","tavily_crawl","tavily_extract","tavily_map","tavily_search","telegram_copy_message","telegram_delete_message","telegram_edit_message_text","telegram_forward_message","telegram_get_chat","telegram_get_chat_member","telegram_message","telegram_pin_message","telegram_send_animation","telegram_send_audio","telegram_send_chat_action","telegram_send_contact","telegram_send_document","telegram_send_location","telegram_send_photo","telegram_send_poll","telegram_send_video","telegram_set_message_reaction","telegram_unpin_message","temporal_cancel_workflow","temporal_count_workflows","temporal_create_schedule","temporal_delete_schedule","temporal_describe_schedule","temporal_describe_task_queue","temporal_describe_workflow","temporal_get_workflow_history","temporal_list_schedules","temporal_list_workflows","temporal_pause_schedule","temporal_query_workflow","temporal_reset_workflow","temporal_signal_with_start","temporal_signal_workflow","temporal_start_workflow","temporal_terminate_workflow","temporal_trigger_schedule","temporal_unpause_schedule","temporal_update_workflow","textract_analyze_expense","textract_analyze_id","textract_parser","textract_parser_v2","thinking_tool","thrive_add_audience_managers","thrive_add_audience_members","thrive_add_user_tags","thrive_create_assignment","thrive_create_audience","thrive_create_completion","thrive_create_user","thrive_delete_assignment","thrive_delete_audience","thrive_delete_user","thrive_get_activity","thrive_get_assignment","thrive_get_audience","thrive_get_completion","thrive_get_content","thrive_get_cpd_category","thrive_get_cpd_entry","thrive_get_cpd_requirement","thrive_get_enrolment","thrive_get_skill_levels","thrive_get_tag","thrive_get_user_by_id","thrive_get_user_by_ref","thrive_list_assignments","thrive_list_audience_managers","thrive_list_audience_members","thrive_list_audiences","thrive_list_completions","thrive_list_enrolments","thrive_list_tags","thrive_query_activities","thrive_query_content","thrive_query_cpd_categories","thrive_query_cpd_entries","thrive_query_cpd_requirements","thrive_query_cpd_user_summaries","thrive_remove_audience_manager","thrive_remove_audience_member","thrive_remove_user_tags","thrive_replace_audience_managers","thrive_replace_audience_members","thrive_search_users","thrive_suspend_user","thrive_update_assignment","thrive_update_audience","thrive_update_user","thrive_update_user_skills","tiktok_get_post_status","tiktok_get_user","tiktok_list_videos","tiktok_query_videos","tiktok_upload_video_draft","tinybird_append_datasource","tinybird_delete_datasource_rows","tinybird_events","tinybird_get_job","tinybird_query","tinybird_query_pipe","tinybird_truncate_datasource","trello_add_checklist","trello_add_checklist_item","trello_add_comment","trello_add_label","trello_add_member","trello_create_board","trello_create_card","trello_create_list","trello_delete_card","trello_get_actions","trello_get_board","trello_get_card","trello_list_cards","trello_list_lists","trello_list_members","trello_remove_label","trello_remove_member","trello_search","trello_update_card","trello_update_checklist_item","trello_update_list","trigger_dev_activate_schedule","trigger_dev_add_run_tags","trigger_dev_batch_trigger_task","trigger_dev_cancel_run","trigger_dev_complete_waitpoint_token","trigger_dev_create_env_var","trigger_dev_create_schedule","trigger_dev_create_waitpoint_token","trigger_dev_deactivate_schedule","trigger_dev_delete_env_var","trigger_dev_delete_schedule","trigger_dev_execute_query","trigger_dev_get_batch","trigger_dev_get_batch_results","trigger_dev_get_deployment","trigger_dev_get_env_var","trigger_dev_get_latest_deployment","trigger_dev_get_query_schema","trigger_dev_get_queue","trigger_dev_get_run","trigger_dev_get_run_events","trigger_dev_get_run_result","trigger_dev_get_run_trace","trigger_dev_get_schedule","trigger_dev_get_waitpoint_token","trigger_dev_import_env_vars","trigger_dev_list_deployments","trigger_dev_list_env_vars","trigger_dev_list_queues","trigger_dev_list_runs","trigger_dev_list_schedules","trigger_dev_list_timezones","trigger_dev_list_waitpoint_tokens","trigger_dev_override_queue_concurrency","trigger_dev_pause_queue","trigger_dev_promote_deployment","trigger_dev_replay_run","trigger_dev_reschedule_run","trigger_dev_reset_queue_concurrency","trigger_dev_resume_queue","trigger_dev_trigger_task","trigger_dev_update_env_var","trigger_dev_update_run_metadata","trigger_dev_update_schedule","tts_azure","tts_cartesia","tts_deepgram","tts_elevenlabs","tts_google","tts_openai","tts_playht","twilio_send_sms","twilio_voice_get_recording","twilio_voice_list_calls","twilio_voice_make_call","typeform_create_form","typeform_delete_form","typeform_files","typeform_get_form","typeform_insights","typeform_list_forms","typeform_responses","typeform_update_form","upstash_redis_command","upstash_redis_delete","upstash_redis_exists","upstash_redis_expire","upstash_redis_get","upstash_redis_hget","upstash_redis_hgetall","upstash_redis_hset","upstash_redis_incr","upstash_redis_incrby","upstash_redis_keys","upstash_redis_lpush","upstash_redis_lrange","upstash_redis_set","upstash_redis_setnx","upstash_redis_ttl","uptimerobot_create_alert_contact","uptimerobot_create_maintenance_window","uptimerobot_create_monitor","uptimerobot_create_psp","uptimerobot_delete_alert_contact","uptimerobot_delete_maintenance_window","uptimerobot_delete_monitor","uptimerobot_delete_psp","uptimerobot_get_account","uptimerobot_get_alert_contact","uptimerobot_get_incident","uptimerobot_get_maintenance_window","uptimerobot_get_monitor","uptimerobot_get_psp","uptimerobot_list_alert_contacts","uptimerobot_list_incidents","uptimerobot_list_maintenance_windows","uptimerobot_list_monitors","uptimerobot_list_psps","uptimerobot_pause_monitor","uptimerobot_start_monitor","uptimerobot_update_maintenance_window","uptimerobot_update_monitor","uptimerobot_update_psp","vanta_download_document_file","vanta_get_control","vanta_get_document","vanta_get_framework","vanta_get_person","vanta_get_policy","vanta_get_risk_scenario","vanta_get_test","vanta_get_vendor","vanta_get_vulnerable_asset","vanta_list_control_documents","vanta_list_control_tests","vanta_list_controls","vanta_list_document_uploads","vanta_list_documents","vanta_list_framework_controls","vanta_list_frameworks","vanta_list_monitored_computers","vanta_list_people","vanta_list_policies","vanta_list_risk_scenarios","vanta_list_test_entities","vanta_list_tests","vanta_list_vendors","vanta_list_vulnerabilities","vanta_list_vulnerability_remediations","vanta_list_vulnerable_assets","vanta_submit_document","vanta_upload_document_file","vercel_add_domain","vercel_add_project_domain","vercel_cancel_deployment","vercel_create_alias","vercel_create_check","vercel_create_deployment","vercel_create_dns_record","vercel_create_edge_config","vercel_create_env_var","vercel_create_project","vercel_create_webhook","vercel_delete_alias","vercel_delete_deployment","vercel_delete_dns_record","vercel_delete_domain","vercel_delete_edge_config","vercel_delete_env_var","vercel_delete_project","vercel_delete_webhook","vercel_get_alias","vercel_get_check","vercel_get_deployment","vercel_get_deployment_events","vercel_get_domain","vercel_get_domain_config","vercel_get_edge_config","vercel_get_edge_config_items","vercel_get_env_vars","vercel_get_project","vercel_get_team","vercel_get_user","vercel_get_webhook","vercel_list_aliases","vercel_list_checks","vercel_list_deployment_files","vercel_list_deployments","vercel_list_dns_records","vercel_list_domains","vercel_list_edge_configs","vercel_list_project_domains","vercel_list_projects","vercel_list_team_members","vercel_list_teams","vercel_list_webhooks","vercel_pause_project","vercel_promote_deployment","vercel_remove_project_domain","vercel_rerequest_check","vercel_unpause_project","vercel_update_check","vercel_update_dns_record","vercel_update_edge_config_items","vercel_update_env_var","vercel_update_project","vercel_update_project_domain","vercel_verify_project_domain","video_falai","video_luma","video_minimax","video_runway","video_veo","vision_tool","vision_tool_v2","wealthbox_read_contact","wealthbox_read_note","wealthbox_read_task","wealthbox_write_contact","wealthbox_write_note","wealthbox_write_task","webflow_create_item","webflow_delete_item","webflow_get_item","webflow_list_items","webflow_update_item","webhook_request","whatsapp_get_media","whatsapp_mark_read","whatsapp_send_interactive","whatsapp_send_media","whatsapp_send_message","whatsapp_send_reaction","whatsapp_send_template","whatsapp_upload_media","wikipedia_content","wikipedia_random","wikipedia_search","wikipedia_summary","windchill_check_in_document","windchill_check_in_documents","windchill_check_out_document","windchill_check_out_documents","windchill_create_document","windchill_create_documents","windchill_delete_document","windchill_delete_documents","windchill_download_attachment","windchill_download_primary_content","windchill_get_document","windchill_get_document_structure","windchill_get_primary_content","windchill_get_valid_state_transitions","windchill_list_attachments","windchill_list_documents","windchill_revise_document","windchill_revise_documents","windchill_set_lifecycle_state","windchill_undo_check_out_document","windchill_undo_check_out_documents","windchill_update_common_properties","windchill_update_document","windchill_update_document_security_labels","windchill_update_documents","windchill_upload_attachments","windchill_upload_primary_content","wiza_company_enrichment","wiza_get_credits","wiza_individual_reveal","wiza_prospect_search","wordpress_create_category","wordpress_create_comment","wordpress_create_page","wordpress_create_post","wordpress_create_tag","wordpress_delete_category","wordpress_delete_comment","wordpress_delete_media","wordpress_delete_page","wordpress_delete_post","wordpress_delete_tag","wordpress_get_category","wordpress_get_current_user","wordpress_get_media","wordpress_get_page","wordpress_get_post","wordpress_get_tag","wordpress_get_user","wordpress_list_categories","wordpress_list_comments","wordpress_list_media","wordpress_list_pages","wordpress_list_posts","wordpress_list_tags","wordpress_list_users","wordpress_search_content","wordpress_update_category","wordpress_update_comment","wordpress_update_page","wordpress_update_post","wordpress_update_tag","wordpress_upload_media","workday_assign_onboarding","workday_change_job","workday_create_prehire","workday_get_compensation","workday_get_organizations","workday_get_worker","workday_hire_employee","workday_list_workers","workday_terminate_worker","workday_update_worker","workflow_executor","x_create_bookmark","x_create_tweet","x_delete_bookmark","x_delete_tweet","x_get_blocking","x_get_bookmarks","x_get_followers","x_get_following","x_get_liked_tweets","x_get_liking_users","x_get_me","x_get_personalized_trends","x_get_quote_tweets","x_get_retweeted_by","x_get_trends_by_woeid","x_get_tweets_by_ids","x_get_usage","x_get_user_mentions","x_get_user_timeline","x_get_user_tweets","x_hide_reply","x_manage_block","x_manage_follow","x_manage_like","x_manage_mute","x_manage_retweet","x_read","x_search","x_search_tweets","x_search_users","x_user","x_write","youtube_channel_info","youtube_channel_playlists","youtube_channel_videos","youtube_comments","youtube_playlist_items","youtube_search","youtube_trending","youtube_video_categories","youtube_video_details","zendesk_autocomplete_organizations","zendesk_create_organization","zendesk_create_organizations_bulk","zendesk_create_ticket","zendesk_create_tickets_bulk","zendesk_create_user","zendesk_create_users_bulk","zendesk_delete_organization","zendesk_delete_ticket","zendesk_delete_user","zendesk_get_current_user","zendesk_get_organization","zendesk_get_organizations","zendesk_get_ticket","zendesk_get_tickets","zendesk_get_user","zendesk_get_users","zendesk_merge_tickets","zendesk_search","zendesk_search_count","zendesk_search_users","zendesk_update_organization","zendesk_update_ticket","zendesk_update_tickets_bulk","zendesk_update_user","zendesk_update_users_bulk","zep_add_messages","zep_add_user","zep_create_thread","zep_delete_thread","zep_get_context","zep_get_messages","zep_get_threads","zep_get_user","zep_get_user_threads","zerobounce_get_credits","zerobounce_verify_email","zoho_desk_add_comment","zoho_desk_get_attachment","zoho_desk_get_contact","zoho_desk_get_thread","zoho_desk_get_ticket","zoho_desk_list_comments","zoho_desk_list_organizations","zoho_desk_list_threads","zoho_desk_list_tickets","zoho_desk_update_ticket","zoom_create_meeting","zoom_delete_meeting","zoom_delete_recording","zoom_get_meeting","zoom_get_meeting_invitation","zoom_get_meeting_recordings","zoom_list_meetings","zoom_list_past_participants","zoom_list_recordings","zoom_update_meeting","zoominfo_enrich_companies","zoominfo_enrich_contacts","zoominfo_search_companies","zoominfo_search_contacts","zoominfo_search_intent","zoominfo_search_news"]' + '["a2a_cancel_task","a2a_get_agent_card","a2a_get_task","a2a_send_message","agentmail_create_draft","agentmail_create_inbox","agentmail_delete_draft","agentmail_delete_inbox","agentmail_delete_thread","agentmail_forward_message","agentmail_get_draft","agentmail_get_inbox","agentmail_get_message","agentmail_get_thread","agentmail_list_drafts","agentmail_list_inboxes","agentmail_list_messages","agentmail_list_threads","agentmail_reply_message","agentmail_send_draft","agentmail_send_message","agentmail_update_draft","agentmail_update_inbox","agentmail_update_message","agentmail_update_thread","agentphone_create_call","agentphone_create_contact","agentphone_create_number","agentphone_delete_contact","agentphone_get_call","agentphone_get_call_transcript","agentphone_get_contact","agentphone_get_conversation","agentphone_get_conversation_messages","agentphone_get_number_messages","agentphone_get_usage","agentphone_get_usage_daily","agentphone_get_usage_monthly","agentphone_list_calls","agentphone_list_contacts","agentphone_list_conversations","agentphone_list_numbers","agentphone_react_to_message","agentphone_release_number","agentphone_send_message","agentphone_update_contact","agentphone_update_conversation","agiloft_async_status","agiloft_attach_file","agiloft_attachment_info","agiloft_create_record","agiloft_delete_record","agiloft_get_choice_line_id","agiloft_list_tables","agiloft_lock_record","agiloft_nlp_search","agiloft_read_record","agiloft_remove_attachment","agiloft_retrieve_attachment","agiloft_run_action_button","agiloft_saved_search","agiloft_search_records","agiloft_select_records","agiloft_update_record","agiloft_upsert_record","ahrefs_anchors","ahrefs_backlinks","ahrefs_backlinks_stats","ahrefs_batch_analysis","ahrefs_broken_backlinks","ahrefs_domain_rating","ahrefs_domain_rating_history","ahrefs_keyword_overview","ahrefs_keywords_history","ahrefs_metrics","ahrefs_metrics_history","ahrefs_organic_competitors","ahrefs_organic_keywords","ahrefs_paid_pages","ahrefs_rank_tracker_competitors_overview","ahrefs_rank_tracker_competitors_stats","ahrefs_rank_tracker_overview","ahrefs_rank_tracker_serp_overview","ahrefs_refdomains_history","ahrefs_referring_domains","ahrefs_related_terms","ahrefs_site_audit_page_explorer","ahrefs_top_pages","airtable_create_records","airtable_delete_records","airtable_get_base_schema","airtable_get_record","airtable_list_bases","airtable_list_records","airtable_list_tables","airtable_update_multiple_records","airtable_update_record","airtable_upsert_records","airweave_search","algolia_add_record","algolia_batch_operations","algolia_browse_records","algolia_clear_records","algolia_copy_move_index","algolia_delete_by_filter","algolia_delete_index","algolia_delete_record","algolia_get_record","algolia_get_records","algolia_get_settings","algolia_get_task_status","algolia_list_indices","algolia_partial_update_record","algolia_search","algolia_update_settings","amplitude_event_segmentation","amplitude_funnels","amplitude_get_active_users","amplitude_get_revenue","amplitude_group_identify","amplitude_identify_user","amplitude_list_events","amplitude_realtime_active_users","amplitude_retention","amplitude_send_event","amplitude_user_activity","amplitude_user_profile","amplitude_user_search","apify_get_dataset_items","apify_get_run","apify_run_actor_async","apify_run_actor_sync","apify_run_task","apollo_account_bulk_create","apollo_account_bulk_update","apollo_account_create","apollo_account_search","apollo_account_update","apollo_contact_bulk_create","apollo_contact_bulk_update","apollo_contact_create","apollo_contact_search","apollo_contact_update","apollo_email_accounts","apollo_opportunity_create","apollo_opportunity_get","apollo_opportunity_search","apollo_opportunity_update","apollo_organization_bulk_enrich","apollo_organization_enrich","apollo_organization_search","apollo_people_bulk_enrich","apollo_people_enrich","apollo_people_search","apollo_sequence_add_contacts","apollo_sequence_search","apollo_task_create","apollo_task_search","appconfig_create_application","appconfig_create_configuration_profile","appconfig_create_environment","appconfig_create_hosted_configuration_version","appconfig_delete_application","appconfig_delete_configuration_profile","appconfig_delete_environment","appconfig_delete_hosted_configuration_version","appconfig_get_application","appconfig_get_configuration","appconfig_get_configuration_profile","appconfig_get_deployment","appconfig_get_environment","appconfig_get_hosted_configuration_version","appconfig_list_applications","appconfig_list_configuration_profiles","appconfig_list_deployment_strategies","appconfig_list_deployments","appconfig_list_environments","appconfig_list_hosted_configuration_versions","appconfig_start_deployment","appconfig_stop_deployment","appconfig_update_application","appconfig_update_configuration_profile","appconfig_update_environment","arxiv_get_author_papers","arxiv_get_paper","arxiv_search","asana_add_comment","asana_add_followers","asana_create_project","asana_create_section","asana_create_subtask","asana_create_task","asana_delete_task","asana_get_project","asana_get_projects","asana_get_task","asana_list_sections","asana_list_workspaces","asana_search_tasks","asana_update_task","ashby_add_candidate_tag","ashby_anonymize_candidate","ashby_change_application_source","ashby_change_application_stage","ashby_create_application","ashby_create_candidate","ashby_create_note","ashby_delete_application","ashby_get_application","ashby_get_candidate","ashby_get_job","ashby_get_job_posting","ashby_get_offer","ashby_list_applications","ashby_list_archive_reasons","ashby_list_candidate_tags","ashby_list_candidates","ashby_list_custom_fields","ashby_list_departments","ashby_list_interviews","ashby_list_job_postings","ashby_list_jobs","ashby_list_locations","ashby_list_notes","ashby_list_offers","ashby_list_openings","ashby_list_sources","ashby_list_users","ashby_remove_candidate_tag","ashby_search_candidates","ashby_set_custom_field_value","ashby_set_custom_field_values","ashby_update_candidate","athena_batch_get_query_execution","athena_create_named_query","athena_delete_named_query","athena_get_named_query","athena_get_query_execution","athena_get_query_results","athena_list_databases","athena_list_named_queries","athena_list_query_executions","athena_list_table_metadata","athena_start_query","athena_stop_query","attio_assert_record","attio_create_attribute","attio_create_comment","attio_create_list","attio_create_list_entry","attio_create_note","attio_create_object","attio_create_record","attio_create_task","attio_create_webhook","attio_delete_comment","attio_delete_list_entry","attio_delete_note","attio_delete_record","attio_delete_task","attio_delete_webhook","attio_get_attribute","attio_get_comment","attio_get_list","attio_get_list_entry","attio_get_member","attio_get_note","attio_get_object","attio_get_record","attio_get_task","attio_get_thread","attio_get_webhook","attio_list_attributes","attio_list_lists","attio_list_members","attio_list_notes","attio_list_objects","attio_list_records","attio_list_tasks","attio_list_threads","attio_list_webhooks","attio_query_list_entries","attio_search_records","attio_update_attribute","attio_update_list","attio_update_list_entry","attio_update_object","attio_update_record","attio_update_task","attio_update_webhook","azure_data_explorer_create_table","azure_data_explorer_drop_table","azure_data_explorer_ingest_from_query","azure_data_explorer_ingest_inline","azure_data_explorer_list_databases","azure_data_explorer_list_functions","azure_data_explorer_list_tables","azure_data_explorer_management","azure_data_explorer_query","azure_data_explorer_show_database_schema","azure_data_explorer_show_ingestion_failures","azure_data_explorer_show_operations","azure_data_explorer_show_table_details","azure_data_explorer_show_table_schema","azure_devops_add_comment","azure_devops_create_work_item","azure_devops_get_build_log","azure_devops_get_build_timeline","azure_devops_get_comments","azure_devops_get_pipeline","azure_devops_get_pipeline_run","azure_devops_get_work_item","azure_devops_get_work_items_batch","azure_devops_get_work_items_between_builds","azure_devops_list_build_logs","azure_devops_list_builds","azure_devops_list_pipeline_runs","azure_devops_list_pipelines","azure_devops_query_work_items","azure_devops_update_work_item","box_copy_file","box_create_folder","box_delete_file","box_delete_folder","box_download_file","box_get_file_info","box_list_folder_items","box_search","box_sign_cancel_request","box_sign_create_request","box_sign_get_request","box_sign_list_requests","box_sign_resend_request","box_update_file","box_upload_file","brandfetch_get_brand","brandfetch_search","brex_archive_budget","brex_create_budget","brex_create_spend_limit","brex_create_transfer","brex_create_vendor","brex_get_budget","brex_get_cash_account","brex_get_company","brex_get_current_user","brex_get_expense","brex_get_spend_limit","brex_get_transfer","brex_get_user","brex_get_vendor","brex_list_budgets","brex_list_card_accounts","brex_list_card_statements","brex_list_card_transactions","brex_list_cards","brex_list_cash_accounts","brex_list_cash_statements","brex_list_cash_transactions","brex_list_departments","brex_list_expenses","brex_list_locations","brex_list_spend_limits","brex_list_titles","brex_list_transfers","brex_list_users","brex_list_vendors","brex_match_receipt","brex_update_expense","brex_update_vendor","brex_upload_receipt","brightdata_cancel_snapshot","brightdata_discover","brightdata_download_snapshot","brightdata_scrape_dataset","brightdata_scrape_url","brightdata_serp_search","brightdata_snapshot_status","brightdata_sync_scrape","browser_use_run_task","buffer_create_idea","buffer_create_post","buffer_delete_post","buffer_edit_post","buffer_get_account","buffer_get_channels","buffer_get_idea_groups","buffer_get_ideas","buffer_get_post","buffer_get_posts","calcom_cancel_booking","calcom_confirm_booking","calcom_create_booking","calcom_create_event_type","calcom_create_schedule","calcom_decline_booking","calcom_delete_event_type","calcom_delete_schedule","calcom_get_booking","calcom_get_default_schedule","calcom_get_event_type","calcom_get_schedule","calcom_get_slots","calcom_list_bookings","calcom_list_event_types","calcom_list_schedules","calcom_reschedule_booking","calcom_update_event_type","calcom_update_schedule","calendly_cancel_event","calendly_create_event_invitee","calendly_create_invitee_no_show","calendly_create_scheduling_link","calendly_create_webhook","calendly_delete_invitee_no_show","calendly_delete_webhook","calendly_get_current_user","calendly_get_event_invitee","calendly_get_event_type","calendly_get_scheduled_event","calendly_get_user","calendly_list_event_invitees","calendly_list_event_type_available_times","calendly_list_event_types","calendly_list_organization_memberships","calendly_list_routing_form_submissions","calendly_list_routing_forms","calendly_list_scheduled_events","calendly_list_user_availability_schedules","calendly_list_user_busy_times","calendly_list_webhooks","clay_populate","clerk_add_organization_member","clerk_ban_user","clerk_create_actor_token","clerk_create_allowlist_identifier","clerk_create_blocklist_identifier","clerk_create_organization","clerk_create_organization_invitation","clerk_create_user","clerk_delete_allowlist_identifier","clerk_delete_blocklist_identifier","clerk_delete_organization","clerk_delete_user","clerk_get_jwt_template","clerk_get_organization","clerk_get_session","clerk_get_user","clerk_get_user_oauth_token","clerk_list_allowlist_identifiers","clerk_list_blocklist_identifiers","clerk_list_jwt_templates","clerk_list_organization_invitations","clerk_list_organization_memberships","clerk_list_organizations","clerk_list_sessions","clerk_list_users","clerk_lock_user","clerk_remove_organization_member","clerk_revoke_actor_token","clerk_revoke_session","clerk_unban_user","clerk_unlock_user","clerk_update_organization","clerk_update_organization_membership","clerk_update_user","clickhouse_count_rows","clickhouse_create_database","clickhouse_create_table","clickhouse_delete","clickhouse_describe_table","clickhouse_drop_database","clickhouse_drop_partition","clickhouse_drop_table","clickhouse_execute","clickhouse_insert","clickhouse_insert_rows","clickhouse_introspect","clickhouse_kill_query","clickhouse_list_clusters","clickhouse_list_databases","clickhouse_list_mutations","clickhouse_list_partitions","clickhouse_list_running_queries","clickhouse_list_tables","clickhouse_optimize_table","clickhouse_query","clickhouse_rename_table","clickhouse_show_create_table","clickhouse_table_stats","clickhouse_truncate_table","clickhouse_update","clickup_add_tag_to_task","clickup_create_checklist","clickup_create_checklist_item","clickup_create_comment","clickup_create_folder","clickup_create_list","clickup_create_task","clickup_create_time_entry","clickup_delete_checklist","clickup_delete_checklist_item","clickup_delete_comment","clickup_delete_task","clickup_delete_time_entry","clickup_get_comments","clickup_get_custom_fields","clickup_get_folders","clickup_get_list_members","clickup_get_lists","clickup_get_running_timer","clickup_get_space_tags","clickup_get_spaces","clickup_get_task","clickup_get_task_members","clickup_get_tasks","clickup_get_time_entries","clickup_get_workspaces","clickup_remove_custom_field_value","clickup_remove_tag_from_task","clickup_search_tasks","clickup_set_custom_field_value","clickup_start_timer","clickup_stop_timer","clickup_update_checklist","clickup_update_checklist_item","clickup_update_comment","clickup_update_task","clickup_update_time_entry","clickup_upload_attachment","cloudflare_create_dns_record","cloudflare_create_zone","cloudflare_delete_dns_record","cloudflare_delete_zone","cloudflare_dns_analytics","cloudflare_get_zone","cloudflare_get_zone_settings","cloudflare_list_certificates","cloudflare_list_dns_records","cloudflare_list_zones","cloudflare_purge_cache","cloudflare_update_dns_record","cloudflare_update_zone_setting","cloudformation_cancel_update_stack","cloudformation_create_change_set","cloudformation_create_stack","cloudformation_delete_stack","cloudformation_describe_change_set","cloudformation_describe_stack_drift_detection_status","cloudformation_describe_stack_events","cloudformation_describe_stacks","cloudformation_detect_stack_drift","cloudformation_execute_change_set","cloudformation_get_template","cloudformation_get_template_summary","cloudformation_list_stack_resources","cloudformation_update_stack","cloudformation_validate_template","cloudwatch_describe_alarm_history","cloudwatch_describe_alarms","cloudwatch_describe_log_groups","cloudwatch_describe_log_streams","cloudwatch_filter_log_events","cloudwatch_get_log_events","cloudwatch_get_metric_statistics","cloudwatch_list_metrics","cloudwatch_mute_alarm","cloudwatch_put_log_group_retention","cloudwatch_put_metric_data","cloudwatch_query_logs","cloudwatch_unmute_alarm","codepipeline_disable_stage_transition","codepipeline_enable_stage_transition","codepipeline_get_pipeline","codepipeline_get_pipeline_execution","codepipeline_get_pipeline_state","codepipeline_list_action_executions","codepipeline_list_pipeline_executions","codepipeline_list_pipelines","codepipeline_put_approval_result","codepipeline_retry_stage_execution","codepipeline_start_execution","codepipeline_stop_execution","confluence_add_label","confluence_create_blogpost","confluence_create_comment","confluence_create_page","confluence_create_page_property","confluence_create_space","confluence_create_space_property","confluence_delete_attachment","confluence_delete_blogpost","confluence_delete_comment","confluence_delete_label","confluence_delete_page","confluence_delete_page_property","confluence_delete_space","confluence_delete_space_property","confluence_get_blogpost","confluence_get_page_ancestors","confluence_get_page_children","confluence_get_page_descendants","confluence_get_page_version","confluence_get_pages_by_label","confluence_get_space","confluence_get_task","confluence_get_user","confluence_list_attachments","confluence_list_blogposts","confluence_list_blogposts_in_space","confluence_list_comments","confluence_list_labels","confluence_list_page_properties","confluence_list_page_versions","confluence_list_pages_in_space","confluence_list_space_labels","confluence_list_space_permissions","confluence_list_space_properties","confluence_list_spaces","confluence_list_tasks","confluence_retrieve","confluence_search","confluence_search_in_space","confluence_update","confluence_update_blogpost","confluence_update_comment","confluence_update_space","confluence_update_task","confluence_upload_attachment","context_dev_classify_naics","context_dev_classify_sic","context_dev_crawl","context_dev_extract","context_dev_extract_product","context_dev_extract_products","context_dev_get_brand","context_dev_get_brand_by_email","context_dev_get_brand_by_name","context_dev_get_brand_by_ticker","context_dev_identify_transaction","context_dev_map","context_dev_scrape_fonts","context_dev_scrape_html","context_dev_scrape_images","context_dev_scrape_markdown","context_dev_scrape_styleguide","context_dev_screenshot","context_dev_search","convex_action","convex_document_deltas","convex_list_documents","convex_list_tables","convex_mutation","convex_query","convex_run_function","crowdstrike_create_indicators","crowdstrike_delete_indicators","crowdstrike_delete_rtr_session","crowdstrike_execute_rtr_command","crowdstrike_get_alert_details","crowdstrike_get_case_details","crowdstrike_get_host_group_details","crowdstrike_get_indicator_details","crowdstrike_get_rtr_command_status","crowdstrike_get_sensor_aggregates","crowdstrike_get_sensor_details","crowdstrike_get_vulnerability_details","crowdstrike_init_rtr_session","crowdstrike_perform_host_action","crowdstrike_perform_host_group_action","crowdstrike_query_alerts","crowdstrike_query_cases","crowdstrike_query_host_groups","crowdstrike_query_indicators","crowdstrike_query_sensors","crowdstrike_query_vulnerabilities","crowdstrike_update_alerts","crowdstrike_update_indicators","cursor_add_followup","cursor_add_followup_v2","cursor_delete_agent","cursor_delete_agent_v2","cursor_download_artifact","cursor_download_artifact_v2","cursor_get_agent","cursor_get_agent_v2","cursor_get_api_key_info","cursor_get_api_key_info_v2","cursor_get_conversation","cursor_get_conversation_v2","cursor_launch_agent","cursor_launch_agent_v2","cursor_list_agents","cursor_list_agents_v2","cursor_list_artifacts","cursor_list_artifacts_v2","cursor_list_models","cursor_list_models_v2","cursor_list_repositories","cursor_list_repositories_v2","cursor_stop_agent","cursor_stop_agent_v2","dagster_delete_run","dagster_get_asset","dagster_get_run","dagster_get_run_logs","dagster_launch_run","dagster_list_assets","dagster_list_jobs","dagster_list_runs","dagster_list_schedules","dagster_list_sensors","dagster_materialize_assets","dagster_reexecute_run","dagster_report_asset_materialization","dagster_start_schedule","dagster_start_sensor","dagster_stop_schedule","dagster_stop_sensor","dagster_terminate_run","dagster_wipe_asset","databricks_cancel_run","databricks_execute_sql","databricks_get_cluster","databricks_get_job","databricks_get_run","databricks_get_run_output","databricks_get_statement","databricks_list_clusters","databricks_list_jobs","databricks_list_runs","databricks_list_warehouses","databricks_run_job","datadog_add_incident_todo","datadog_cancel_downtime","datadog_create_dashboard","datadog_create_downtime","datadog_create_event","datadog_create_incident","datadog_create_monitor","datadog_create_slo","datadog_delete_dashboard","datadog_delete_slo","datadog_get_browser_synthetics_results","datadog_get_dashboard","datadog_get_incident","datadog_get_monitor","datadog_get_security_signal","datadog_get_slo","datadog_get_slo_history","datadog_get_synthetics_results","datadog_get_synthetics_test","datadog_list_dashboards","datadog_list_downtimes","datadog_list_incidents","datadog_list_monitors","datadog_list_security_rules","datadog_list_security_signals","datadog_list_services","datadog_list_slos","datadog_list_synthetics_tests","datadog_mute_monitor","datadog_query_logs","datadog_query_timeseries","datadog_search_spans","datadog_send_logs","datadog_submit_metrics","datadog_trigger_synthetics_tests","datadog_unmute_monitor","datadog_update_incident","datadog_update_security_signal_assignee","datadog_update_security_signal_state","datadog_update_slo","datadog_update_synthetics_status","datagma_enrich_company","datagma_enrich_person","datagma_find_email","datagma_find_phone","datagma_get_credits","daytona_create_sandbox","daytona_delete_sandbox","daytona_download_file","daytona_execute_command","daytona_get_sandbox","daytona_git_clone","daytona_list_files","daytona_list_sandboxes","daytona_run_code","daytona_start_sandbox","daytona_stop_sandbox","daytona_upload_file","deployed_block_executor","deployments_deploy","deployments_get_version","deployments_list_versions","deployments_promote","deployments_undeploy","devin_append_session_tags","devin_archive_session","devin_create_session","devin_get_session","devin_get_session_tags","devin_list_session_attachments","devin_list_session_messages","devin_list_sessions","devin_replace_session_tags","devin_send_message","devin_terminate_session","discord_add_reaction","discord_archive_thread","discord_assign_role","discord_ban_member","discord_bulk_delete_messages","discord_create_channel","discord_create_invite","discord_create_role","discord_create_thread","discord_create_webhook","discord_delete_channel","discord_delete_invite","discord_delete_message","discord_delete_role","discord_delete_webhook","discord_edit_message","discord_execute_webhook","discord_get_channel","discord_get_invite","discord_get_member","discord_get_messages","discord_get_pinned_messages","discord_get_server","discord_get_user","discord_get_webhook","discord_join_thread","discord_kick_member","discord_leave_thread","discord_list_channels","discord_list_roles","discord_pin_message","discord_remove_reaction","discord_remove_role","discord_send_message","discord_unban_member","discord_unpin_message","discord_update_channel","discord_update_member","discord_update_role","docusign_create_from_template","docusign_download_document","docusign_get_envelope","docusign_list_envelopes","docusign_list_recipients","docusign_list_templates","docusign_send_envelope","docusign_void_envelope","downdetector_get_company","downdetector_get_company_attribution","downdetector_get_company_baseline","downdetector_get_company_events","downdetector_get_company_incidents","downdetector_get_company_indicators","downdetector_get_company_last_15","downdetector_get_company_status","downdetector_get_provider","downdetector_get_reports","downdetector_get_site_companies","downdetector_list_categories","downdetector_list_incidents","downdetector_list_sites","downdetector_search_companies","dropbox_copy","dropbox_create_folder","dropbox_create_shared_link","dropbox_delete","dropbox_download","dropbox_get_metadata","dropbox_list_folder","dropbox_list_revisions","dropbox_list_shared_links","dropbox_move","dropbox_restore","dropbox_search","dropbox_upload","dropcontact_enrich_contact","dspy_chain_of_thought","dspy_predict","dspy_react","dub_bulk_create_links","dub_bulk_delete_links","dub_bulk_update_links","dub_create_link","dub_create_tag","dub_delete_link","dub_get_analytics","dub_get_events","dub_get_link","dub_get_links_count","dub_get_qr_code","dub_list_domains","dub_list_folders","dub_list_links","dub_list_tags","dub_update_link","dub_upsert_link","duckduckgo_search","dynamodb_delete","dynamodb_get","dynamodb_introspect","dynamodb_put","dynamodb_query","dynamodb_scan","dynamodb_update","dynatrace_add_problem_comment","dynatrace_add_tags","dynatrace_close_problem","dynatrace_create_settings_object","dynatrace_create_slo","dynatrace_delete_problem_comment","dynatrace_delete_settings_object","dynatrace_delete_slo","dynatrace_delete_tag","dynatrace_execute_synthetic_monitors","dynatrace_get_attack","dynatrace_get_audit_logs","dynatrace_get_entity","dynatrace_get_event","dynatrace_get_metric","dynatrace_get_problem","dynatrace_get_problem_comment","dynatrace_get_security_problem","dynatrace_get_settings_object","dynatrace_get_slo","dynatrace_get_synthetic_batch","dynatrace_ingest_event","dynatrace_ingest_logs","dynatrace_ingest_metrics","dynatrace_list_attacks","dynatrace_list_entities","dynatrace_list_entity_types","dynatrace_list_events","dynatrace_list_metrics","dynatrace_list_problem_comments","dynatrace_list_problems","dynatrace_list_remediation_items","dynatrace_list_security_problems","dynatrace_list_settings_objects","dynatrace_list_settings_schemas","dynatrace_list_slos","dynatrace_list_synthetic_monitors","dynatrace_list_tags","dynatrace_mute_security_problem","dynatrace_mute_security_problems","dynatrace_query_metrics","dynatrace_search_logs","dynatrace_unmute_security_problem","dynatrace_unmute_security_problems","dynatrace_update_problem_comment","dynatrace_update_settings_object","dynatrace_update_slo","elasticsearch_bulk","elasticsearch_cluster_health","elasticsearch_cluster_stats","elasticsearch_count","elasticsearch_create_index","elasticsearch_delete_document","elasticsearch_delete_index","elasticsearch_get_document","elasticsearch_get_index","elasticsearch_index_document","elasticsearch_list_indices","elasticsearch_search","elasticsearch_update_document","elevenlabs_audio_isolation","elevenlabs_edit_voice_settings","elevenlabs_get_user","elevenlabs_get_voice","elevenlabs_get_voice_settings","elevenlabs_list_models","elevenlabs_list_voices","elevenlabs_sound_effects","elevenlabs_speech_to_speech","elevenlabs_tts","emailbison_attach_leads_to_campaign","emailbison_attach_tags_to_leads","emailbison_create_campaign","emailbison_create_lead","emailbison_create_tag","emailbison_get_lead","emailbison_list_campaigns","emailbison_list_leads","emailbison_list_replies","emailbison_list_tags","emailbison_update_campaign","emailbison_update_campaign_status","emailbison_update_lead","embeddings_cohere","embeddings_gemini","embeddings_mistral","embeddings_openai","embeddings_openrouter","enrich_check_credits","enrich_company_funding","enrich_company_lookup","enrich_company_revenue","enrich_disposable_email_check","enrich_email_to_ip","enrich_email_to_person_lite","enrich_email_to_phone","enrich_email_to_profile","enrich_find_email","enrich_get_post_details","enrich_ip_to_company","enrich_linkedin_profile","enrich_linkedin_to_personal_email","enrich_linkedin_to_work_email","enrich_phone_finder","enrich_reverse_hash_lookup","enrich_sales_pointer_people","enrich_search_company","enrich_search_company_activities","enrich_search_company_employees","enrich_search_jobs","enrich_search_logo","enrich_search_people","enrich_search_people_activities","enrich_search_post_comments","enrich_search_post_comments_by_url","enrich_search_post_reactions","enrich_search_post_reactions_by_url","enrich_search_posts","enrich_search_similar_companies","enrich_verify_email","enrichment_run","enrow_find_email","enrow_verify_email","evernote_copy_note","evernote_create_note","evernote_create_notebook","evernote_create_tag","evernote_delete_note","evernote_get_note","evernote_get_notebook","evernote_list_notebooks","evernote_list_tags","evernote_search_notes","evernote_update_note","exa_agent","exa_answer","exa_find_similar_links","exa_get_contents","exa_search","extend_parser","extend_parser_v2","fathom_get_summary","fathom_get_transcript","fathom_list_meeting_types","fathom_list_meetings","fathom_list_team_members","fathom_list_teams","file_append","file_compress","file_decompress","file_fetch","file_get","file_get_content","file_manage_sharing","file_parser","file_parser_v2","file_parser_v3","file_read","file_write","findymail_find_email_from_linkedin","findymail_find_email_from_name","findymail_find_emails_by_domain","findymail_find_employees","findymail_find_phone","findymail_get_company","findymail_get_credits","findymail_lookup_technologies","findymail_reverse_email_lookup","findymail_search_technologies","findymail_verify_email","firecrawl_agent","firecrawl_batch_scrape","firecrawl_batch_scrape_status","firecrawl_cancel_crawl","firecrawl_crawl","firecrawl_crawl_status","firecrawl_credit_usage","firecrawl_extract","firecrawl_extract_status","firecrawl_map","firecrawl_parse","firecrawl_scrape","firecrawl_search","fireflies_add_to_live_meeting","fireflies_create_bite","fireflies_delete_transcript","fireflies_get_transcript","fireflies_get_user","fireflies_list_bites","fireflies_list_contacts","fireflies_list_transcripts","fireflies_list_users","fireflies_upload_audio","flint_create_task","flint_generate_pages","flint_get_task","function_execute","gamma_check_status","gamma_generate","gamma_generate_from_template","gamma_list_folders","gamma_list_themes","github_add_assignees","github_add_assignees_v2","github_add_labels","github_add_labels_v2","github_cancel_workflow_run","github_cancel_workflow_run_v2","github_check_star","github_check_star_v2","github_close_issue","github_close_issue_v2","github_close_pr","github_close_pr_v2","github_comment","github_comment_v2","github_compare_commits","github_compare_commits_v2","github_create_branch","github_create_branch_v2","github_create_comment_reaction","github_create_comment_reaction_v2","github_create_file","github_create_file_v2","github_create_gist","github_create_gist_v2","github_create_issue","github_create_issue_reaction","github_create_issue_reaction_v2","github_create_issue_v2","github_create_milestone","github_create_milestone_v2","github_create_pr","github_create_pr_review","github_create_pr_review_v2","github_create_pr_v2","github_create_project","github_create_project_v2","github_create_release","github_create_release_v2","github_delete_branch","github_delete_branch_v2","github_delete_comment","github_delete_comment_reaction","github_delete_comment_reaction_v2","github_delete_comment_v2","github_delete_file","github_delete_file_v2","github_delete_gist","github_delete_gist_v2","github_delete_issue_reaction","github_delete_issue_reaction_v2","github_delete_milestone","github_delete_milestone_v2","github_delete_project","github_delete_project_v2","github_delete_release","github_delete_release_v2","github_fork_gist","github_fork_gist_v2","github_fork_repo","github_fork_repo_v2","github_get_branch","github_get_branch_protection","github_get_branch_protection_v2","github_get_branch_v2","github_get_commit","github_get_commit_v2","github_get_file_content","github_get_file_content_v2","github_get_gist","github_get_gist_v2","github_get_issue","github_get_issue_v2","github_get_latest_release","github_get_latest_release_v2","github_get_milestone","github_get_milestone_v2","github_get_pr_files","github_get_pr_files_v2","github_get_project","github_get_project_v2","github_get_readme","github_get_readme_v2","github_get_release","github_get_release_v2","github_get_tree","github_get_tree_v2","github_get_workflow","github_get_workflow_run","github_get_workflow_run_v2","github_get_workflow_v2","github_issue_comment","github_issue_comment_v2","github_job_logs","github_latest_commit","github_latest_commit_v2","github_list_branches","github_list_branches_v2","github_list_commits","github_list_commits_v2","github_list_forks","github_list_forks_v2","github_list_gists","github_list_gists_v2","github_list_issue_comments","github_list_issue_comments_v2","github_list_issues","github_list_issues_v2","github_list_milestones","github_list_milestones_v2","github_list_pr_comments","github_list_pr_comments_v2","github_list_projects","github_list_projects_v2","github_list_prs","github_list_prs_v2","github_list_releases","github_list_releases_v2","github_list_review_threads","github_list_stargazers","github_list_stargazers_v2","github_list_tags","github_list_tags_v2","github_list_workflow_runs","github_list_workflow_runs_v2","github_list_workflows","github_list_workflows_v2","github_merge_pr","github_merge_pr_v2","github_pr","github_pr_v2","github_remove_label","github_remove_label_v2","github_reply_review_thread","github_repo_info","github_repo_info_v2","github_request_reviewers","github_request_reviewers_v2","github_rerun_workflow","github_rerun_workflow_v2","github_resolve_review_thread","github_search_code","github_search_code_v2","github_search_commits","github_search_commits_v2","github_search_issues","github_search_issues_v2","github_search_repos","github_search_repos_v2","github_search_users","github_search_users_v2","github_star_gist","github_star_gist_v2","github_star_repo","github_star_repo_v2","github_status_check_rollup","github_trigger_workflow","github_trigger_workflow_v2","github_unstar_gist","github_unstar_gist_v2","github_unstar_repo","github_unstar_repo_v2","github_update_branch_protection","github_update_branch_protection_v2","github_update_comment","github_update_comment_v2","github_update_file","github_update_file_v2","github_update_gist","github_update_gist_v2","github_update_issue","github_update_issue_v2","github_update_milestone","github_update_milestone_v2","github_update_pr","github_update_pr_v2","github_update_project","github_update_project_v2","github_update_release","github_update_release_v2","gitlab_activate_user","gitlab_add_member","gitlab_add_saml_group_link","gitlab_approve_access_request","gitlab_approve_merge_request","gitlab_approve_user","gitlab_ban_user","gitlab_block_user","gitlab_cancel_pipeline","gitlab_compare_branches","gitlab_create_branch","gitlab_create_file","gitlab_create_issue","gitlab_create_issue_note","gitlab_create_merge_request","gitlab_create_merge_request_note","gitlab_create_pipeline","gitlab_create_release","gitlab_create_user","gitlab_deactivate_user","gitlab_delete_branch","gitlab_delete_issue","gitlab_delete_saml_group_link","gitlab_delete_user","gitlab_delete_user_identity","gitlab_deny_access_request","gitlab_get_file","gitlab_get_group","gitlab_get_issue","gitlab_get_job_log","gitlab_get_merge_request","gitlab_get_merge_request_changes","gitlab_get_pipeline","gitlab_get_project","gitlab_invite_member","gitlab_list_access_requests","gitlab_list_branches","gitlab_list_commits","gitlab_list_groups","gitlab_list_invitations","gitlab_list_issues","gitlab_list_members","gitlab_list_merge_requests","gitlab_list_pipeline_jobs","gitlab_list_pipelines","gitlab_list_projects","gitlab_list_releases","gitlab_list_repository_tree","gitlab_list_saml_group_links","gitlab_list_user_memberships","gitlab_merge_merge_request","gitlab_play_job","gitlab_reject_user","gitlab_remove_member","gitlab_retry_pipeline","gitlab_revoke_invitation","gitlab_search_users","gitlab_unban_user","gitlab_unblock_user","gitlab_update_file","gitlab_update_invitation","gitlab_update_issue","gitlab_update_member","gitlab_update_merge_request","gitlab_update_user","gmail_add_label","gmail_add_label_v2","gmail_archive","gmail_archive_v2","gmail_create_label_v2","gmail_delete","gmail_delete_draft_v2","gmail_delete_label_v2","gmail_delete_v2","gmail_draft","gmail_draft_v2","gmail_edit_draft_v2","gmail_get_draft_v2","gmail_get_thread_v2","gmail_list_drafts_v2","gmail_list_labels_v2","gmail_list_threads_v2","gmail_mark_read","gmail_mark_read_v2","gmail_mark_unread","gmail_mark_unread_v2","gmail_move","gmail_move_v2","gmail_read","gmail_read_v2","gmail_remove_label","gmail_remove_label_v2","gmail_search","gmail_search_v2","gmail_send","gmail_send_v2","gmail_trash_thread_v2","gmail_unarchive","gmail_unarchive_v2","gmail_untrash_thread_v2","gmail_update_label_v2","gong_aggregate_activity","gong_aggregate_by_period","gong_answered_scorecards","gong_ask_anything","gong_assign_flow_prospects","gong_create_call","gong_day_by_day_activity","gong_get_brief","gong_get_call","gong_get_call_transcript","gong_get_coaching","gong_get_extensive_calls","gong_get_folder_content","gong_get_logs","gong_get_prospect_flows","gong_get_user","gong_interaction_stats","gong_list_calls","gong_list_flows","gong_list_library_folders","gong_list_scorecards","gong_list_trackers","gong_list_users","gong_list_workspaces","gong_lookup_email","gong_lookup_phone","gong_purge_email_address","gong_purge_phone_number","gong_unassign_flow_prospects","google_ads_ad_performance","google_ads_campaign_performance","google_ads_list_ad_groups","google_ads_list_campaigns","google_ads_list_customers","google_ads_search","google_appsheet_add_rows","google_appsheet_delete_rows","google_appsheet_edit_rows","google_appsheet_find_rows","google_bigquery_create_dataset","google_bigquery_create_table","google_bigquery_delete_dataset","google_bigquery_delete_table","google_bigquery_get_query_results","google_bigquery_get_table","google_bigquery_insert_rows","google_bigquery_list_datasets","google_bigquery_list_table_data","google_bigquery_list_tables","google_bigquery_query","google_books_volume_details","google_books_volume_search","google_calendar_create","google_calendar_create_calendar","google_calendar_create_calendar_v2","google_calendar_create_v2","google_calendar_delete","google_calendar_delete_calendar","google_calendar_delete_calendar_v2","google_calendar_delete_v2","google_calendar_freebusy","google_calendar_freebusy_v2","google_calendar_get","google_calendar_get_v2","google_calendar_instances","google_calendar_instances_v2","google_calendar_invite","google_calendar_invite_v2","google_calendar_list","google_calendar_list_acl","google_calendar_list_acl_v2","google_calendar_list_calendars","google_calendar_list_calendars_v2","google_calendar_list_v2","google_calendar_move","google_calendar_move_v2","google_calendar_quick_add","google_calendar_quick_add_v2","google_calendar_share_calendar","google_calendar_share_calendar_v2","google_calendar_unshare_calendar","google_calendar_unshare_calendar_v2","google_calendar_update","google_calendar_update_acl","google_calendar_update_acl_v2","google_calendar_update_calendar","google_calendar_update_calendar_v2","google_calendar_update_v2","google_contacts_create","google_contacts_delete","google_contacts_get","google_contacts_list","google_contacts_search","google_contacts_update","google_docs_create","google_docs_create_named_range","google_docs_create_paragraph_bullets","google_docs_delete_content_range","google_docs_delete_named_range","google_docs_delete_paragraph_bullets","google_docs_insert_image","google_docs_insert_page_break","google_docs_insert_table","google_docs_insert_text","google_docs_read","google_docs_replace_text","google_docs_update_paragraph_style","google_docs_update_text_style","google_docs_write","google_drive_copy","google_drive_create_comment","google_drive_create_folder","google_drive_delete","google_drive_delete_comment","google_drive_download","google_drive_export","google_drive_get_about","google_drive_get_content","google_drive_get_file","google_drive_get_revision","google_drive_list","google_drive_list_comments","google_drive_list_permissions","google_drive_list_revisions","google_drive_move","google_drive_search","google_drive_share","google_drive_trash","google_drive_unshare","google_drive_untrash","google_drive_update","google_drive_upload","google_forms_batch_update","google_forms_create_form","google_forms_create_watch","google_forms_delete_watch","google_forms_get_form","google_forms_get_responses","google_forms_list_watches","google_forms_renew_watch","google_forms_set_publish_settings","google_groups_add_alias","google_groups_add_member","google_groups_create_group","google_groups_delete_group","google_groups_get_group","google_groups_get_member","google_groups_get_settings","google_groups_has_member","google_groups_list_aliases","google_groups_list_groups","google_groups_list_members","google_groups_remove_alias","google_groups_remove_member","google_groups_update_group","google_groups_update_member","google_groups_update_settings","google_maps_air_quality","google_maps_directions","google_maps_distance_matrix","google_maps_elevation","google_maps_geocode","google_maps_geolocate","google_maps_place_details","google_maps_places_nearby","google_maps_places_search","google_maps_pollen","google_maps_reverse_geocode","google_maps_snap_to_roads","google_maps_solar","google_maps_speed_limits","google_maps_timezone","google_maps_validate_address","google_meet_create_space","google_meet_end_conference","google_meet_get_conference_record","google_meet_get_space","google_meet_list_conference_records","google_meet_list_participants","google_pagespeed_analyze","google_search","google_sheets_append","google_sheets_append_v2","google_sheets_batch_clear_v2","google_sheets_batch_get_v2","google_sheets_batch_update_v2","google_sheets_clear_v2","google_sheets_copy_sheet_v2","google_sheets_create_spreadsheet_v2","google_sheets_delete_rows_v2","google_sheets_delete_sheet_v2","google_sheets_delete_spreadsheet_v2","google_sheets_get_spreadsheet_v2","google_sheets_read","google_sheets_read_v2","google_sheets_update","google_sheets_update_v2","google_sheets_write","google_sheets_write_v2","google_slides_add_image","google_slides_add_slide","google_slides_batch_update","google_slides_copy_presentation","google_slides_create","google_slides_create_line","google_slides_create_paragraph_bullets","google_slides_create_shape","google_slides_create_sheets_chart","google_slides_create_table","google_slides_create_video","google_slides_delete_object","google_slides_delete_paragraph_bullets","google_slides_delete_table_column","google_slides_delete_table_row","google_slides_delete_text","google_slides_duplicate_object","google_slides_export_presentation","google_slides_get_page","google_slides_get_thumbnail","google_slides_group_objects","google_slides_insert_table_columns","google_slides_insert_table_rows","google_slides_insert_text","google_slides_merge_table_cells","google_slides_read","google_slides_refresh_sheets_chart","google_slides_replace_all_shapes_with_image","google_slides_replace_all_shapes_with_sheets_chart","google_slides_replace_all_text","google_slides_replace_image","google_slides_reroute_line","google_slides_ungroup_objects","google_slides_unmerge_table_cells","google_slides_update_image_properties","google_slides_update_line_category","google_slides_update_line_properties","google_slides_update_page_element_alt_text","google_slides_update_page_element_transform","google_slides_update_page_elements_z_order","google_slides_update_page_properties","google_slides_update_paragraph_style","google_slides_update_shape_properties","google_slides_update_slide_properties","google_slides_update_slides_position","google_slides_update_table_border_properties","google_slides_update_table_cell_properties","google_slides_update_table_column_properties","google_slides_update_table_row_properties","google_slides_update_text_style","google_slides_update_video_properties","google_slides_write","google_tasks_create","google_tasks_delete","google_tasks_get","google_tasks_list","google_tasks_list_task_lists","google_tasks_update","google_translate_detect","google_translate_text","google_vault_add_held_accounts","google_vault_add_matters_permissions","google_vault_close_matters","google_vault_create_matters","google_vault_create_matters_export","google_vault_create_matters_holds","google_vault_create_saved_query","google_vault_delete_matters","google_vault_delete_matters_export","google_vault_delete_matters_holds","google_vault_delete_saved_query","google_vault_download_export_file","google_vault_list_matters","google_vault_list_matters_export","google_vault_list_matters_holds","google_vault_list_saved_queries","google_vault_remove_held_accounts","google_vault_remove_matters_permissions","google_vault_reopen_matters","google_vault_undelete_matters","google_vault_update_matters","google_vault_update_matters_holds","grafana_check_data_source_health","grafana_create_alert_rule","grafana_create_annotation","grafana_create_contact_point","grafana_create_dashboard","grafana_create_folder","grafana_delete_alert_rule","grafana_delete_annotation","grafana_delete_contact_point","grafana_delete_dashboard","grafana_delete_folder","grafana_get_alert_rule","grafana_get_alert_rule_group","grafana_get_dashboard","grafana_get_data_source","grafana_get_folder","grafana_get_health","grafana_list_alert_rules","grafana_list_annotations","grafana_list_contact_points","grafana_list_dashboards","grafana_list_data_sources","grafana_list_folders","grafana_move_folder","grafana_query_data_source","grafana_update_alert_rule","grafana_update_annotation","grafana_update_contact_point","grafana_update_dashboard","grafana_update_folder","grain_create_hook","grain_create_hook_v2","grain_delete_hook","grain_delete_hook_v2","grain_get_recording","grain_get_transcript","grain_list_hooks","grain_list_hooks_v2","grain_list_meeting_types","grain_list_recordings","grain_list_teams","grain_list_views","granola_get_note","granola_list_folders","granola_list_notes","greenhouse_get_application","greenhouse_get_candidate","greenhouse_get_job","greenhouse_get_user","greenhouse_list_applications","greenhouse_list_candidates","greenhouse_list_departments","greenhouse_list_job_stages","greenhouse_list_jobs","greenhouse_list_offices","greenhouse_list_users","greptile_index_repo","greptile_query","greptile_search","greptile_status","guardrails_validate","hex_cancel_run","hex_create_collection","hex_create_group","hex_deactivate_user","hex_delete_group","hex_get_collection","hex_get_data_connection","hex_get_group","hex_get_project","hex_get_project_runs","hex_get_queried_tables","hex_get_run_status","hex_list_collections","hex_list_data_connections","hex_list_groups","hex_list_projects","hex_list_users","hex_run_project","hex_update_collection","hex_update_group","hex_update_project","http_request","hubspot_add_list_memberships","hubspot_create_appointment","hubspot_create_association","hubspot_create_company","hubspot_create_contact","hubspot_create_deal","hubspot_create_email","hubspot_create_line_item","hubspot_create_list","hubspot_create_note","hubspot_create_ticket","hubspot_delete_association","hubspot_delete_company","hubspot_delete_contact","hubspot_delete_deal","hubspot_delete_line_item","hubspot_delete_ticket","hubspot_get_appointment","hubspot_get_association_labels","hubspot_get_cart","hubspot_get_company","hubspot_get_contact","hubspot_get_deal","hubspot_get_email","hubspot_get_line_item","hubspot_get_list","hubspot_get_list_memberships","hubspot_get_marketing_event","hubspot_get_note","hubspot_get_properties","hubspot_get_quote","hubspot_get_ticket","hubspot_get_users","hubspot_list_appointments","hubspot_list_associations","hubspot_list_carts","hubspot_list_companies","hubspot_list_contacts","hubspot_list_deals","hubspot_list_emails","hubspot_list_line_items","hubspot_list_lists","hubspot_list_marketing_events","hubspot_list_notes","hubspot_list_owners","hubspot_list_quotes","hubspot_list_tickets","hubspot_remove_list_memberships","hubspot_search_companies","hubspot_search_contacts","hubspot_search_deals","hubspot_search_emails","hubspot_search_line_items","hubspot_search_notes","hubspot_search_quotes","hubspot_search_tickets","hubspot_update_appointment","hubspot_update_company","hubspot_update_contact","hubspot_update_deal","hubspot_update_line_item","hubspot_update_ticket","huggingface_chat","hunter_companies_find","hunter_discover","hunter_domain_search","hunter_email_count","hunter_email_finder","hunter_email_verifier","iam_add_user_to_group","iam_attach_role_policy","iam_attach_user_policy","iam_create_access_key","iam_create_role","iam_create_user","iam_delete_access_key","iam_delete_role","iam_delete_user","iam_detach_role_policy","iam_detach_user_policy","iam_get_role","iam_get_user","iam_list_attached_role_policies","iam_list_attached_user_policies","iam_list_groups","iam_list_policies","iam_list_roles","iam_list_users","iam_remove_user_from_group","iam_simulate_principal_policy","icypeas_find_email","icypeas_verify_email","identity_center_check_assignment_deletion_status","identity_center_check_assignment_status","identity_center_create_account_assignment","identity_center_delete_account_assignment","identity_center_describe_account","identity_center_get_group","identity_center_get_user","identity_center_list_account_assignments","identity_center_list_accounts","identity_center_list_groups","identity_center_list_instances","identity_center_list_permission_sets","image_generate","incidentio_actions_create","incidentio_actions_list","incidentio_actions_show","incidentio_actions_update","incidentio_alert_events_create","incidentio_alerts_list","incidentio_alerts_resolve","incidentio_alerts_show","incidentio_catalog_entries_list","incidentio_catalog_types_list","incidentio_custom_fields_create","incidentio_custom_fields_delete","incidentio_custom_fields_list","incidentio_custom_fields_show","incidentio_custom_fields_update","incidentio_escalation_paths_create","incidentio_escalation_paths_delete","incidentio_escalation_paths_list","incidentio_escalation_paths_show","incidentio_escalation_paths_update","incidentio_escalations_cancel","incidentio_escalations_create","incidentio_escalations_list","incidentio_escalations_show","incidentio_follow_ups_create","incidentio_follow_ups_list","incidentio_follow_ups_show","incidentio_follow_ups_update","incidentio_incident_alerts_list","incidentio_incident_memberships_create","incidentio_incident_memberships_revoke","incidentio_incident_participants_list","incidentio_incident_roles_create","incidentio_incident_roles_delete","incidentio_incident_roles_list","incidentio_incident_roles_show","incidentio_incident_roles_update","incidentio_incident_statuses_list","incidentio_incident_timestamps_list","incidentio_incident_timestamps_show","incidentio_incident_types_list","incidentio_incident_updates_list","incidentio_incidents_create","incidentio_incidents_list","incidentio_incidents_show","incidentio_incidents_update","incidentio_on_call_now","incidentio_schedule_entries_list","incidentio_schedule_overrides_create","incidentio_schedule_overrides_list","incidentio_schedules_create","incidentio_schedules_delete","incidentio_schedules_list","incidentio_schedules_show","incidentio_schedules_update","incidentio_severities_list","incidentio_teams_list","incidentio_teams_show","incidentio_users_list","incidentio_users_show","incidentio_workflows_create","incidentio_workflows_delete","incidentio_workflows_list","incidentio_workflows_show","incidentio_workflows_update","infisical_create_secret","infisical_delete_secret","infisical_get_secret","infisical_list_secrets","infisical_update_secret","instagram_delete_comment","instagram_download_media","instagram_get_account_insights","instagram_get_container_status","instagram_get_conversation_messages","instagram_get_media","instagram_get_media_insights","instagram_get_message","instagram_get_profile","instagram_get_publishing_limit","instagram_hide_comment","instagram_list_comments","instagram_list_conversations","instagram_list_media","instagram_list_stories","instagram_private_reply","instagram_publish_carousel","instagram_publish_image","instagram_publish_reel","instagram_publish_story","instagram_publish_video","instagram_reply_to_comment","instagram_send_text_message","instagram_set_comments_enabled","instantly_activate_campaign","instantly_create_campaign","instantly_create_lead","instantly_create_lead_list","instantly_delete_campaign","instantly_delete_leads","instantly_get_lead","instantly_list_campaigns","instantly_list_emails","instantly_list_lead_lists","instantly_list_leads","instantly_patch_campaign","instantly_patch_lead","instantly_pause_campaign","instantly_reply_to_email","instantly_update_lead_interest_status","intercom_assign_conversation_v2","intercom_attach_contact_to_company_v2","intercom_close_conversation_v2","intercom_create_company","intercom_create_company_v2","intercom_create_contact","intercom_create_contact_v2","intercom_create_event_v2","intercom_create_message","intercom_create_message_v2","intercom_create_note_v2","intercom_create_tag_v2","intercom_create_ticket","intercom_create_ticket_v2","intercom_delete_contact","intercom_delete_contact_v2","intercom_detach_contact_from_company_v2","intercom_get_company","intercom_get_company_v2","intercom_get_contact","intercom_get_contact_v2","intercom_get_conversation","intercom_get_conversation_v2","intercom_get_ticket","intercom_get_ticket_v2","intercom_list_admins_v2","intercom_list_companies","intercom_list_companies_v2","intercom_list_contacts","intercom_list_contacts_v2","intercom_list_conversations","intercom_list_conversations_v2","intercom_list_tags_v2","intercom_open_conversation_v2","intercom_reply_conversation","intercom_reply_conversation_v2","intercom_search_contacts","intercom_search_contacts_v2","intercom_search_conversations","intercom_search_conversations_v2","intercom_snooze_conversation_v2","intercom_tag_contact_v2","intercom_tag_conversation_v2","intercom_untag_contact_v2","intercom_update_contact","intercom_update_contact_v2","intercom_update_ticket_v2","jina_read_url","jina_search","jira_add_attachment","jira_add_comment","jira_add_watcher","jira_add_worklog","jira_assign_issue","jira_bulk_read","jira_create_issue_link","jira_delete_attachment","jira_delete_comment","jira_delete_issue","jira_delete_issue_link","jira_delete_worklog","jira_get_attachments","jira_get_comments","jira_get_fields","jira_get_project","jira_get_transitions","jira_get_users","jira_get_worklogs","jira_list_issue_types","jira_list_projects","jira_remove_watcher","jira_retrieve","jira_search_issues","jira_search_users","jira_transition_issue","jira_update","jira_update_comment","jira_update_worklog","jira_write","jsm_add_comment","jsm_add_customer","jsm_add_organization","jsm_add_participants","jsm_answer_approval","jsm_attach_form","jsm_copy_forms","jsm_create_object","jsm_create_organization","jsm_create_request","jsm_delete_form","jsm_delete_object","jsm_externalise_form","jsm_get_approvals","jsm_get_comments","jsm_get_customers","jsm_get_form","jsm_get_form_answers","jsm_get_form_structure","jsm_get_form_templates","jsm_get_issue_forms","jsm_get_object","jsm_get_object_schema","jsm_get_object_type_attributes","jsm_get_organizations","jsm_get_participants","jsm_get_queues","jsm_get_request","jsm_get_request_type_fields","jsm_get_request_types","jsm_get_requests","jsm_get_service_desks","jsm_get_sla","jsm_get_transitions","jsm_internalise_form","jsm_list_object_schemas","jsm_list_object_types","jsm_reopen_form","jsm_save_form_answers","jsm_search_objects_aql","jsm_submit_form","jsm_transition_request","jsm_update_object","jupyter_copy_content","jupyter_create_file","jupyter_create_session","jupyter_delete_content","jupyter_delete_session","jupyter_get_content","jupyter_interrupt_kernel","jupyter_list_contents","jupyter_list_kernels","jupyter_list_kernelspecs","jupyter_list_sessions","jupyter_rename_content","jupyter_restart_kernel","jupyter_start_kernel","jupyter_stop_kernel","jupyter_upload_file","kalshi_amend_order","kalshi_amend_order_v2","kalshi_cancel_order","kalshi_cancel_order_v2","kalshi_create_order","kalshi_create_order_v2","kalshi_get_balance","kalshi_get_balance_v2","kalshi_get_candlesticks","kalshi_get_candlesticks_v2","kalshi_get_event","kalshi_get_event_candlesticks","kalshi_get_event_candlesticks_v2","kalshi_get_event_v2","kalshi_get_events","kalshi_get_events_v2","kalshi_get_exchange_announcements","kalshi_get_exchange_announcements_v2","kalshi_get_exchange_schedule","kalshi_get_exchange_schedule_v2","kalshi_get_exchange_status","kalshi_get_exchange_status_v2","kalshi_get_fills","kalshi_get_fills_v2","kalshi_get_market","kalshi_get_market_v2","kalshi_get_markets","kalshi_get_markets_v2","kalshi_get_order","kalshi_get_order_v2","kalshi_get_orderbook","kalshi_get_orderbook_v2","kalshi_get_orders","kalshi_get_orders_v2","kalshi_get_positions","kalshi_get_positions_v2","kalshi_get_series_by_ticker","kalshi_get_series_by_ticker_v2","kalshi_get_series_list","kalshi_get_series_list_v2","kalshi_get_settlements","kalshi_get_settlements_v2","kalshi_get_trades","kalshi_get_trades_v2","ketch_get_consent","ketch_get_subscriptions","ketch_invoke_right","ketch_set_consent","ketch_set_subscriptions","knowledge_create_document","knowledge_delete_chunk","knowledge_delete_document","knowledge_get_connector","knowledge_get_document","knowledge_list_chunks","knowledge_list_connectors","knowledge_list_documents","knowledge_list_tags","knowledge_search","knowledge_trigger_sync","knowledge_update_chunk","knowledge_upload_chunk","knowledge_upsert_document","langsmith_create_feedback","langsmith_create_run","langsmith_create_runs_batch","langsmith_get_run","langsmith_update_run","latex_compile","latex_get_package","latex_list_fonts","latex_search_packages","launchdarkly_create_flag","launchdarkly_delete_flag","launchdarkly_get_audit_log","launchdarkly_get_flag","launchdarkly_get_flag_status","launchdarkly_list_environments","launchdarkly_list_flags","launchdarkly_list_members","launchdarkly_list_projects","launchdarkly_list_segments","launchdarkly_toggle_flag","launchdarkly_update_flag","leadmagic_company_search","leadmagic_email_to_profile","leadmagic_find_email","leadmagic_find_mobile","leadmagic_get_credits","leadmagic_profile_search","leadmagic_profile_to_email","leadmagic_role_finder","leadmagic_validate_email","lemlist_get_activities","lemlist_get_lead","lemlist_send_email","linear_add_label_to_issue","linear_add_label_to_project","linear_archive_issue","linear_archive_label","linear_archive_project","linear_create_attachment","linear_create_comment","linear_create_customer","linear_create_customer_request","linear_create_customer_status","linear_create_customer_tier","linear_create_cycle","linear_create_favorite","linear_create_issue","linear_create_issue_relation","linear_create_label","linear_create_project","linear_create_project_label","linear_create_project_milestone","linear_create_project_status","linear_create_project_update","linear_create_workflow_state","linear_delete_attachment","linear_delete_comment","linear_delete_customer","linear_delete_customer_status","linear_delete_customer_tier","linear_delete_issue","linear_delete_issue_relation","linear_delete_project","linear_delete_project_label","linear_delete_project_milestone","linear_delete_project_status","linear_get_active_cycle","linear_get_customer","linear_get_cycle","linear_get_issue","linear_get_project","linear_get_viewer","linear_list_attachments","linear_list_comments","linear_list_customer_requests","linear_list_customer_statuses","linear_list_customer_tiers","linear_list_customers","linear_list_cycles","linear_list_favorites","linear_list_issue_relations","linear_list_labels","linear_list_notifications","linear_list_project_labels","linear_list_project_milestones","linear_list_project_statuses","linear_list_project_updates","linear_list_projects","linear_list_teams","linear_list_users","linear_list_workflow_states","linear_merge_customers","linear_read_issues","linear_remove_label_from_issue","linear_remove_label_from_project","linear_search_issues","linear_unarchive_issue","linear_update_attachment","linear_update_comment","linear_update_customer","linear_update_customer_request","linear_update_customer_status","linear_update_customer_tier","linear_update_issue","linear_update_label","linear_update_notification","linear_update_project","linear_update_project_label","linear_update_project_milestone","linear_update_project_status","linear_update_workflow_state","linkedin_get_profile","linkedin_share_post","linkup_search","linq_add_participant","linq_check_imessage","linq_check_rcs","linq_create_attachment","linq_create_chat","linq_create_contact_card","linq_create_webhook_subscription","linq_delete_attachment","linq_delete_message","linq_delete_webhook_subscription","linq_edit_message","linq_get_attachment","linq_get_chat","linq_get_contact_card","linq_get_message","linq_get_webhook_subscription","linq_leave_chat","linq_list_chats","linq_list_messages","linq_list_phone_numbers","linq_list_thread","linq_list_webhook_events","linq_list_webhook_subscriptions","linq_mark_chat_read","linq_react_to_message","linq_remove_participant","linq_send_message","linq_send_voice_memo","linq_share_contact_card","linq_start_typing","linq_stop_typing","linq_update_chat","linq_update_contact_card","linq_update_webhook_subscription","llm_chat","logfire_get_token_info","logfire_get_trace","logfire_query","logfire_search_records","logrocket_create_release","logrocket_get_audit_logs","logrocket_get_highlights","logrocket_identify_user","logrocket_list_exported_sessions","logrocket_request_highlights","logs_get","logs_get_execution","logs_get_run_details","logs_query","logs_query_runs","loops_check_contact_suppression","loops_create_contact","loops_create_contact_property","loops_delete_contact","loops_find_contact","loops_get_transactional_email","loops_list_contact_properties","loops_list_mailing_lists","loops_list_transactional_emails","loops_remove_contact_suppression","loops_send_event","loops_send_transactional_email","loops_update_contact","luma_add_guests","luma_cancel_event","luma_create_event","luma_get_event","luma_get_guest","luma_get_guests","luma_list_events","luma_lookup_event","luma_send_invites","luma_update_event","luma_update_guest_status","mailchimp_add_member","mailchimp_add_member_tags","mailchimp_add_or_update_member","mailchimp_add_segment_member","mailchimp_add_subscriber_to_automation","mailchimp_archive_member","mailchimp_create_audience","mailchimp_create_batch_operation","mailchimp_create_campaign","mailchimp_create_interest","mailchimp_create_interest_category","mailchimp_create_landing_page","mailchimp_create_merge_field","mailchimp_create_segment","mailchimp_create_template","mailchimp_delete_audience","mailchimp_delete_batch_operation","mailchimp_delete_campaign","mailchimp_delete_interest","mailchimp_delete_interest_category","mailchimp_delete_landing_page","mailchimp_delete_member","mailchimp_delete_merge_field","mailchimp_delete_segment","mailchimp_delete_template","mailchimp_get_audience","mailchimp_get_audiences","mailchimp_get_automation","mailchimp_get_automations","mailchimp_get_batch_operation","mailchimp_get_batch_operations","mailchimp_get_campaign","mailchimp_get_campaign_content","mailchimp_get_campaign_report","mailchimp_get_campaign_reports","mailchimp_get_campaigns","mailchimp_get_interest","mailchimp_get_interest_categories","mailchimp_get_interest_category","mailchimp_get_interests","mailchimp_get_landing_page","mailchimp_get_landing_pages","mailchimp_get_member","mailchimp_get_member_tags","mailchimp_get_members","mailchimp_get_merge_field","mailchimp_get_merge_fields","mailchimp_get_segment","mailchimp_get_segment_members","mailchimp_get_segments","mailchimp_get_template","mailchimp_get_templates","mailchimp_pause_automation","mailchimp_publish_landing_page","mailchimp_remove_member_tags","mailchimp_remove_segment_member","mailchimp_replicate_campaign","mailchimp_schedule_campaign","mailchimp_send_campaign","mailchimp_set_campaign_content","mailchimp_start_automation","mailchimp_unarchive_member","mailchimp_unpublish_landing_page","mailchimp_unschedule_campaign","mailchimp_update_audience","mailchimp_update_campaign","mailchimp_update_interest","mailchimp_update_interest_category","mailchimp_update_landing_page","mailchimp_update_member","mailchimp_update_merge_field","mailchimp_update_segment","mailchimp_update_template","mailgun_add_list_member","mailgun_create_mailing_list","mailgun_get_domain","mailgun_get_mailing_list","mailgun_get_message","mailgun_list_domains","mailgun_list_messages","mailgun_send_message","managed_agent_archive_session","managed_agent_create_session","managed_agent_delete_session","managed_agent_get_session","managed_agent_interrupt_session","managed_agent_list_events","managed_agent_respond_custom_tool","managed_agent_respond_tool_confirmation","managed_agent_run_session","managed_agent_send_message","managed_agent_update_session","mem0_add_memories","mem0_get_memories","mem0_search_memories","memory_add","memory_delete","memory_get","memory_get_all","microsoft_ad_add_group_member","microsoft_ad_create_group","microsoft_ad_create_user","microsoft_ad_delete_group","microsoft_ad_delete_user","microsoft_ad_get_group","microsoft_ad_get_user","microsoft_ad_list_group_members","microsoft_ad_list_groups","microsoft_ad_list_users","microsoft_ad_remove_group_member","microsoft_ad_update_group","microsoft_ad_update_user","microsoft_dataverse_associate","microsoft_dataverse_create_multiple","microsoft_dataverse_create_record","microsoft_dataverse_delete_record","microsoft_dataverse_disassociate","microsoft_dataverse_download_file","microsoft_dataverse_execute_action","microsoft_dataverse_execute_function","microsoft_dataverse_fetchxml_query","microsoft_dataverse_get_entity_metadata","microsoft_dataverse_get_record","microsoft_dataverse_list_records","microsoft_dataverse_search","microsoft_dataverse_update_multiple","microsoft_dataverse_update_record","microsoft_dataverse_upload_file","microsoft_dataverse_upsert_record","microsoft_dataverse_whoami","microsoft_excel_clear_range","microsoft_excel_create_table","microsoft_excel_delete_worksheet","microsoft_excel_format_range","microsoft_excel_read","microsoft_excel_read_v2","microsoft_excel_sort_range","microsoft_excel_table_add","microsoft_excel_worksheet_add","microsoft_excel_write","microsoft_excel_write_v2","microsoft_planner_create_bucket","microsoft_planner_create_plan","microsoft_planner_create_task","microsoft_planner_delete_bucket","microsoft_planner_delete_plan","microsoft_planner_delete_task","microsoft_planner_get_plan_details","microsoft_planner_get_task_details","microsoft_planner_list_buckets","microsoft_planner_list_plans","microsoft_planner_read_bucket","microsoft_planner_read_plan","microsoft_planner_read_task","microsoft_planner_update_bucket","microsoft_planner_update_plan","microsoft_planner_update_plan_details","microsoft_planner_update_task","microsoft_planner_update_task_details","microsoft_teams_delete_channel_message","microsoft_teams_delete_chat_message","microsoft_teams_get_message","microsoft_teams_list_channel_members","microsoft_teams_list_channels","microsoft_teams_list_chat_members","microsoft_teams_list_chats","microsoft_teams_list_team_members","microsoft_teams_list_teams","microsoft_teams_read_channel","microsoft_teams_read_chat","microsoft_teams_reply_to_message","microsoft_teams_set_reaction","microsoft_teams_unset_reaction","microsoft_teams_update_channel_message","microsoft_teams_update_chat_message","microsoft_teams_write_channel","microsoft_teams_write_chat","millionverifier_get_credits","millionverifier_verify_email","mintlify_create_agent_job","mintlify_create_assistant_message","mintlify_detect_ai_prose","mintlify_get_agent_job","mintlify_get_assistant_caller_stats","mintlify_get_assistant_conversations","mintlify_get_feedback","mintlify_get_feedback_by_page","mintlify_get_page_content","mintlify_get_searches","mintlify_get_update_status","mintlify_get_views","mintlify_get_visitors","mintlify_search","mintlify_send_agent_message","mintlify_trigger_automation","mintlify_trigger_preview","mintlify_trigger_update","mistral_parser","mistral_parser_v2","mistral_parser_v3","monday_archive_item","monday_change_column_value","monday_create_board","monday_create_column","monday_create_group","monday_create_item","monday_create_subitem","monday_create_update","monday_delete_item","monday_duplicate_item","monday_get_board","monday_get_groups","monday_get_item","monday_get_items","monday_list_boards","monday_move_item_to_group","monday_search_items","monday_update_item","mongodb_delete","mongodb_execute","mongodb_insert","mongodb_introspect","mongodb_query","mongodb_update","mysql_delete","mysql_execute","mysql_insert","mysql_introspect","mysql_query","mysql_update","neo4j_create","neo4j_delete","neo4j_execute","neo4j_introspect","neo4j_merge","neo4j_query","neo4j_update","netsuite_attach_record","netsuite_batch_create_records","netsuite_batch_delete_records","netsuite_batch_get_records","netsuite_batch_update_records","netsuite_batch_upsert_records","netsuite_create_record","netsuite_delete_record","netsuite_detach_record","netsuite_execute_action","netsuite_execute_dataset","netsuite_execute_suiteql","netsuite_get_async_result","netsuite_get_async_status","netsuite_get_governance_limits","netsuite_get_record","netsuite_get_record_form","netsuite_get_record_metadata","netsuite_get_select_options","netsuite_get_server_time","netsuite_get_subresource","netsuite_list_datasets","netsuite_list_record_types","netsuite_list_records","netsuite_transform_record","netsuite_update_record","netsuite_upsert_record","neverbounce_get_credits","neverbounce_verify_email","new_relic_create_deployment_event","new_relic_get_entity","new_relic_nrql_query","new_relic_search_entities","notion_add_database_row","notion_add_database_row_v2","notion_append_blocks","notion_append_blocks_v2","notion_create_comment","notion_create_comment_v2","notion_create_database","notion_create_database_v2","notion_create_page","notion_create_page_v2","notion_delete_block","notion_delete_block_v2","notion_list_comments","notion_list_comments_v2","notion_list_users","notion_list_users_v2","notion_query_database","notion_query_database_v2","notion_read","notion_read_database","notion_read_database_v2","notion_read_v2","notion_retrieve_block","notion_retrieve_block_children","notion_retrieve_block_children_v2","notion_retrieve_block_v2","notion_retrieve_user","notion_retrieve_user_v2","notion_search","notion_search_v2","notion_update_block","notion_update_block_v2","notion_update_page","notion_update_page_v2","notion_write","notion_write_v2","obsidian_append_active","obsidian_append_note","obsidian_append_periodic_note","obsidian_create_note","obsidian_delete_note","obsidian_execute_command","obsidian_get_active","obsidian_get_note","obsidian_get_periodic_note","obsidian_list_commands","obsidian_list_files","obsidian_open_file","obsidian_patch_active","obsidian_patch_note","obsidian_search","okta_activate_group_rule","okta_activate_user","okta_add_user_to_group","okta_assign_group_to_app","okta_assign_user_role","okta_assign_user_to_app","okta_clear_user_sessions","okta_create_group","okta_create_group_rule","okta_create_user","okta_deactivate_group_rule","okta_deactivate_user","okta_delete_group","okta_delete_group_rule","okta_delete_user","okta_enroll_factor","okta_get_app","okta_get_factor","okta_get_group","okta_get_group_rule","okta_get_logs","okta_get_session","okta_get_user","okta_list_app_groups","okta_list_app_users","okta_list_apps","okta_list_factors","okta_list_group_members","okta_list_group_rules","okta_list_groups","okta_list_user_roles","okta_list_users","okta_remove_group_from_app","okta_remove_user_from_app","okta_remove_user_from_group","okta_remove_user_role","okta_reset_all_factors","okta_reset_factor","okta_reset_password","okta_revoke_session","okta_suspend_user","okta_unsuspend_user","okta_update_group","okta_update_user","onedrive_copy","onedrive_create_folder","onedrive_create_share_link","onedrive_delete","onedrive_download","onedrive_get_drive_info","onedrive_get_item","onedrive_list","onedrive_move","onedrive_search","onedrive_upload","onepassword_create_item","onepassword_delete_item","onepassword_get_item","onepassword_get_item_file","onepassword_get_vault","onepassword_list_items","onepassword_list_vaults","onepassword_replace_item","onepassword_resolve_secret","onepassword_update_item","openai_embeddings","openai_image","outlook_calendar_create_event","outlook_calendar_delete_event","outlook_calendar_get_event","outlook_calendar_list_events","outlook_calendar_respond","outlook_calendar_update_event","outlook_copy","outlook_create_folder","outlook_delete","outlook_draft","outlook_forward","outlook_get_attachment","outlook_list_attachments","outlook_list_folders","outlook_mark_read","outlook_mark_unread","outlook_move","outlook_read","outlook_reply","outlook_reply_all","outlook_search","outlook_send","outlook_update_message","pagerduty_add_note","pagerduty_create_incident","pagerduty_get_incident","pagerduty_get_service","pagerduty_list_escalation_policies","pagerduty_list_incident_alerts","pagerduty_list_incidents","pagerduty_list_oncalls","pagerduty_list_schedules","pagerduty_list_services","pagerduty_list_users","pagerduty_merge_incidents","pagerduty_send_event","pagerduty_snooze_incident","pagerduty_update_incident","parallel_deep_research","parallel_extract","parallel_search","pdl_autocomplete","pdl_bulk_company_enrich","pdl_bulk_person_enrich","pdl_clean_company","pdl_clean_location","pdl_clean_school","pdl_company_enrich","pdl_company_search","pdl_person_enrich","pdl_person_identify","pdl_person_search","perplexity_chat","perplexity_search","persona_approve_inquiry","persona_create_account","persona_create_inquiry","persona_create_report","persona_decline_inquiry","persona_expire_inquiry","persona_generate_inquiry_link","persona_get_account","persona_get_case","persona_get_document","persona_get_inquiry","persona_get_report","persona_get_verification","persona_import_accounts","persona_list_accounts","persona_list_cases","persona_list_inquiries","persona_list_inquiry_templates","persona_list_reports","persona_mark_inquiry_for_review","persona_print_inquiry_pdf","persona_redact_account","persona_redact_inquiry","persona_resume_inquiry","persona_update_account","persona_update_inquiry","pinecone_delete_vectors","pinecone_describe_index","pinecone_describe_index_stats","pinecone_fetch","pinecone_generate_embeddings","pinecone_list_indexes","pinecone_list_vector_ids","pinecone_search_text","pinecone_search_vector","pinecone_update_vector","pinecone_upsert_text","pipedrive_create_activity","pipedrive_create_deal","pipedrive_create_lead","pipedrive_create_project","pipedrive_delete_lead","pipedrive_get_activities","pipedrive_get_all_deals","pipedrive_get_deal","pipedrive_get_files","pipedrive_get_leads","pipedrive_get_mail_messages","pipedrive_get_mail_thread","pipedrive_get_pipeline_deals","pipedrive_get_pipelines","pipedrive_get_projects","pipedrive_update_activity","pipedrive_update_deal","pipedrive_update_lead","polymarket_get_activity","polymarket_get_event","polymarket_get_events","polymarket_get_holders","polymarket_get_last_trade_price","polymarket_get_leaderboard","polymarket_get_market","polymarket_get_markets","polymarket_get_midpoint","polymarket_get_orderbook","polymarket_get_positions","polymarket_get_price","polymarket_get_price_history","polymarket_get_series","polymarket_get_series_by_id","polymarket_get_spread","polymarket_get_tags","polymarket_get_tick_size","polymarket_get_trades","polymarket_search","postgresql_delete","postgresql_execute","postgresql_insert","postgresql_introspect","postgresql_query","postgresql_update","posthog_batch_events","posthog_capture_event","posthog_create_annotation","posthog_create_cohort","posthog_create_dashboard","posthog_create_experiment","posthog_create_feature_flag","posthog_create_insight","posthog_create_survey","posthog_delete_feature_flag","posthog_delete_person","posthog_delete_survey","posthog_evaluate_flags","posthog_get_cohort","posthog_get_dashboard","posthog_get_event_definition","posthog_get_experiment","posthog_get_feature_flag","posthog_get_insight","posthog_get_organization","posthog_get_person","posthog_get_project","posthog_get_property_definition","posthog_get_session_recording","posthog_get_survey","posthog_list_actions","posthog_list_annotations","posthog_list_cohorts","posthog_list_dashboards","posthog_list_event_definitions","posthog_list_experiments","posthog_list_feature_flags","posthog_list_insights","posthog_list_organizations","posthog_list_persons","posthog_list_projects","posthog_list_property_definitions","posthog_list_recording_playlists","posthog_list_session_recordings","posthog_list_surveys","posthog_query","posthog_update_cohort","posthog_update_event_definition","posthog_update_experiment","posthog_update_feature_flag","posthog_update_insight","posthog_update_property_definition","posthog_update_survey","profound_bot_logs","profound_bots_report","profound_category_assets","profound_category_personas","profound_category_prompts","profound_category_tags","profound_category_topics","profound_citation_prompts","profound_citations_report","profound_list_assets","profound_list_categories","profound_list_domains","profound_list_models","profound_list_optimizations","profound_list_personas","profound_list_regions","profound_optimization_analysis","profound_prompt_answers","profound_prompt_volume","profound_query_fanouts","profound_raw_logs","profound_referrals_report","profound_sentiment_report","profound_visibility_report","prospeo_account_information","prospeo_bulk_enrich_company","prospeo_bulk_enrich_person","prospeo_enrich_company","prospeo_enrich_person","prospeo_search_company","prospeo_search_person","prospeo_search_suggestions","pulse_parser","pulse_parser_v2","qdrant_fetch_points","qdrant_search_vector","qdrant_upsert_points","quartr_get_audio","quartr_get_company","quartr_get_event","quartr_get_event_summary","quartr_get_report","quartr_get_slide_deck","quartr_get_transcript","quartr_list_audio","quartr_list_companies","quartr_list_document_types","quartr_list_documents","quartr_list_event_types","quartr_list_events","quartr_list_live_events","quartr_list_reports","quartr_list_slide_decks","quartr_list_transcripts","quiver_image_to_svg","quiver_list_models","quiver_text_to_svg","rabbitmq_create_binding","rabbitmq_create_exchange","rabbitmq_create_policy","rabbitmq_create_queue","rabbitmq_delete_binding","rabbitmq_delete_exchange","rabbitmq_delete_policy","rabbitmq_delete_queue","rabbitmq_get_exchange","rabbitmq_get_messages","rabbitmq_get_overview","rabbitmq_get_queue","rabbitmq_health_check","rabbitmq_list_bindings","rabbitmq_list_channels","rabbitmq_list_connections","rabbitmq_list_consumers","rabbitmq_list_exchange_bindings","rabbitmq_list_exchanges","rabbitmq_list_nodes","rabbitmq_list_policies","rabbitmq_list_queues","rabbitmq_list_vhosts","rabbitmq_publish_message","rabbitmq_purge_queue","railway_create_environment","railway_create_project","railway_create_service","railway_delete_environment","railway_delete_project","railway_delete_service","railway_delete_variable","railway_deploy_service","railway_get_deployment","railway_get_deployment_logs","railway_get_project","railway_list_deployments","railway_list_project_members","railway_list_projects","railway_list_variables","railway_restart_deployment","railway_rollback_deployment","railway_transfer_project","railway_update_project","railway_upsert_variable","rb2b_credit_check","rb2b_email_to_activity","rb2b_hem_to_best_linkedin","rb2b_hem_to_business_profile","rb2b_hem_to_linkedin","rb2b_hem_to_maid","rb2b_ip_to_company","rb2b_ip_to_hem","rb2b_ip_to_maid","rb2b_linkedin_slug_search","rb2b_linkedin_to_best_personal_email","rb2b_linkedin_to_business_profile","rb2b_linkedin_to_hashed_emails","rb2b_linkedin_to_mobile_phone","rb2b_linkedin_to_personal_email","rds_delete","rds_execute","rds_insert","rds_introspect","rds_query","rds_update","reddit_delete","reddit_edit","reddit_get_comments","reddit_get_controversial","reddit_get_info","reddit_get_me","reddit_get_messages","reddit_get_posts","reddit_get_saved","reddit_get_subreddit_info","reddit_get_subreddit_rules","reddit_get_user","reddit_get_user_comments","reddit_get_user_posts","reddit_hide","reddit_hot_posts","reddit_list_my_subreddits","reddit_lock","reddit_mark_all_read","reddit_mark_read","reddit_marknsfw","reddit_mod_approve","reddit_mod_distinguish","reddit_mod_remove","reddit_mod_sticky","reddit_reply","reddit_report","reddit_save","reddit_search","reddit_search_subreddits","reddit_send_message","reddit_submit_post","reddit_subscribe","reddit_unhide","reddit_unlock","reddit_unmarknsfw","reddit_unsave","reddit_vote","redis_command","redis_delete","redis_exists","redis_expire","redis_get","redis_hdel","redis_hget","redis_hgetall","redis_hset","redis_incr","redis_incrby","redis_keys","redis_llen","redis_lpop","redis_lpush","redis_lrange","redis_persist","redis_rpop","redis_rpush","redis_set","redis_setnx","redis_ttl","reducto_parser","reducto_parser_v2","resend_cancel_email","resend_create_audience","resend_create_broadcast","resend_create_contact","resend_delete_audience","resend_delete_contact","resend_get_audience","resend_get_broadcast","resend_get_contact","resend_get_email","resend_list_audiences","resend_list_contacts","resend_list_domains","resend_send","resend_send_broadcast","resend_update_contact","revenuecat_create_purchase","revenuecat_defer_google_subscription","revenuecat_delete_customer","revenuecat_get_customer","revenuecat_grant_entitlement","revenuecat_list_offerings","revenuecat_refund_google_subscription","revenuecat_revoke_entitlement","revenuecat_revoke_google_subscription","revenuecat_update_subscriber_attributes","rippling_bulk_create_custom_object_records","rippling_bulk_delete_custom_object_records","rippling_bulk_update_custom_object_records","rippling_create_business_partner","rippling_create_business_partner_group","rippling_create_custom_app","rippling_create_custom_object","rippling_create_custom_object_field","rippling_create_custom_object_record","rippling_create_custom_page","rippling_create_custom_setting","rippling_create_department","rippling_create_draft_hires","rippling_create_object_category","rippling_create_title","rippling_create_work_location","rippling_delete_business_partner","rippling_delete_business_partner_group","rippling_delete_custom_app","rippling_delete_custom_object","rippling_delete_custom_object_field","rippling_delete_custom_object_record","rippling_delete_custom_page","rippling_delete_custom_setting","rippling_delete_object_category","rippling_delete_title","rippling_delete_work_location","rippling_get_business_partner","rippling_get_business_partner_group","rippling_get_current_user","rippling_get_custom_app","rippling_get_custom_object","rippling_get_custom_object_field","rippling_get_custom_object_record","rippling_get_custom_object_record_by_external_id","rippling_get_custom_page","rippling_get_custom_setting","rippling_get_department","rippling_get_employment_type","rippling_get_job_function","rippling_get_object_category","rippling_get_report_run","rippling_get_supergroup","rippling_get_team","rippling_get_title","rippling_get_user","rippling_get_work_location","rippling_get_worker","rippling_list_business_partner_groups","rippling_list_business_partners","rippling_list_companies","rippling_list_custom_apps","rippling_list_custom_fields","rippling_list_custom_object_fields","rippling_list_custom_object_records","rippling_list_custom_objects","rippling_list_custom_pages","rippling_list_custom_settings","rippling_list_departments","rippling_list_employment_types","rippling_list_entitlements","rippling_list_job_functions","rippling_list_object_categories","rippling_list_supergroup_exclusion_members","rippling_list_supergroup_inclusion_members","rippling_list_supergroup_members","rippling_list_supergroups","rippling_list_teams","rippling_list_titles","rippling_list_users","rippling_list_work_locations","rippling_list_workers","rippling_query_custom_object_records","rippling_trigger_report_run","rippling_update_custom_app","rippling_update_custom_object","rippling_update_custom_object_field","rippling_update_custom_object_record","rippling_update_custom_page","rippling_update_custom_setting","rippling_update_department","rippling_update_object_category","rippling_update_supergroup_exclusion_members","rippling_update_supergroup_inclusion_members","rippling_update_title","rippling_update_work_location","rocketlane_add_field_option","rocketlane_add_project_members","rocketlane_add_task_assignees","rocketlane_add_task_dependencies","rocketlane_add_task_followers","rocketlane_archive_project","rocketlane_assign_placeholders","rocketlane_create_field","rocketlane_create_phase","rocketlane_create_project","rocketlane_create_space","rocketlane_create_space_document","rocketlane_create_task","rocketlane_create_time_entry","rocketlane_create_time_off","rocketlane_delete_field","rocketlane_delete_phase","rocketlane_delete_project","rocketlane_delete_space","rocketlane_delete_space_document","rocketlane_delete_task","rocketlane_delete_time_entry","rocketlane_delete_time_off","rocketlane_get_field","rocketlane_get_invoice","rocketlane_get_invoice_line_items","rocketlane_get_invoice_payments","rocketlane_get_phase","rocketlane_get_project","rocketlane_get_space","rocketlane_get_space_document","rocketlane_get_task","rocketlane_get_time_entry","rocketlane_get_time_off","rocketlane_get_user","rocketlane_import_template","rocketlane_list_fields","rocketlane_list_invoices","rocketlane_list_phases","rocketlane_list_placeholders","rocketlane_list_projects","rocketlane_list_resource_allocations","rocketlane_list_space_documents","rocketlane_list_spaces","rocketlane_list_tasks","rocketlane_list_time_entries","rocketlane_list_time_entry_categories","rocketlane_list_time_offs","rocketlane_list_users","rocketlane_move_task_to_phase","rocketlane_remove_project_members","rocketlane_remove_task_assignees","rocketlane_remove_task_dependencies","rocketlane_remove_task_followers","rocketlane_search_time_entries","rocketlane_unassign_placeholders","rocketlane_update_field","rocketlane_update_field_option","rocketlane_update_phase","rocketlane_update_project","rocketlane_update_space","rocketlane_update_space_document","rocketlane_update_task","rocketlane_update_time_entry","rootly_acknowledge_alert","rootly_add_incident_event","rootly_add_subscribers","rootly_assign_incident_role","rootly_create_action_item","rootly_create_alert","rootly_create_incident","rootly_create_status_page_event","rootly_delete_action_item","rootly_delete_incident","rootly_escalate_alert","rootly_get_alert","rootly_get_incident","rootly_list_action_items","rootly_list_alerts","rootly_list_causes","rootly_list_environments","rootly_list_escalation_policies","rootly_list_functionalities","rootly_list_incident_events","rootly_list_incident_roles","rootly_list_incident_types","rootly_list_incidents","rootly_list_on_calls","rootly_list_playbooks","rootly_list_retrospectives","rootly_list_schedules","rootly_list_services","rootly_list_severities","rootly_list_teams","rootly_list_users","rootly_mitigate_incident","rootly_remove_subscribers","rootly_resolve_alert","rootly_resolve_incident","rootly_run_workflow","rootly_snooze_alert","rootly_unassign_incident_role","rootly_update_action_item","rootly_update_alert","rootly_update_incident","s3_copy_object","s3_create_bucket","s3_delete_bucket","s3_delete_object","s3_delete_objects","s3_get_object","s3_head_object","s3_list_buckets","s3_list_objects","s3_presigned_url","s3_put_object","salesforce_create_account","salesforce_create_case","salesforce_create_contact","salesforce_create_custom_field","salesforce_create_custom_object","salesforce_create_lead","salesforce_create_opportunity","salesforce_create_task","salesforce_delete_account","salesforce_delete_case","salesforce_delete_contact","salesforce_delete_custom_field","salesforce_delete_lead","salesforce_delete_opportunity","salesforce_delete_task","salesforce_describe_object","salesforce_get_accounts","salesforce_get_cases","salesforce_get_contacts","salesforce_get_dashboard","salesforce_get_leads","salesforce_get_opportunities","salesforce_get_report","salesforce_get_tasks","salesforce_list_dashboards","salesforce_list_objects","salesforce_list_report_types","salesforce_list_reports","salesforce_query","salesforce_query_more","salesforce_refresh_dashboard","salesforce_run_report","salesforce_tooling_query","salesforce_update_account","salesforce_update_case","salesforce_update_contact","salesforce_update_custom_field","salesforce_update_lead","salesforce_update_opportunity","salesforce_update_task","sap_concur_approve_expense_report","sap_concur_associate_attendees","sap_concur_create_cash_advance","sap_concur_create_expected_expense","sap_concur_create_expense_report","sap_concur_create_list_item","sap_concur_create_purchase_request","sap_concur_create_quick_expense","sap_concur_create_quick_expense_with_image","sap_concur_create_report_comment","sap_concur_create_travel_request","sap_concur_create_user","sap_concur_delete_expected_expense","sap_concur_delete_expense","sap_concur_delete_expense_report","sap_concur_delete_list_item","sap_concur_delete_travel_request","sap_concur_delete_user","sap_concur_get_allocation","sap_concur_get_budget","sap_concur_get_cash_advance","sap_concur_get_expected_expense","sap_concur_get_expense","sap_concur_get_expense_report","sap_concur_get_itemizations","sap_concur_get_itinerary","sap_concur_get_list","sap_concur_get_list_item","sap_concur_get_purchase_request","sap_concur_get_receipt","sap_concur_get_receipt_status","sap_concur_get_request_cash_advance","sap_concur_get_travel_profile","sap_concur_get_travel_request","sap_concur_get_user","sap_concur_issue_cash_advance","sap_concur_list_allocations","sap_concur_list_attendee_associations","sap_concur_list_budget_categories","sap_concur_list_budgets","sap_concur_list_exceptions","sap_concur_list_expected_expenses","sap_concur_list_expense_reports","sap_concur_list_expenses","sap_concur_list_itineraries","sap_concur_list_list_items","sap_concur_list_lists","sap_concur_list_receipts","sap_concur_list_report_comments","sap_concur_list_reports_to_approve","sap_concur_list_travel_profiles_summary","sap_concur_list_travel_request_comments","sap_concur_list_travel_requests","sap_concur_list_users","sap_concur_move_travel_request","sap_concur_recall_expense_report","sap_concur_remove_all_attendees","sap_concur_search_locations","sap_concur_search_users","sap_concur_send_back_expense_report","sap_concur_submit_expense_report","sap_concur_update_allocation","sap_concur_update_expected_expense","sap_concur_update_expense","sap_concur_update_expense_report","sap_concur_update_list_item","sap_concur_update_travel_request","sap_concur_update_user","sap_concur_upload_exchange_rates","sap_concur_upload_receipt_image","sap_s4hana_create_business_partner","sap_s4hana_create_purchase_order","sap_s4hana_create_purchase_requisition","sap_s4hana_create_sales_order","sap_s4hana_delete_sales_order","sap_s4hana_get_billing_document","sap_s4hana_get_business_partner","sap_s4hana_get_customer","sap_s4hana_get_inbound_delivery","sap_s4hana_get_material_document","sap_s4hana_get_outbound_delivery","sap_s4hana_get_product","sap_s4hana_get_purchase_order","sap_s4hana_get_purchase_requisition","sap_s4hana_get_sales_order","sap_s4hana_get_supplier","sap_s4hana_get_supplier_invoice","sap_s4hana_list_billing_documents","sap_s4hana_list_business_partners","sap_s4hana_list_customers","sap_s4hana_list_inbound_deliveries","sap_s4hana_list_material_documents","sap_s4hana_list_material_stock","sap_s4hana_list_outbound_deliveries","sap_s4hana_list_products","sap_s4hana_list_purchase_orders","sap_s4hana_list_purchase_requisitions","sap_s4hana_list_sales_orders","sap_s4hana_list_supplier_invoices","sap_s4hana_list_suppliers","sap_s4hana_odata_query","sap_s4hana_update_business_partner","sap_s4hana_update_customer","sap_s4hana_update_product","sap_s4hana_update_purchase_order","sap_s4hana_update_purchase_requisition","sap_s4hana_update_sales_order","sap_s4hana_update_supplier","search_tool","secrets_manager_create_secret","secrets_manager_delete_secret","secrets_manager_describe_secret","secrets_manager_get_secret","secrets_manager_list_secrets","secrets_manager_restore_secret","secrets_manager_rotate_secret","secrets_manager_tag_resource","secrets_manager_untag_resource","secrets_manager_update_secret","sendblue_evaluate_service","sendblue_get_message","sendblue_send_group_message","sendblue_send_message","sendblue_send_typing_indicator","sendgrid_add_contact","sendgrid_add_contacts_to_list","sendgrid_create_list","sendgrid_create_template","sendgrid_create_template_version","sendgrid_delete_contacts","sendgrid_delete_list","sendgrid_delete_template","sendgrid_get_contact","sendgrid_get_list","sendgrid_get_template","sendgrid_list_all_lists","sendgrid_list_templates","sendgrid_remove_contacts_from_list","sendgrid_search_contacts","sendgrid_send_mail","sentry_events_get","sentry_events_list","sentry_issues_get","sentry_issues_list","sentry_issues_update","sentry_projects_create","sentry_projects_get","sentry_projects_list","sentry_projects_update","sentry_releases_create","sentry_releases_deploy","sentry_releases_list","sentry_teams_list","serper_search","servicenow_add_incident_comment","servicenow_aggregate","servicenow_close_incident","servicenow_create_change_request","servicenow_create_incident","servicenow_create_record","servicenow_delete_record","servicenow_download_attachment","servicenow_find_user","servicenow_get_change_next_states","servicenow_get_change_request","servicenow_get_ci","servicenow_get_incident","servicenow_get_knowledge_article","servicenow_get_requested_item","servicenow_list_approvals","servicenow_list_attachments","servicenow_list_catalog_items","servicenow_list_change_requests","servicenow_list_change_tasks","servicenow_list_ci_relationships","servicenow_list_group_members","servicenow_list_incidents","servicenow_list_requested_items","servicenow_order_catalog_item","servicenow_read_record","servicenow_resolve_incident","servicenow_search_cis","servicenow_search_knowledge","servicenow_update_approval","servicenow_update_change_request","servicenow_update_change_state","servicenow_update_incident","servicenow_update_record","servicenow_upload_attachment","ses_create_configuration_set","ses_create_email_identity","ses_create_template","ses_delete_email_identity","ses_delete_suppressed_destination","ses_delete_template","ses_get_account","ses_get_email_identity","ses_get_suppressed_destination","ses_get_template","ses_list_identities","ses_list_suppressed_destinations","ses_list_templates","ses_put_suppressed_destination","ses_send_bulk_email","ses_send_custom_verification_email","ses_send_email","ses_send_templated_email","ses_update_template","sftp_delete","sftp_download","sftp_list","sftp_mkdir","sftp_upload","sharepoint_add_list_items","sharepoint_create_list","sharepoint_create_page","sharepoint_delete_file","sharepoint_delete_list_item","sharepoint_delete_page","sharepoint_download_file","sharepoint_get_drive_item","sharepoint_get_list","sharepoint_get_list_item","sharepoint_list_sites","sharepoint_publish_page","sharepoint_read_page","sharepoint_update_list","sharepoint_update_page","sharepoint_upload_file","shopify_adjust_inventory","shopify_cancel_order","shopify_create_customer","shopify_create_fulfillment","shopify_create_product","shopify_delete_customer","shopify_delete_product","shopify_get_collection","shopify_get_customer","shopify_get_inventory_level","shopify_get_order","shopify_get_product","shopify_list_collections","shopify_list_customers","shopify_list_inventory_items","shopify_list_locations","shopify_list_orders","shopify_list_products","shopify_update_customer","shopify_update_order","shopify_update_product","similarweb_bounce_rate","similarweb_page_views","similarweb_pages_per_visit","similarweb_traffic_visits","similarweb_visit_duration","similarweb_website_overview","sixtyfour_enrich_company","sixtyfour_enrich_lead","sixtyfour_find_email","sixtyfour_find_phone","slack_add_reaction","slack_archive_conversation","slack_canvas","slack_create_channel_canvas","slack_create_conversation","slack_delete_canvas","slack_delete_message","slack_delete_scheduled_message","slack_download","slack_edit_canvas","slack_ephemeral_message","slack_get_canvas","slack_get_channel_history","slack_get_channel_info","slack_get_message","slack_get_permalink","slack_get_thread","slack_get_thread_replies","slack_get_user","slack_get_user_presence","slack_invite_to_conversation","slack_list_canvases","slack_list_channels","slack_list_members","slack_list_scheduled_messages","slack_list_users","slack_lookup_canvas_sections","slack_message","slack_message_reader","slack_open_view","slack_publish_view","slack_push_view","slack_remove_reaction","slack_rename_conversation","slack_schedule_message","slack_set_conversation_purpose","slack_set_conversation_topic","slack_set_status","slack_set_suggested_prompts","slack_set_title","slack_update_message","slack_update_view","smartlead_add_email_accounts_to_campaign","smartlead_add_leads_to_campaign","smartlead_create_campaign","smartlead_create_lead_list","smartlead_delete_campaign","smartlead_delete_campaign_webhook","smartlead_delete_lead_from_campaign","smartlead_delete_lead_list","smartlead_duplicate_campaign","smartlead_export_campaign_leads","smartlead_get_campaign","smartlead_get_campaign_analytics","smartlead_get_campaign_analytics_by_date","smartlead_get_campaign_lead_statistics","smartlead_get_campaign_mailbox_statistics","smartlead_get_campaign_sequences","smartlead_get_campaign_statistics","smartlead_get_campaign_top_level_analytics_by_date","smartlead_get_campaign_webhook_summary","smartlead_get_lead_by_email","smartlead_get_lead_by_id","smartlead_get_lead_list","smartlead_get_lead_message_history","smartlead_list_campaign_email_accounts","smartlead_list_campaign_leads","smartlead_list_campaign_webhooks","smartlead_list_campaigns","smartlead_list_clients","smartlead_list_email_accounts","smartlead_list_inbox_replies","smartlead_list_lead_activities","smartlead_list_lead_categories","smartlead_list_lead_lists","smartlead_mark_lead_complete","smartlead_pause_lead","smartlead_remove_email_accounts_from_campaign","smartlead_resume_lead","smartlead_save_campaign_sequences","smartlead_unsubscribe_lead_from_campaign","smartlead_unsubscribe_lead_globally","smartlead_update_campaign_schedule","smartlead_update_campaign_settings","smartlead_update_campaign_status","smartlead_update_lead","smartlead_update_lead_category","smartlead_update_lead_list","smartlead_upsert_campaign_webhook","sms_send","smtp_send_mail","snowflake_alter_warehouse","snowflake_call_procedure","snowflake_cancel_statement","snowflake_cancel_task_run","snowflake_delete_rows","snowflake_execute_sql","snowflake_get_statement","snowflake_get_task","snowflake_get_task_run","snowflake_get_task_run_output","snowflake_get_warehouse","snowflake_insert_rows","snowflake_introspect_schema","snowflake_list_copy_history","snowflake_list_databases","snowflake_list_query_history","snowflake_list_schemas","snowflake_list_tables","snowflake_list_task_runs","snowflake_list_tasks","snowflake_list_warehouses","snowflake_load_data","snowflake_resume_task","snowflake_resume_warehouse","snowflake_run_task","snowflake_suspend_task","snowflake_suspend_warehouse","snowflake_unload_data","snowflake_update_rows","snowflake_upsert_rows","splunk_cancel_search_job","splunk_create_search_job","splunk_dispatch_saved_search","splunk_get_fired_alerts","splunk_get_saved_search","splunk_get_search_job","splunk_get_search_results","splunk_list_apps","splunk_list_fired_alerts","splunk_list_indexes","splunk_list_saved_searches","splunk_run_search","sportmonks_core_get_cities","sportmonks_core_get_city","sportmonks_core_get_continent","sportmonks_core_get_continents","sportmonks_core_get_countries","sportmonks_core_get_country","sportmonks_core_get_entity_filters","sportmonks_core_get_my_usage","sportmonks_core_get_region","sportmonks_core_get_regions","sportmonks_core_get_timezones","sportmonks_core_get_type","sportmonks_core_get_type_by_entity","sportmonks_core_get_types","sportmonks_core_search_cities","sportmonks_core_search_countries","sportmonks_core_search_regions","sportmonks_football_expected_by_player","sportmonks_football_expected_by_team","sportmonks_football_get_all_commentaries","sportmonks_football_get_all_fixtures","sportmonks_football_get_all_players","sportmonks_football_get_all_rivals","sportmonks_football_get_all_teams","sportmonks_football_get_all_transfer_rumours","sportmonks_football_get_all_transfers","sportmonks_football_get_brackets_by_season","sportmonks_football_get_coach","sportmonks_football_get_coaches","sportmonks_football_get_coaches_by_country","sportmonks_football_get_commentaries_by_fixture","sportmonks_football_get_current_leagues_by_team","sportmonks_football_get_expected_lineups_by_player","sportmonks_football_get_expected_lineups_by_team","sportmonks_football_get_extended_team_squad","sportmonks_football_get_fixture","sportmonks_football_get_fixtures_by_date","sportmonks_football_get_fixtures_by_date_range","sportmonks_football_get_fixtures_by_date_range_for_team","sportmonks_football_get_fixtures_by_ids","sportmonks_football_get_grouped_standings_by_round","sportmonks_football_get_head_to_head","sportmonks_football_get_inplay_livescores","sportmonks_football_get_latest_coaches","sportmonks_football_get_latest_fixtures","sportmonks_football_get_latest_livescores","sportmonks_football_get_latest_players","sportmonks_football_get_latest_totw","sportmonks_football_get_latest_transfers","sportmonks_football_get_league","sportmonks_football_get_leagues","sportmonks_football_get_leagues_by_country","sportmonks_football_get_leagues_by_date","sportmonks_football_get_leagues_by_team","sportmonks_football_get_live_leagues","sportmonks_football_get_live_probabilities","sportmonks_football_get_live_probabilities_by_fixture","sportmonks_football_get_live_standings_by_league","sportmonks_football_get_livescores","sportmonks_football_get_match_facts","sportmonks_football_get_match_facts_by_date_range","sportmonks_football_get_match_facts_by_fixture","sportmonks_football_get_match_facts_by_league","sportmonks_football_get_past_fixtures_by_tv_station","sportmonks_football_get_player","sportmonks_football_get_players_by_country","sportmonks_football_get_postmatch_news","sportmonks_football_get_postmatch_news_by_season","sportmonks_football_get_predictability_by_league","sportmonks_football_get_prematch_news","sportmonks_football_get_prematch_news_by_season","sportmonks_football_get_prematch_news_upcoming","sportmonks_football_get_probabilities","sportmonks_football_get_probabilities_by_fixture","sportmonks_football_get_referee","sportmonks_football_get_referees","sportmonks_football_get_referees_by_country","sportmonks_football_get_referees_by_season","sportmonks_football_get_rivals_by_team","sportmonks_football_get_round","sportmonks_football_get_round_statistics","sportmonks_football_get_rounds","sportmonks_football_get_rounds_by_season","sportmonks_football_get_schedules_by_season","sportmonks_football_get_schedules_by_season_and_team","sportmonks_football_get_schedules_by_team","sportmonks_football_get_season","sportmonks_football_get_seasons","sportmonks_football_get_seasons_by_team","sportmonks_football_get_stage","sportmonks_football_get_stage_statistics","sportmonks_football_get_stages","sportmonks_football_get_stages_by_season","sportmonks_football_get_standing_corrections_by_season","sportmonks_football_get_standings","sportmonks_football_get_standings_by_round","sportmonks_football_get_standings_by_season","sportmonks_football_get_state","sportmonks_football_get_states","sportmonks_football_get_team","sportmonks_football_get_team_rankings","sportmonks_football_get_team_rankings_by_date","sportmonks_football_get_team_rankings_by_team","sportmonks_football_get_team_squad","sportmonks_football_get_team_squad_by_season","sportmonks_football_get_teams_by_country","sportmonks_football_get_teams_by_season","sportmonks_football_get_topscorers_by_season","sportmonks_football_get_topscorers_by_stage","sportmonks_football_get_totw","sportmonks_football_get_totw_by_round","sportmonks_football_get_transfer","sportmonks_football_get_transfer_rumour","sportmonks_football_get_transfer_rumours_between_dates","sportmonks_football_get_transfer_rumours_by_player","sportmonks_football_get_transfer_rumours_by_team","sportmonks_football_get_transfers_between_dates","sportmonks_football_get_transfers_by_player","sportmonks_football_get_transfers_by_team","sportmonks_football_get_tv_station","sportmonks_football_get_tv_stations","sportmonks_football_get_tv_stations_by_fixture","sportmonks_football_get_upcoming_fixtures_by_market","sportmonks_football_get_upcoming_fixtures_by_tv_station","sportmonks_football_get_value_bets","sportmonks_football_get_value_bets_by_fixture","sportmonks_football_get_venue","sportmonks_football_get_venues","sportmonks_football_get_venues_by_season","sportmonks_football_search_coaches","sportmonks_football_search_fixtures","sportmonks_football_search_leagues","sportmonks_football_search_players","sportmonks_football_search_referees","sportmonks_football_search_rounds","sportmonks_football_search_seasons","sportmonks_football_search_stages","sportmonks_football_search_teams","sportmonks_football_search_venues","sportmonks_motorsport_get_all_fixtures","sportmonks_motorsport_get_current_leagues_by_team","sportmonks_motorsport_get_driver","sportmonks_motorsport_get_driver_standings","sportmonks_motorsport_get_driver_standings_by_season","sportmonks_motorsport_get_drivers","sportmonks_motorsport_get_drivers_by_country","sportmonks_motorsport_get_drivers_by_season","sportmonks_motorsport_get_fixture","sportmonks_motorsport_get_fixtures_by_date","sportmonks_motorsport_get_fixtures_by_date_range","sportmonks_motorsport_get_fixtures_by_ids","sportmonks_motorsport_get_laps_by_fixture","sportmonks_motorsport_get_laps_by_fixture_and_driver","sportmonks_motorsport_get_laps_by_fixture_and_lap","sportmonks_motorsport_get_latest_laps_by_fixture","sportmonks_motorsport_get_latest_pitstops_by_fixture","sportmonks_motorsport_get_latest_stints_by_fixture","sportmonks_motorsport_get_latest_updated_drivers","sportmonks_motorsport_get_latest_updated_fixtures","sportmonks_motorsport_get_league","sportmonks_motorsport_get_leagues","sportmonks_motorsport_get_leagues_by_country","sportmonks_motorsport_get_leagues_by_date","sportmonks_motorsport_get_leagues_by_live","sportmonks_motorsport_get_leagues_by_team","sportmonks_motorsport_get_livescores","sportmonks_motorsport_get_pitstops_by_fixture","sportmonks_motorsport_get_pitstops_by_fixture_and_driver","sportmonks_motorsport_get_pitstops_by_fixture_and_lap","sportmonks_motorsport_get_race_results_by_season_and_driver","sportmonks_motorsport_get_race_results_by_season_and_team","sportmonks_motorsport_get_schedules_by_season","sportmonks_motorsport_get_season","sportmonks_motorsport_get_seasons","sportmonks_motorsport_get_stage","sportmonks_motorsport_get_stages","sportmonks_motorsport_get_stages_by_season","sportmonks_motorsport_get_state","sportmonks_motorsport_get_states","sportmonks_motorsport_get_stints_by_fixture","sportmonks_motorsport_get_stints_by_fixture_and_driver","sportmonks_motorsport_get_stints_by_fixture_and_stint","sportmonks_motorsport_get_team","sportmonks_motorsport_get_team_standings","sportmonks_motorsport_get_team_standings_by_season","sportmonks_motorsport_get_teams","sportmonks_motorsport_get_teams_by_country","sportmonks_motorsport_get_teams_by_season","sportmonks_motorsport_get_venue","sportmonks_motorsport_get_venues","sportmonks_motorsport_get_venues_by_season","sportmonks_motorsport_search_drivers","sportmonks_motorsport_search_leagues","sportmonks_motorsport_search_stages","sportmonks_motorsport_search_teams","sportmonks_motorsport_search_venues","sportmonks_odds_get_all_historical_odds","sportmonks_odds_get_all_inplay_odds","sportmonks_odds_get_all_pre_match_odds","sportmonks_odds_get_all_premium_odds","sportmonks_odds_get_bookmaker","sportmonks_odds_get_bookmaker_event_ids_by_fixture","sportmonks_odds_get_bookmakers","sportmonks_odds_get_bookmakers_by_fixture","sportmonks_odds_get_inplay_odds_by_fixture","sportmonks_odds_get_inplay_odds_by_fixture_and_bookmaker","sportmonks_odds_get_inplay_odds_by_fixture_and_market","sportmonks_odds_get_last_updated_inplay_odds","sportmonks_odds_get_last_updated_pre_match_odds","sportmonks_odds_get_market","sportmonks_odds_get_markets","sportmonks_odds_get_pre_match_odds_by_fixture","sportmonks_odds_get_pre_match_odds_by_fixture_and_bookmaker","sportmonks_odds_get_pre_match_odds_by_fixture_and_market","sportmonks_odds_get_premium_odds_by_fixture","sportmonks_odds_get_premium_odds_by_fixture_and_bookmaker","sportmonks_odds_get_premium_odds_by_fixture_and_market","sportmonks_odds_get_updated_historical_odds_between","sportmonks_odds_get_updated_premium_odds_between","sportmonks_odds_search_bookmakers","sportmonks_odds_search_markets","spotify_add_playlist_cover","spotify_add_to_queue","spotify_add_tracks_to_playlist","spotify_check_following","spotify_check_playlist_followers","spotify_check_saved_albums","spotify_check_saved_audiobooks","spotify_check_saved_episodes","spotify_check_saved_shows","spotify_check_saved_tracks","spotify_create_playlist","spotify_follow_artists","spotify_follow_playlist","spotify_get_album","spotify_get_album_tracks","spotify_get_albums","spotify_get_artist","spotify_get_artist_albums","spotify_get_artist_top_tracks","spotify_get_artists","spotify_get_audiobook","spotify_get_audiobook_chapters","spotify_get_audiobooks","spotify_get_categories","spotify_get_current_user","spotify_get_currently_playing","spotify_get_devices","spotify_get_episode","spotify_get_episodes","spotify_get_followed_artists","spotify_get_markets","spotify_get_new_releases","spotify_get_playback_state","spotify_get_playlist","spotify_get_playlist_cover","spotify_get_playlist_tracks","spotify_get_queue","spotify_get_recently_played","spotify_get_saved_albums","spotify_get_saved_audiobooks","spotify_get_saved_episodes","spotify_get_saved_shows","spotify_get_saved_tracks","spotify_get_show","spotify_get_show_episodes","spotify_get_shows","spotify_get_top_artists","spotify_get_top_tracks","spotify_get_track","spotify_get_tracks","spotify_get_user_playlists","spotify_get_user_profile","spotify_pause","spotify_play","spotify_remove_saved_albums","spotify_remove_saved_audiobooks","spotify_remove_saved_episodes","spotify_remove_saved_shows","spotify_remove_saved_tracks","spotify_remove_tracks_from_playlist","spotify_reorder_playlist_items","spotify_replace_playlist_items","spotify_save_albums","spotify_save_audiobooks","spotify_save_episodes","spotify_save_shows","spotify_save_tracks","spotify_search","spotify_seek","spotify_set_repeat","spotify_set_shuffle","spotify_set_volume","spotify_skip_next","spotify_skip_previous","spotify_transfer_playback","spotify_unfollow_artists","spotify_unfollow_playlist","spotify_update_playlist","sqs_send","square_batch_retrieve_inventory_counts","square_cancel_invoice","square_cancel_payment","square_complete_payment","square_create_catalog_image","square_create_customer","square_create_invoice","square_create_order","square_create_payment","square_delete_catalog_object","square_delete_customer","square_delete_invoice","square_get_catalog_object","square_get_customer","square_get_invoice","square_get_location","square_get_order","square_get_payment","square_get_refund","square_list_catalog","square_list_customers","square_list_invoices","square_list_locations","square_list_payments","square_list_refunds","square_pay_order","square_publish_invoice","square_refund_payment","square_search_catalog_objects","square_search_customers","square_search_invoices","square_search_orders","square_update_customer","square_upsert_catalog_object","ssh_check_command_exists","ssh_check_file_exists","ssh_create_directory","ssh_delete_file","ssh_download_file","ssh_execute_command","ssh_execute_script","ssh_get_system_info","ssh_list_directory","ssh_move_rename","ssh_read_file_content","ssh_upload_file","ssh_write_file_content","stagehand_agent","stagehand_extract","stripe_cancel_payment_intent","stripe_cancel_subscription","stripe_capture_charge","stripe_capture_payment_intent","stripe_confirm_payment_intent","stripe_create_charge","stripe_create_customer","stripe_create_invoice","stripe_create_payment_intent","stripe_create_price","stripe_create_product","stripe_create_subscription","stripe_delete_customer","stripe_delete_invoice","stripe_delete_product","stripe_finalize_invoice","stripe_list_charges","stripe_list_customers","stripe_list_events","stripe_list_invoices","stripe_list_payment_intents","stripe_list_prices","stripe_list_products","stripe_list_subscriptions","stripe_pay_invoice","stripe_resume_subscription","stripe_retrieve_charge","stripe_retrieve_customer","stripe_retrieve_event","stripe_retrieve_invoice","stripe_retrieve_payment_intent","stripe_retrieve_price","stripe_retrieve_product","stripe_retrieve_subscription","stripe_search_charges","stripe_search_customers","stripe_search_invoices","stripe_search_payment_intents","stripe_search_prices","stripe_search_products","stripe_search_subscriptions","stripe_send_invoice","stripe_update_charge","stripe_update_customer","stripe_update_invoice","stripe_update_payment_intent","stripe_update_price","stripe_update_product","stripe_update_subscription","stripe_void_invoice","sts_assume_role","sts_assume_role_with_saml","sts_assume_role_with_web_identity","sts_get_access_key_info","sts_get_caller_identity","sts_get_session_token","stt_assemblyai","stt_assemblyai_v2","stt_deepgram","stt_deepgram_v2","stt_elevenlabs","stt_elevenlabs_v2","stt_gemini","stt_gemini_v2","stt_whisper","stt_whisper_v2","supabase_count","supabase_delete","supabase_get_row","supabase_insert","supabase_introspect","supabase_invoke_function","supabase_query","supabase_rpc","supabase_storage_copy","supabase_storage_create_bucket","supabase_storage_create_signed_upload_url","supabase_storage_create_signed_url","supabase_storage_delete","supabase_storage_delete_bucket","supabase_storage_download","supabase_storage_empty_bucket","supabase_storage_get_public_url","supabase_storage_list","supabase_storage_list_buckets","supabase_storage_move","supabase_storage_update_bucket","supabase_storage_upload","supabase_text_search","supabase_update","supabase_upsert","supabase_vector_search","table_batch_insert_rows","table_create","table_delete_row","table_delete_rows_by_filter","table_get_row","table_get_schema","table_insert_row","table_list","table_query_rows","table_query_rows_v2","table_update_row","table_update_rows_by_filter","table_upsert_row","tailscale_authorize_device","tailscale_create_auth_key","tailscale_delete_auth_key","tailscale_delete_device","tailscale_delete_user","tailscale_expire_device_key","tailscale_get_acl","tailscale_get_auth_key","tailscale_get_device","tailscale_get_device_routes","tailscale_get_dns_preferences","tailscale_get_dns_searchpaths","tailscale_list_auth_keys","tailscale_list_devices","tailscale_list_dns_nameservers","tailscale_list_users","tailscale_set_acl","tailscale_set_device_routes","tailscale_set_device_tags","tailscale_set_dns_nameservers","tailscale_set_dns_preferences","tailscale_set_dns_searchpaths","tailscale_suspend_user","tailscale_update_device_key","tavily_crawl","tavily_extract","tavily_map","tavily_search","telegram_copy_message","telegram_delete_message","telegram_edit_message_text","telegram_forward_message","telegram_get_chat","telegram_get_chat_member","telegram_message","telegram_pin_message","telegram_send_animation","telegram_send_audio","telegram_send_chat_action","telegram_send_contact","telegram_send_document","telegram_send_location","telegram_send_photo","telegram_send_poll","telegram_send_video","telegram_set_message_reaction","telegram_unpin_message","temporal_cancel_workflow","temporal_count_workflows","temporal_create_schedule","temporal_delete_schedule","temporal_describe_schedule","temporal_describe_task_queue","temporal_describe_workflow","temporal_get_workflow_history","temporal_list_schedules","temporal_list_workflows","temporal_pause_schedule","temporal_query_workflow","temporal_reset_workflow","temporal_signal_with_start","temporal_signal_workflow","temporal_start_workflow","temporal_terminate_workflow","temporal_trigger_schedule","temporal_unpause_schedule","temporal_update_workflow","textract_analyze_expense","textract_analyze_id","textract_parser","textract_parser_v2","thinking_tool","thrive_add_audience_managers","thrive_add_audience_members","thrive_add_user_tags","thrive_create_assignment","thrive_create_audience","thrive_create_completion","thrive_create_user","thrive_delete_assignment","thrive_delete_audience","thrive_delete_user","thrive_get_activity","thrive_get_assignment","thrive_get_audience","thrive_get_completion","thrive_get_content","thrive_get_cpd_category","thrive_get_cpd_entry","thrive_get_cpd_requirement","thrive_get_enrolment","thrive_get_skill_levels","thrive_get_tag","thrive_get_user_by_id","thrive_get_user_by_ref","thrive_list_assignments","thrive_list_audience_managers","thrive_list_audience_members","thrive_list_audiences","thrive_list_completions","thrive_list_enrolments","thrive_list_tags","thrive_query_activities","thrive_query_content","thrive_query_cpd_categories","thrive_query_cpd_entries","thrive_query_cpd_requirements","thrive_query_cpd_user_summaries","thrive_remove_audience_manager","thrive_remove_audience_member","thrive_remove_user_tags","thrive_replace_audience_managers","thrive_replace_audience_members","thrive_search_users","thrive_suspend_user","thrive_update_assignment","thrive_update_audience","thrive_update_user","thrive_update_user_skills","tiktok_get_post_status","tiktok_get_user","tiktok_list_videos","tiktok_query_videos","tiktok_upload_video_draft","tinybird_append_datasource","tinybird_delete_datasource_rows","tinybird_events","tinybird_get_job","tinybird_query","tinybird_query_pipe","tinybird_truncate_datasource","trello_add_checklist","trello_add_checklist_item","trello_add_comment","trello_add_label","trello_add_member","trello_create_board","trello_create_card","trello_create_list","trello_delete_card","trello_get_actions","trello_get_board","trello_get_card","trello_list_cards","trello_list_lists","trello_list_members","trello_remove_label","trello_remove_member","trello_search","trello_update_card","trello_update_checklist_item","trello_update_list","trigger_dev_activate_schedule","trigger_dev_add_run_tags","trigger_dev_batch_trigger_task","trigger_dev_cancel_run","trigger_dev_complete_waitpoint_token","trigger_dev_create_env_var","trigger_dev_create_schedule","trigger_dev_create_waitpoint_token","trigger_dev_deactivate_schedule","trigger_dev_delete_env_var","trigger_dev_delete_schedule","trigger_dev_execute_query","trigger_dev_get_batch","trigger_dev_get_batch_results","trigger_dev_get_deployment","trigger_dev_get_env_var","trigger_dev_get_latest_deployment","trigger_dev_get_query_schema","trigger_dev_get_queue","trigger_dev_get_run","trigger_dev_get_run_events","trigger_dev_get_run_result","trigger_dev_get_run_trace","trigger_dev_get_schedule","trigger_dev_get_waitpoint_token","trigger_dev_import_env_vars","trigger_dev_list_deployments","trigger_dev_list_env_vars","trigger_dev_list_queues","trigger_dev_list_runs","trigger_dev_list_schedules","trigger_dev_list_timezones","trigger_dev_list_waitpoint_tokens","trigger_dev_override_queue_concurrency","trigger_dev_pause_queue","trigger_dev_promote_deployment","trigger_dev_replay_run","trigger_dev_reschedule_run","trigger_dev_reset_queue_concurrency","trigger_dev_resume_queue","trigger_dev_trigger_task","trigger_dev_update_env_var","trigger_dev_update_run_metadata","trigger_dev_update_schedule","tts_azure","tts_cartesia","tts_deepgram","tts_elevenlabs","tts_google","tts_openai","tts_playht","twilio_send_sms","twilio_voice_get_recording","twilio_voice_list_calls","twilio_voice_make_call","typeform_create_form","typeform_delete_form","typeform_files","typeform_get_form","typeform_insights","typeform_list_forms","typeform_responses","typeform_update_form","upstash_redis_command","upstash_redis_delete","upstash_redis_exists","upstash_redis_expire","upstash_redis_get","upstash_redis_hget","upstash_redis_hgetall","upstash_redis_hset","upstash_redis_incr","upstash_redis_incrby","upstash_redis_keys","upstash_redis_lpush","upstash_redis_lrange","upstash_redis_set","upstash_redis_setnx","upstash_redis_ttl","uptimerobot_create_alert_contact","uptimerobot_create_maintenance_window","uptimerobot_create_monitor","uptimerobot_create_psp","uptimerobot_delete_alert_contact","uptimerobot_delete_maintenance_window","uptimerobot_delete_monitor","uptimerobot_delete_psp","uptimerobot_get_account","uptimerobot_get_alert_contact","uptimerobot_get_incident","uptimerobot_get_maintenance_window","uptimerobot_get_monitor","uptimerobot_get_psp","uptimerobot_list_alert_contacts","uptimerobot_list_incidents","uptimerobot_list_maintenance_windows","uptimerobot_list_monitors","uptimerobot_list_psps","uptimerobot_pause_monitor","uptimerobot_start_monitor","uptimerobot_update_maintenance_window","uptimerobot_update_monitor","uptimerobot_update_psp","vanta_download_document_file","vanta_get_control","vanta_get_document","vanta_get_framework","vanta_get_person","vanta_get_policy","vanta_get_risk_scenario","vanta_get_test","vanta_get_vendor","vanta_get_vulnerable_asset","vanta_list_control_documents","vanta_list_control_tests","vanta_list_controls","vanta_list_document_uploads","vanta_list_documents","vanta_list_framework_controls","vanta_list_frameworks","vanta_list_monitored_computers","vanta_list_people","vanta_list_policies","vanta_list_risk_scenarios","vanta_list_test_entities","vanta_list_tests","vanta_list_vendors","vanta_list_vulnerabilities","vanta_list_vulnerability_remediations","vanta_list_vulnerable_assets","vanta_submit_document","vanta_upload_document_file","vercel_add_domain","vercel_add_project_domain","vercel_cancel_deployment","vercel_create_alias","vercel_create_check","vercel_create_deployment","vercel_create_dns_record","vercel_create_edge_config","vercel_create_env_var","vercel_create_project","vercel_create_webhook","vercel_delete_alias","vercel_delete_deployment","vercel_delete_dns_record","vercel_delete_domain","vercel_delete_edge_config","vercel_delete_env_var","vercel_delete_project","vercel_delete_webhook","vercel_get_alias","vercel_get_check","vercel_get_deployment","vercel_get_deployment_events","vercel_get_domain","vercel_get_domain_config","vercel_get_edge_config","vercel_get_edge_config_items","vercel_get_env_vars","vercel_get_project","vercel_get_team","vercel_get_user","vercel_get_webhook","vercel_list_aliases","vercel_list_checks","vercel_list_deployment_files","vercel_list_deployments","vercel_list_dns_records","vercel_list_domains","vercel_list_edge_configs","vercel_list_project_domains","vercel_list_projects","vercel_list_team_members","vercel_list_teams","vercel_list_webhooks","vercel_pause_project","vercel_promote_deployment","vercel_remove_project_domain","vercel_rerequest_check","vercel_unpause_project","vercel_update_check","vercel_update_dns_record","vercel_update_edge_config_items","vercel_update_env_var","vercel_update_project","vercel_update_project_domain","vercel_verify_project_domain","video_falai","video_luma","video_minimax","video_runway","video_veo","vision_tool","vision_tool_v2","wealthbox_read_contact","wealthbox_read_note","wealthbox_read_task","wealthbox_write_contact","wealthbox_write_note","wealthbox_write_task","webflow_create_item","webflow_delete_item","webflow_get_item","webflow_list_items","webflow_update_item","webhook_request","whatsapp_get_media","whatsapp_mark_read","whatsapp_send_interactive","whatsapp_send_media","whatsapp_send_message","whatsapp_send_reaction","whatsapp_send_template","whatsapp_upload_media","wikipedia_content","wikipedia_random","wikipedia_search","wikipedia_summary","windchill_check_in_document","windchill_check_in_documents","windchill_check_out_document","windchill_check_out_documents","windchill_create_document","windchill_create_documents","windchill_delete_document","windchill_delete_documents","windchill_download_attachment","windchill_download_primary_content","windchill_get_document","windchill_get_document_structure","windchill_get_primary_content","windchill_get_valid_state_transitions","windchill_list_attachments","windchill_list_documents","windchill_revise_document","windchill_revise_documents","windchill_set_lifecycle_state","windchill_undo_check_out_document","windchill_undo_check_out_documents","windchill_update_common_properties","windchill_update_document","windchill_update_document_security_labels","windchill_update_documents","windchill_upload_attachments","windchill_upload_primary_content","wiza_company_enrichment","wiza_get_credits","wiza_individual_reveal","wiza_prospect_search","wordpress_create_category","wordpress_create_comment","wordpress_create_page","wordpress_create_post","wordpress_create_tag","wordpress_delete_category","wordpress_delete_comment","wordpress_delete_media","wordpress_delete_page","wordpress_delete_post","wordpress_delete_tag","wordpress_get_category","wordpress_get_current_user","wordpress_get_media","wordpress_get_page","wordpress_get_post","wordpress_get_tag","wordpress_get_user","wordpress_list_categories","wordpress_list_comments","wordpress_list_media","wordpress_list_pages","wordpress_list_posts","wordpress_list_tags","wordpress_list_users","wordpress_search_content","wordpress_update_category","wordpress_update_comment","wordpress_update_page","wordpress_update_post","wordpress_update_tag","wordpress_upload_media","workday_assign_onboarding","workday_change_job","workday_create_prehire","workday_get_compensation","workday_get_organizations","workday_get_worker","workday_hire_employee","workday_list_workers","workday_terminate_worker","workday_update_worker","workflow_executor","x_create_bookmark","x_create_tweet","x_delete_bookmark","x_delete_tweet","x_get_blocking","x_get_bookmarks","x_get_followers","x_get_following","x_get_liked_tweets","x_get_liking_users","x_get_me","x_get_personalized_trends","x_get_quote_tweets","x_get_retweeted_by","x_get_trends_by_woeid","x_get_tweets_by_ids","x_get_usage","x_get_user_mentions","x_get_user_timeline","x_get_user_tweets","x_hide_reply","x_manage_block","x_manage_follow","x_manage_like","x_manage_mute","x_manage_retweet","x_read","x_search","x_search_tweets","x_search_users","x_user","x_write","youtube_channel_info","youtube_channel_playlists","youtube_channel_videos","youtube_comments","youtube_playlist_items","youtube_search","youtube_trending","youtube_video_categories","youtube_video_details","zendesk_autocomplete_organizations","zendesk_create_organization","zendesk_create_organizations_bulk","zendesk_create_ticket","zendesk_create_tickets_bulk","zendesk_create_user","zendesk_create_users_bulk","zendesk_delete_organization","zendesk_delete_ticket","zendesk_delete_user","zendesk_get_current_user","zendesk_get_organization","zendesk_get_organizations","zendesk_get_ticket","zendesk_get_tickets","zendesk_get_user","zendesk_get_users","zendesk_merge_tickets","zendesk_search","zendesk_search_count","zendesk_search_users","zendesk_update_organization","zendesk_update_ticket","zendesk_update_tickets_bulk","zendesk_update_user","zendesk_update_users_bulk","zep_add_messages","zep_add_user","zep_create_thread","zep_delete_thread","zep_get_context","zep_get_messages","zep_get_threads","zep_get_user","zep_get_user_threads","zerobounce_get_credits","zerobounce_verify_email","zoho_desk_add_comment","zoho_desk_get_attachment","zoho_desk_get_contact","zoho_desk_get_thread","zoho_desk_get_ticket","zoho_desk_list_comments","zoho_desk_list_organizations","zoho_desk_list_threads","zoho_desk_list_tickets","zoho_desk_update_ticket","zoom_create_meeting","zoom_delete_meeting","zoom_delete_recording","zoom_get_meeting","zoom_get_meeting_invitation","zoom_get_meeting_recordings","zoom_list_meetings","zoom_list_past_participants","zoom_list_recordings","zoom_update_meeting","zoominfo_enrich_companies","zoominfo_enrich_contacts","zoominfo_search_companies","zoominfo_search_contacts","zoominfo_search_intent","zoominfo_search_news"]' ) export default toolIds diff --git a/apps/sim/tools/generated/tool-metadata.ts b/apps/sim/tools/generated/tool-metadata.ts index 760172e97f..832cd44cc3 100644 --- a/apps/sim/tools/generated/tool-metadata.ts +++ b/apps/sim/tools/generated/tool-metadata.ts @@ -3,7 +3,7 @@ /** Serializable metadata for every built-in tool, keyed by tool id. */ const toolMetadata: Record = JSON.parse( - '{"a2a_cancel_task":{"id":"a2a_cancel_task","name":"A2A Cancel Task","description":"Request cancellation of an in-progress A2A task.","version":"1.0.0","params":{"agentUrl":{"type":"string","required":true,"visibility":"user-only","description":"The A2A agent endpoint URL"},"taskId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The task ID to cancel"},"apiKey":{"type":"string","required":false,"visibility":"user-only","description":"API key for authentication (if required)"}}},"a2a_get_agent_card":{"id":"a2a_get_agent_card","name":"A2A Get Agent Card","description":"Fetch the Agent Card (discovery document) for an external A2A agent.","version":"1.0.0","params":{"agentUrl":{"type":"string","required":true,"visibility":"user-only","description":"The A2A agent endpoint URL"},"apiKey":{"type":"string","required":false,"visibility":"user-only","description":"API key for authentication (if required)"}}},"a2a_get_task":{"id":"a2a_get_task","name":"A2A Get Task","description":"Retrieve the current state and result of an A2A task.","version":"1.0.0","params":{"agentUrl":{"type":"string","required":true,"visibility":"user-only","description":"The A2A agent endpoint URL"},"taskId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The task ID to retrieve"},"historyLength":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of history messages to include"},"apiKey":{"type":"string","required":false,"visibility":"user-only","description":"API key for authentication (if required)"}}},"a2a_send_message":{"id":"a2a_send_message","name":"A2A Send Message","description":"Send a message to an external A2A agent and return its response.","version":"1.0.0","params":{"agentUrl":{"type":"string","required":true,"visibility":"user-only","description":"The A2A agent endpoint URL"},"message":{"type":"string","required":true,"visibility":"user-or-llm","description":"The message text to send"},"data":{"type":"json","required":false,"visibility":"user-or-llm","description":"Optional structured JSON data to attach"},"files":{"type":"json","required":false,"visibility":"user-or-llm","description":"Optional files to attach"},"taskId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Existing task ID to continue"},"contextId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Conversation context ID to continue"},"apiKey":{"type":"string","required":false,"visibility":"user-only","description":"API key for authentication (if required)"}}},"agentmail_create_draft":{"id":"agentmail_create_draft","name":"Create Draft","description":"Create a new email draft in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to create the draft in"},"to":{"type":"string","required":false,"visibility":"user-or-llm","description":"Recipient email addresses (comma-separated)"},"subject":{"type":"string","required":false,"visibility":"user-or-llm","description":"Draft subject line"},"text":{"type":"string","required":false,"visibility":"user-or-llm","description":"Plain text draft body"},"html":{"type":"string","required":false,"visibility":"user-or-llm","description":"HTML draft body"},"cc":{"type":"string","required":false,"visibility":"user-or-llm","description":"CC recipient email addresses (comma-separated)"},"bcc":{"type":"string","required":false,"visibility":"user-or-llm","description":"BCC recipient email addresses (comma-separated)"},"inReplyTo":{"type":"string","required":false,"visibility":"user-or-llm","description":"ID of message being replied to"},"sendAt":{"type":"string","required":false,"visibility":"user-or-llm","description":"ISO 8601 timestamp to schedule sending"}}},"agentmail_create_inbox":{"id":"agentmail_create_inbox","name":"Create Inbox","description":"Create a new email inbox with AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"username":{"type":"string","required":false,"visibility":"user-or-llm","description":"Username for the inbox email address"},"domain":{"type":"string","required":false,"visibility":"user-or-llm","description":"Domain for the inbox email address"},"displayName":{"type":"string","required":false,"visibility":"user-or-llm","description":"Display name for the inbox"}}},"agentmail_delete_draft":{"id":"agentmail_delete_draft","name":"Delete Draft","description":"Delete an email draft in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the draft"},"draftId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the draft to delete"}}},"agentmail_delete_inbox":{"id":"agentmail_delete_inbox","name":"Delete Inbox","description":"Delete an email inbox in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to delete"}}},"agentmail_delete_thread":{"id":"agentmail_delete_thread","name":"Delete Thread","description":"Delete an email thread in AgentMail (moves to trash, or permanently deletes if already in trash)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the thread"},"threadId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the thread to delete"},"permanent":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Force permanent deletion instead of moving to trash"}}},"agentmail_forward_message":{"id":"agentmail_forward_message","name":"Forward Message","description":"Forward an email message to new recipients in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the message"},"messageId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the message to forward"},"to":{"type":"string","required":true,"visibility":"user-or-llm","description":"Recipient email addresses (comma-separated)"},"subject":{"type":"string","required":false,"visibility":"user-or-llm","description":"Override subject line"},"text":{"type":"string","required":false,"visibility":"user-or-llm","description":"Additional plain text to prepend"},"html":{"type":"string","required":false,"visibility":"user-or-llm","description":"Additional HTML to prepend"},"cc":{"type":"string","required":false,"visibility":"user-or-llm","description":"CC recipient email addresses (comma-separated)"},"bcc":{"type":"string","required":false,"visibility":"user-or-llm","description":"BCC recipient email addresses (comma-separated)"}}},"agentmail_get_draft":{"id":"agentmail_get_draft","name":"Get Draft","description":"Get details of a specific email draft in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox the draft belongs to"},"draftId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the draft to retrieve"}}},"agentmail_get_inbox":{"id":"agentmail_get_inbox","name":"Get Inbox","description":"Get details of a specific email inbox in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to retrieve"}}},"agentmail_get_message":{"id":"agentmail_get_message","name":"Get Message","description":"Get details of a specific email message in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the message"},"messageId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the message to retrieve"}}},"agentmail_get_thread":{"id":"agentmail_get_thread","name":"Get Thread","description":"Get details of a specific email thread including messages in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the thread"},"threadId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the thread to retrieve"}}},"agentmail_list_drafts":{"id":"agentmail_list_drafts","name":"List Drafts","description":"List email drafts in an inbox in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to list drafts from"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of drafts to return"},"pageToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token for next page of results"}}},"agentmail_list_inboxes":{"id":"agentmail_list_inboxes","name":"List Inboxes","description":"List all email inboxes in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of inboxes to return"},"pageToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token for next page of results"}}},"agentmail_list_messages":{"id":"agentmail_list_messages","name":"List Messages","description":"List messages in an inbox in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to list messages from"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of messages to return"},"pageToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token for next page of results"}}},"agentmail_list_threads":{"id":"agentmail_list_threads","name":"List Threads","description":"List email threads in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to list threads from"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of threads to return"},"pageToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token for next page of results"},"labels":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated labels to filter threads by"},"before":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter threads before this ISO 8601 timestamp"},"after":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter threads after this ISO 8601 timestamp"}}},"agentmail_reply_message":{"id":"agentmail_reply_message","name":"Reply to Message","description":"Reply to an existing email message in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to reply from"},"messageId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the message to reply to"},"text":{"type":"string","required":false,"visibility":"user-or-llm","description":"Plain text reply body"},"html":{"type":"string","required":false,"visibility":"user-or-llm","description":"HTML reply body"},"to":{"type":"string","required":false,"visibility":"user-or-llm","description":"Override recipient email addresses (comma-separated)"},"cc":{"type":"string","required":false,"visibility":"user-or-llm","description":"CC email addresses (comma-separated)"},"bcc":{"type":"string","required":false,"visibility":"user-or-llm","description":"BCC email addresses (comma-separated)"},"replyAll":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Reply to all recipients of the original message"}}},"agentmail_send_draft":{"id":"agentmail_send_draft","name":"Send Draft","description":"Send an existing email draft in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the draft"},"draftId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the draft to send"}}},"agentmail_send_message":{"id":"agentmail_send_message","name":"Send Message","description":"Send an email message from an AgentMail inbox","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to send from"},"to":{"type":"string","required":true,"visibility":"user-or-llm","description":"Recipient email address (comma-separated for multiple)"},"subject":{"type":"string","required":true,"visibility":"user-or-llm","description":"Email subject line"},"text":{"type":"string","required":false,"visibility":"user-or-llm","description":"Plain text email body"},"html":{"type":"string","required":false,"visibility":"user-or-llm","description":"HTML email body"},"cc":{"type":"string","required":false,"visibility":"user-or-llm","description":"CC recipient email addresses (comma-separated)"},"bcc":{"type":"string","required":false,"visibility":"user-or-llm","description":"BCC recipient email addresses (comma-separated)"}}},"agentmail_update_draft":{"id":"agentmail_update_draft","name":"Update Draft","description":"Update an existing email draft in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the draft"},"draftId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the draft to update"},"to":{"type":"string","required":false,"visibility":"user-or-llm","description":"Recipient email addresses (comma-separated)"},"subject":{"type":"string","required":false,"visibility":"user-or-llm","description":"Draft subject line"},"text":{"type":"string","required":false,"visibility":"user-or-llm","description":"Plain text draft body"},"html":{"type":"string","required":false,"visibility":"user-or-llm","description":"HTML draft body"},"cc":{"type":"string","required":false,"visibility":"user-or-llm","description":"CC recipient email addresses (comma-separated)"},"bcc":{"type":"string","required":false,"visibility":"user-or-llm","description":"BCC recipient email addresses (comma-separated)"},"sendAt":{"type":"string","required":false,"visibility":"user-or-llm","description":"ISO 8601 timestamp to schedule sending"}}},"agentmail_update_inbox":{"id":"agentmail_update_inbox","name":"Update Inbox","description":"Update the display name of an email inbox in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox to update"},"displayName":{"type":"string","required":true,"visibility":"user-or-llm","description":"New display name for the inbox"}}},"agentmail_update_message":{"id":"agentmail_update_message","name":"Update Message","description":"Add or remove labels on an email message in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the message"},"messageId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the message to update"},"addLabels":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated labels to add to the message"},"removeLabels":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated labels to remove from the message"}}},"agentmail_update_thread":{"id":"agentmail_update_thread","name":"Update Thread Labels","description":"Add or remove labels on an email thread in AgentMail","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentMail API key"},"inboxId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the inbox containing the thread"},"threadId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the thread to update"},"addLabels":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated labels to add to the thread"},"removeLabels":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated labels to remove from the thread"}}},"agentphone_create_call":{"id":"agentphone_create_call","name":"Create Outbound Call","description":"Initiate an outbound voice call from an AgentPhone agent","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"agentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Agent that will handle the call"},"toNumber":{"type":"string","required":true,"visibility":"user-or-llm","description":"Phone number to call in E.164 format (e.g. +14155551234)"},"fromNumberId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Phone number ID to use as caller ID. Must belong to the agent. If omitted, the agent\'s first assigned number is used."},"initialGreeting":{"type":"string","required":false,"visibility":"user-or-llm","description":"Optional greeting spoken when the recipient answers"},"voice":{"type":"string","required":false,"visibility":"user-or-llm","description":"Voice ID override for this call (defaults to the agent\'s configured voice)"},"systemPrompt":{"type":"string","required":false,"visibility":"user-or-llm","description":"When provided, uses a built-in LLM for the conversation instead of forwarding to your webhook"}}},"agentphone_create_contact":{"id":"agentphone_create_contact","name":"Create Contact","description":"Create a new contact in AgentPhone","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"phoneNumber":{"type":"string","required":true,"visibility":"user-or-llm","description":"Phone number in E.164 format (e.g. +14155551234)"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Contact\'s full name"},"email":{"type":"string","required":false,"visibility":"user-or-llm","description":"Contact\'s email address"},"notes":{"type":"string","required":false,"visibility":"user-or-llm","description":"Freeform notes stored on the contact"}}},"agentphone_create_number":{"id":"agentphone_create_number","name":"Create Phone Number","description":"Provision a new SMS- and voice-enabled phone number","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Two-letter country code (e.g. US, CA). Defaults to US."},"areaCode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Preferred area code (US/CA only, e.g. \\"415\\"). Best-effort — may be ignored if unavailable."},"agentId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Optionally attach the number to an agent immediately"}}},"agentphone_delete_contact":{"id":"agentphone_delete_contact","name":"Delete Contact","description":"Delete a contact by ID","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"contactId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Contact ID"}}},"agentphone_get_call":{"id":"agentphone_get_call","name":"Get Call","description":"Fetch a call and its full transcript","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"callId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the call to retrieve"}}},"agentphone_get_call_transcript":{"id":"agentphone_get_call_transcript","name":"Get Call Transcript","description":"Get the full ordered transcript for a call","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"callId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the call to retrieve the transcript for"}}},"agentphone_get_contact":{"id":"agentphone_get_contact","name":"Get Contact","description":"Fetch a single contact by ID","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"contactId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Contact ID"}}},"agentphone_get_conversation":{"id":"agentphone_get_conversation","name":"Get Conversation","description":"Get a conversation along with its recent messages","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"conversationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Conversation ID"},"messageLimit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of recent messages to include (default 50, max 100)"}}},"agentphone_get_conversation_messages":{"id":"agentphone_get_conversation_messages","name":"Get Conversation Messages","description":"Get paginated messages for a conversation","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"conversationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Conversation ID"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of messages to return (default 50, max 200)"},"before":{"type":"string","required":false,"visibility":"user-or-llm","description":"Return messages received before this ISO 8601 timestamp"},"after":{"type":"string","required":false,"visibility":"user-or-llm","description":"Return messages received after this ISO 8601 timestamp"}}},"agentphone_get_number_messages":{"id":"agentphone_get_number_messages","name":"Get Phone Number Messages","description":"Fetch messages received on a specific phone number","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"numberId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the phone number"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of messages to return (default 50, max 200)"},"before":{"type":"string","required":false,"visibility":"user-or-llm","description":"Return messages received before this ISO 8601 timestamp"},"after":{"type":"string","required":false,"visibility":"user-or-llm","description":"Return messages received after this ISO 8601 timestamp"}}},"agentphone_get_usage":{"id":"agentphone_get_usage","name":"Get Usage","description":"Retrieve current usage statistics for the AgentPhone account","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"}}},"agentphone_get_usage_daily":{"id":"agentphone_get_usage_daily","name":"Get Daily Usage","description":"Get a daily breakdown of usage (messages, calls, webhooks) for the last N days","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"days":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of days to return (1-365, default 30)"}}},"agentphone_get_usage_monthly":{"id":"agentphone_get_usage_monthly","name":"Get Monthly Usage","description":"Get monthly usage aggregation (messages, calls, webhooks) for the last N months","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"months":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of months to return (1-24, default 6)"}}},"agentphone_list_calls":{"id":"agentphone_list_calls","name":"List Calls","description":"List voice calls for this AgentPhone account","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to return (default 20, max 100)"},"offset":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to skip (min 0)"},"status":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter by status (completed, in-progress, failed)"},"direction":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter by direction (inbound, outbound)"},"type":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter by call type (pstn, web)"},"search":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search by phone number (matches fromNumber or toNumber)"}}},"agentphone_list_contacts":{"id":"agentphone_list_contacts","name":"List Contacts","description":"List contacts for this AgentPhone account","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"search":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter by name or phone number (case-insensitive contains)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to return (default 50, max 200)"},"offset":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to skip (min 0)"}}},"agentphone_list_conversations":{"id":"agentphone_list_conversations","name":"List Conversations","description":"List conversations (message threads) for this AgentPhone account","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to return (default 20, max 100)"},"offset":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to skip (min 0)"}}},"agentphone_list_numbers":{"id":"agentphone_list_numbers","name":"List Phone Numbers","description":"List all phone numbers provisioned for this AgentPhone account","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to return (default 20, max 100)"},"offset":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to skip (min 0)"}}},"agentphone_react_to_message":{"id":"agentphone_react_to_message","name":"React to Message","description":"Send an iMessage tapback reaction to a message (iMessage only)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"messageId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the message to react to"},"reaction":{"type":"string","required":true,"visibility":"user-or-llm","description":"Reaction type: love, like, dislike, laugh, emphasize, or question"}}},"agentphone_release_number":{"id":"agentphone_release_number","name":"Release Phone Number","description":"Release (delete) a phone number. This action is irreversible.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"numberId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the phone number to release"}}},"agentphone_send_message":{"id":"agentphone_send_message","name":"Send Message","description":"Send an outbound SMS or iMessage from an AgentPhone agent","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"agentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Agent sending the message"},"toNumber":{"type":"string","required":true,"visibility":"user-or-llm","description":"Recipient phone number in E.164 format (e.g. +14155551234)"},"body":{"type":"string","required":true,"visibility":"user-or-llm","description":"Message text to send"},"mediaUrl":{"type":"string","required":false,"visibility":"user-or-llm","description":"Optional URL of an image, video, or file to attach"},"numberId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Phone number ID to send from. If omitted, the agent\'s first assigned number is used."}}},"agentphone_update_contact":{"id":"agentphone_update_contact","name":"Update Contact","description":"Update a contact\'s fields","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"contactId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Contact ID"},"phoneNumber":{"type":"string","required":false,"visibility":"user-or-llm","description":"New phone number in E.164 format"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"New contact name"},"email":{"type":"string","required":false,"visibility":"user-or-llm","description":"New email address"},"notes":{"type":"string","required":false,"visibility":"user-or-llm","description":"New freeform notes"}}},"agentphone_update_conversation":{"id":"agentphone_update_conversation","name":"Update Conversation","description":"Update conversation metadata (stored state). Pass null to clear existing metadata.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"AgentPhone API key"},"conversationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Conversation ID"},"metadata":{"type":"json","required":false,"visibility":"user-or-llm","description":"Custom key-value metadata to store on the conversation. Pass null to clear existing metadata."}}},"agiloft_async_status":{"id":"agiloft_async_status","name":"Agiloft Async Status","description":"Check whether an asynchronous Agiloft call, such as a run action button, has completed.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table the asynchronous call was made against"},"callbackId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Callback ID returned by the asynchronous call, e.g. from Run Action Button"}}},"agiloft_attach_file":{"id":"agiloft_attach_file","name":"Agiloft Attach File","description":"Attach a file to a field in an Agiloft record.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to attach the file to"},"fieldName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the attachment field"},"file":{"type":"file","required":true,"visibility":"user-or-llm","description":"File to attach"},"fileName":{"type":"string","required":false,"visibility":"user-or-llm","description":"Name to assign to the file (defaults to original file name)"},"overwrite":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Replace the contents of the field instead of adding another file to it"}}},"agiloft_attachment_info":{"id":"agiloft_attachment_info","name":"Agiloft Attachment Info","description":"Get information about file attachments on a record field.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to check attachments on"},"fieldName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the attachment field to inspect"}}},"agiloft_create_record":{"id":"agiloft_create_record","name":"Agiloft Create Record","description":"Create a new record in an Agiloft table.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"contacts.employees\\")"},"data":{"type":"string","required":true,"visibility":"user-or-llm","description":"Record field values as a JSON object (e.g., {\\"first_name\\": \\"John\\", \\"status\\": \\"Active\\"})"}}},"agiloft_delete_record":{"id":"agiloft_delete_record","name":"Agiloft Delete Record","description":"Delete a record from an Agiloft table.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"contacts.employees\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to delete"},"substituteIds":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated IDs of records that adopt the dependants of the deleted record. Read only when the delete rule is REPLACE_WITH_ANOTHER."},"deleteRule":{"type":"string","required":false,"visibility":"user-or-llm","description":"How to treat records that depend on this one: ERROR_IF_DEPENDANTS (default — fails rather than cascading), APPLY_DELETE_WHERE_POSSIBLE, DELETE_WHERE_POSSIBLE_OTHERWISE_UNLINK, APPLY_UNLINK, UNLINK_WHERE_POSSIBLE_OTHERWISE_DELETE, or REPLACE_WITH_ANOTHER"}}},"agiloft_get_choice_line_id":{"id":"agiloft_get_choice_line_id","name":"Agiloft Get Choice Line ID","description":"Resolve the internal numeric ID of a choice-list value, for use in EWSelect WHERE clauses against choice fields.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"case\\", \\"contracts\\")"},"fieldName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Choice field name (e.g., \\"priority\\", \\"status\\")"},"value":{"type":"string","required":true,"visibility":"user-or-llm","description":"Choice display value to resolve (e.g., \\"High\\", \\"Active\\")"}}},"agiloft_list_tables":{"id":"agiloft_list_tables","name":"Agiloft List Tables","description":"List the tables and fields in an Agiloft knowledge base, to discover the logical names other operations need.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":false,"visibility":"user-or-llm","description":"Logical name of a single table to describe (e.g., \\"contacts\\"). Leave empty to list every table in the knowledge base."},"includeLinkedInfo":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Include the source table and column behind each linked field"},"skipColumnsInfo":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Return table names only, omitting field details, for a much smaller response"}}},"agiloft_lock_record":{"id":"agiloft_lock_record","name":"Agiloft Lock Record","description":"Lock, unlock, or check the lock status of an Agiloft record.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to lock, unlock, or check"},"lockAction":{"type":"string","required":true,"visibility":"user-or-llm","description":"Action to perform: \\"lock\\", \\"unlock\\", or \\"check\\""},"force":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Unlock only: release a lock held by another user."}}},"agiloft_nlp_search":{"id":"agiloft_nlp_search","name":"Agiloft Natural Language Search","description":"Search Agiloft records by describing what you want in plain language, such as \\"active NDAs submitted last month\\".","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"nlpQuery":{"type":"string","required":true,"visibility":"user-or-llm","description":"The request in plain language, e.g. \\"Show me open, high-priority contracts\\". Structured field filters are not accepted — use Search Records for those."},"fields":{"type":"string","required":true,"visibility":"user-or-llm","description":"Comma-separated field names to return, e.g. \\"id, contract_title1, company_name\\""},"page":{"type":"string","required":false,"visibility":"user-or-llm","description":"Page number, starting from 0"},"limit":{"type":"string","required":false,"visibility":"user-or-llm","description":"Records per page"}}},"agiloft_read_record":{"id":"agiloft_read_record","name":"Agiloft Read Record","description":"Read a record by ID from an Agiloft table.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"contacts.employees\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to read"},"fields":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of field names to include in the response"}}},"agiloft_remove_attachment":{"id":"agiloft_remove_attachment","name":"Agiloft Remove Attachment","description":"Remove an attached file from a field in an Agiloft record.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record containing the attachment"},"fieldName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the attachment field"},"position":{"type":"string","required":true,"visibility":"user-or-llm","description":"Position index of the file to remove (starting from 0)"}}},"agiloft_retrieve_attachment":{"id":"agiloft_retrieve_attachment","name":"Agiloft Retrieve Attachment","description":"Download an attached file from an Agiloft record field.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record containing the attachment"},"fieldName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the attachment field"},"position":{"type":"string","required":true,"visibility":"user-or-llm","description":"Position index of the file in the field (starting from 0)"}}},"agiloft_run_action_button":{"id":"agiloft_run_action_button","name":"Agiloft Run Action Button","description":"Run an action button on an Agiloft record, such as an approval or send-for-signature step.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"case\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to run the action button on"},"actionButtonField":{"type":"string","required":true,"visibility":"user-or-llm","description":"Logical name of the field holding the action button (e.g., \\"ab_field\\")"}}},"agiloft_saved_search":{"id":"agiloft_saved_search","name":"Agiloft Saved Search","description":"List the saved searches defined for an Agiloft table.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Logical table name to list saved searches for (e.g., \\"contract\\")"}}},"agiloft_search_records":{"id":"agiloft_search_records","name":"Agiloft Search Records","description":"Search for records in an Agiloft table using a query.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name to search in (e.g., \\"contracts\\", \\"contacts.employees\\")"},"query":{"type":"string","required":false,"visibility":"user-or-llm","description":"Ad hoc EWSearch query. Combine conditions with && (and) or || (or) and quote every value — e.g. \\"summary~=\'test\'&&priority=\'High\'\\". Required unless a saved search is given."},"search":{"type":"string","required":false,"visibility":"user-or-llm","description":"Label of a saved search defined on the table (e.g., \\"C: Status is Closed\\"). Can be combined with a query to narrow it further."},"fields":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of field names to include in the results"},"page":{"type":"string","required":false,"visibility":"user-or-llm","description":"Page number for paginated results (starting from 0)"},"limit":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum number of records to return per page. Agiloft treats 0 as \\"all records\\", so leave it unset or use a positive value to keep result sizes bounded."}}},"agiloft_select_records":{"id":"agiloft_select_records","name":"Agiloft Select Records","description":"Select record IDs matching a SQL WHERE clause from an Agiloft table.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"contacts.employees\\")"},"where":{"type":"string","required":true,"visibility":"user-or-llm","description":"SQL WHERE clause using database column names (e.g., \\"summary like \'%new%\'\\" or \\"assigned_person=\'John Doe\'\\"). EWSelect has no page size and returns every matching ID, so append a database limit such as \\"limit 0,200\\" to bound the result."}}},"agiloft_update_record":{"id":"agiloft_update_record","name":"Agiloft Update Record","description":"Update an existing record in an Agiloft table.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"contacts.employees\\")"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the record to update"},"data":{"type":"string","required":true,"visibility":"user-or-llm","description":"Updated field values as a JSON object (e.g., {\\"status\\": \\"Active\\", \\"priority\\": \\"High\\"})"}}},"agiloft_upsert_record":{"id":"agiloft_upsert_record","name":"Agiloft Upsert Record","description":"Create an Agiloft record, or update it when a record already matches the given fields.","version":"1.0.0","params":{"instanceUrl":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft instance URL (e.g., https://mycompany.agiloft.com)"},"knowledgeBase":{"type":"string","required":true,"visibility":"user-only","description":"Knowledge base name"},"login":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft username"},"password":{"type":"string","required":true,"visibility":"user-only","description":"Agiloft password"},"table":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table name (e.g., \\"contracts\\", \\"contacts.employees\\")"},"match":{"type":"string","required":true,"visibility":"user-or-llm","description":"Field used to find an existing record (e.g., \\"ext_id\\"). Pick something that identifies a record uniquely — if more than one record matches, Agiloft writes nothing and returns a conflict."},"async":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Queue the write instead of waiting for it. Returns a callback ID instead of a record ID; pass that to Async Status to poll the result."},"data":{"type":"string","required":true,"visibility":"user-or-llm","description":"Field values as a JSON object. On create these populate the new record; on update only the supplied fields change."}}},"ahrefs_anchors":{"id":"ahrefs_anchors","name":"Ahrefs Anchors","description":"Get the anchor text distribution for a target domain or URL\'s backlinks, showing how many links and referring domains use each anchor text.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\" or \\"https://example.com/page\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match)"},"history":{"type":"string","required":false,"visibility":"user-or-llm","description":"Historical scope: \\"live\\" (currently live), \\"all_time\\" (default, includes lost backlinks), or \\"since:YYYY-MM-DD\\" (backlinks found since a date)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_backlinks":{"id":"ahrefs_backlinks","name":"Ahrefs Backlinks","description":"Get a list of backlinks pointing to a target domain or URL. Returns details about each backlink including source URL, anchor text, and domain rating.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\" or \\"https://example.com/page\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"history":{"type":"string","required":false,"visibility":"user-or-llm","description":"Historical scope: \\"live\\" (currently live backlinks), \\"all_time\\" (default, includes lost backlinks), or \\"since:YYYY-MM-DD\\" (backlinks found since a date)."},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_backlinks_stats":{"id":"ahrefs_backlinks_stats","name":"Ahrefs Backlinks Stats","description":"Get backlink and referring domain totals for a target domain or URL, both currently live and across all time.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\" or \\"https://example.com/page\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date to report metrics on, in YYYY-MM-DD format (defaults to today)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_batch_analysis":{"id":"ahrefs_batch_analysis","name":"Ahrefs Batch Analysis","description":"Get bulk SEO metrics (Domain Rating, backlinks, referring domains, organic traffic, and more) for multiple domains or URLs in a single request. Useful for comparing many competitors at once.","version":"1.0.0","params":{"targets":{"type":"string","required":true,"visibility":"user-or-llm","description":"Comma-separated list of domains or URLs to analyze. Example: \\"example.com,competitor.com\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode applied to every target: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match)"},"protocol":{"type":"string","required":false,"visibility":"user-or-llm","description":"Protocol applied to every target: \\"both\\" (default), \\"http\\", or \\"https\\""},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for traffic data. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"volumeMode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search volume calculation: \\"monthly\\" or \\"average\\" (default: \\"monthly\\")"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_broken_backlinks":{"id":"ahrefs_broken_backlinks","name":"Ahrefs Broken Backlinks","description":"Get a list of broken backlinks pointing to a target domain or URL. Useful for identifying link reclamation opportunities.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\" or \\"https://example.com/page\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_domain_rating":{"id":"ahrefs_domain_rating","name":"Ahrefs Domain Rating","description":"Get the Domain Rating (DR) and Ahrefs Rank for a target domain. Domain Rating shows the strength of a website\'s backlink profile on a scale from 0 to 100.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain to analyze (e.g., example.com)"},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date for historical data in YYYY-MM-DD format (defaults to today)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_domain_rating_history":{"id":"ahrefs_domain_rating_history","name":"Ahrefs Domain Rating History","description":"Get the historical Domain Rating (DR) trend for a target domain or URL over a date range, grouped daily, weekly, or monthly.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"dateFrom":{"type":"string","required":true,"visibility":"user-only","description":"Start date of the historical period, in YYYY-MM-DD format"},"dateTo":{"type":"string","required":false,"visibility":"user-only","description":"End date of the historical period, in YYYY-MM-DD format (defaults to today)"},"historyGrouping":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval for grouping data points: \\"daily\\", \\"weekly\\", or \\"monthly\\" (default: \\"monthly\\")"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_keyword_overview":{"id":"ahrefs_keyword_overview","name":"Ahrefs Keyword Overview","description":"Get detailed metrics for a keyword including search volume, keyword difficulty, CPC, clicks, and traffic potential.","version":"1.0.0","params":{"keyword":{"type":"string","required":true,"visibility":"user-or-llm","description":"The keyword to analyze"},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for keyword data. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_keywords_history":{"id":"ahrefs_keywords_history","name":"Ahrefs Keywords History","description":"Get the historical organic keyword ranking distribution for a target domain or URL over a date range: how many keywords rank in each position bucket at each point in time.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"dateFrom":{"type":"string","required":true,"visibility":"user-only","description":"Start date of the historical period, in YYYY-MM-DD format"},"dateTo":{"type":"string","required":false,"visibility":"user-only","description":"End date of the historical period, in YYYY-MM-DD format (defaults to today)"},"historyGrouping":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval for grouping data points: \\"daily\\", \\"weekly\\", or \\"monthly\\" (default: \\"monthly\\")"},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for search results. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_metrics":{"id":"ahrefs_metrics","name":"Ahrefs Metrics","description":"Get a one-call organic and paid search overview for a target domain or URL: organic traffic, organic keywords, paid traffic, paid keywords, and estimated traffic cost.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for traffic data. Example: \\"us\\", \\"gb\\", \\"de\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date to report metrics on, in YYYY-MM-DD format (defaults to today)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_metrics_history":{"id":"ahrefs_metrics_history","name":"Ahrefs Metrics History","description":"Get the historical organic and paid traffic trend for a target domain or URL over a date range: organic traffic/cost and paid traffic/cost at each point in time.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"dateFrom":{"type":"string","required":true,"visibility":"user-only","description":"Start date of the historical period, in YYYY-MM-DD format"},"dateTo":{"type":"string","required":false,"visibility":"user-only","description":"End date of the historical period, in YYYY-MM-DD format (defaults to today)"},"volumeMode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search volume calculation: \\"monthly\\" or \\"average\\" (default: \\"monthly\\")"},"historyGrouping":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval for grouping data points: \\"daily\\", \\"weekly\\", or \\"monthly\\" (default: \\"monthly\\")"},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for traffic data. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_organic_competitors":{"id":"ahrefs_organic_competitors","name":"Ahrefs Organic Competitors","description":"Get domains that compete with a target domain or URL for the same organic keywords, ranked by keyword overlap.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for search results. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date to report metrics on, in YYYY-MM-DD format (defaults to today)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_organic_keywords":{"id":"ahrefs_organic_keywords","name":"Ahrefs Organic Keywords","description":"Get organic keywords that a target domain or URL ranks for in Google search results. Returns keyword details including search volume, ranking position, and estimated traffic.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\" or \\"https://example.com/page\\""},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for search results. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date to report metrics on, in YYYY-MM-DD format (defaults to today)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_paid_pages":{"id":"ahrefs_paid_pages","name":"Ahrefs Paid Pages","description":"Get a target domain\'s pages that receive paid search traffic, sorted by estimated paid traffic. Returns page URLs with their paid traffic, keyword counts, and estimated spend.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for traffic data. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match)"},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date to report metrics on, in YYYY-MM-DD format (defaults to today)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_rank_tracker_competitors_overview":{"id":"ahrefs_rank_tracker_competitors_overview","name":"Ahrefs Rank Tracker Competitors Overview","description":"Get competitor rankings for the keywords tracked in an Ahrefs Rank Tracker project: each tracked keyword\'s volume and difficulty alongside every competitor\'s position, traffic, and traffic value. This endpoint is free and does not consume API units.","version":"1.0.0","params":{"projectId":{"type":"number","required":true,"visibility":"user-or-llm","description":"The Rank Tracker project ID (found in the project URL in Ahrefs)"},"date":{"type":"string","required":true,"visibility":"user-only","description":"Date to report rankings for, in YYYY-MM-DD format"},"device":{"type":"string","required":true,"visibility":"user-or-llm","description":"Rankings device type: \\"desktop\\" or \\"mobile\\""},"dateCompared":{"type":"string","required":false,"visibility":"user-only","description":"Comparison date in YYYY-MM-DD format, to compute position/traffic deltas"},"volumeMode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search volume calculation: \\"monthly\\" or \\"average\\" (default: \\"monthly\\")"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_rank_tracker_competitors_stats":{"id":"ahrefs_rank_tracker_competitors_stats","name":"Ahrefs Rank Tracker Competitors Stats","description":"Get aggregate competitor stats for an Ahrefs Rank Tracker project: each competitor\'s traffic, traffic value, average position, and share of voice across all tracked keywords. This endpoint is free and does not consume API units.","version":"1.0.0","params":{"projectId":{"type":"number","required":true,"visibility":"user-or-llm","description":"The Rank Tracker project ID (found in the project URL in Ahrefs)"},"date":{"type":"string","required":true,"visibility":"user-only","description":"Date to report metrics for, in YYYY-MM-DD format"},"device":{"type":"string","required":true,"visibility":"user-or-llm","description":"Rankings device type: \\"desktop\\" or \\"mobile\\""},"volumeMode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search volume calculation: \\"monthly\\" or \\"average\\" (default: \\"monthly\\")"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_rank_tracker_overview":{"id":"ahrefs_rank_tracker_overview","name":"Ahrefs Rank Tracker Overview","description":"Get ranking overview metrics for the keywords tracked in an Ahrefs Rank Tracker project: position, search volume, keyword difficulty, and estimated traffic. This endpoint is free and does not consume API units.","version":"1.0.0","params":{"projectId":{"type":"number","required":true,"visibility":"user-or-llm","description":"The Rank Tracker project ID (found in the project URL in Ahrefs)"},"date":{"type":"string","required":true,"visibility":"user-only","description":"Date to report rankings for, in YYYY-MM-DD format"},"device":{"type":"string","required":true,"visibility":"user-or-llm","description":"Rankings device type: \\"desktop\\" or \\"mobile\\""},"dateCompared":{"type":"string","required":false,"visibility":"user-only","description":"Comparison date in YYYY-MM-DD format, to compute position/traffic deltas"},"volumeMode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search volume calculation: \\"monthly\\" or \\"average\\" (default: \\"monthly\\")"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_rank_tracker_serp_overview":{"id":"ahrefs_rank_tracker_serp_overview","name":"Ahrefs Rank Tracker SERP Overview","description":"Get the full SERP (search engine results page) for a keyword tracked in an Ahrefs Rank Tracker project, including every ranking URL with its position, title, and authority metrics. This endpoint is free and does not consume API units.","version":"1.0.0","params":{"projectId":{"type":"number","required":true,"visibility":"user-or-llm","description":"The Rank Tracker project ID (found in the project URL in Ahrefs)"},"keyword":{"type":"string","required":true,"visibility":"user-or-llm","description":"The tracked keyword to retrieve SERP data for"},"country":{"type":"string","required":true,"visibility":"user-or-llm","description":"Country code for the tracked keyword. Example: \\"us\\", \\"gb\\", \\"de\\""},"device":{"type":"string","required":true,"visibility":"user-or-llm","description":"Rankings device type: \\"desktop\\" or \\"mobile\\""},"topPositions":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of top organic positions to return (defaults to all available)"},"date":{"type":"string","required":false,"visibility":"user-only","description":"Timestamp to return the last available SERP Overview at, in YYYY-MM-DDThh:mm:ss format"},"locationId":{"type":"number","required":false,"visibility":"user-or-llm","description":"Location ID of the tracked keyword, if tracked at a specific location"},"languageCode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Language code of the tracked keyword"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_refdomains_history":{"id":"ahrefs_refdomains_history","name":"Ahrefs Referring Domains History","description":"Get the historical referring domains trend for a target domain or URL over a date range, grouped daily, weekly, or monthly.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\""},"dateFrom":{"type":"string","required":true,"visibility":"user-only","description":"Start date of the historical period, in YYYY-MM-DD format"},"dateTo":{"type":"string","required":false,"visibility":"user-only","description":"End date of the historical period, in YYYY-MM-DD format (defaults to today)"},"historyGrouping":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval for grouping data points: \\"daily\\", \\"weekly\\", or \\"monthly\\" (default: \\"monthly\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_referring_domains":{"id":"ahrefs_referring_domains","name":"Ahrefs Referring Domains","description":"Get a list of domains that link to a target domain or URL. Returns unique referring domains with their domain rating, backlink counts, and discovery dates.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain or URL to analyze. Example: \\"example.com\\" or \\"https://example.com/page\\""},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"history":{"type":"string","required":false,"visibility":"user-or-llm","description":"Historical scope: \\"live\\" (currently live), \\"all_time\\" (default, includes lost domains), or \\"since:YYYY-MM-DD\\" (domains found since a date)."},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_related_terms":{"id":"ahrefs_related_terms","name":"Ahrefs Related Terms","description":"Get keyword ideas related to a seed keyword: terms the same top-ranking pages also rank for (\\"also rank for\\") or also discuss (\\"also talk about\\"), with volume, difficulty, and CPC.","version":"1.0.0","params":{"keyword":{"type":"string","required":true,"visibility":"user-or-llm","description":"The seed keyword to find related terms for"},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for keyword data. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"terms":{"type":"string","required":false,"visibility":"user-or-llm","description":"Type of related keywords to return: \\"also_rank_for\\", \\"also_talk_about\\", or \\"all\\" (default: \\"all\\")"},"viewFor":{"type":"string","required":false,"visibility":"user-or-llm","description":"Whether to derive related terms from the top 10 or top 100 ranking pages (default: \\"top_10\\")"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_site_audit_page_explorer":{"id":"ahrefs_site_audit_page_explorer","name":"Ahrefs Site Audit Page Explorer","description":"Get crawled pages from an Ahrefs Site Audit project with health and SEO metrics: HTTP status, title, link counts, backlinks, indexability, and traffic. Optionally filter to pages affected by a specific issue.","version":"1.0.0","params":{"projectId":{"type":"number","required":true,"visibility":"user-or-llm","description":"The Site Audit project ID (found in the project URL in Ahrefs)"},"date":{"type":"string","required":false,"visibility":"user-only","description":"Crawl date in YYYY-MM-DDThh:mm:ss format (defaults to the most recent crawl)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"offset":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of results to skip, for pagination"},"issueId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Only return pages affected by this issue ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"ahrefs_top_pages":{"id":"ahrefs_top_pages","name":"Ahrefs Top Pages","description":"Get the top pages of a target domain sorted by organic traffic. Returns page URLs with their traffic, keyword counts, and estimated traffic value.","version":"1.0.0","params":{"target":{"type":"string","required":true,"visibility":"user-or-llm","description":"The target domain to analyze. Example: \\"example.com\\""},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Country code for traffic data. Example: \\"us\\", \\"gb\\", \\"de\\" (default: \\"us\\")"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Analysis mode: domain (entire domain), prefix (URL prefix), subdomains (include all subdomains, default), exact (exact URL match). Example: \\"domain\\""},"date":{"type":"string","required":false,"visibility":"user-only","description":"Date to report metrics on, in YYYY-MM-DD format (defaults to today)"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of results to return. Example: 50 (default: 1000)"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ahrefs API Key"}}},"airtable_create_records":{"id":"airtable_create_records","name":"Airtable Create Records","description":"Write new records to an Airtable table","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"records":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of records to create, each with a `fields` object"},"typecast":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"When true, Airtable automatically converts string values to the field type"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_delete_records":{"id":"airtable_delete_records","name":"Airtable Delete Records","description":"Delete one or more records from an Airtable table by ID","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"recordIds":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of record IDs to delete (each starts with \\"rec\\", e.g., [\\"recXXXXXXXXXXXXXX\\"]). Pass a single-element array to delete one record."}},"oauth":{"required":true,"provider":"airtable"}},"airtable_get_base_schema":{"id":"airtable_get_base_schema","name":"Airtable Get Base Schema","description":"Get the schema of all tables, fields, and views in an Airtable base","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_get_record":{"id":"airtable_get_record","name":"Airtable Get Record","description":"Retrieve a single record from an Airtable table by its ID","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Record ID to retrieve (starts with \\"rec\\", e.g., \\"recXXXXXXXXXXXXXX\\")"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_list_bases":{"id":"airtable_list_bases","name":"Airtable List Bases","description":"List all bases the authenticated user has access to","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"offset":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination offset for retrieving additional bases"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_list_records":{"id":"airtable_list_records","name":"Airtable List Records","description":"Read records from an Airtable table","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"maxRecords":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of records to return (default: all records)"},"filterFormula":{"type":"string","required":false,"visibility":"user-or-llm","description":"Formula to filter records (e.g., \\"({Field Name} = \'Value\')\\")"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_list_tables":{"id":"airtable_list_tables","name":"Airtable List Tables","description":"List all tables and their schema in an Airtable base","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_update_multiple_records":{"id":"airtable_update_multiple_records","name":"Airtable Update Multiple Records","description":"Update multiple existing records in an Airtable table","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"records":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of records to update, each with an `id` and a `fields` object"},"typecast":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"When true, Airtable automatically converts string values to the field type"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_update_record":{"id":"airtable_update_record","name":"Airtable Update Record","description":"Update an existing record in an Airtable table by ID","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"recordId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Record ID to update (starts with \\"rec\\", e.g., \\"recXXXXXXXXXXXXXX\\")"},"fields":{"type":"json","required":true,"visibility":"user-or-llm","description":"An object containing the field names and their new values"},"typecast":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"When true, Airtable automatically converts string values to the field type"}},"oauth":{"required":true,"provider":"airtable"}},"airtable_upsert_records":{"id":"airtable_upsert_records","name":"Airtable Upsert Records","description":"Update existing records or create new ones in an Airtable table, matching on the specified merge fields","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token"},"baseId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Airtable base ID (starts with \\"app\\", e.g., \\"appXXXXXXXXXXXXXX\\")"},"tableId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Table ID (starts with \\"tbl\\") or table name"},"records":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of records to upsert, each with a `fields` object"},"fieldsToMergeOn":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of field names used to match existing records (max 3). A record is updated when all merge fields match, otherwise it is created. Example: [\\"Name\\"]"},"typecast":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"When true, Airtable automatically converts string values to the field type"}},"oauth":{"required":true,"provider":"airtable"}},"airweave_search":{"id":"airweave_search","name":"Airweave Search","description":"Search your synced data collections using Airweave. Supports semantic search with hybrid, neural, or keyword retrieval strategies. Optionally generate AI-powered answers from search results.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Airweave API Key for authentication"},"collectionId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The readable ID of the collection to search"},"query":{"type":"string","required":true,"visibility":"user-or-llm","description":"The search query text"},"limit":{"type":"number","required":false,"visibility":"user-only","description":"Maximum number of results to return (default: 100)"},"retrievalStrategy":{"type":"string","required":false,"visibility":"user-or-llm","description":"Retrieval strategy: hybrid (default), neural, or keyword"},"expandQuery":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Generate query variations to improve recall"},"rerank":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Reorder results for improved relevance using LLM"},"generateAnswer":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Generate a natural-language answer to the query"}}},"algolia_add_record":{"id":"algolia_add_record","name":"Algolia Add Record","description":"Add or replace a record in an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"objectID":{"type":"string","required":false,"visibility":"user-or-llm","description":"Object ID for the record (auto-generated if not provided)"},"record":{"type":"json","required":true,"visibility":"user-or-llm","description":"JSON object representing the record to add"}}},"algolia_batch_operations":{"id":"algolia_batch_operations","name":"Algolia Batch Operations","description":"Perform batch add, update, partial update, or delete operations on records in an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"requests":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of batch operations. Each item has \\"action\\" (addObject, updateObject, partialUpdateObject, partialUpdateObjectNoCreate, deleteObject, delete, clear) and \\"body\\" (the record data; must include objectID for update/delete; use an empty object {} for the index-level delete/clear actions)"}}},"algolia_browse_records":{"id":"algolia_browse_records","name":"Algolia Browse Records","description":"Browse and iterate over all records in an Algolia index using cursor pagination","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key (must have browse ACL)"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index to browse"},"query":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search query to filter browsed records"},"filters":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter string to narrow down results"},"attributesToRetrieve":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of attributes to retrieve"},"hitsPerPage":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of hits per page (default: 1000, max: 1000)"},"cursor":{"type":"string","required":false,"visibility":"user-or-llm","description":"Cursor from a previous browse response for pagination"},"aroundLatLng":{"type":"string","required":false,"visibility":"user-or-llm","description":"Coordinates for geo-search (e.g., \\"40.71,-74.01\\")"},"aroundRadius":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum radius in meters for geo-search, or \\"all\\" for unlimited"},"insideBoundingBox":{"type":"json","required":false,"visibility":"user-or-llm","description":"Bounding box coordinates as [[lat1, lng1, lat2, lng2]] for geo-search"},"insidePolygon":{"type":"json","required":false,"visibility":"user-or-llm","description":"Polygon coordinates as [[lat1, lng1, lat2, lng2, lat3, lng3, ...]] for geo-search"}}},"algolia_clear_records":{"id":"algolia_clear_records","name":"Algolia Clear Records","description":"Clear all records from an Algolia index while keeping settings, synonyms, and rules","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key (must have deleteIndex ACL)"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index to clear"}}},"algolia_copy_move_index":{"id":"algolia_copy_move_index","name":"Algolia Copy/Move Index","description":"Copy or move an Algolia index to a new destination","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the source index"},"operation":{"type":"string","required":true,"visibility":"user-or-llm","description":"Operation to perform: \\"copy\\" or \\"move\\""},"destination":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the destination index"},"scope":{"type":"json","required":false,"visibility":"user-or-llm","description":"Array of scopes to copy (only for \\"copy\\" operation): [\\"settings\\", \\"synonyms\\", \\"rules\\"]. Omit to copy everything including records."}}},"algolia_delete_by_filter":{"id":"algolia_delete_by_filter","name":"Algolia Delete By Filter","description":"Delete all records matching a filter from an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key (must have deleteIndex ACL)"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"filters":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter expression to match records for deletion (e.g., \\"category:outdated\\")"},"facetFilters":{"type":"json","required":false,"visibility":"user-or-llm","description":"Array of facet filters (e.g., [\\"brand:Acme\\"])"},"numericFilters":{"type":"json","required":false,"visibility":"user-or-llm","description":"Array of numeric filters (e.g., [\\"price > 100\\"])"},"tagFilters":{"type":"json","required":false,"visibility":"user-or-llm","description":"Array of tag filters using the _tags attribute (e.g., [\\"published\\"])"},"aroundLatLng":{"type":"string","required":false,"visibility":"user-or-llm","description":"Coordinates for geo-search filter (e.g., \\"40.71,-74.01\\")"},"aroundRadius":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum radius in meters for geo-search, or \\"all\\" for unlimited"},"insideBoundingBox":{"type":"json","required":false,"visibility":"user-or-llm","description":"Bounding box coordinates as [[lat1, lng1, lat2, lng2]] for geo-search filter"},"insidePolygon":{"type":"json","required":false,"visibility":"user-or-llm","description":"Polygon coordinates as [[lat1, lng1, lat2, lng2, lat3, lng3, ...]] for geo-search filter"}}},"algolia_delete_index":{"id":"algolia_delete_index","name":"Algolia Delete Index","description":"Delete an entire Algolia index and all its records","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key (must have deleteIndex ACL)"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index to delete"}}},"algolia_delete_record":{"id":"algolia_delete_record","name":"Algolia Delete Record","description":"Delete a record by objectID from an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"objectID":{"type":"string","required":true,"visibility":"user-or-llm","description":"The objectID of the record to delete"}}},"algolia_get_record":{"id":"algolia_get_record","name":"Algolia Get Record","description":"Get a record by objectID from an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"objectID":{"type":"string","required":true,"visibility":"user-or-llm","description":"The objectID of the record to retrieve"},"attributesToRetrieve":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of attributes to retrieve"}}},"algolia_get_records":{"id":"algolia_get_records","name":"Algolia Get Records","description":"Retrieve multiple records by objectID from one or more Algolia indices","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Default index name for all requests"},"requests":{"type":"json","required":true,"visibility":"user-or-llm","description":"Array of objects specifying records to retrieve. Each must have \\"objectID\\" and optionally \\"indexName\\" and \\"attributesToRetrieve\\"."}}},"algolia_get_settings":{"id":"algolia_get_settings","name":"Algolia Get Settings","description":"Retrieve the settings of an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"}}},"algolia_get_task_status":{"id":"algolia_get_task_status","name":"Algolia Get Task Status","description":"Check whether an Algolia indexing task has finished publishing","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index the task ran against"},"taskID":{"type":"number","required":true,"visibility":"user-or-llm","description":"The taskID returned by a previous write operation"}}},"algolia_list_indices":{"id":"algolia_list_indices","name":"Algolia List Indices","description":"List all indices in an Algolia application","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key"},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for paginating indices (default: not paginated)"},"hitsPerPage":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of indices per page (default: 100)"}}},"algolia_partial_update_record":{"id":"algolia_partial_update_record","name":"Algolia Partial Update Record","description":"Partially update a record in an Algolia index without replacing it entirely","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"objectID":{"type":"string","required":true,"visibility":"user-or-llm","description":"The objectID of the record to update"},"attributes":{"type":"json","required":true,"visibility":"user-or-llm","description":"JSON object with attributes to update. Supports built-in operations like {\\"stock\\": {\\"_operation\\": \\"Decrement\\", \\"value\\": 1}}"},"createIfNotExists":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Whether to create the record if it does not exist (default: true)"}}},"algolia_search":{"id":"algolia_search","name":"Algolia Search","description":"Search an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia API Key"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index to search"},"query":{"type":"string","required":true,"visibility":"user-or-llm","description":"Search query text"},"hitsPerPage":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of hits per page (default: 20)"},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number to retrieve (default: 0)"},"filters":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter string (e.g., \\"category:electronics AND price < 100\\")"},"attributesToRetrieve":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of attributes to retrieve"},"facets":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of facet attribute names to retrieve counts for (use \\"*\\" for all)"},"getRankingInfo":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Whether to include detailed ranking information in each hit"},"aroundLatLng":{"type":"string","required":false,"visibility":"user-or-llm","description":"Coordinates for geo-search (e.g., \\"40.71,-74.01\\")"},"aroundRadius":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum radius in meters for geo-search, or \\"all\\" for unlimited"},"insideBoundingBox":{"type":"json","required":false,"visibility":"user-or-llm","description":"Bounding box coordinates as [[lat1, lng1, lat2, lng2]] for geo-search"},"insidePolygon":{"type":"json","required":false,"visibility":"user-or-llm","description":"Polygon coordinates as [[lat1, lng1, lat2, lng2, lat3, lng3, ...]] for geo-search"}}},"algolia_update_settings":{"id":"algolia_update_settings","name":"Algolia Update Settings","description":"Update the settings of an Algolia index","version":"1.0","params":{"applicationId":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Application ID"},"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Algolia Admin API Key (must have editSettings ACL)"},"indexName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the Algolia index"},"settings":{"type":"json","required":true,"visibility":"user-or-llm","description":"JSON object with settings to update (e.g., {\\"searchableAttributes\\": [\\"name\\", \\"description\\"], \\"customRanking\\": [\\"desc(popularity)\\"]})"},"forwardToReplicas":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Whether to apply changes to replica indices (default: false)"}}},"amplitude_event_segmentation":{"id":"amplitude_event_segmentation","name":"Amplitude Event Segmentation","description":"Query event analytics data with segmentation. Get event counts, uniques, averages, and more.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"eventType":{"type":"string","required":true,"visibility":"user-or-llm","description":"Event type name to analyze"},"start":{"type":"string","required":true,"visibility":"user-or-llm","description":"Start date in YYYYMMDD format"},"end":{"type":"string","required":true,"visibility":"user-or-llm","description":"End date in YYYYMMDD format"},"metric":{"type":"string","required":false,"visibility":"user-or-llm","description":"Metric type: uniques, totals, pct_dau, average, histogram, sums, value_avg, or formula (default: uniques)"},"interval":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval: 1 (daily), 7 (weekly), or 30 (monthly)"},"groupBy":{"type":"string","required":false,"visibility":"user-or-llm","description":"Property name to group by (prefix custom user properties with \\"gp:\\")"},"groupBy2":{"type":"string","required":false,"visibility":"user-or-llm","description":"Second property name to group by (prefix custom user properties with \\"gp:\\")"},"limit":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum number of group-by values (max 1000)"},"filters":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON array of filter objects applied to the event, e.g. [{\\"subprop_type\\":\\"event\\",\\"subprop_key\\":\\"city\\",\\"subprop_op\\":\\"is\\",\\"subprop_value\\":[\\"San Francisco\\"]}]"},"formula":{"type":"string","required":false,"visibility":"user-or-llm","description":"Required when metric is \\"formula\\", e.g. \\"UNIQUES(A)/UNIQUES(B)\\""},"segment":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON segment definition(s) applied to the query"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_funnels":{"id":"amplitude_funnels","name":"Amplitude Funnels","description":"Analyze conversion rates and drop-off between a sequence of events.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"events":{"type":"string","required":true,"visibility":"user-or-llm","description":"JSON array of event objects, one per funnel step in order, e.g. [{\\"event_type\\":\\"signup\\"},{\\"event_type\\":\\"purchase\\"}]"},"start":{"type":"string","required":true,"visibility":"user-or-llm","description":"Start date in YYYYMMDD format"},"end":{"type":"string","required":true,"visibility":"user-or-llm","description":"End date in YYYYMMDD format"},"mode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Funnel ordering: \\"ordered\\", \\"unordered\\", or \\"sequential\\" (default: ordered)"},"userType":{"type":"string","required":false,"visibility":"user-or-llm","description":"User type: \\"new\\" or \\"active\\" (default: active)"},"interval":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval: -300000 (real-time), -3600000 (hourly), 1 (daily), 7 (weekly), or 30 (monthly)"},"conversionWindowSeconds":{"type":"string","required":false,"visibility":"user-or-llm","description":"Conversion window in seconds (default: 2592000, i.e. 30 days)"},"groupBy":{"type":"string","required":false,"visibility":"user-or-llm","description":"Property to group by (limit: one; prefix custom properties with \\"gp:\\")"},"limit":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum number of group-by values (default: 100, max: 1000)"},"segment":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON segment definition(s) applied to the query"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_get_active_users":{"id":"amplitude_get_active_users","name":"Amplitude Get Active Users","description":"Get active or new user counts over a date range from the Dashboard REST API.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"start":{"type":"string","required":true,"visibility":"user-or-llm","description":"Start date in YYYYMMDD format"},"end":{"type":"string","required":true,"visibility":"user-or-llm","description":"End date in YYYYMMDD format"},"metric":{"type":"string","required":false,"visibility":"user-or-llm","description":"Metric type: \\"active\\" or \\"new\\" (default: active)"},"interval":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval: 1 (daily), 7 (weekly), or 30 (monthly)"},"groupBy":{"type":"string","required":false,"visibility":"user-or-llm","description":"Property name to group by"},"segment":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON segment definition(s) applied to the query"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_get_revenue":{"id":"amplitude_get_revenue","name":"Amplitude Get Revenue","description":"Get revenue LTV data including ARPU, ARPPU, total revenue, and paying user counts.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"start":{"type":"string","required":true,"visibility":"user-or-llm","description":"Start date in YYYYMMDD format"},"end":{"type":"string","required":true,"visibility":"user-or-llm","description":"End date in YYYYMMDD format"},"metric":{"type":"string","required":false,"visibility":"user-or-llm","description":"Metric: 0 (ARPU), 1 (ARPPU), 2 (Total Revenue), 3 (Paying Users)"},"interval":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval: 1 (daily), 7 (weekly), or 30 (monthly)"},"groupBy":{"type":"string","required":false,"visibility":"user-or-llm","description":"Property name to group by (limit: one)"},"segment":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON segment definition(s) applied to the query"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_group_identify":{"id":"amplitude_group_identify","name":"Amplitude Group Identify","description":"Set group-level properties in Amplitude. Supports $set, $setOnce, $add, $append, $unset operations.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"groupType":{"type":"string","required":true,"visibility":"user-or-llm","description":"Group classification (e.g., \\"company\\", \\"org_id\\")"},"groupValue":{"type":"string","required":true,"visibility":"user-or-llm","description":"Specific group identifier (e.g., \\"Acme Corp\\")"},"groupProperties":{"type":"string","required":true,"visibility":"user-or-llm","description":"JSON object of group properties. Use operations like $set, $setOnce, $add, $append, $unset."},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_identify_user":{"id":"amplitude_identify_user","name":"Amplitude Identify User","description":"Set user properties in Amplitude using the Identify API. Supports $set, $setOnce, $add, $append, $unset operations.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"userId":{"type":"string","required":false,"visibility":"user-or-llm","description":"User ID (required if no device_id)"},"deviceId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Device ID (required if no user_id)"},"userProperties":{"type":"string","required":true,"visibility":"user-or-llm","description":"JSON object of user properties. Use operations like $set, $setOnce, $add, $append, $unset."},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_list_events":{"id":"amplitude_list_events","name":"Amplitude List Events","description":"List all event types in the Amplitude project with their weekly totals and unique counts.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_realtime_active_users":{"id":"amplitude_realtime_active_users","name":"Amplitude Real-time Active Users","description":"Get real-time active user counts at 5-minute granularity for the last 2 days.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_retention":{"id":"amplitude_retention","name":"Amplitude Retention","description":"Measure how many users return to perform an action after a starting action.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"startEvent":{"type":"string","required":true,"visibility":"user-or-llm","description":"JSON starting event object, e.g. {\\"event_type\\":\\"_new\\"} or {\\"event_type\\":\\"_active\\"}"},"returnEvent":{"type":"string","required":true,"visibility":"user-or-llm","description":"JSON returning event object, e.g. {\\"event_type\\":\\"_all\\"} or {\\"event_type\\":\\"_active\\"}"},"start":{"type":"string","required":true,"visibility":"user-or-llm","description":"Start date in YYYYMMDD format"},"end":{"type":"string","required":true,"visibility":"user-or-llm","description":"End date in YYYYMMDD format"},"retentionMode":{"type":"string","required":false,"visibility":"user-or-llm","description":"Retention type: \\"bracket\\", \\"rolling\\", or \\"n-day\\" (default: n-day)"},"retentionBrackets":{"type":"string","required":false,"visibility":"user-or-llm","description":"Required when Retention Mode is \\"bracket\\". Day ranges, e.g. [[0,4]]"},"interval":{"type":"string","required":false,"visibility":"user-or-llm","description":"Time interval: 1 (daily), 7 (weekly), or 30 (monthly)"},"groupBy":{"type":"string","required":false,"visibility":"user-or-llm","description":"Property to group by (limit: one; prefix custom properties with \\"gp:\\")"},"segment":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON segment definition(s) applied to the query"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_send_event":{"id":"amplitude_send_event","name":"Amplitude Send Event","description":"Track an event in Amplitude using the HTTP V2 API.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"userId":{"type":"string","required":false,"visibility":"user-or-llm","description":"User ID (required if no device_id)"},"deviceId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Device ID (required if no user_id)"},"eventType":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the event (e.g., \\"page_view\\", \\"purchase\\")"},"eventProperties":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON object of custom event properties"},"userProperties":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON object of user properties to set (supports $set, $setOnce, $add, $append, $unset)"},"time":{"type":"string","required":false,"visibility":"user-or-llm","description":"Event timestamp in milliseconds since epoch"},"sessionId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Session start time in milliseconds since epoch"},"insertId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Unique ID for deduplication (within 7-day window)"},"appVersion":{"type":"string","required":false,"visibility":"user-or-llm","description":"Application version string"},"platform":{"type":"string","required":false,"visibility":"user-or-llm","description":"Platform (e.g., \\"Web\\", \\"iOS\\", \\"Android\\")"},"country":{"type":"string","required":false,"visibility":"user-or-llm","description":"Two-letter country code"},"language":{"type":"string","required":false,"visibility":"user-or-llm","description":"Language code (e.g., \\"en\\")"},"ip":{"type":"string","required":false,"visibility":"user-or-llm","description":"IP address for geo-location"},"price":{"type":"string","required":false,"visibility":"user-or-llm","description":"Price of the item purchased"},"quantity":{"type":"string","required":false,"visibility":"user-or-llm","description":"Quantity of items purchased"},"revenue":{"type":"string","required":false,"visibility":"user-or-llm","description":"Revenue amount"},"productId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Product identifier"},"revenueType":{"type":"string","required":false,"visibility":"user-or-llm","description":"Revenue type (e.g., \\"purchase\\", \\"refund\\")"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_user_activity":{"id":"amplitude_user_activity","name":"Amplitude User Activity","description":"Get the event stream for a specific user by their Amplitude ID.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"amplitudeId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Amplitude internal user ID"},"offset":{"type":"string","required":false,"visibility":"user-or-llm","description":"Offset for pagination (default 0)"},"limit":{"type":"string","required":false,"visibility":"user-or-llm","description":"Maximum number of events to return (default 1000, max 1000)"},"direction":{"type":"string","required":false,"visibility":"user-or-llm","description":"Sort direction: \\"latest\\" or \\"earliest\\" (default: latest)"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"amplitude_user_profile":{"id":"amplitude_user_profile","name":"Amplitude User Profile","description":"Get a user profile including properties, cohort memberships, and computed properties. Not available for EU data-residency projects.","version":"1.0.0","params":{"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"userId":{"type":"string","required":false,"visibility":"user-or-llm","description":"External user ID (required if no device_id)"},"deviceId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Device ID (required if no user_id)"},"getAmpProps":{"type":"string","required":false,"visibility":"user-or-llm","description":"Include Amplitude user properties (true/false, default: false)"},"getCohortIds":{"type":"string","required":false,"visibility":"user-or-llm","description":"Include cohort IDs the user belongs to (true/false, default: false)"},"getComputations":{"type":"string","required":false,"visibility":"user-or-llm","description":"Include computed user properties (true/false, default: false)"}}},"amplitude_user_search":{"id":"amplitude_user_search","name":"Amplitude User Search","description":"Search for a user by User ID, Device ID, or Amplitude ID using the Dashboard REST API.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude API Key"},"secretKey":{"type":"string","required":true,"visibility":"user-only","description":"Amplitude Secret Key"},"user":{"type":"string","required":true,"visibility":"user-or-llm","description":"User ID, Device ID, or Amplitude ID to search for"},"dataResidency":{"type":"string","required":false,"visibility":"user-or-llm","description":"Data residency region: \\"us\\" (default) or \\"eu\\""}}},"apify_get_dataset_items":{"id":"apify_get_dataset_items","name":"APIFY Get Dataset Items","description":"Retrieve items stored in an APIFY dataset","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"APIFY API token from console.apify.com/account#/integrations"},"datasetId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Dataset ID to read items from. Example: \\"9RnD3Pql2vGZkc5H5\\""},"itemLimit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Max items to return (1-250000). Default: all items. Example: 500"},"offset":{"type":"number","required":false,"visibility":"user-or-llm","description":"Number of items to skip at the start. Default: 0"},"fields":{"type":"string","required":false,"visibility":"user-or-llm","description":"Comma-separated list of fields to include. Example: \\"title,url,price\\""}}},"apify_get_run":{"id":"apify_get_run","name":"APIFY Get Run","description":"Get the status and details of an APIFY actor run","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"APIFY API token from console.apify.com/account#/integrations"},"runId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Actor run ID to fetch. Example: \\"HG7ML7M8z78YcAPEB\\""}}},"apify_run_actor_async":{"id":"apify_run_actor_async","name":"APIFY Run Actor (Async)","description":"Run an APIFY actor asynchronously with polling for long-running tasks","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"APIFY API token from console.apify.com/account#/integrations"},"actorId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Actor ID or username/actor-name. Examples: \\"apify/web-scraper\\", \\"janedoe/my-actor\\", \\"moJRLRc85AitArpNN\\""},"input":{"type":"string","required":false,"visibility":"user-or-llm","description":"Actor input as JSON string. Example: {\\"startUrls\\": [{\\"url\\": \\"https://example.com\\"}], \\"maxPages\\": 10}"},"waitForFinish":{"type":"number","required":false,"visibility":"user-or-llm","description":"Initial wait time in seconds (0-60) before polling starts. Example: 30"},"itemLimit":{"type":"number","required":false,"default":100,"visibility":"user-or-llm","description":"Max dataset items to fetch (1-250000). Default: 100. Example: 500"},"memory":{"type":"number","required":false,"visibility":"user-or-llm","description":"Memory in megabytes allocated for the actor run (128-32768). Example: 1024 for 1GB, 2048 for 2GB"},"timeout":{"type":"number","required":false,"visibility":"user-or-llm","description":"Timeout in seconds for the actor run. Example: 300 for 5 minutes, 3600 for 1 hour"},"build":{"type":"string","required":false,"visibility":"user-or-llm","description":"Actor build to run. Examples: \\"latest\\", \\"beta\\", \\"1.2.3\\", \\"build-tag-name\\""}}},"apify_run_actor_sync":{"id":"apify_run_actor_sync","name":"APIFY Run Actor (Sync)","description":"Run an APIFY actor synchronously and get results (max 5 minutes)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"APIFY API token from console.apify.com/account#/integrations"},"actorId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Actor ID or username/actor-name. Examples: \\"apify/web-scraper\\", \\"janedoe/my-actor\\", \\"moJRLRc85AitArpNN\\""},"input":{"type":"string","required":false,"visibility":"user-or-llm","description":"Actor input as JSON string. Example: {\\"startUrls\\": [{\\"url\\": \\"https://example.com\\"}], \\"maxPages\\": 10}"},"memory":{"type":"number","required":false,"visibility":"user-or-llm","description":"Memory in megabytes allocated for the actor run (128-32768). Example: 1024 for 1GB, 2048 for 2GB"},"timeout":{"type":"number","required":false,"visibility":"user-or-llm","description":"Timeout in seconds for the actor run. Example: 300 for 5 minutes, 3600 for 1 hour"},"build":{"type":"string","required":false,"visibility":"user-or-llm","description":"Actor build to run. Examples: \\"latest\\", \\"beta\\", \\"1.2.3\\", \\"build-tag-name\\""}}},"apify_run_task":{"id":"apify_run_task","name":"APIFY Run Task","description":"Run a saved APIFY actor task synchronously and get dataset items (max 5 minutes)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"APIFY API token from console.apify.com/account#/integrations"},"taskId":{"type":"string","required":true,"visibility":"user-or-llm","description":"Task ID or username/task-name. Examples: \\"janedoe/my-task\\", \\"moJRLRc85AitArpNN\\""},"input":{"type":"string","required":false,"visibility":"user-or-llm","description":"JSON string that overrides the task\'s saved input. Example: {\\"startUrls\\": [{\\"url\\": \\"https://example.com\\"}]}"},"itemLimit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Max dataset items to return (1-250000). Example: 500"},"memory":{"type":"number","required":false,"visibility":"user-or-llm","description":"Memory in megabytes allocated for the run (128-32768). Example: 1024 for 1GB"},"timeout":{"type":"number","required":false,"visibility":"user-or-llm","description":"Timeout in seconds for the run. Example: 300 for 5 minutes"},"build":{"type":"string","required":false,"visibility":"user-or-llm","description":"Actor build to run. Examples: \\"latest\\", \\"beta\\", \\"1.2.3\\""}}},"apollo_account_bulk_create":{"id":"apollo_account_bulk_create","name":"Apollo Bulk Create Accounts","description":"Create up to 100 accounts at once in your Apollo database. Set run_dedupe=true to deduplicate by domain, organization_id, and name. Master key required.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"accounts":{"type":"array","required":true,"visibility":"user-or-llm","description":"Array of accounts to create (max 100). Each account should include a name, and may optionally include domain, phone, phone_status_cd, raw_address, owner_id, linkedin_url, facebook_url, twitter_url, salesforce_id, and hubspot_id."},"append_label_names":{"type":"array","required":false,"visibility":"user-only","description":"Array of label names to add to ALL accounts in this request"},"run_dedupe":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"When true, performs aggressive deduplication by domain, organization_id, and name (defaults to false)"}}},"apollo_account_bulk_update":{"id":"apollo_account_bulk_update","name":"Apollo Bulk Update Accounts","description":"Update up to 1000 existing accounts at once in your Apollo database (higher limit than contacts!). Each account must include an id field. Master key required.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"account_ids":{"type":"array","required":false,"visibility":"user-or-llm","description":"Array of account IDs to update with the same values (max 1000). Use with name/owner_id for uniform updates. Use either this OR account_attributes."},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"When using account_ids, apply this name to all accounts"},"owner_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"When using account_ids, apply this owner to all accounts"},"account_stage_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"When using account_ids, apply this account stage to all accounts"},"account_attributes":{"type":"json","required":false,"visibility":"user-or-llm","description":"Array of account objects with individual updates (each must include id). Example: [{\\"id\\": \\"acc1\\", \\"name\\": \\"Acme\\", \\"owner_id\\": \\"u1\\", \\"account_stage_id\\": \\"s1\\", \\"typed_custom_fields\\": {\\"field_id\\": \\"value\\"}}]"},"async":{"type":"boolean","required":false,"visibility":"user-only","description":"When true, processes the update asynchronously. Only supported when using account_ids; returns 422 if used with account_attributes."}}},"apollo_account_create":{"id":"apollo_account_create","name":"Apollo Create Account","description":"Create a new account (company) in your Apollo database","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Company name (e.g., \\"Acme Corporation\\")"},"domain":{"type":"string","required":false,"visibility":"user-or-llm","description":"Company domain without www. prefix (e.g., \\"acme.com\\")"},"phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Primary phone number for the account"},"owner_id":{"type":"string","required":false,"visibility":"user-only","description":"Apollo user ID of the account owner"},"account_stage_id":{"type":"string","required":false,"visibility":"user-only","description":"Apollo ID for the account stage to assign this account to"},"raw_address":{"type":"string","required":false,"visibility":"user-or-llm","description":"Corporate location (e.g., \\"San Francisco, CA, USA\\")"},"typed_custom_fields":{"type":"json","required":false,"visibility":"user-only","description":"Custom field values as { custom_field_id: value } map"}}},"apollo_account_search":{"id":"apollo_account_search","name":"Apollo Search Accounts","description":"Search your team\'s accounts in Apollo. Display limit: 50,000 records (100 records per page, 500 pages max). Use filters to narrow results. Master key required.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"q_organization_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter accounts by organization name (partial-match search)"},"account_stage_ids":{"type":"array","required":false,"visibility":"user-only","description":"Filter by account stage IDs"},"account_label_ids":{"type":"array","required":false,"visibility":"user-only","description":"Filter by account label IDs"},"sort_by_field":{"type":"string","required":false,"visibility":"user-or-llm","description":"Sort field: \\"account_last_activity_date\\", \\"account_created_at\\", or \\"account_updated_at\\""},"sort_ascending":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Sort ascending when true. Defaults to descending."},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, max 100 (e.g., 25, 50, 100)"}}},"apollo_account_update":{"id":"apollo_account_update","name":"Apollo Update Account","description":"Update an existing account in your Apollo database","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"account_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the account to update (e.g., \\"acc_abc123\\")"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Company name (e.g., \\"Acme Corporation\\")"},"domain":{"type":"string","required":false,"visibility":"user-or-llm","description":"Company domain (e.g., \\"acme.com\\")"},"phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Company phone number"},"owner_id":{"type":"string","required":false,"visibility":"user-only","description":"Apollo user ID of the account owner"},"account_stage_id":{"type":"string","required":false,"visibility":"user-only","description":"Apollo ID for the account stage to assign this account to"},"raw_address":{"type":"string","required":false,"visibility":"user-or-llm","description":"Corporate location (e.g., \\"San Francisco, CA, USA\\")"},"typed_custom_fields":{"type":"json","required":false,"visibility":"user-only","description":"Custom field values as { custom_field_id: value } map"}}},"apollo_contact_bulk_create":{"id":"apollo_contact_bulk_create","name":"Apollo Bulk Create Contacts","description":"Create up to 100 contacts at once in your Apollo database. Supports deduplication to prevent creating duplicate contacts. Master key required.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"contacts":{"type":"array","required":true,"visibility":"user-or-llm","description":"Array of contacts to create (max 100). Each contact may include first_name, last_name, email, title, organization_name, account_id, owner_id, contact_stage_id, linkedin_url, phone (single string) or phone_numbers (array of {raw_number, position}), contact_emails, typed_custom_fields, and CRM IDs (salesforce_contact_id, hubspot_id, team_id) for cross-system matching"},"append_label_names":{"type":"array","required":false,"visibility":"user-or-llm","description":"Label names to add to all contacts in this request (e.g., [\\"Hot Lead\\"])"},"run_dedupe":{"type":"boolean","required":false,"visibility":"user-only","description":"Enable deduplication to prevent creating duplicate contacts. When true, existing contacts are returned without modification"}}},"apollo_contact_bulk_update":{"id":"apollo_contact_bulk_update","name":"Apollo Bulk Update Contacts","description":"Update up to 100 existing contacts at once in your Apollo database. Each contact must include an id field. Master key required.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"contact_ids":{"type":"array","required":false,"visibility":"user-or-llm","description":"Array of contact IDs to update. Must be paired with an object-form contact_attributes specifying the fields to apply uniformly to all listed contacts."},"contact_attributes":{"type":"json","required":false,"visibility":"user-or-llm","description":"Required. Either an array of per-contact updates (each with id) — used standalone — or a single object of attributes to apply to all contact_ids. Supported fields: owner_id, email, organization_name, title, first_name, last_name, account_id, present_raw_address, linkedin_url, typed_custom_fields"},"async":{"type":"boolean","required":false,"visibility":"user-only","description":"Force asynchronous processing. Automatically enabled for >100 contacts"}}},"apollo_contact_create":{"id":"apollo_contact_create","name":"Apollo Create Contact","description":"Create a new contact in your Apollo database","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"first_name":{"type":"string","required":true,"visibility":"user-or-llm","description":"First name of the contact"},"last_name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Last name of the contact"},"email":{"type":"string","required":false,"visibility":"user-or-llm","description":"Email address of the contact"},"title":{"type":"string","required":false,"visibility":"user-or-llm","description":"Job title (e.g., \\"VP of Sales\\", \\"Software Engineer\\")"},"account_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"Apollo account ID to associate with (e.g., \\"acc_abc123\\")"},"owner_id":{"type":"string","required":false,"visibility":"user-only","description":"User ID of the contact owner (accepted by Apollo but not officially documented for POST /contacts)"},"organization_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Name of the contact\'s employer (e.g., \\"Apollo\\")"},"website_url":{"type":"string","required":false,"visibility":"user-or-llm","description":"Corporate website URL (e.g., \\"https://www.apollo.io/\\")"},"label_names":{"type":"array","required":false,"visibility":"user-or-llm","description":"Lists/labels to add the contact to (e.g., [\\"Prospects\\"])"},"contact_stage_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"Apollo ID for the contact stage"},"present_raw_address":{"type":"string","required":false,"visibility":"user-or-llm","description":"Personal location for the contact (e.g., \\"Atlanta, United States\\")"},"direct_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Primary phone number"},"corporate_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Work/office phone number"},"mobile_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Mobile phone number"},"home_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Home phone number"},"other_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Alternative phone number"},"typed_custom_fields":{"type":"json","required":false,"visibility":"user-or-llm","description":"Custom field values keyed by custom field ID"},"run_dedupe":{"type":"boolean","required":false,"visibility":"user-only","description":"When true, Apollo deduplicates against existing contacts"}}},"apollo_contact_search":{"id":"apollo_contact_search","name":"Apollo Search Contacts","description":"Search your team\'s contacts in Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"q_keywords":{"type":"string","required":false,"visibility":"user-or-llm","description":"Keywords to search for"},"contact_stage_ids":{"type":"array","required":false,"visibility":"user-only","description":"Filter by contact stage IDs"},"contact_label_ids":{"type":"array","required":false,"visibility":"user-only","description":"Filter by Apollo label IDs (lists)"},"sort_by_field":{"type":"string","required":false,"visibility":"user-only","description":"Sort field: contact_last_activity_date, contact_email_last_opened_at, contact_email_last_clicked_at, contact_created_at, or contact_updated_at"},"sort_ascending":{"type":"boolean","required":false,"visibility":"user-only","description":"When true, sort ascending. Must be used together with sort_by_field"},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, max 100 (e.g., 25, 50, 100)"}}},"apollo_contact_update":{"id":"apollo_contact_update","name":"Apollo Update Contact","description":"Update an existing contact in your Apollo database","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"contact_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the contact to update (e.g., \\"con_abc123\\")"},"first_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"First name of the contact"},"last_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Last name of the contact"},"email":{"type":"string","required":false,"visibility":"user-or-llm","description":"Email address"},"title":{"type":"string","required":false,"visibility":"user-or-llm","description":"Job title (e.g., \\"VP of Sales\\", \\"Software Engineer\\")"},"account_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"Apollo account ID (e.g., \\"acc_abc123\\")"},"owner_id":{"type":"string","required":false,"visibility":"user-only","description":"User ID of the contact owner (accepted by Apollo but not officially documented for PATCH /contacts/{id})"},"organization_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Name of the contact\'s employer (e.g., \\"Apollo\\")"},"website_url":{"type":"string","required":false,"visibility":"user-or-llm","description":"Corporate website URL (e.g., \\"https://www.apollo.io/\\")"},"label_names":{"type":"array","required":false,"visibility":"user-or-llm","description":"Lists/labels to add the contact to (e.g., [\\"Prospects\\"])"},"contact_stage_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"Apollo ID for the contact stage"},"present_raw_address":{"type":"string","required":false,"visibility":"user-or-llm","description":"Personal location for the contact (e.g., \\"Atlanta, United States\\")"},"direct_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Primary phone number"},"corporate_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Work/office phone number"},"mobile_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Mobile phone number"},"home_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Home phone number"},"other_phone":{"type":"string","required":false,"visibility":"user-or-llm","description":"Alternative phone number"},"typed_custom_fields":{"type":"json","required":false,"visibility":"user-or-llm","description":"Custom field values keyed by custom field ID"}}},"apollo_email_accounts":{"id":"apollo_email_accounts","name":"Apollo Get Email Accounts","description":"Get list of team\'s linked email accounts in Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"}}},"apollo_opportunity_create":{"id":"apollo_opportunity_create","name":"Apollo Create Opportunity","description":"Create a new deal for an account in your Apollo database (master key required)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the opportunity/deal (e.g., \\"Enterprise License - Q1\\")"},"account_id":{"type":"string","required":false,"visibility":"user-or-llm","description":"ID of the account this opportunity belongs to (e.g., \\"acc_abc123\\")"},"amount":{"type":"string","required":false,"visibility":"user-or-llm","description":"Monetary value as a plain number string with no commas or currency symbols"},"opportunity_stage_id":{"type":"string","required":false,"visibility":"user-only","description":"ID of the opportunity stage"},"owner_id":{"type":"string","required":false,"visibility":"user-only","description":"User ID of the opportunity owner"},"closed_date":{"type":"string","required":false,"visibility":"user-or-llm","description":"Expected close date in YYYY-MM-DD format"},"typed_custom_fields":{"type":"json","required":false,"visibility":"user-only","description":"Custom field values as { custom_field_id: value } map"}}},"apollo_opportunity_get":{"id":"apollo_opportunity_get","name":"Apollo Get Opportunity","description":"Retrieve complete details of a specific deal/opportunity by ID","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"opportunity_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the opportunity to retrieve (e.g., \\"opp_abc123\\")"}}},"apollo_opportunity_search":{"id":"apollo_opportunity_search","name":"Apollo Search Opportunities","description":"Search and list all deals/opportunities in your team\'s Apollo account","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"sort_by_field":{"type":"string","required":false,"visibility":"user-or-llm","description":"Sort field: \\"amount\\", \\"is_closed\\", or \\"is_won\\""},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, max 100 (e.g., 25, 50, 100)"}}},"apollo_opportunity_update":{"id":"apollo_opportunity_update","name":"Apollo Update Opportunity","description":"Update an existing deal/opportunity in your Apollo database","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"opportunity_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the opportunity to update (e.g., \\"opp_abc123\\")"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Name of the opportunity/deal (e.g., \\"Enterprise License - Q1\\")"},"amount":{"type":"string","required":false,"visibility":"user-or-llm","description":"Monetary value as a plain number string with no commas or currency symbols"},"opportunity_stage_id":{"type":"string","required":false,"visibility":"user-only","description":"ID of the opportunity stage"},"owner_id":{"type":"string","required":false,"visibility":"user-only","description":"User ID of the opportunity owner"},"closed_date":{"type":"string","required":false,"visibility":"user-or-llm","description":"Expected close date in YYYY-MM-DD format"},"typed_custom_fields":{"type":"json","required":false,"visibility":"user-only","description":"Custom field values as { custom_field_id: value } map"}}},"apollo_organization_bulk_enrich":{"id":"apollo_organization_bulk_enrich","name":"Apollo Bulk Organization Enrichment","description":"Enrich data for up to 10 organizations at once using Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"domains":{"type":"array","required":true,"visibility":"user-or-llm","description":"Array of company domains to enrich (max 10, no www. or @, e.g., [\\"apollo.io\\", \\"stripe.com\\"])"}}},"apollo_organization_enrich":{"id":"apollo_organization_enrich","name":"Apollo Organization Enrichment","description":"Enrich data for a single organization using Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"domain":{"type":"string","required":true,"visibility":"user-or-llm","description":"Company domain (e.g., \\"apollo.io\\", \\"acme.com\\")"}}},"apollo_organization_search":{"id":"apollo_organization_search","name":"Apollo Organization Search","description":"Search Apollo\'s database for companies using filters","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"organization_locations":{"type":"array","required":false,"visibility":"user-or-llm","description":"Company HQ locations (cities, US states, or countries)"},"organization_not_locations":{"type":"array","required":false,"visibility":"user-or-llm","description":"Exclude companies whose HQ is in these locations"},"organization_num_employees_ranges":{"type":"array","required":false,"visibility":"user-or-llm","description":"Employee count ranges as \\"min,max\\" strings (e.g., [\\"1,10\\", \\"250,500\\", \\"10000,20000\\"])"},"q_organization_keyword_tags":{"type":"array","required":false,"visibility":"user-or-llm","description":"Industry or keyword tags"},"q_organization_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Organization name to search for (e.g., \\"Acme\\", \\"TechCorp\\")"},"organization_ids":{"type":"array","required":false,"visibility":"user-or-llm","description":"Apollo organization IDs to include (e.g., [\\"5e66b6381e05b4008c8331b8\\"])"},"q_organization_domains_list":{"type":"array","required":false,"visibility":"user-or-llm","description":"Domain names to filter by (no www. or @, up to 1,000)"},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, max 100 (e.g., 25, 50, 100)"}}},"apollo_people_bulk_enrich":{"id":"apollo_people_bulk_enrich","name":"Apollo Bulk People Enrichment","description":"Enrich data for up to 10 people at once using Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"people":{"type":"array","required":true,"visibility":"user-or-llm","description":"Array of people to enrich (max 10)"},"reveal_personal_emails":{"type":"boolean","required":false,"visibility":"user-only","description":"Reveal personal email addresses (uses credits)"},"reveal_phone_number":{"type":"boolean","required":false,"visibility":"user-only","description":"Reveal phone numbers (uses credits, requires webhook_url)"},"webhook_url":{"type":"string","required":false,"visibility":"user-only","description":"Webhook URL for async phone number delivery (required when reveal_phone_number is true)"}}},"apollo_people_enrich":{"id":"apollo_people_enrich","name":"Apollo People Enrichment","description":"Enrich data for a single person using Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"first_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"First name of the person"},"last_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Last name of the person"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Full name of the person (alternative to first_name/last_name)"},"id":{"type":"string","required":false,"visibility":"user-or-llm","description":"Apollo ID for the person"},"hashed_email":{"type":"string","required":false,"visibility":"user-or-llm","description":"MD5 or SHA-256 hashed email"},"email":{"type":"string","required":false,"visibility":"user-or-llm","description":"Email address of the person"},"organization_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Company name where the person works"},"domain":{"type":"string","required":false,"visibility":"user-or-llm","description":"Company domain (e.g., \\"apollo.io\\", \\"acme.com\\")"},"linkedin_url":{"type":"string","required":false,"visibility":"user-or-llm","description":"LinkedIn profile URL"},"reveal_personal_emails":{"type":"boolean","required":false,"visibility":"user-only","description":"Reveal personal email addresses (uses credits)"},"reveal_phone_number":{"type":"boolean","required":false,"visibility":"user-only","description":"Reveal phone numbers (uses credits, requires webhook_url)"},"webhook_url":{"type":"string","required":false,"visibility":"user-only","description":"Webhook URL for async phone number delivery (required when reveal_phone_number is true)"}}},"apollo_people_search":{"id":"apollo_people_search","name":"Apollo People Search","description":"Search Apollo\'s database for people using demographic filters","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key"},"person_titles":{"type":"array","required":false,"visibility":"user-or-llm","description":"Job titles to search for (e.g., [\\"CEO\\", \\"VP of Sales\\"])"},"include_similar_titles":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Whether to return people with job titles similar to person_titles"},"person_locations":{"type":"array","required":false,"visibility":"user-or-llm","description":"Locations to search in (e.g., [\\"San Francisco, CA\\", \\"New York, NY\\"])"},"person_seniorities":{"type":"array","required":false,"visibility":"user-or-llm","description":"Seniority levels (one of: owner, founder, c_suite, partner, vp, head, director, manager, senior, entry, intern)"},"organization_ids":{"type":"array","required":false,"visibility":"user-or-llm","description":"Apollo organization IDs to filter by (e.g., [\\"5e66b6381e05b4008c8331b8\\"])"},"organization_names":{"type":"array","required":false,"visibility":"user-or-llm","description":"Company names to search within (legacy filter)"},"organization_locations":{"type":"array","required":false,"visibility":"user-or-llm","description":"Headquarters locations of the people\'s current employer (e.g., [\'texas\', \'tokyo\', \'spain\'])"},"q_organization_domains_list":{"type":"array","required":false,"visibility":"user-or-llm","description":"Employer domain names (e.g., [\\"apollo.io\\", \\"microsoft.com\\"]) — up to 1,000, no www. or @"},"organization_num_employees_ranges":{"type":"array","required":false,"visibility":"user-or-llm","description":"Employee count ranges for the person\'s current employer. Each entry is \\"min,max\\" (e.g., [\\"1,10\\", \\"250,500\\", \\"10000,20000\\"])"},"contact_email_status":{"type":"array","required":false,"visibility":"user-or-llm","description":"Email statuses to filter by: \\"verified\\", \\"unverified\\", \\"likely to engage\\", \\"unavailable\\""},"q_keywords":{"type":"string","required":false,"visibility":"user-or-llm","description":"Keywords to search for"},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination, default 1 (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, default 25, max 100 (e.g., 25, 50, 100)"}}},"apollo_sequence_add_contacts":{"id":"apollo_sequence_add_contacts","name":"Apollo Add Contacts to Sequence","description":"Add contacts to an Apollo sequence","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"sequence_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the sequence to add contacts to (e.g., \\"seq_abc123\\")"},"contact_ids":{"type":"array","required":false,"visibility":"user-or-llm","description":"Array of contact IDs to add to the sequence (e.g., [\\"con_abc123\\", \\"con_def456\\"]). Either contact_ids or label_names must be provided."},"label_names":{"type":"array","required":false,"visibility":"user-or-llm","description":"Array of label names to identify contacts to add to the sequence. Either contact_ids or label_names must be provided."},"send_email_from_email_account_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the email account to send from. Use the Get Email Accounts operation to look this up."},"send_email_from_email_address":{"type":"string","required":false,"visibility":"user-only","description":"Specific email address to send from within the email account."},"sequence_no_email":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts even if they have no email address"},"sequence_unverified_email":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts with unverified email addresses"},"sequence_job_change":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts who recently changed jobs"},"sequence_active_in_other_campaigns":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts active in other campaigns"},"sequence_finished_in_other_campaigns":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts who finished other campaigns"},"sequence_same_company_in_same_campaign":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts even if others from the same company are in the sequence"},"contacts_without_ownership_permission":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts without ownership permission"},"add_if_in_queue":{"type":"boolean","required":false,"visibility":"user-only","description":"Add contacts even if they are in the queue"},"contact_verification_skipped":{"type":"boolean","required":false,"visibility":"user-only","description":"Skip contact verification when adding"},"user_id":{"type":"string","required":false,"visibility":"user-only","description":"ID of the user performing the action"},"status":{"type":"string","required":false,"visibility":"user-only","description":"Initial status for added contacts: \\"active\\" or \\"paused\\""},"auto_unpause_at":{"type":"string","required":false,"visibility":"user-only","description":"ISO 8601 datetime to automatically unpause contacts"}}},"apollo_sequence_search":{"id":"apollo_sequence_search","name":"Apollo Search Sequences","description":"Search for sequences/campaigns in your team\'s Apollo account (master key required)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"q_name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Search sequences by name (e.g., \\"Outbound Q1\\", \\"Follow-up\\")"},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, max 100 (e.g., 25, 50, 100)"}}},"apollo_task_create":{"id":"apollo_task_create","name":"Apollo Create Task","description":"Create one or more tasks in Apollo (one task per contact_id, master key required)","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"user_id":{"type":"string","required":true,"visibility":"user-or-llm","description":"ID of the Apollo user the task is assigned to"},"contact_ids":{"type":"array","required":true,"visibility":"user-or-llm","description":"Array of contact IDs. One task is created per contact."},"priority":{"type":"string","required":false,"visibility":"user-or-llm","description":"Task priority: \\"high\\", \\"medium\\", or \\"low\\" (defaults to \\"medium\\")"},"due_at":{"type":"string","required":true,"visibility":"user-or-llm","description":"Due date/time in ISO 8601 format (e.g., \\"2024-12-31T23:59:59Z\\")"},"type":{"type":"string","required":true,"visibility":"user-or-llm","description":"Task type: \\"call\\", \\"outreach_manual_email\\", \\"linkedin_step_connect\\", \\"linkedin_step_message\\", \\"linkedin_step_view_profile\\", \\"linkedin_step_interact_post\\", or \\"action_item\\""},"status":{"type":"string","required":true,"visibility":"user-or-llm","description":"Task status: \\"scheduled\\", \\"completed\\", or \\"skipped\\""},"note":{"type":"string","required":false,"visibility":"user-or-llm","description":"Free-form note providing context for the task"}}},"apollo_task_search":{"id":"apollo_task_search","name":"Apollo Search Tasks","description":"Search for tasks in Apollo","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Apollo API key (master key required)"},"sort_by_field":{"type":"string","required":false,"visibility":"user-or-llm","description":"Sort field: \\"task_due_at\\" or \\"task_priority\\""},"open_factor_names":{"type":"array","required":false,"visibility":"user-or-llm","description":"Filter by status. Common values: [\\"task_types\\"] for open tasks, [\\"task_completed_at\\"] for completed tasks."},"page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Page number for pagination (e.g., 1, 2, 3)"},"per_page":{"type":"number","required":false,"visibility":"user-or-llm","description":"Results per page, max 100 (e.g., 25, 50, 100)"}}},"appconfig_create_application":{"id":"appconfig_create_application","name":"AppConfig Create Application","description":"Create an application in AWS AppConfig","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the application to create"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"Description of the application"}}},"appconfig_create_configuration_profile":{"id":"appconfig_create_configuration_profile","name":"AppConfig Create Configuration Profile","description":"Create a configuration profile in an AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID to create the configuration profile in"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the configuration profile"},"locationUri":{"type":"string","required":true,"visibility":"user-or-llm","description":"Where the configuration is stored. Use \\"hosted\\" for AppConfig-hosted configurations, or an SSM/S3 URI"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"Description of the configuration profile"},"retrievalRoleArn":{"type":"string","required":false,"visibility":"user-or-llm","description":"ARN of an IAM role to retrieve the configuration (required for non-hosted URIs)"},"type":{"type":"string","required":false,"visibility":"user-or-llm","description":"Profile type: AWS.Freeform (default) or AWS.AppConfig.FeatureFlags"}}},"appconfig_create_environment":{"id":"appconfig_create_environment","name":"AppConfig Create Environment","description":"Create an environment for an AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID to create the environment in"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the environment to create"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"Description of the environment"}}},"appconfig_create_hosted_configuration_version":{"id":"appconfig_create_hosted_configuration_version","name":"AppConfig Create Hosted Configuration Version","description":"Create a new hosted configuration version for an AppConfig configuration profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to add the version to"},"content":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration content (e.g., a JSON or YAML document)"},"contentType":{"type":"string","required":true,"visibility":"user-or-llm","description":"Content type of the configuration (e.g., application/json, text/plain)"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"Description of the configuration version"},"latestVersionNumber":{"type":"number","required":false,"visibility":"user-or-llm","description":"The version number of the latest version, used for optimistic concurrency"},"versionLabel":{"type":"string","required":false,"visibility":"user-or-llm","description":"A user-defined label for the configuration version"}}},"appconfig_delete_application":{"id":"appconfig_delete_application","name":"AppConfig Delete Application","description":"Delete an AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID to delete"}}},"appconfig_delete_configuration_profile":{"id":"appconfig_delete_configuration_profile","name":"AppConfig Delete Configuration Profile","description":"Delete an AWS AppConfig configuration profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to delete"}}},"appconfig_delete_environment":{"id":"appconfig_delete_environment","name":"AppConfig Delete Environment","description":"Delete an AWS AppConfig environment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the environment"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID to delete"}}},"appconfig_delete_hosted_configuration_version":{"id":"appconfig_delete_hosted_configuration_version","name":"AppConfig Delete Hosted Configuration Version","description":"Delete a specific hosted configuration version from an AppConfig profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID that owns the version"},"versionNumber":{"type":"number","required":true,"visibility":"user-or-llm","description":"The version number to delete"}}},"appconfig_get_application":{"id":"appconfig_get_application","name":"AppConfig Get Application","description":"Get details about a single AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID to retrieve"}}},"appconfig_get_configuration":{"id":"appconfig_get_configuration","name":"AppConfig Get Configuration","description":"Retrieve the latest deployed configuration for an AppConfig application, environment, and profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID or name to retrieve configuration for"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID or name to retrieve configuration for"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID or name to retrieve"}}},"appconfig_get_configuration_profile":{"id":"appconfig_get_configuration_profile","name":"AppConfig Get Configuration Profile","description":"Get details about a single AWS AppConfig configuration profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to retrieve"}}},"appconfig_get_deployment":{"id":"appconfig_get_deployment","name":"AppConfig Get Deployment","description":"Get details about a specific AWS AppConfig deployment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID of the deployment"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID of the deployment"},"deploymentNumber":{"type":"number","required":true,"visibility":"user-or-llm","description":"The sequence number of the deployment"}}},"appconfig_get_environment":{"id":"appconfig_get_environment","name":"AppConfig Get Environment","description":"Get details about a single AWS AppConfig environment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the environment"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID to retrieve"}}},"appconfig_get_hosted_configuration_version":{"id":"appconfig_get_hosted_configuration_version","name":"AppConfig Get Hosted Configuration Version","description":"Retrieve a specific hosted configuration version from an AppConfig profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to read the version from"},"versionNumber":{"type":"number","required":true,"visibility":"user-or-llm","description":"The version number to retrieve"}}},"appconfig_list_applications":{"id":"appconfig_list_applications","name":"AppConfig List Applications","description":"List applications in AWS AppConfig","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"maxResults":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of applications to return (1-50)"},"nextToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token from a previous response"}}},"appconfig_list_configuration_profiles":{"id":"appconfig_list_configuration_profiles","name":"AppConfig List Configuration Profiles","description":"List configuration profiles for an AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profiles"},"maxResults":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of configuration profiles to return (1-50)"},"nextToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token from a previous response"}}},"appconfig_list_deployment_strategies":{"id":"appconfig_list_deployment_strategies","name":"AppConfig List Deployment Strategies","description":"List deployment strategies available in AWS AppConfig","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"maxResults":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of deployment strategies to return (1-50)"},"nextToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token from a previous response"}}},"appconfig_list_deployments":{"id":"appconfig_list_deployments","name":"AppConfig List Deployments","description":"List deployments for an AWS AppConfig environment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID of the deployments"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID of the deployments"},"maxResults":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of deployments to return (1-50)"},"nextToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token from a previous response"}}},"appconfig_list_environments":{"id":"appconfig_list_environments","name":"AppConfig List Environments","description":"List environments for an AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the environments"},"maxResults":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of environments to return (1-50)"},"nextToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token from a previous response"}}},"appconfig_list_hosted_configuration_versions":{"id":"appconfig_list_hosted_configuration_versions","name":"AppConfig List Hosted Configuration Versions","description":"List hosted configuration versions for an AWS AppConfig configuration profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to list versions for"},"maxResults":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of versions to return (1-50)"},"nextToken":{"type":"string","required":false,"visibility":"user-or-llm","description":"Pagination token from a previous response"}}},"appconfig_start_deployment":{"id":"appconfig_start_deployment","name":"AppConfig Start Deployment","description":"Start deploying a configuration version to an AWS AppConfig environment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID to deploy in"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID to deploy to"},"deploymentStrategyId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The deployment strategy ID to use"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to deploy"},"configurationVersion":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration version to deploy"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"Description of the deployment"}}},"appconfig_stop_deployment":{"id":"appconfig_stop_deployment","name":"AppConfig Stop Deployment","description":"Stop an in-progress AWS AppConfig deployment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID of the deployment"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID of the deployment"},"deploymentNumber":{"type":"number","required":true,"visibility":"user-or-llm","description":"The sequence number of the deployment to stop"}}},"appconfig_update_application":{"id":"appconfig_update_application","name":"AppConfig Update Application","description":"Update the name or description of an AWS AppConfig application","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID to update"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"New name for the application"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"New description for the application"}}},"appconfig_update_configuration_profile":{"id":"appconfig_update_configuration_profile","name":"AppConfig Update Configuration Profile","description":"Update the name, description, or retrieval role of an AppConfig configuration profile","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the configuration profile"},"configurationProfileId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The configuration profile ID to update"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"New name for the configuration profile"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"New description for the configuration profile"},"retrievalRoleArn":{"type":"string","required":false,"visibility":"user-or-llm","description":"New ARN of the IAM role used to retrieve the configuration"}}},"appconfig_update_environment":{"id":"appconfig_update_environment","name":"AppConfig Update Environment","description":"Update the name or description of an AWS AppConfig environment","version":"1.0","params":{"region":{"type":"string","required":true,"visibility":"user-only","description":"AWS region (e.g., us-east-1)"},"accessKeyId":{"type":"string","required":true,"visibility":"user-only","description":"AWS access key ID"},"secretAccessKey":{"type":"string","required":true,"visibility":"user-only","description":"AWS secret access key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The application ID that owns the environment"},"environmentId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The environment ID to update"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"New name for the environment"},"description":{"type":"string","required":false,"visibility":"user-or-llm","description":"New description for the environment"}}},"arxiv_get_author_papers":{"id":"arxiv_get_author_papers","name":"ArXiv Get Author Papers","description":"Search for papers by a specific author on ArXiv.","version":"1.0.0","params":{"authorName":{"type":"string","required":true,"visibility":"user-or-llm","description":"Author name to search for"},"maxResults":{"type":"number","required":false,"visibility":"user-only","description":"Maximum number of results to return (default: 10, max: 2000)"}}},"arxiv_get_paper":{"id":"arxiv_get_paper","name":"ArXiv Get Paper","description":"Get detailed information about a specific ArXiv paper by its ID.","version":"1.0.0","params":{"paperId":{"type":"string","required":true,"visibility":"user-or-llm","description":"ArXiv paper ID (e.g., \\"1706.03762\\")"}}},"arxiv_search":{"id":"arxiv_search","name":"ArXiv Search","description":"Search for academic papers on ArXiv by keywords, authors, titles, or other fields.","version":"1.0.0","params":{"searchQuery":{"type":"string","required":true,"visibility":"user-or-llm","description":"The search query to execute"},"searchField":{"type":"string","required":false,"visibility":"user-only","description":"Field to search in: all, ti (title), au (author), abs (abstract), co (comment), jr (journal), cat (category), rn (report number)"},"maxResults":{"type":"number","required":false,"visibility":"user-only","description":"Maximum number of results to return (default: 10, max: 2000)"},"sortBy":{"type":"string","required":false,"visibility":"user-only","description":"Sort by: relevance, lastUpdatedDate, submittedDate (default: relevance)"},"sortOrder":{"type":"string","required":false,"visibility":"user-only","description":"Sort order: ascending, descending (default: descending)"}}},"asana_add_comment":{"id":"asana_add_comment","name":"Asana Add Comment","description":"Add a comment (story) to an Asana task","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"taskGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana task GID (numeric string)"},"text":{"type":"string","required":true,"visibility":"user-or-llm","description":"The text content of the comment"}},"oauth":{"required":true,"provider":"asana"}},"asana_add_followers":{"id":"asana_add_followers","name":"Asana Add Followers","description":"Add one or more followers to an Asana task","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"taskGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"GID of the Asana task (numeric string)"},"followers":{"type":"array","required":true,"visibility":"user-or-llm","description":"Array of user GIDs to add as followers to the task"}},"oauth":{"required":true,"provider":"asana"}},"asana_create_project":{"id":"asana_create_project","name":"Asana Create Project","description":"Create a new project in an Asana workspace","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"workspace":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana workspace GID (numeric string) where the project will be created"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the project"},"notes":{"type":"string","required":false,"visibility":"user-or-llm","description":"Notes or description for the project"}},"oauth":{"required":true,"provider":"asana"}},"asana_create_section":{"id":"asana_create_section","name":"Asana Create Section","description":"Create a new section in an Asana project","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"projectGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"GID of the Asana project (numeric string) to add the section to"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the section"}},"oauth":{"required":true,"provider":"asana"}},"asana_create_subtask":{"id":"asana_create_subtask","name":"Asana Create Subtask","description":"Create a subtask under an existing Asana task","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"taskGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"GID of the parent Asana task (numeric string)"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the subtask"},"notes":{"type":"string","required":false,"visibility":"user-or-llm","description":"Notes or description for the subtask"},"assignee":{"type":"string","required":false,"visibility":"user-or-llm","description":"User GID to assign the subtask to"},"due_on":{"type":"string","required":false,"visibility":"user-or-llm","description":"Due date in YYYY-MM-DD format"}},"oauth":{"required":true,"provider":"asana"}},"asana_create_task":{"id":"asana_create_task","name":"Asana Create Task","description":"Create a new task in Asana","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"workspace":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana workspace GID (numeric string) where the task will be created"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"Name of the task"},"notes":{"type":"string","required":false,"visibility":"user-or-llm","description":"Notes or description for the task"},"assignee":{"type":"string","required":false,"visibility":"user-or-llm","description":"User GID to assign the task to"},"due_on":{"type":"string","required":false,"visibility":"user-or-llm","description":"Due date in YYYY-MM-DD format"}},"oauth":{"required":true,"provider":"asana"}},"asana_delete_task":{"id":"asana_delete_task","name":"Asana Delete Task","description":"Delete an Asana task by its GID (moves it to the trash)","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"taskGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"GID of the Asana task to delete (numeric string)"}},"oauth":{"required":true,"provider":"asana"}},"asana_get_project":{"id":"asana_get_project","name":"Asana Get Project","description":"Retrieve a single Asana project by its GID","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"projectGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana project GID (numeric string) to retrieve"}},"oauth":{"required":true,"provider":"asana"}},"asana_get_projects":{"id":"asana_get_projects","name":"Asana Get Projects","description":"Retrieve all projects from an Asana workspace","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"workspace":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana workspace GID (numeric string) to retrieve projects from"}},"oauth":{"required":true,"provider":"asana"}},"asana_get_task":{"id":"asana_get_task","name":"Asana Get Task","description":"Retrieve a single task by GID or get multiple tasks with filters","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"taskGid":{"type":"string","required":false,"visibility":"user-or-llm","description":"The globally unique identifier (GID) of the task. If not provided, will get multiple tasks."},"workspace":{"type":"string","required":false,"visibility":"user-or-llm","description":"Asana workspace GID (numeric string) to filter tasks (required when not using taskGid)"},"project":{"type":"string","required":false,"visibility":"user-or-llm","description":"Asana project GID (numeric string) to filter tasks"},"limit":{"type":"number","required":false,"visibility":"user-or-llm","description":"Maximum number of tasks to return (default: 50)"}},"oauth":{"required":true,"provider":"asana"}},"asana_list_sections":{"id":"asana_list_sections","name":"Asana List Sections","description":"List all sections in an Asana project","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"projectGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"GID of the Asana project (numeric string) to list sections from"}},"oauth":{"required":true,"provider":"asana"}},"asana_list_workspaces":{"id":"asana_list_workspaces","name":"Asana List Workspaces","description":"List all Asana workspaces and organizations the authenticated user belongs to","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"}},"oauth":{"required":true,"provider":"asana"}},"asana_search_tasks":{"id":"asana_search_tasks","name":"Asana Search Tasks","description":"Search for tasks in an Asana workspace","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"workspace":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana workspace GID (numeric string) to search tasks in"},"text":{"type":"string","required":false,"visibility":"user-or-llm","description":"Text to search for in task names"},"assignee":{"type":"string","required":false,"visibility":"user-or-llm","description":"Filter tasks by assignee user GID"},"projects":{"type":"array","required":false,"visibility":"user-or-llm","description":"Array of Asana project GIDs (numeric strings) to filter tasks by"},"completed":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Filter by completion status"}},"oauth":{"required":true,"provider":"asana"}},"asana_update_task":{"id":"asana_update_task","name":"Asana Update Task","description":"Update an existing task in Asana","version":"1.0.0","params":{"accessToken":{"type":"string","required":true,"visibility":"hidden","description":"OAuth access token for Asana"},"taskGid":{"type":"string","required":true,"visibility":"user-or-llm","description":"Asana task GID (numeric string) of the task to update"},"name":{"type":"string","required":false,"visibility":"user-or-llm","description":"Updated name for the task"},"notes":{"type":"string","required":false,"visibility":"user-or-llm","description":"Updated notes or description for the task"},"assignee":{"type":"string","required":false,"visibility":"user-or-llm","description":"Updated assignee user GID"},"completed":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Mark task as completed or not completed"},"due_on":{"type":"string","required":false,"visibility":"user-or-llm","description":"Updated due date in YYYY-MM-DD format"}},"oauth":{"required":true,"provider":"asana"}},"ashby_add_candidate_tag":{"id":"ashby_add_candidate_tag","name":"Ashby Add Candidate Tag","description":"Adds a tag to a candidate in Ashby and returns the updated candidate.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"candidateId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the candidate to add the tag to"},"tagId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the tag to add"}}},"ashby_anonymize_candidate":{"id":"ashby_anonymize_candidate","name":"Ashby Anonymize Candidate","description":"Strips personally identifiable information from a candidate in Ashby. This does not delete the candidate - the record and its applications remain, with the PII removed. Ashby exposes no candidate deletion endpoint; true deletion is UI-only, restricted by role, and limited to a 10-day window. Requires the candidatesWrite permission.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"candidateId":{"type":"string","required":true,"visibility":"user-or-llm","description":"UUID of the candidate to anonymize"}}},"ashby_change_application_source":{"id":"ashby_change_application_source","name":"Ashby Change Application Source","description":"Changes the source attributed to an existing application, so programmatically created applications report correctly on the recruiting side. Requires the candidatesWrite permission.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"UUID of the application whose source should change"},"sourceId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the source to attribute the application to, as returned by List Sources. Omit only when unsetSource is true."},"unsetSource":{"type":"boolean","required":false,"visibility":"user-or-llm","description":"Set true to deliberately clear the application source. Required to unset, so that a missing or empty sourceId cannot wipe attribution by accident."}}},"ashby_change_application_stage":{"id":"ashby_change_application_stage","name":"Ashby Change Application Stage","description":"Moves an application to a different interview stage. Requires an archive reason when moving to an Archived stage.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"applicationId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the application to update the stage of"},"interviewStageId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the interview stage to move the application to"},"archiveReasonId":{"type":"string","required":false,"visibility":"user-or-llm","description":"Archive reason UUID. Required when moving to an Archived stage, ignored otherwise"}}},"ashby_create_application":{"id":"ashby_create_application","name":"Ashby Create Application","description":"Creates a new application for a candidate on a job. Optionally specify interview plan, stage, source, and credited user.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"candidateId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the candidate to consider for the job"},"jobId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the job to consider the candidate for"},"interviewPlanId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the interview plan to use (defaults to the job default plan)"},"interviewStageId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the interview stage to place the application in (defaults to first Lead stage)"},"sourceId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the source to set on the application"},"creditedToUserId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the user the application is credited to"},"createdAt":{"type":"string","required":false,"visibility":"user-or-llm","description":"ISO 8601 timestamp to set as the application creation date (defaults to now)"}}},"ashby_create_candidate":{"id":"ashby_create_candidate","name":"Ashby Create Candidate","description":"Creates a new candidate record in Ashby.","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"name":{"type":"string","required":true,"visibility":"user-or-llm","description":"The candidate full name"},"email":{"type":"string","required":false,"visibility":"user-or-llm","description":"Primary email address for the candidate"},"phoneNumber":{"type":"string","required":false,"visibility":"user-or-llm","description":"Primary phone number for the candidate"},"linkedInUrl":{"type":"string","required":false,"visibility":"user-or-llm","description":"LinkedIn profile URL"},"githubUrl":{"type":"string","required":false,"visibility":"user-or-llm","description":"GitHub profile URL"},"website":{"type":"string","required":false,"visibility":"user-or-llm","description":"Personal website URL"},"sourceId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the source to attribute the candidate to"},"creditedToUserId":{"type":"string","required":false,"visibility":"user-or-llm","description":"UUID of the Ashby user to credit with sourcing this candidate"},"createdAt":{"type":"string","required":false,"visibility":"user-or-llm","description":"Backdated creation timestamp in ISO 8601 (e.g. 2024-01-01T00:00:00Z). Defaults to now."},"alternateEmailAddresses":{"type":"json","required":false,"visibility":"user-or-llm","description":"Array of additional email address strings to add to the candidate, e.g. [\\"a@x.com\\",\\"b@y.com\\"]"}}},"ashby_create_note":{"id":"ashby_create_note","name":"Ashby Create Note","description":"Creates a note on a candidate in Ashby. Supports plain text and HTML content (bold, italic, underline, links, lists, code).","version":"1.0.0","params":{"apiKey":{"type":"string","required":true,"visibility":"user-only","description":"Ashby API Key"},"candidateId":{"type":"string","required":true,"visibility":"user-or-llm","description":"The UUID of the candidate to add the note to"},"note":{"type":"string","required":true,"visibility":"user-or-llm","description":"The note content. If noteType is text/html, supports: , , , ,