diff --git a/dashboards.go b/dashboards.go new file mode 100644 index 0000000..0be75d1 --- /dev/null +++ b/dashboards.go @@ -0,0 +1,246 @@ +// Code generated by internal/cmd/gen; DO NOT EDIT. + +package flashduty + +import "context" + +// DashboardsService handles the "Monitors/Dashboards" API resource. +type DashboardsService service + +// Preview draft panel. +// +// Execute a draft panel inline without saving a dashboard revision. +// +// API: POST /monit/dashboard/panel/preview (monit-dashboard-panel-read-preview). +func (s *DashboardsService) PanelReadPreview(ctx context.Context, req *DashboardPanelPreviewRequest) (*DashboardPanelPreviewResponse, *Response, error) { + out := new(DashboardPanelPreviewResponse) + resp, err := s.client.do(ctx, "/monit/dashboard/panel/preview", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Run dashboard panel. +// +// Execute one panel of a stored dashboard and return the datasource results. +// +// API: POST /monit/dashboard/panel/run (monit-dashboard-panel-read-run). +func (s *DashboardsService) PanelReadRun(ctx context.Context, req *DashboardPanelRunRequest) (*DashboardPanelRunResponse, *Response, error) { + out := new(DashboardPanelRunResponse) + resp, err := s.client.do(ctx, "/monit/dashboard/panel/run", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Resolve panel queries. +// +// Bind panel queries to datasources and substitute variables without executing them. +// +// API: POST /monit/dashboard/runtime/queries/resolve (monit-dashboard-query-read-resolve). +func (s *DashboardsService) QueryReadResolve(ctx context.Context, req *DashboardQueriesResolveRequest) (*DashboardQueriesResolveResponse, *Response, error) { + out := new(DashboardQueriesResolveResponse) + resp, err := s.client.do(ctx, "/monit/dashboard/runtime/queries/resolve", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Get dashboard detail. +// +// Fetch one dashboard with its full definition. +// +// API: POST /monit/dashboard/get (monit-dashboard-read-get). +func (s *DashboardsService) ReadGet(ctx context.Context, req *DashboardIDRequest) (*DashboardResource, *Response, error) { + out := new(DashboardResource) + resp, err := s.client.do(ctx, "/monit/dashboard/get", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// List dashboards. +// +// List the dashboards in one folder. +// +// API: POST /monit/dashboard/list (monit-dashboard-read-list). +func (s *DashboardsService) ReadList(ctx context.Context, req *DashboardListRequest) (*DashboardListOutput, *Response, error) { + out := new(DashboardListOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/list", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Get dashboard outline. +// +// Get a dashboard's structure without queries or definitions. +// +// API: POST /monit/dashboard/outline (monit-dashboard-read-outline). +func (s *DashboardsService) ReadOutline(ctx context.Context, req *DashboardOutlineRequest) (*DashboardOutline, *Response, error) { + out := new(DashboardOutline) + resp, err := s.client.do(ctx, "/monit/dashboard/outline", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Search dashboards. +// +// Search dashboards across every readable folder. +// +// API: POST /monit/dashboard/search (monit-dashboard-read-search). +func (s *DashboardsService) ReadSearch(ctx context.Context, req *DashboardSearchRequest) (*DashboardListOutput, *Response, error) { + out := new(DashboardListOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/search", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Get dashboard revision. +// +// Fetch one historical revision with its full definition. +// +// API: POST /monit/dashboard/revisions/get (monit-dashboard-revision-read-get). +func (s *DashboardsService) RevisionReadGet(ctx context.Context, req *DashboardRevisionGetRequest) (*DashboardRevisionResource, *Response, error) { + out := new(DashboardRevisionResource) + resp, err := s.client.do(ctx, "/monit/dashboard/revisions/get", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// List dashboard revisions. +// +// List a dashboard's revision history, newest first. +// +// API: POST /monit/dashboard/revisions/list (monit-dashboard-revision-read-list). +func (s *DashboardsService) RevisionReadList(ctx context.Context, req *DashboardIDRequest) (*DashboardRevisionListOutput, *Response, error) { + out := new(DashboardRevisionListOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/revisions/list", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// List trashed dashboards. +// +// List deleted dashboards still inside the 30-day retention window. +// +// API: POST /monit/dashboard/trash/list (monit-dashboard-trash-read-list). +func (s *DashboardsService) TrashReadList(ctx context.Context, req *DashboardTrashListRequest) (*DashboardTrashListOutput, *Response, error) { + out := new(DashboardTrashListOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/trash/list", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Preview draft variables. +// +// Resolve a draft variable set that is not stored in any dashboard. +// +// API: POST /monit/dashboard/runtime/variables/preview (monit-dashboard-variable-read-preview). +func (s *DashboardsService) VariableReadPreview(ctx context.Context, req *DashboardVariablesPreviewRequest) (*DashboardVariablesPreviewResponse, *Response, error) { + out := new(DashboardVariablesPreviewResponse) + resp, err := s.client.do(ctx, "/monit/dashboard/runtime/variables/preview", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Resolve dashboard variables. +// +// Resolve every variable of a stored dashboard for a time range. +// +// API: POST /monit/dashboard/runtime/variables/resolve (monit-dashboard-variable-read-resolve). +func (s *DashboardsService) VariableReadResolve(ctx context.Context, req *DashboardVariablesResolveRequest) (*DashboardVariablesResolveResponse, *Response, error) { + out := new(DashboardVariablesResolveResponse) + resp, err := s.client.do(ctx, "/monit/dashboard/runtime/variables/resolve", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Create dashboard. +// +// Create a dashboard from a full definition. +// +// API: POST /monit/dashboard/create (monit-dashboard-write-create). +func (s *DashboardsService) WriteCreate(ctx context.Context, req *DashboardCreateRequest) (*DashboardResource, *Response, error) { + out := new(DashboardResource) + resp, err := s.client.do(ctx, "/monit/dashboard/create", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Delete dashboard. +// +// Move a dashboard to the trash. +// +// API: POST /monit/dashboard/delete (monit-dashboard-write-delete). +func (s *DashboardsService) WriteDelete(ctx context.Context, req *DashboardDeleteRequest) (*DashboardDeleteOutput, *Response, error) { + out := new(DashboardDeleteOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/delete", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Move dashboard. +// +// Move a dashboard to another folder without changing its definition. +// +// API: POST /monit/dashboard/move (monit-dashboard-write-move). +func (s *DashboardsService) WriteMove(ctx context.Context, req *DashboardMoveRequest) (*DashboardUpdateOutput, *Response, error) { + out := new(DashboardUpdateOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/move", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Restore dashboard. +// +// Bring a trashed dashboard back, optionally into a different folder. +// +// API: POST /monit/dashboard/restore (monit-dashboard-write-restore). +func (s *DashboardsService) WriteRestore(ctx context.Context, req *DashboardRestoreRequest) (*DashboardResource, *Response, error) { + out := new(DashboardResource) + resp, err := s.client.do(ctx, "/monit/dashboard/restore", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Update dashboard. +// +// Replace a dashboard definition with compare-and-swap on the revision counter. +// +// API: POST /monit/dashboard/update (monit-dashboard-write-update). +func (s *DashboardsService) WriteUpdate(ctx context.Context, req *DashboardUpdateRequest) (*DashboardUpdateOutput, *Response, error) { + out := new(DashboardUpdateOutput) + resp, err := s.client.do(ctx, "/monit/dashboard/update", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} diff --git a/integrations.go b/integrations.go index c719853..288b5fb 100644 --- a/integrations.go +++ b/integrations.go @@ -21,6 +21,117 @@ func (s *IntegrationsService) DatasourceImPersonTryLink(ctx context.Context, req return out, resp, nil } +// Get integration detail. +// +// Return one integration, including its settings with sensitive values masked. +// +// API: POST /integration/info (integration-api-read-info). +func (s *IntegrationsService) IntegrationAPIReadInfo(ctx context.Context, req *GetIntegrationRequest) (*IntegrationDetail, *Response, error) { + out := new(IntegrationDetail) + resp, err := s.client.do(ctx, "/integration/info", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// List integrations. +// +// List the account's alert-source and change-source integrations. +// +// API: POST /integration/list (integration-api-read-list). +func (s *IntegrationsService) IntegrationAPIReadList(ctx context.Context, req *ListIntegrationsRequest) (*ListIntegrationsResponse, *Response, error) { + out := new(ListIntegrationsResponse) + resp, err := s.client.do(ctx, "/integration/list", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// List integration types. +// +// List the integration types the account can configure. +// +// API: POST /integration/type/list (integration-api-read-type-list). +func (s *IntegrationsService) IntegrationAPIReadTypeList(ctx context.Context, req *IntegrationTypeListRequest) (*ListIntegrationTypesResponse, *Response, error) { + out := new(ListIntegrationTypesResponse) + resp, err := s.client.do(ctx, "/integration/type/list", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Create integration. +// +// Create an integration for an alert source or change source. +// +// API: POST /integration/create (integration-api-write-create). +func (s *IntegrationsService) IntegrationAPIWriteCreate(ctx context.Context, req *CreateIntegrationRequest) (*CreateIntegrationResponse, *Response, error) { + out := new(CreateIntegrationResponse) + resp, err := s.client.do(ctx, "/integration/create", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Delete integration. +// +// Delete an integration that nothing else references. +// +// API: POST /integration/delete (integration-api-write-delete). +func (s *IntegrationsService) IntegrationAPIWriteDelete(ctx context.Context, req *IntegrationLifecycleRequest) (*Response, error) { + return s.client.do(ctx, "/integration/delete", req, nil) +} + +// Disable integration. +// +// Disable an integration without deleting its configuration. +// +// API: POST /integration/disable (integration-api-write-disable). +func (s *IntegrationsService) IntegrationAPIWriteDisable(ctx context.Context, req *IntegrationLifecycleRequest) (*Response, error) { + return s.client.do(ctx, "/integration/disable", req, nil) +} + +// Enable integration. +// +// Re-enable a disabled integration so it accepts events again. +// +// API: POST /integration/enable (integration-api-write-enable). +func (s *IntegrationsService) IntegrationAPIWriteEnable(ctx context.Context, req *IntegrationLifecycleRequest) (*Response, error) { + return s.client.do(ctx, "/integration/enable", req, nil) +} + +// Rotate integration key. +// +// Issue a new integration key and invalidate the previous one. +// +// API: POST /integration/key/rotate (integration-api-write-rotate-key). +func (s *IntegrationsService) IntegrationAPIWriteRotateKey(ctx context.Context, req *IntegrationLifecycleRequest) (*RotateIntegrationKeyResponse, *Response, error) { + out := new(RotateIntegrationKeyResponse) + resp, err := s.client.do(ctx, "/integration/key/rotate", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + +// Update integration. +// +// Update an integration's name, description, team, or settings. +// +// API: POST /integration/update (integration-api-write-update). +func (s *IntegrationsService) IntegrationAPIWriteUpdate(ctx context.Context, req *UpdateIntegrationRequest) (*IntegrationDetail, *Response, error) { + out := new(IntegrationDetail) + resp, err := s.client.do(ctx, "/integration/update", req, out) + if err != nil { + return nil, resp, err + } + return out, resp, nil +} + // Get webhook delivery detail. // // Retrieve the detailed payload and response for a specific webhook delivery attempt. diff --git a/knowledge.go b/knowledge.go index 79e069a..bb18931 100644 --- a/knowledge.go +++ b/knowledge.go @@ -23,7 +23,7 @@ func (s *KnowledgeService) FileReadGet(ctx context.Context, req *KnowledgeFileGe // List knowledge files. // -// List the files in a knowledge pack with metadata such as size and checksum. +// List knowledge files with metadata such as size and checksum. // // API: POST /safari/knowledge/file/list (knowledge-file-read-list). func (s *KnowledgeService) FileReadList(ctx context.Context, req *KnowledgeFileListRequest) (*KnowledgeFileListResponse, *Response, error) { @@ -37,7 +37,7 @@ func (s *KnowledgeService) FileReadList(ctx context.Context, req *KnowledgeFileL // Delete knowledge file. // -// Delete a file from a knowledge pack by its relative path. +// Delete a knowledge file by its relative path. // // API: POST /safari/knowledge/file/delete (knowledge-file-write-delete). func (s *KnowledgeService) FileWriteDelete(ctx context.Context, req *KnowledgeFileDeleteRequest) (*KnowledgeFileDeleteResponse, *Response, error) { @@ -51,7 +51,7 @@ func (s *KnowledgeService) FileWriteDelete(ctx context.Context, req *KnowledgeFi // Upload knowledge file. // -// Create or overwrite a file in a knowledge pack with base64-encoded content. +// Create or overwrite a knowledge file with base64-encoded content. // // API: POST /safari/knowledge/file/put (knowledge-file-write-put). func (s *KnowledgeService) FileWritePut(ctx context.Context, req *KnowledgeFilePutRequest) (*KnowledgeFilePutResponse, *Response, error) { @@ -63,9 +63,9 @@ func (s *KnowledgeService) FileWritePut(ctx context.Context, req *KnowledgeFileP return out, resp, nil } -// Get account knowledge pack. +// Get account knowledge. // -// Return the account-scope knowledge pack metadata and its file list. +// Return the metadata and file list of the account-scope knowledge. // // API: POST /safari/knowledge/get (knowledge-pack-read-get). func (s *KnowledgeService) PackReadGet(ctx context.Context) (*KnowledgeGetResponse, *Response, error) { @@ -77,9 +77,9 @@ func (s *KnowledgeService) PackReadGet(ctx context.Context) (*KnowledgeGetRespon return out, resp, nil } -// List knowledge packs. +// List knowledge. // -// List knowledge packs visible to the caller across account and team scopes. +// List the knowledge visible to the caller across account and team scopes. // // API: POST /safari/knowledge/pack/list (knowledge-pack-read-list). func (s *KnowledgeService) PackReadList(ctx context.Context, req *KnowledgePackListRequest) (*KnowledgePackListResponse, *Response, error) { @@ -91,9 +91,9 @@ func (s *KnowledgeService) PackReadList(ctx context.Context, req *KnowledgePackL return out, resp, nil } -// Delete knowledge pack. +// Delete knowledge. // -// Delete a knowledge pack and all of its files. +// Delete knowledge and all of its files. // // API: POST /safari/knowledge/pack/delete (knowledge-pack-write-delete). func (s *KnowledgeService) PackWriteDelete(ctx context.Context, req *KnowledgePackDeleteRequest) (*KnowledgePackDeleteResponse, *Response, error) { @@ -105,9 +105,9 @@ func (s *KnowledgeService) PackWriteDelete(ctx context.Context, req *KnowledgePa return out, resp, nil } -// Ensure knowledge pack. +// Ensure knowledge. // -// Idempotently create the knowledge pack at the given scope, or return the existing one. +// Idempotently create the knowledge at the given scope, or return the existing one. // // API: POST /safari/knowledge/pack/ensure (knowledge-pack-write-ensure). func (s *KnowledgeService) PackWriteEnsure(ctx context.Context, req *KnowledgePackEnsureRequest) (*KnowledgePackItem, *Response, error) { @@ -119,9 +119,9 @@ func (s *KnowledgeService) PackWriteEnsure(ctx context.Context, req *KnowledgePa return out, resp, nil } -// Update knowledge pack. +// Update knowledge. // -// Move a knowledge pack to a different account or team scope. +// Move knowledge to a different account or team scope. // // API: POST /safari/knowledge/pack/update (knowledge-pack-write-update). func (s *KnowledgeService) PackWriteUpdate(ctx context.Context, req *KnowledgePackUpdateRequest) (*KnowledgePackItem, *Response, error) { diff --git a/models_gen.go b/models_gen.go index 45bb5d3..8c34cf6 100644 --- a/models_gen.go +++ b/models_gen.go @@ -2058,15 +2058,15 @@ type CompleteWorkItemRequest struct { // ContextResolvedItem is generated from the Flashduty OpenAPI schema. type ContextResolvedItem struct { - // Resolved account-scoped pack id. + // Resolved account-scope knowledge ID. AccountPackID string `json:"account_pack_id" toon:"account_pack_id"` // Bound incident id, when war-room originated. IncidentID string `json:"incident_id" toon:"incident_id"` - // Unix timestamp in milliseconds when the packs were resolved. + // Unix timestamp in milliseconds when the knowledge was resolved. ResolvedAtMs TimestampMilli `json:"resolved_at_ms" toon:"resolved_at_ms"` - // Resolved team-scoped pack id. + // Resolved team-scope knowledge ID. TeamPackID string `json:"team_pack_id" toon:"team_pack_id"` - // Per-pack resolved version map. + // Resolved version map, one entry per knowledge. Versions map[string]int64 `json:"versions" toon:"versions"` } @@ -2239,6 +2239,28 @@ type CreateInhibitRuleRequest struct { TargetFilters [][]CreateInhibitRuleRequestTargetFiltersItemItem `json:"target_filters,omitempty" toon:"target_filters,omitempty"` } +// CreateIntegrationRequest is generated from the Flashduty OpenAPI schema. +type CreateIntegrationRequest struct { + // Free-form description, at most 499 characters. + Description string `json:"description,omitempty" toon:"description,omitempty"` + // Integration name. 2–49 characters. + Name string `json:"name,omitempty" toon:"name,omitempty"` + // Integration type. Must be one listed by `POST /integration/type/list` with `supports_api_create: true`. + PluginType string `json:"plugin_type" toon:"plugin_type"` + // Type-specific configuration; the accepted keys depend on `plugin_type`. + Settings map[string]any `json:"settings,omitempty" toon:"settings,omitempty"` + // Owning team ID. + TeamID int64 `json:"team_id,omitempty" toon:"team_id,omitempty"` +} + +// CreateIntegrationResponse is generated from the Flashduty OpenAPI schema. +type CreateIntegrationResponse struct { + // ID of the new integration. + IntegrationID int64 `json:"integration_id" toon:"integration_id"` + // Key used to authenticate inbound pushes to this integration. Returned here only; fetch a new one with `POST /integration/key/rotate`. + IntegrationKey string `json:"integration_key" toon:"integration_key"` +} + // CreateSilenceRuleRequest is generated from the Flashduty OpenAPI schema. type CreateSilenceRuleRequest struct { // Owning channel ID; obtain it from `POST /channel/list`. @@ -2733,6 +2755,217 @@ type DsVictoriaLogsConfig struct { TlsSkipVerify bool `json:"tls_skip_verify,omitempty" toon:"tls_skip_verify,omitempty"` } +// DashboardAbsoluteTimeRange is generated from the Flashduty OpenAPI schema. +type DashboardAbsoluteTimeRange struct { + // Unix timestamp in milliseconds. + FromMs int64 `json:"from_ms" toon:"from_ms"` + // Unix timestamp in milliseconds. + ToMs int64 `json:"to_ms" toon:"to_ms"` +} + +// DashboardActor is generated from the Flashduty OpenAPI schema. +type DashboardActor struct { + // Member ID. + ID uint64 `json:"id" toon:"id"` + // Member display name. + Name string `json:"name" toon:"name"` +} + +// DashboardBarViz is generated from the Flashduty OpenAPI schema. +type DashboardBarViz struct { + // Field supplying the category axis. + CategoryField string `json:"category_field" toon:"category_field"` + DataLink DashboardDataLink `json:"data_link,omitzero" toon:"data_link,omitempty"` + // Fixed decimal places; omit or send null to let the renderer decide. + Decimals *int64 `json:"decimals,omitempty" toon:"decimals,omitempty"` + // Visualization kind discriminator; always `bar`. + Kind string `json:"kind" toon:"kind"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` + Threshold DashboardThreshold `json:"threshold,omitzero" toon:"threshold,omitempty"` + // Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second. + Unit string `json:"unit,omitempty" toon:"unit,omitempty"` + // Fields supplying the bar values. + ValueFields []string `json:"value_fields" toon:"value_fields"` +} + +// DashboardCandidate is generated from the Flashduty OpenAPI schema. +type DashboardCandidate struct { + // Label shown in the picker. + Text string `json:"text" toon:"text"` + // Value substituted into templates. + Value string `json:"value" toon:"value"` +} + +// DashboardColumnOption is generated from the Flashduty OpenAPI schema. +type DashboardColumnOption struct { + DataLink DashboardDataLink `json:"data_link,omitzero" toon:"data_link,omitempty"` + // Header text replacing the raw field name. + DisplayName string `json:"display_name,omitempty" toon:"display_name,omitempty"` + // Hide the column; omit to keep it visible. + Hidden *bool `json:"hidden,omitempty" toon:"hidden,omitempty"` + Threshold DashboardThreshold `json:"threshold,omitzero" toon:"threshold,omitempty"` + // How the threshold is painted: `text` = colours the cell text; `background` = colours the cell background. + ThresholdDisplay string `json:"threshold_display,omitempty" toon:"threshold_display,omitempty"` + // Unit override for the column: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second. + Unit string `json:"unit,omitempty" toon:"unit,omitempty"` + // Column width in pixels, 80–1200. + WidthPx *int64 `json:"width_px,omitempty" toon:"width_px,omitempty"` +} + +// DashboardCreateRequest is generated from the Flashduty OpenAPI schema. +type DashboardCreateRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + Definition DashboardDefinition `json:"definition" toon:"definition"` + // Folder the dashboard is created in. Must be a folder the caller can write. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Wire schema version; only `dashboard.v1` is accepted. + SchemaVersion string `json:"schema_version" toon:"schema_version"` +} + +// DashboardCustomVariable is generated from the Flashduty OpenAPI schema. +type DashboardCustomVariable struct { + Default DashboardSelection `json:"default,omitzero" toon:"default,omitempty"` + // Variable kind discriminator; always `custom`, with candidates from a fixed list supplied inline. + Kind string `json:"kind" toon:"kind"` + // Optional display label; falls back to `name`. + Label string `json:"label,omitempty" toon:"label,omitempty"` + // Variable name used in `{{ }}` templates, at most 64 characters. + Name string `json:"name" toon:"name"` + // Candidate list, 1–1000 entries. Values must be non-empty, unique and must not be `$__all`. + Options []DashboardCandidate `json:"options" toon:"options"` + Selection DashboardSelectionConfig `json:"selection" toon:"selection"` +} + +// DashboardDataLink is generated from the Flashduty OpenAPI schema. +type DashboardDataLink struct { + // Target dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // When true the current time range is forwarded to the target. + PassTime bool `json:"pass_time" toon:"pass_time"` + // Optional tab, section or panel ID to focus in the target dashboard. + TargetID string `json:"target_id,omitempty" toon:"target_id,omitempty"` + // Maps target variable names to a source value such as a column or a source variable. + VariableMappings map[string]DashboardLinkMapping `json:"variable_mappings" toon:"variable_mappings"` +} + +// DashboardDatasourceRef is generated from the Flashduty OpenAPI schema. +type DashboardDatasourceRef struct { + // Datasource ID. Required when `kind` is `fixed`, forbidden when `kind` is `variable`. + DatasourceID uint64 `json:"datasource_id,omitempty" toon:"datasource_id,omitempty"` + // Datasource type identifier, e.g. `prometheus` or `victorialogs`. + DatasourceType string `json:"datasource_type" toon:"datasource_type"` + // `fixed` uses `datasource_id`; `variable` resolves `name` against a datasource variable. + Kind string `json:"kind" toon:"kind"` + // Datasource variable name. Required when `kind` is `variable`, forbidden when `kind` is `fixed`. + Name string `json:"name,omitempty" toon:"name,omitempty"` +} + +// DashboardDatasourceVariable is generated from the Flashduty OpenAPI schema. +type DashboardDatasourceVariable struct { + // Datasource type the candidates are drawn from. + DatasourceType string `json:"datasource_type" toon:"datasource_type"` + // Default datasource ID. Without a usable default the runtime picks the first candidate by name, then ID. + DefaultDatasourceID uint64 `json:"default_datasource_id,omitempty" toon:"default_datasource_id,omitempty"` + // Variable kind discriminator; always `datasource`, selecting a datasource. + Kind string `json:"kind" toon:"kind"` + // Optional display label; falls back to `name`. + Label string `json:"label,omitempty" toon:"label,omitempty"` + // Variable name used in `{{ }}` templates, at most 64 characters. + Name string `json:"name" toon:"name"` + // Wildcard patterns narrowing the candidates; empty means every datasource of the type. + NamePatterns []string `json:"name_patterns,omitempty" toon:"name_patterns,omitempty"` +} + +// DashboardDefinition is generated from the Flashduty OpenAPI schema. +type DashboardDefinition struct { + DefaultTimeRange DashboardRelativeTimeRange `json:"default_time_range" toon:"default_time_range"` + // Optional description, at most 1024 Unicode code points. + Description string `json:"description,omitempty" toon:"description,omitempty"` + // Auto-refresh cadence applied by the console: `off` disables auto-refresh; `30s` = every 30 seconds; `1m` = every minute; `5m` = every 5 minutes. + RefreshInterval string `json:"refresh_interval" toon:"refresh_interval"` + // Tabs, 1–10. Every tab title is unique and every tab or section ID must be a canonical UUIDv7 used only once across the definition. + Tabs []DashboardTab `json:"tabs" toon:"tabs"` + // Dashboard title, 1–189 Unicode code points after trimming. + Title string `json:"title" toon:"title"` + // Dashboard variables, at most 20. Names must be unique within the definition and match the variable-name pattern. + Variables []DashboardVariable `json:"variables" toon:"variables"` +} + +// DashboardDeleteOutput is generated from the Flashduty OpenAPI schema. +type DashboardDeleteOutput struct { + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Revision recorded for the deletion. + Revision uint64 `json:"revision" toon:"revision"` +} + +// DashboardDeleteRequest is generated from the Flashduty OpenAPI schema. +type DashboardDeleteRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision. + ExpectedRevision uint64 `json:"expected_revision" toon:"expected_revision"` +} + +// DashboardDraftContext is generated from the Flashduty OpenAPI schema. +type DashboardDraftContext struct { + // Required for `existing`, forbidden for `new`. + DashboardID string `json:"dashboard_id,omitempty" toon:"dashboard_id,omitempty"` + // Required for `new`, forbidden for `existing`. + FolderID uint64 `json:"folder_id,omitempty" toon:"folder_id,omitempty"` + // Draft context kind: `existing` = targets a stored dashboard (`dashboard_id` required); `new` = a folder that does not contain one yet (`folder_id` required). + Kind string `json:"kind" toon:"kind"` +} + +// DashboardFieldSort is generated from the Flashduty OpenAPI schema. +type DashboardFieldSort struct { + // Sort direction: `asc` = ascending; `desc` = descending. + Direction string `json:"direction" toon:"direction"` + // Field name to sort by. + Field string `json:"field" toon:"field"` +} + +// DashboardGaugeViz is generated from the Flashduty OpenAPI schema. +type DashboardGaugeViz struct { + // Fixed decimal places; omit or send null to let the renderer decide. + Decimals *int64 `json:"decimals,omitempty" toon:"decimals,omitempty"` + // Visualization kind discriminator; always `gauge`. + Kind string `json:"kind" toon:"kind"` + // Scale upper bound; must exceed `min` when both are set. + Max *float64 `json:"max,omitempty" toon:"max,omitempty"` + // Scale lower bound. + Min *float64 `json:"min,omitempty" toon:"min,omitempty"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` + // Reduction applied across the returned rows: `last_non_null` = most recent non-null value; `min` = minimum; `max` = maximum; `mean` = average; `sum` = sum. + Reducer string `json:"reducer" toon:"reducer"` + Threshold DashboardThreshold `json:"threshold,omitzero" toon:"threshold,omitempty"` + // Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second. + Unit string `json:"unit,omitempty" toon:"unit,omitempty"` + // Fields reduced to the gauge value. + ValueFields []string `json:"value_fields" toon:"value_fields"` +} + +// DashboardGridPosition is generated from the Flashduty OpenAPI schema. +type DashboardGridPosition struct { + // Height in grid rows, 1–100. + H int64 `json:"h" toon:"h"` + // Width in grid columns, 1–24. + W int64 `json:"w" toon:"w"` + // Zero-based column offset. + X int64 `json:"x" toon:"x"` + // Zero-based row offset. + Y int64 `json:"y" toon:"y"` +} + +// DashboardIDRequest is generated from the Flashduty OpenAPI schema. +type DashboardIDRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` +} + // DashboardInvestigationTarget is generated from the Flashduty OpenAPI schema. type DashboardInvestigationTarget struct { // Target dashboard ID; must be a canonical UUIDv7. @@ -2743,6 +2976,341 @@ type DashboardInvestigationTarget struct { Variables map[string]string `json:"variables" toon:"variables"` } +// DashboardLabelFilter is generated from the Flashduty OpenAPI schema. +type DashboardLabelFilter struct { + // Label name. + Label string `json:"label" toon:"label"` + // Matcher operator: `=` = equals; `!=` = not equals; `=~` = regex match; `!~` = regex does-not-match. + Op string `json:"op" toon:"op"` + // Matcher value; may reference other variables through `{{ }}`. + Value string `json:"value" toon:"value"` +} + +// DashboardLinkMapping is generated from the Flashduty OpenAPI schema. +type DashboardLinkMapping struct { + // Source column name; required when `source` is `row_column`. + Column string `json:"column,omitempty" toon:"column,omitempty"` + // Source dashboard variable name; required when `source` is `variable`. + Name string `json:"name,omitempty" toon:"name,omitempty"` + // Where the value comes from: `variable` = a dashboard variable; `row_column` = a table column (requires `column`); `category` = the bar category; `series` = the series name; `value` = the value itself. `category`, `series` and `value` are only valid for bar panels. + Source string `json:"source" toon:"source"` +} + +// DashboardListItem is generated from the Flashduty OpenAPI schema. +type DashboardListItem struct { + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Dashboard description; empty when unset. + Description string `json:"description" toon:"description"` + // Folder path from the root. + FolderBreadcrumb []string `json:"folder_breadcrumb" toon:"folder_breadcrumb"` + // Folder ID. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Current revision number. + Revision uint64 `json:"revision" toon:"revision"` + // Dashboard title. + Title string `json:"title" toon:"title"` + // Unix timestamp in seconds. + UpdatedAt Timestamp `json:"updated_at" toon:"updated_at"` + UpdatedBy DashboardActor `json:"updated_by" toon:"updated_by"` +} + +// DashboardListOutput is generated from the Flashduty OpenAPI schema. +type DashboardListOutput struct { + // Dashboards in this page. + Items []DashboardListItem `json:"items" toon:"items"` + // Total number of matching dashboards across all pages. + Total int64 `json:"total" toon:"total"` +} + +// DashboardListRequest is generated from the Flashduty OpenAPI schema. +type DashboardListRequest struct { + ListOptions + // Folder whose dashboards are listed. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Optional space-separated search words matched against title and description; at most 128 Unicode code points. + Query string `json:"query,omitempty" toon:"query,omitempty"` + // Sort keys; defaults to `updated_at` descending. + Sort []DashboardSort `json:"sort,omitempty" toon:"sort,omitempty"` +} + +// DashboardLogsVariableQuery is generated from the Flashduty OpenAPI schema. +type DashboardLogsVariableQuery struct { + // Named query arguments; defaults to an empty object. + Args map[string]string `json:"args" toon:"args"` + // Logs query expression; may reference other variables through `{{ }}`. + Expr string `json:"expr" toon:"expr"` + // Log field whose values become candidates. + Field string `json:"field" toon:"field"` + // Query kind discriminator; always `logs`, a logs query returning one field's values as candidates. + Kind string `json:"kind" toon:"kind"` +} + +// DashboardLogsViz is generated from the Flashduty OpenAPI schema. +type DashboardLogsViz struct { + // Log fields rendered for each row. + DisplayFields []string `json:"display_fields,omitempty" toon:"display_fields,omitempty"` + // Visualization kind discriminator; always `logs`. + Kind string `json:"kind" toon:"kind"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` +} + +// DashboardMoveRequest is generated from the Flashduty OpenAPI schema. +type DashboardMoveRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision. + ExpectedRevision uint64 `json:"expected_revision" toon:"expected_revision"` + // Destination folder ID. + FolderID uint64 `json:"folder_id" toon:"folder_id"` +} + +// DashboardOutline is generated from the Flashduty OpenAPI schema. +type DashboardOutline struct { + Dashboard DashboardOutlineInfo `json:"dashboard" toon:"dashboard"` + Folder DashboardOutlineFolder `json:"folder" toon:"folder"` + // Tabs, narrowed by `target_id` when supplied. + Tabs []DashboardOutlineTab `json:"tabs" toon:"tabs"` + // Variable summaries. + Variables []DashboardOutlineVariable `json:"variables" toon:"variables"` +} + +// DashboardOutlineFolder is generated from the Flashduty OpenAPI schema. +type DashboardOutlineFolder struct { + // Folder names from the root. + Breadcrumb []string `json:"breadcrumb" toon:"breadcrumb"` + // Folder ID. + FolderID uint64 `json:"folder_id" toon:"folder_id"` +} + +// DashboardOutlineInfo is generated from the Flashduty OpenAPI schema. +type DashboardOutlineInfo struct { + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Dashboard description; empty when unset. + Description string `json:"description" toon:"description"` + // Current revision number. + Revision uint64 `json:"revision" toon:"revision"` + // Dashboard title. + Title string `json:"title" toon:"title"` + // Unix timestamp in seconds. + UpdatedAt Timestamp `json:"updated_at" toon:"updated_at"` +} + +// DashboardOutlinePanel is generated from the Flashduty OpenAPI schema. +type DashboardOutlinePanel struct { + // Full path of titles from the dashboard down to the panel. + Breadcrumb []string `json:"breadcrumb" toon:"breadcrumb"` + // Datasource type the panel queries; empty when the panel has no datasource (text panels). + DatasourceType string `json:"datasource_type" toon:"datasource_type"` + // Panel description; empty when unset. + Description string `json:"description" toon:"description"` + // Panel ID. + ID string `json:"id" toon:"id"` + // Panel title. + Title string `json:"title" toon:"title"` + VizConfig DashboardOutlineVizConfig `json:"viz_config" toon:"viz_config"` +} + +// DashboardOutlineRequest is generated from the Flashduty OpenAPI schema. +type DashboardOutlineRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Optional tab, section or panel ID. When set, the response keeps only the branch that contains it, and an unknown ID returns `TargetNotFound`. + TargetID string `json:"target_id,omitempty" toon:"target_id,omitempty"` +} + +// DashboardOutlineSection is generated from the Flashduty OpenAPI schema. +type DashboardOutlineSection struct { + // Dashboard, tab and section titles. + Breadcrumb []string `json:"breadcrumb" toon:"breadcrumb"` + // Section description; empty when unset. + Description string `json:"description" toon:"description"` + // Section ID. + ID string `json:"id" toon:"id"` + // Panels in the section. + Panels []DashboardOutlinePanel `json:"panels" toon:"panels"` + // Section title. + Title string `json:"title" toon:"title"` +} + +// DashboardOutlineTab is generated from the Flashduty OpenAPI schema. +type DashboardOutlineTab struct { + // Dashboard title followed by the tab title. + Breadcrumb []string `json:"breadcrumb" toon:"breadcrumb"` + // Tab description; empty when unset. + Description string `json:"description" toon:"description"` + // Tab ID. + ID string `json:"id" toon:"id"` + // Sections on the tab. + Sections []DashboardOutlineSection `json:"sections" toon:"sections"` + // Tab title. + Title string `json:"title" toon:"title"` + // Panels placed directly on the tab. + TopPanels []DashboardOutlinePanel `json:"top_panels" toon:"top_panels"` +} + +// DashboardOutlineVariable is generated from the Flashduty OpenAPI schema. +type DashboardOutlineVariable struct { + // Variable kind: `datasource` = selects a datasource; `custom` = fixed inline list; `query` = resolved by running a query. + Kind string `json:"kind" toon:"kind"` + // Display label; empty when unset. + Label string `json:"label" toon:"label"` + // Variable name. + Name string `json:"name" toon:"name"` + Selection DashboardSelectionConfig `json:"selection" toon:"selection"` +} + +// DashboardOutlineVizConfig is generated from the Flashduty OpenAPI schema. +type DashboardOutlineVizConfig struct { + // Visualization kind: `time_series` = time series; `table` = table; `stat` = single value; `bar` = bar chart; `gauge` = gauge; `logs` = log stream; `text` = Markdown text. + Kind string `json:"kind" toon:"kind"` +} + +// DashboardPanel is generated from the Flashduty OpenAPI schema. +type DashboardPanel struct { + DatasourceRef DashboardDatasourceRef `json:"datasource_ref,omitzero" toon:"datasource_ref,omitempty"` + // Optional panel description. + Description string `json:"description,omitempty" toon:"description,omitempty"` + Grid DashboardGridPosition `json:"grid" toon:"grid"` + // Canonical UUIDv7 identifying the panel; unique across the definition. + ID string `json:"id" toon:"id"` + // Queries in the panel. `time_series` accepts 1–26, `text` accepts none, every other kind accepts exactly one. + Queries []DashboardPanelQuery `json:"queries" toon:"queries"` + // Panel title. + Title string `json:"title" toon:"title"` + VizConfig DashboardVizConfig `json:"viz_config" toon:"viz_config"` +} + +// DashboardPanelPreviewRequest is generated from the Flashduty OpenAPI schema. +type DashboardPanelPreviewRequest struct { + Context DashboardDraftContext `json:"context" toon:"context"` + // Downsampling target, 2–5000 points. + MaxDataPoints *int64 `json:"max_data_points,omitempty" toon:"max_data_points,omitempty"` + Panel DashboardPanel `json:"panel" toon:"panel"` + // Selections keyed by variable name. + Selections map[string]DashboardSelection `json:"selections" toon:"selections"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Draft variables the panel may reference. + Variables []DashboardVariable `json:"variables" toon:"variables"` +} + +// DashboardPanelPreviewResponse is generated from the Flashduty OpenAPI schema. +type DashboardPanelPreviewResponse struct { + Budget DashboardPanelRunBudget `json:"budget" toon:"budget"` + Display DashboardVizConfig `json:"display" toon:"display"` + // Panel ID. + PanelID string `json:"panel_id" toon:"panel_id"` + // One entry per query in the panel. + Refs []DashboardPanelRunRef `json:"refs" toon:"refs"` + // Aggregate state of the run: `success` = all queries succeeded; `partial` = some succeeded; `incompatible` = at least one query is incompatible with its datasource; `cancelled` = the run was cancelled; `error` = all queries failed. + RunState string `json:"run_state" toon:"run_state"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Selections that resolved successfully. + Variables map[string]DashboardSelection `json:"variables" toon:"variables"` +} + +// DashboardPanelQuery is generated from the Flashduty OpenAPI schema. +type DashboardPanelQuery struct { + // Optional legend label; supports the same variable templates as `expr`. + LegendAlias string `json:"legend_alias,omitempty" toon:"legend_alias,omitempty"` + Query DashboardQuery `json:"query" toon:"query"` + // Single uppercase letter (A–Z) naming the query inside its panel. + RefID string `json:"ref_id" toon:"ref_id"` +} + +// DashboardPanelRunBudget is generated from the Flashduty OpenAPI schema. +type DashboardPanelRunBudget struct { + // Number of queries launched. + ExecutionCount int64 `json:"execution_count" toon:"execution_count"` + // Concurrency cap applied to the panel's queries. + MaxConcurrency int64 `json:"max_concurrency" toon:"max_concurrency"` +} + +// DashboardPanelRunRef is generated from the Flashduty OpenAPI schema. +type DashboardPanelRunRef struct { + // Request ID of the underlying datasource execution; use it when tracing a single query. + ChildRequestID string `json:"child_request_id" toon:"child_request_id"` + Error DashboardRuntimeError `json:"error" toon:"error"` + // Datasource-specific execution payload, passed through unmodified. + Execution map[string]any `json:"execution" toon:"execution"` + // Panel-local query reference. + RefID string `json:"ref_id" toon:"ref_id"` + // Per-query execution state: `success` = the query executed; `error` = the query failed; `incompatible` = the datasource accepted the call but the query mode or field selection does not fit the datasource type. + State string `json:"state" toon:"state"` +} + +// DashboardPanelRunRequest is generated from the Flashduty OpenAPI schema. +type DashboardPanelRunRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Downsampling target, 2–5000 points; omit or send null for the server default of 100. + MaxDataPoints *int64 `json:"max_data_points,omitempty" toon:"max_data_points,omitempty"` + // Panel to execute. + PanelID string `json:"panel_id" toon:"panel_id"` + // Revision guard; when set it must equal the current revision. + Revision uint64 `json:"revision,omitempty" toon:"revision,omitempty"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Selections keyed by variable name, at most 20 entries. + Variables map[string]DashboardSelection `json:"variables" toon:"variables"` +} + +// DashboardPanelRunResponse is generated from the Flashduty OpenAPI schema. +type DashboardPanelRunResponse struct { + Budget DashboardPanelRunBudget `json:"budget" toon:"budget"` + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + Display DashboardVizConfig `json:"display" toon:"display"` + // Panel ID. + PanelID string `json:"panel_id" toon:"panel_id"` + // One entry per query in the panel. + Refs []DashboardPanelRunRef `json:"refs" toon:"refs"` + // Revision the run executed against. + Revision uint64 `json:"revision" toon:"revision"` + // Aggregate state of the run: `success` = all queries succeeded; `partial` = some succeeded; `incompatible` = at least one query is incompatible with its datasource; `cancelled` = the run was cancelled; `error` = all queries failed. + RunState string `json:"run_state" toon:"run_state"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Selections that resolved successfully. + Variables map[string]DashboardSelection `json:"variables" toon:"variables"` +} + +// DashboardPrometheusVariableQuery is generated from the Flashduty OpenAPI schema. +type DashboardPrometheusVariableQuery struct { + // Query kind discriminator; always `prometheus`, a label-values query against Prometheus. + Kind string `json:"kind" toon:"kind"` + // Label whose values become candidates. + Label string `json:"label" toon:"label"` + // Optional matchers narrowing the series before label values are read. + LabelFilters []DashboardLabelFilter `json:"label_filters,omitempty" toon:"label_filters,omitempty"` + // Optional metric used to restrict the series considered. + Metric string `json:"metric,omitempty" toon:"metric,omitempty"` +} + +// DashboardQueriesResolveRequest is generated from the Flashduty OpenAPI schema. +type DashboardQueriesResolveRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Panels to resolve, 1–100 unique IDs. A panel that does not exist yields an `error` arm rather than failing the call. + PanelIDs []string `json:"panel_ids" toon:"panel_ids"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Selections keyed by variable name, at most 20 entries. + Variables map[string]DashboardSelection `json:"variables" toon:"variables"` +} + +// DashboardQueriesResolveResponse is generated from the Flashduty OpenAPI schema. +type DashboardQueriesResolveResponse struct { + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Per-panel results. + Panels []DashboardResolvedPanelQueries `json:"panels" toon:"panels"` + // Revision the resolution ran against. + Revision uint64 `json:"revision" toon:"revision"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Selections that resolved successfully. + Variables map[string]DashboardSelection `json:"variables" toon:"variables"` +} + // DashboardQuery is generated from the Flashduty OpenAPI schema. type DashboardQuery struct { // Named query arguments; defaults to an empty object. Values are passed through verbatim and must not contain `{{ }}` templates. @@ -2755,6 +3323,477 @@ type DashboardQuery struct { Mode string `json:"mode" toon:"mode"` } +// DashboardQueryVariable is generated from the Flashduty OpenAPI schema. +type DashboardQueryVariable struct { + DatasourceRef DashboardDatasourceRef `json:"datasource_ref" toon:"datasource_ref"` + Default DashboardSelection `json:"default,omitzero" toon:"default,omitempty"` + // Variable kind discriminator; always `query`, with candidates resolved by running a query against a datasource. + Kind string `json:"kind" toon:"kind"` + // Optional display label; falls back to `name`. + Label string `json:"label,omitempty" toon:"label,omitempty"` + // Variable name used in `{{ }}` templates, at most 64 characters. + Name string `json:"name" toon:"name"` + // When the candidates are recomputed: `on_dashboard_load` = once when the dashboard loads; `on_time_range_change` = every time the time range changes. + Refresh string `json:"refresh" toon:"refresh"` + Selection DashboardSelectionConfig `json:"selection" toon:"selection"` + VariableQuery DashboardVariableQuery `json:"variable_query" toon:"variable_query"` +} + +// DashboardRelativeTimeRange is generated from the Flashduty OpenAPI schema. +type DashboardRelativeTimeRange struct { + // Start offset relative to `to`: `now-15m` = 15 minutes ago; `now-30m` = 30 minutes ago; `now-1h` = 1 hour ago; `now-3h` = 3 hours ago; `now-6h` = 6 hours ago; `now-12h` = 12 hours ago; `now-24h` = 24 hours ago; `now-7d` = 7 days ago. + From string `json:"from" toon:"from"` + // End of the window; only `now` is accepted. + To string `json:"to" toon:"to"` +} + +// DashboardResolvedPanelQueries is generated from the Flashduty OpenAPI schema. +type DashboardResolvedPanelQueries struct { + Error DashboardRuntimeError `json:"error" toon:"error"` + // Panel ID. + PanelID string `json:"panel_id" toon:"panel_id"` + // Successfully resolved queries. + Queries []DashboardResolvedQuery `json:"queries" toon:"queries"` + // Aggregate state of the panel's queries: `success` = every query resolved; `partial` = some resolved; `error` = none resolved. + State string `json:"state" toon:"state"` +} + +// DashboardResolvedQuery is generated from the Flashduty OpenAPI schema. +type DashboardResolvedQuery struct { + // Query arguments; empty object when none. + Args map[string]string `json:"args" toon:"args"` + Datasource DashboardRuntimeDatasource `json:"datasource" toon:"datasource"` + // Expression with variable templates substituted. + Expr string `json:"expr" toon:"expr"` + // Minimum step in seconds; null when unset. + MinStepSeconds int64 `json:"min_step_seconds" toon:"min_step_seconds"` + // Evaluation mode: `range` = a stepped time series; `instant` = a single point in time; `window` = raw rows inside a bounded time window. + Mode string `json:"mode" toon:"mode"` + // Panel-local query reference. + RefID string `json:"ref_id" toon:"ref_id"` +} + +// DashboardResolvedVariable is generated from the Flashduty OpenAPI schema. +type DashboardResolvedVariable struct { + // Resolved candidates, at most 1000. + Candidates []DashboardCandidate `json:"candidates" toon:"candidates"` + Datasource DashboardRuntimeDatasource `json:"datasource" toon:"datasource"` + Error DashboardRuntimeError `json:"error" toon:"error"` + // Variable kind: `datasource` = selects a datasource; `custom` = fixed inline list; `query` = resolved by running a query. + Kind string `json:"kind" toon:"kind"` + // Variable name. + Name string `json:"name" toon:"name"` + Selection DashboardSelection `json:"selection" toon:"selection"` +} + +// DashboardResource is generated from the Flashduty OpenAPI schema. +type DashboardResource struct { + // Unix timestamp in seconds. + CreatedAt Timestamp `json:"created_at" toon:"created_at"` + CreatedBy DashboardActor `json:"created_by" toon:"created_by"` + // Canonical UUIDv7 assigned by the caller at creation time. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + Definition DashboardDefinition `json:"definition" toon:"definition"` + // Folder names from the root down to `folder_id`. + FolderBreadcrumb []string `json:"folder_breadcrumb" toon:"folder_breadcrumb"` + // ID of the dashboard's folder. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Current revision number. + Revision uint64 `json:"revision" toon:"revision"` + // Wire schema version of `definition`; only `dashboard.v1` is accepted. + SchemaVersion string `json:"schema_version" toon:"schema_version"` + // Unix timestamp in seconds. + UpdatedAt Timestamp `json:"updated_at" toon:"updated_at"` + UpdatedBy DashboardActor `json:"updated_by" toon:"updated_by"` +} + +// DashboardRestoreRequest is generated from the Flashduty OpenAPI schema. +type DashboardRestoreRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision. + ExpectedRevision uint64 `json:"expected_revision" toon:"expected_revision"` + // Destination folder. Omit to restore to the original folder; when the original folder is no longer writable the call fails with `RestoreFolderRequired` and you must pass one. + FolderID *uint64 `json:"folder_id,omitempty" toon:"folder_id,omitempty"` +} + +// DashboardRevisionGetRequest is generated from the Flashduty OpenAPI schema. +type DashboardRevisionGetRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Revision number to fetch. + Revision uint64 `json:"revision" toon:"revision"` +} + +// DashboardRevisionItem is generated from the Flashduty OpenAPI schema. +type DashboardRevisionItem struct { + Actor DashboardActor `json:"actor" toon:"actor"` + // Unix timestamp in seconds. + CreatedAt Timestamp `json:"created_at" toon:"created_at"` + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Folder the dashboard sat in at that revision. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Optional commit message; at most 1024 Unicode code points. + Message string `json:"message" toon:"message"` + // Revision number. + Revision uint64 `json:"revision" toon:"revision"` +} + +// DashboardRevisionListOutput is generated from the Flashduty OpenAPI schema. +type DashboardRevisionListOutput struct { + // Revisions, at most 20. + Items []DashboardRevisionItem `json:"items" toon:"items"` +} + +// DashboardRevisionResource is generated from the Flashduty OpenAPI schema. +type DashboardRevisionResource struct { + Actor DashboardActor `json:"actor" toon:"actor"` + // Unix timestamp in seconds. + CreatedAt Timestamp `json:"created_at" toon:"created_at"` + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + Definition DashboardDefinition `json:"definition" toon:"definition"` + // Folder the dashboard sat in at that revision. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Optional commit message. + Message string `json:"message" toon:"message"` + // Revision number. + Revision uint64 `json:"revision" toon:"revision"` + // Wire schema version of `definition`; only `dashboard.v1` is accepted. + SchemaVersion string `json:"schema_version" toon:"schema_version"` +} + +// DashboardRuntimeDatasource is generated from the Flashduty OpenAPI schema. +type DashboardRuntimeDatasource struct { + // Datasource ID. + ID uint64 `json:"id" toon:"id"` + // Datasource name. + Name string `json:"name" toon:"name"` + // Datasource type identifier. + Type string `json:"type" toon:"type"` +} + +// DashboardRuntimeError is generated from the Flashduty OpenAPI schema. +type DashboardRuntimeError struct { + // Human-readable detail for the failure. + Message string `json:"message" toon:"message"` + // Machine-readable failure reason. Observed values include `invalid_request`, `variable_invalid`, `panel_missing`, `field_missing`, `datasource_permission_denied`, `timeout`, `panel_deadline`, `panel_canceled`, `canceled`, `overloaded`, `source_too_large`, `edge_unavailable`, `edge_upgrade_required`, `edge_version_unknown`, `mixed_edge_versions` and `internal`. + Reason string `json:"reason" toon:"reason"` +} + +// DashboardSqlVariableQuery is generated from the Flashduty OpenAPI schema. +type DashboardSqlVariableQuery struct { + // Named query arguments; defaults to an empty object. + Args map[string]string `json:"args" toon:"args"` + // SQL statement; may reference other variables through `{{ }}`. + Expr string `json:"expr" toon:"expr"` + // Query kind discriminator; always `sql`, a SQL query returning one column of candidates. + Kind string `json:"kind" toon:"kind"` + // Column used as the candidate label; defaults to the value column. + TextField string `json:"text_field,omitempty" toon:"text_field,omitempty"` + // Column used as the candidate value. + ValueField string `json:"value_field" toon:"value_field"` +} + +// DashboardSearchRequest is generated from the Flashduty OpenAPI schema. +type DashboardSearchRequest struct { + ListOptions + // Space-separated search words; at least one word and at most 128 Unicode code points. + Query string `json:"query" toon:"query"` + // Sort keys; defaults to `updated_at` descending. + Sort []DashboardSort `json:"sort,omitempty" toon:"sort,omitempty"` +} + +// DashboardSection is generated from the Flashduty OpenAPI schema. +type DashboardSection struct { + // Whether the section renders collapsed by default. + Collapsed bool `json:"collapsed" toon:"collapsed"` + // Optional section description. + Description string `json:"description,omitempty" toon:"description,omitempty"` + // Canonical UUIDv7 identifying the section; unique across the definition. + ID string `json:"id" toon:"id"` + // Panels in the section, at most 30. + Panels []DashboardPanel `json:"panels" toon:"panels"` + // Section title. + Title string `json:"title" toon:"title"` +} + +// DashboardSelection is generated from the Flashduty OpenAPI schema. +type DashboardSelection struct { + // `values` selects the listed entries, `all` selects everything (only allowed when `include_all` is true). + Kind string `json:"kind" toon:"kind"` + // Selected values, unique and never `$__all`. Must be empty when `kind` is `all`. + Values []string `json:"values,omitempty" toon:"values,omitempty"` +} + +// DashboardSelectionConfig is generated from the Flashduty OpenAPI schema. +type DashboardSelectionConfig struct { + // When true the variable also offers an `all` selection. + IncludeAll bool `json:"include_all" toon:"include_all"` + // Selection cardinality: `single` makes the resolved selection hold exactly one value; `multi` allows multiple values. + Mode string `json:"mode" toon:"mode"` +} + +// DashboardSort is generated from the Flashduty OpenAPI schema. +type DashboardSort struct { + // Sort direction: `asc` = ascending; `desc` = descending. + Direction string `json:"direction" toon:"direction"` + // `title` is available everywhere; `updated_at` only on list/search, `deleted_at` only on the trash listing. + Field string `json:"field" toon:"field"` +} + +// DashboardStatViz is generated from the Flashduty OpenAPI schema. +type DashboardStatViz struct { + // Fixed decimal places; omit or send null to let the renderer decide. + Decimals *int64 `json:"decimals,omitempty" toon:"decimals,omitempty"` + // Visualization kind discriminator; always `stat`. + Kind string `json:"kind" toon:"kind"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` + // Reduction applied across the returned rows: `last_non_null` = most recent non-null value; `min` = minimum; `max` = maximum; `mean` = average; `sum` = sum. + Reducer string `json:"reducer" toon:"reducer"` + Threshold DashboardThreshold `json:"threshold,omitzero" toon:"threshold,omitempty"` + // Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second. + Unit string `json:"unit,omitempty" toon:"unit,omitempty"` + // Fields reduced to the displayed values. + ValueFields []string `json:"value_fields" toon:"value_fields"` +} + +// DashboardTab is generated from the Flashduty OpenAPI schema. +type DashboardTab struct { + // Optional tab description. + Description string `json:"description,omitempty" toon:"description,omitempty"` + // Canonical UUIDv7 identifying the tab; unique across the definition. + ID string `json:"id" toon:"id"` + // Sections on the tab, at most 10. + Sections []DashboardSection `json:"sections" toon:"sections"` + // Tab title, 1–189 Unicode code points. Unique among tabs. + Title string `json:"title" toon:"title"` + // Panels placed directly on the tab, at most 30. + TopPanels []DashboardPanel `json:"top_panels" toon:"top_panels"` +} + +// DashboardTableViz is generated from the Flashduty OpenAPI schema. +type DashboardTableViz struct { + // Per-column display overrides keyed by field name, at most 100 entries. + ColumnOptions map[string]DashboardColumnOption `json:"column_options,omitempty" toon:"column_options,omitempty"` + // Visualization kind discriminator; always `table`. + Kind string `json:"kind" toon:"kind"` + // Drill-down links rendered as table columns. Together with per-column links a table allows at most 5. + LinkColumns []DashboardDataLink `json:"link_columns,omitempty" toon:"link_columns,omitempty"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` + // Initial sort keys; fields must be unique. + Sort []DashboardFieldSort `json:"sort,omitempty" toon:"sort,omitempty"` +} + +// DashboardTextViz is generated from the Flashduty OpenAPI schema. +type DashboardTextViz struct { + // Visualization kind discriminator; always `text`. + Kind string `json:"kind" toon:"kind"` + // Markdown body, at most 64 KiB. Only a restricted node set (headings, lists, tables, links, code) survives validation. + Markdown string `json:"markdown" toon:"markdown"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` +} + +// DashboardThreshold is generated from the Flashduty OpenAPI schema. +type DashboardThreshold struct { + // Critical bound; must be finite. + Critical *float64 `json:"critical,omitempty" toon:"critical,omitempty"` + // Direction of the comparison: `higher_is_worse` = values at or above the bound breach it; `lower_is_worse` = values at or below the bound breach it. + Mode string `json:"mode" toon:"mode"` + // Warning bound; must be finite. + Warning *float64 `json:"warning,omitempty" toon:"warning,omitempty"` +} + +// DashboardTimeSeriesViz is generated from the Flashduty OpenAPI schema. +type DashboardTimeSeriesViz struct { + // Fixed decimal places; omit or send null to let the renderer decide. + Decimals *int64 `json:"decimals,omitempty" toon:"decimals,omitempty"` + // Visualization kind discriminator; always `time_series`. + Kind string `json:"kind" toon:"kind"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` + Threshold DashboardThreshold `json:"threshold,omitzero" toon:"threshold,omitempty"` + // Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second. + Unit string `json:"unit,omitempty" toon:"unit,omitempty"` +} + +// DashboardTrashItem is generated from the Flashduty OpenAPI schema. +type DashboardTrashItem struct { + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Unix timestamp in seconds. + DeletedAt Timestamp `json:"deleted_at" toon:"deleted_at"` + DeletedBy DashboardActor `json:"deleted_by" toon:"deleted_by"` + // Dashboard description; empty when unset. + Description string `json:"description" toon:"description"` + // Folder path from the root. + FolderBreadcrumb []string `json:"folder_breadcrumb" toon:"folder_breadcrumb"` + // Folder the dashboard sat in when deleted. + FolderID uint64 `json:"folder_id" toon:"folder_id"` + // Revision the dashboard had when deleted. + Revision uint64 `json:"revision" toon:"revision"` + // Dashboard title. + Title string `json:"title" toon:"title"` +} + +// DashboardTrashListOutput is generated from the Flashduty OpenAPI schema. +type DashboardTrashListOutput struct { + // Deleted dashboards in this page. + Items []DashboardTrashItem `json:"items" toon:"items"` + // Total number of deleted dashboards. + Total int64 `json:"total" toon:"total"` +} + +// DashboardTrashListRequest is generated from the Flashduty OpenAPI schema. +type DashboardTrashListRequest struct { + ListOptions + // Sort keys; only `title` and `deleted_at` are accepted here. + Sort []DashboardSort `json:"sort,omitempty" toon:"sort,omitempty"` +} + +// DashboardUpdateOutput is generated from the Flashduty OpenAPI schema. +type DashboardUpdateOutput struct { + // Whether the stored dashboard actually changed. + Changed bool `json:"changed" toon:"changed"` + Resource DashboardResource `json:"resource" toon:"resource"` +} + +// DashboardUpdateRequest is generated from the Flashduty OpenAPI schema. +type DashboardUpdateRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + Definition DashboardDefinition `json:"definition" toon:"definition"` + // Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision. + ExpectedRevision uint64 `json:"expected_revision" toon:"expected_revision"` + // Optional revision message, at most 1024 Unicode code points. Stored with the revision and never returned by this endpoint. + Message string `json:"message,omitempty" toon:"message,omitempty"` + // Wire schema version; only `dashboard.v1` is accepted. + SchemaVersion string `json:"schema_version" toon:"schema_version"` +} + +// DashboardVariable is generated from the Flashduty OpenAPI schema. +type DashboardVariable struct { + DatasourceRef DashboardDatasourceRef `json:"datasource_ref,omitzero" toon:"datasource_ref,omitempty"` + // Datasource type the candidates are drawn from. + DatasourceType string `json:"datasource_type,omitempty" toon:"datasource_type,omitempty"` + Default DashboardSelection `json:"default,omitzero" toon:"default,omitempty"` + // Default datasource ID. Without a usable default the runtime picks the first candidate by name, then ID. + DefaultDatasourceID uint64 `json:"default_datasource_id,omitempty" toon:"default_datasource_id,omitempty"` + // Variable kind discriminator; always `query`, with candidates resolved by running a query against a datasource. + Kind string `json:"kind" toon:"kind"` + // Optional display label; falls back to `name`. + Label string `json:"label,omitempty" toon:"label,omitempty"` + // Variable name used in `{{ }}` templates, at most 64 characters. + Name string `json:"name" toon:"name"` + // Wildcard patterns narrowing the candidates; empty means every datasource of the type. + NamePatterns []string `json:"name_patterns,omitempty" toon:"name_patterns,omitempty"` + // Candidate list, 1–1000 entries. Values must be non-empty, unique and must not be `$__all`. + Options []DashboardCandidate `json:"options,omitempty" toon:"options,omitempty"` + // When the candidates are recomputed: `on_dashboard_load` = once when the dashboard loads; `on_time_range_change` = every time the time range changes. + Refresh string `json:"refresh,omitempty" toon:"refresh,omitempty"` + Selection DashboardSelectionConfig `json:"selection,omitzero" toon:"selection,omitempty"` + VariableQuery DashboardVariableQuery `json:"variable_query,omitempty" toon:"variable_query,omitempty"` +} + +// DashboardVariableQuery is generated from the Flashduty OpenAPI schema. +type DashboardVariableQuery struct { + // Named query arguments; defaults to an empty object. + Args map[string]string `json:"args,omitempty" toon:"args,omitempty"` + // Logs query expression; may reference other variables through `{{ }}`. + Expr string `json:"expr,omitempty" toon:"expr,omitempty"` + // Log field whose values become candidates. + Field string `json:"field,omitempty" toon:"field,omitempty"` + // Query kind discriminator; always `logs`, a logs query returning one field's values as candidates. + Kind string `json:"kind" toon:"kind"` + // Label whose values become candidates. + Label string `json:"label,omitempty" toon:"label,omitempty"` + // Optional matchers narrowing the series before label values are read. + LabelFilters []DashboardLabelFilter `json:"label_filters,omitempty" toon:"label_filters,omitempty"` + // Optional metric used to restrict the series considered. + Metric string `json:"metric,omitempty" toon:"metric,omitempty"` + // Column used as the candidate label; defaults to the value column. + TextField string `json:"text_field,omitempty" toon:"text_field,omitempty"` + // Column used as the candidate value. + ValueField string `json:"value_field,omitempty" toon:"value_field,omitempty"` +} + +// DashboardVariablesPreviewRequest is generated from the Flashduty OpenAPI schema. +type DashboardVariablesPreviewRequest struct { + Context DashboardDraftContext `json:"context" toon:"context"` + // Selections keyed by variable name, at most 20 entries. + Selections map[string]DashboardSelection `json:"selections" toon:"selections"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Draft variables, at most 20. + Variables []DashboardVariable `json:"variables" toon:"variables"` +} + +// DashboardVariablesPreviewResponse is generated from the Flashduty OpenAPI schema. +type DashboardVariablesPreviewResponse struct { + // Effective selections keyed by variable name. + Selections map[string]DashboardSelection `json:"selections" toon:"selections"` + // Resolved variables. + Variables []DashboardResolvedVariable `json:"variables" toon:"variables"` +} + +// DashboardVariablesResolveRequest is generated from the Flashduty OpenAPI schema. +type DashboardVariablesResolveRequest struct { + // Canonical UUIDv7 of the dashboard. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + Time DashboardAbsoluteTimeRange `json:"time" toon:"time"` + // Selections already made, keyed by variable name, at most 20 entries. Variables omitted here fall back to their stored defaults. + Variables map[string]DashboardSelection `json:"variables" toon:"variables"` +} + +// DashboardVariablesResolveResponse is generated from the Flashduty OpenAPI schema. +type DashboardVariablesResolveResponse struct { + // Dashboard ID. + DashboardID string `json:"dashboard_id" toon:"dashboard_id"` + // Revision the resolution ran against. + Revision uint64 `json:"revision" toon:"revision"` + // Effective selections keyed by variable name; only variables that resolved successfully appear. + Selections map[string]DashboardSelection `json:"selections" toon:"selections"` + // Resolved variables, in definition order. + Variables []DashboardResolvedVariable `json:"variables" toon:"variables"` +} + +// DashboardVizConfig is generated from the Flashduty OpenAPI schema. +type DashboardVizConfig struct { + // Field supplying the category axis. + CategoryField string `json:"category_field,omitempty" toon:"category_field,omitempty"` + // Per-column display overrides keyed by field name, at most 100 entries. + ColumnOptions map[string]DashboardColumnOption `json:"column_options,omitempty" toon:"column_options,omitempty"` + DataLink DashboardDataLink `json:"data_link,omitzero" toon:"data_link,omitempty"` + // Fixed decimal places; omit or send null to let the renderer decide. + Decimals *int64 `json:"decimals,omitempty" toon:"decimals,omitempty"` + // Log fields rendered for each row. + DisplayFields []string `json:"display_fields,omitempty" toon:"display_fields,omitempty"` + // Visualization kind discriminator; always `text`. + Kind string `json:"kind" toon:"kind"` + // Drill-down links rendered as table columns. Together with per-column links a table allows at most 5. + LinkColumns []DashboardDataLink `json:"link_columns,omitempty" toon:"link_columns,omitempty"` + // Markdown body, at most 64 KiB. Only a restricted node set (headings, lists, tables, links, code) survives validation. + Markdown string `json:"markdown,omitempty" toon:"markdown,omitempty"` + // Scale upper bound; must exceed `min` when both are set. + Max *float64 `json:"max,omitempty" toon:"max,omitempty"` + // Scale lower bound. + Min *float64 `json:"min,omitempty" toon:"min,omitempty"` + // Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`. + Options map[string]any `json:"options" toon:"options"` + // Reduction applied across the returned rows: `last_non_null` = most recent non-null value; `min` = minimum; `max` = maximum; `mean` = average; `sum` = sum. + Reducer string `json:"reducer,omitempty" toon:"reducer,omitempty"` + // Initial sort keys; fields must be unique. + Sort []DashboardFieldSort `json:"sort,omitempty" toon:"sort,omitempty"` + Threshold DashboardThreshold `json:"threshold,omitzero" toon:"threshold,omitempty"` + // Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second. + Unit string `json:"unit,omitempty" toon:"unit,omitempty"` + // Fields reduced to the gauge value. + ValueFields []string `json:"value_fields,omitempty" toon:"value_fields,omitempty"` +} + // DataSourceItem is generated from the Flashduty OpenAPI schema. type DataSourceItem struct { // Account ID. @@ -3920,6 +4959,42 @@ type Flapping struct { MuteMins int64 `json:"mute_mins,omitempty" toon:"mute_mins,omitempty"` } +// FolderItem is generated from the Flashduty OpenAPI schema. +type FolderItem struct { + // Owning account ID. + AccountID uint64 `json:"account_id" toon:"account_id"` + // Unix timestamp in seconds. + CreatedAt Timestamp `json:"created_at" toon:"created_at"` + // Member ID of the creator. + CreatorID uint64 `json:"creator_id" toon:"creator_id"` + // Name of the creator. + CreatorName string `json:"creator_name" toon:"creator_name"` + // Folder ID. + ID uint64 `json:"id" toon:"id"` + // Folder name. + Name string `json:"name" toon:"name"` + // Free-form note. + Note string `json:"note" toon:"note"` + // Parent folder ID; 0 at the root. + ParentID uint64 `json:"parent_id" toon:"parent_id"` + // Comma-separated ancestor IDs from the root, excluding this folder; empty at the root. + ParentPath string `json:"parent_path" toon:"parent_path"` + // Team the folder is scoped to; 0 when account-wide. + TeamID uint64 `json:"team_id" toon:"team_id"` + // Unix timestamp in seconds. + UpdatedAt Timestamp `json:"updated_at" toon:"updated_at"` + // Member ID of the last updater. + UpdaterID uint64 `json:"updater_id" toon:"updater_id"` + // Name of the last updater. + UpdaterName string `json:"updater_name" toon:"updater_name"` +} + +// GetIntegrationRequest is generated from the Flashduty OpenAPI schema. +type GetIntegrationRequest struct { + // Integration ID. + IntegrationID int64 `json:"integration_id" toon:"integration_id"` +} + // GetRemoteConfigRequest is generated from the Flashduty OpenAPI schema. type GetRemoteConfigRequest struct { // RUM application ID. @@ -4603,6 +5678,85 @@ type InsightTopkAlertByLabelRequest struct { TimeZone string `json:"time_zone,omitempty" toon:"time_zone,omitempty"` } +// IntegrationDetail is generated from the Flashduty OpenAPI schema. +type IntegrationDetail struct { + Category any `json:"category" toon:"category"` + CreatedAt any `json:"created_at" toon:"created_at"` + Description any `json:"description" toon:"description"` + IntegrationID any `json:"integration_id" toon:"integration_id"` + LastTime any `json:"last_time" toon:"last_time"` + Name any `json:"name" toon:"name"` + PluginType any `json:"plugin_type" toon:"plugin_type"` + PluginTypeName any `json:"plugin_type_name" toon:"plugin_type_name"` + RefID any `json:"ref_id" toon:"ref_id"` + // Type-specific configuration. Sensitive values (endpoint, headers, secrets, passwords) are returned masked as `******`. + Settings map[string]any `json:"settings" toon:"settings"` + Status any `json:"status" toon:"status"` + TeamID any `json:"team_id" toon:"team_id"` + UpdatedAt any `json:"updated_at" toon:"updated_at"` +} + +// IntegrationItem is generated from the Flashduty OpenAPI schema. +type IntegrationItem struct { + // Category the integration belongs to: `event.alert` alert events, `event.change` change events, `im` IM bots, `webhook` custom webhooks. + Category string `json:"category" toon:"category"` + // Unix timestamp in seconds when the integration was created. + CreatedAt Timestamp `json:"created_at" toon:"created_at"` + // Free-form description. + Description string `json:"description" toon:"description"` + // Integration ID. + IntegrationID int64 `json:"integration_id" toon:"integration_id"` + // Unix timestamp in seconds of the most recent event received. `0` when no event has arrived yet. + LastTime Timestamp `json:"last_time" toon:"last_time"` + // Integration name. + Name string `json:"name" toon:"name"` + // Integration type, for example `standard.alert` or `zabbix.alert`. + PluginType string `json:"plugin_type" toon:"plugin_type"` + // Display name of the integration type, in the language of the request. + PluginTypeName string `json:"plugin_type_name" toon:"plugin_type_name"` + // Source reference ID: `a_`-prefixed for an account-scoped integration, `c_`-prefixed when it is shared into a channel, `w_`-prefixed on legacy workspace-scoped integrations. + RefID string `json:"ref_id" toon:"ref_id"` + // Lifecycle status: `enabled` while the integration accepts events, `disabled` when it is paused. + Status string `json:"status" toon:"status"` + // ID of the team that owns the integration. `0` when it is not assigned to a team. + TeamID int64 `json:"team_id" toon:"team_id"` + // Unix timestamp in seconds when the integration was last updated. + UpdatedAt Timestamp `json:"updated_at" toon:"updated_at"` +} + +// IntegrationLifecycleRequest is generated from the Flashduty OpenAPI schema. +type IntegrationLifecycleRequest struct { + // Integration ID. + IntegrationID int64 `json:"integration_id" toon:"integration_id"` +} + +// IntegrationTypeItem is generated from the Flashduty OpenAPI schema. +type IntegrationTypeItem struct { + // Category the type belongs to: `event.alert` alert events, `event.change` change events, `im` IM bots, `webhook` custom webhooks. + Category string `json:"category" toon:"category"` + // Type identifier to pass as `plugin_type` when creating an integration. + PluginType string `json:"plugin_type" toon:"plugin_type"` + // Logo URL of the type. + PluginTypeLogoURL string `json:"plugin_type_logo_url" toon:"plugin_type_logo_url"` + // Display name of the type. + PluginTypeName string `json:"plugin_type_name" toon:"plugin_type_name"` + // Platform status of the type. + Status string `json:"status" toon:"status"` + // Whether `POST /integration/create` accepts this type. + SupportsAPICreate bool `json:"supports_api_create" toon:"supports_api_create"` +} + +// IntegrationTypeListRequest is generated from the Flashduty OpenAPI schema. +type IntegrationTypeListRequest struct { + ListOptions + // Sort ascending when `true` (the default); descending when `false`. + Asc *bool `json:"asc,omitempty" toon:"asc,omitempty"` + // Filter by category. Accepts a comma-separated list, for example `event.alert,event.change`. + Category string `json:"category,omitempty" toon:"category,omitempty"` + // Sort field. When omitted, types are returned in console ranking order. + Orderby string `json:"orderby,omitempty" toon:"orderby,omitempty"` +} + // InvestigationTarget is generated from the Flashduty OpenAPI schema. type InvestigationTarget struct { // Configuration for the `dashboard` kind; required when `kind` is `dashboard`. @@ -4645,25 +5799,25 @@ type InviteMemberItem struct { // KnowledgeFileDeleteRequest is generated from the Flashduty OpenAPI schema. type KnowledgeFileDeleteRequest struct { - // Delete even when other pack files reference this file; the referrers are then returned as warnings instead of blocking the delete. + // Delete even when other knowledge files reference this file; the referrers are then returned as warnings instead of blocking the delete. Force bool `json:"force,omitempty" toon:"force,omitempty"` - // Knowledge pack ID; defaults to the caller's account-scope pack. + // Knowledge ID; defaults to the caller's account-scope knowledge. PackID string `json:"pack_id,omitempty" toon:"pack_id,omitempty"` - // Path of the file relative to the pack root. + // Path of the file relative to the knowledge root. RelPath string `json:"rel_path" toon:"rel_path"` } // KnowledgeFileDeleteResponse is generated from the Flashduty OpenAPI schema. type KnowledgeFileDeleteResponse struct { - // Non-blocking warnings after deletion; `code=still_referenced_by` means the (force-)deleted file is still @ref-referenced by other files in the pack (`refs` lists the referrers). Absent when there are no warnings (omitempty). + // Non-blocking warnings after deletion; `code=still_referenced_by` means the (force-)deleted file is still @ref-referenced by other files in the knowledge (`refs` lists the referrers). Absent when there are no warnings (omitempty). Warnings []KnowledgeWarning `json:"warnings" toon:"warnings"` } // KnowledgeFileGetRequest is generated from the Flashduty OpenAPI schema. type KnowledgeFileGetRequest struct { - // Knowledge pack ID; defaults to the caller's account-scope pack. + // Knowledge ID; defaults to the caller's account-scope knowledge. PackID string `json:"pack_id,omitempty" toon:"pack_id,omitempty"` - // Path of the file relative to the pack root. + // Path of the file relative to the knowledge root. RelPath string `json:"rel_path" toon:"rel_path"` } @@ -4682,9 +5836,9 @@ type KnowledgeFileItem struct { ContentType string `json:"content_type" toon:"content_type"` // File ID (`kfl_` prefix). FileID string `json:"file_id" toon:"file_id"` - // ID of the knowledge pack that contains the file. + // ID of the knowledge that contains the file. PackID string `json:"pack_id" toon:"pack_id"` - // Path relative to the pack root, e.g. `runbooks/restart.md`. + // Path relative to the knowledge root, e.g. `runbooks/restart.md`. RelPath string `json:"rel_path" toon:"rel_path"` // File size in bytes. SizeBytes int64 `json:"size_bytes" toon:"size_bytes"` @@ -4697,15 +5851,15 @@ type KnowledgeFileItem struct { // KnowledgeFileListRequest is generated from the Flashduty OpenAPI schema. type KnowledgeFileListRequest struct { ListOptions - // Knowledge pack ID; defaults to the caller's account-scope pack. + // Knowledge ID; defaults to the caller's account-scope knowledge. PackID string `json:"pack_id,omitempty" toon:"pack_id,omitempty"` } // KnowledgeFileListResponse is generated from the Flashduty OpenAPI schema. type KnowledgeFileListResponse struct { - // Array of files in the specified knowledge pack; empty array when the pack has no files. + // Array of files in the specified knowledge; empty array when it has no files. Files []KnowledgeFileItem `json:"files" toon:"files"` - // Total number of files in the pack. + // Total number of files in the knowledge. Total int64 `json:"total" toon:"total"` } @@ -4715,16 +5869,16 @@ type KnowledgeFilePutRequest struct { ContentB64 string `json:"content_b64,omitempty" toon:"content_b64,omitempty"` // MIME type; inferred from the file extension when omitted. ContentType string `json:"content_type,omitempty" toon:"content_type,omitempty"` - // Knowledge pack ID; defaults to the caller's account-scope pack. + // Knowledge ID; defaults to the caller's account-scope knowledge. PackID string `json:"pack_id,omitempty" toon:"pack_id,omitempty"` - // Destination path relative to the pack root; existing files are overwritten. + // Destination path relative to the knowledge root; existing files are overwritten. RelPath string `json:"rel_path" toon:"rel_path"` } // KnowledgeFilePutResponse is generated from the Flashduty OpenAPI schema. type KnowledgeFilePutResponse struct { File KnowledgeFileItem `json:"file" toon:"file"` - // Non-blocking warnings after a successful write; `code=unresolved_reference` means an @ref in the file content points to a file that does not exist in the pack. Absent when there are no warnings (omitempty). + // Non-blocking warnings after a successful write; `code=unresolved_reference` means an @ref in the file content points to a file that does not exist in the knowledge. Absent when there are no warnings (omitempty). Warnings []KnowledgeWarning `json:"warnings" toon:"warnings"` } @@ -4733,26 +5887,26 @@ type KnowledgeGetRequest struct{} // KnowledgeGetResponse is generated from the Flashduty OpenAPI schema. type KnowledgeGetResponse struct { - // Array of files in this knowledge pack; empty array when the pack has no files. + // Array of files in this knowledge; empty array when it has no files. Files []KnowledgeFileItem `json:"files" toon:"files"` Pack KnowledgePackItem `json:"pack" toon:"pack"` } // KnowledgePackDeleteRequest is generated from the Flashduty OpenAPI schema. type KnowledgePackDeleteRequest struct { - // Knowledge pack ID to delete. + // Knowledge ID to delete. PackID string `json:"pack_id" toon:"pack_id"` } // KnowledgePackDeleteResponse is generated from the Flashduty OpenAPI schema. type KnowledgePackDeleteResponse struct { - // True when the pack was deleted. + // True when the knowledge was deleted. OK bool `json:"ok" toon:"ok"` } // KnowledgePackEnsureRequest is generated from the Flashduty OpenAPI schema. type KnowledgePackEnsureRequest struct { - // Scope of the pack to ensure. One of: `account` (account-level pack; scope_id is forced to the caller's account ID and only account admins may create it; first creation seeds a default DUTY.md), `team` (team-level pack; the `scope_id` team ID is required and the caller must belong to that team). + // Scope of the knowledge to ensure. One of: `account` (account-level knowledge; scope_id is forced to the caller's account ID and only account admins may create it; first creation seeds a default DUTY.md), `team` (team-level knowledge; the `scope_id` team ID is required and the caller must belong to that team). Scope string `json:"scope" toon:"scope"` // Team ID; required for `team` scope, ignored for `account` scope. ScopeID int64 `json:"scope_id,omitempty" toon:"scope_id,omitempty"` @@ -4760,21 +5914,21 @@ type KnowledgePackEnsureRequest struct { // KnowledgePackItem is generated from the Flashduty OpenAPI schema. type KnowledgePackItem struct { - // Account that owns the pack. + // Account that owns the knowledge. AccountID int64 `json:"account_id" toon:"account_id"` - // Whether the caller can edit this pack. + // Whether the caller can edit this knowledge. CanEdit bool `json:"can_edit" toon:"can_edit"` - // Unix timestamp in milliseconds when the pack was created. + // Unix timestamp in milliseconds when the knowledge was created. CreatedAtMs TimestampMilli `json:"created_at_ms" toon:"created_at_ms"` - // Person ID of the member who created the pack. + // Person ID of the member who created the knowledge. CreatedBy int64 `json:"created_by" toon:"created_by"` - // Pack version at which DUTY.md was last authored or re-affirmed. When `version` is greater, DUTY.md no longer reflects every file in the pack. + // Knowledge version at which DUTY.md was last authored or re-affirmed. When `version` is greater, DUTY.md no longer reflects every file in the knowledge. DutyVersion int64 `json:"duty_version" toon:"duty_version"` - // Number of files in the pack. + // Number of files in the knowledge. FileCount int64 `json:"file_count" toon:"file_count"` - // Knowledge pack ID (`kpk_` prefix). + // Knowledge ID (`kpk_` prefix). PackID string `json:"pack_id" toon:"pack_id"` - // Pack scope. `channel` is a legacy scope; new packs are `account` or `team`. + // Knowledge scope. `channel` is a legacy scope; new knowledge is `account` or `team` scope. Scope string `json:"scope" toon:"scope"` // Scope owner: the account ID for `account` scope, the team ID for `team` scope. ScopeID int64 `json:"scope_id" toon:"scope_id"` @@ -4782,20 +5936,20 @@ type KnowledgePackItem struct { TeamName string `json:"team_name" toon:"team_name"` // Total size of all files in bytes. TotalBytes int64 `json:"total_bytes" toon:"total_bytes"` - // Unix timestamp in milliseconds when the pack was last modified. + // Unix timestamp in milliseconds when the knowledge was last modified. UpdatedAtMs TimestampMilli `json:"updated_at_ms" toon:"updated_at_ms"` - // Pack version, incremented on every file change. + // Knowledge version, incremented on every file change. Version int64 `json:"version" toon:"version"` } // KnowledgePackListRequest is generated from the Flashduty OpenAPI schema. type KnowledgePackListRequest struct { ListOptions - // Include the account-scope pack; defaults to true. + // Include the account-scope knowledge; defaults to true. IncludeAccount *bool `json:"include_account,omitempty" toon:"include_account,omitempty"` - // Case-insensitive substring filter over pack ID, scope, scope ID/account ID, and team name. + // Case-insensitive substring filter over knowledge ID, scope, scope ID/account ID, and team name. Query string `json:"query,omitempty" toon:"query,omitempty"` - // Restrict to one scope; `all` (default) overrides `include_account`. One of: `all` (account scope plus visible team scopes), `account` (account-level packs only), `team` (team-level packs only, can be combined with `team_ids`). + // Restrict to one scope; `all` (default) overrides `include_account`. One of: `all` (account scope plus visible team scopes), `account` (account-level knowledge only), `team` (team-level knowledge only, can be combined with `team_ids`). Scope string `json:"scope,omitempty" toon:"scope,omitempty"` // Restrict to these team IDs; for non-admins the list is intersected with their own teams. TeamIDs []int64 `json:"team_ids,omitempty" toon:"team_ids,omitempty"` @@ -4803,17 +5957,17 @@ type KnowledgePackListRequest struct { // KnowledgePackListResponse is generated from the Flashduty OpenAPI schema. type KnowledgePackListResponse struct { - // Array of visible knowledge packs after filtering (current page), used with `total` for pagination. + // Array of visible knowledge after filtering (current page), used with `total` for pagination. Packs []KnowledgePackItem `json:"packs" toon:"packs"` - // Total number of packs after filtering, before pagination. + // Total number of knowledge entries after filtering, before pagination. Total int64 `json:"total" toon:"total"` } // KnowledgePackUpdateRequest is generated from the Flashduty OpenAPI schema. type KnowledgePackUpdateRequest struct { - // Knowledge pack ID to update. + // Knowledge ID to update. PackID string `json:"pack_id" toon:"pack_id"` - // Destination scope; omit for a no-op that returns the current pack. + // Destination scope; omit for a no-op that returns the current knowledge. Scope *string `json:"scope,omitempty" toon:"scope,omitempty"` // Destination team ID; required when `scope` is `team`, set automatically for `account`. ScopeID *int64 `json:"scope_id,omitempty" toon:"scope_id,omitempty"` @@ -4821,7 +5975,7 @@ type KnowledgePackUpdateRequest struct { // KnowledgeWarning is generated from the Flashduty OpenAPI schema. type KnowledgeWarning struct { - // Warning code. One of: `unresolved_reference` (an @ref in the written file's content points to a file that does not exist in the pack; `ref` carries it), `still_referenced_by` (the deleted file is still @ref-referenced by other files in the pack; `refs` lists the referrers). + // Warning code. One of: `unresolved_reference` (an @ref in the written file's content points to a file that does not exist in the knowledge; `ref` carries it), `still_referenced_by` (the deleted file is still @ref-referenced by other files in the knowledge; `refs` lists the referrers). Code string `json:"code" toon:"code"` // Single reference related to the warning. Ref string `json:"ref" toon:"ref"` @@ -4909,7 +6063,7 @@ type ListChannelsRequest struct { Asc bool `json:"asc,omitempty" toon:"asc,omitempty"` // Filter by explicit channel IDs. ChannelIDs []int64 `json:"channel_ids,omitempty" toon:"channel_ids,omitempty"` - // Exact-match filter on channel name. Takes priority over `query` for name filtering. + // Exact-match filter on channel name. Takes priority over `query` for name filtering. Must be valid UTF-8 — invalid byte sequences are rejected with `InvalidParameter`. ChannelName string `json:"channel_name,omitempty" toon:"channel_name,omitempty"` // When true, return only `channel_id`, `channel_name`, `description` and `status`, and return all matches without pagination. IsBrief bool `json:"is_brief,omitempty" toon:"is_brief,omitempty"` @@ -4921,7 +6075,7 @@ type ListChannelsRequest struct { IsMyTeam bool `json:"is_my_team,omitempty" toon:"is_my_team,omitempty"` // Field used to order results. Defaults to `created_at`. Orderby string `json:"orderby,omitempty" toon:"orderby,omitempty"` - // Case-insensitive regular expression matched against channel name and description; invalid regex syntax falls back to a literal match. + // Case-insensitive regular expression matched against channel name and description; invalid regex syntax falls back to a literal match. Must be valid UTF-8 — invalid byte sequences are rejected with `InvalidParameter`. Query string `json:"query,omitempty" toon:"query,omitempty"` // Filter by team IDs. TeamIDs []int64 `json:"team_ids,omitempty" toon:"team_ids,omitempty"` @@ -5051,6 +6205,49 @@ type ListInhibitRulesResponse struct { Items []InhibitRuleItem `json:"items" toon:"items"` } +// ListIntegrationTypesResponse is generated from the Flashduty OpenAPI schema. +type ListIntegrationTypesResponse struct { + ListOptions + // Integration types on the current page. + Items []IntegrationTypeItem `json:"items" toon:"items"` + // Total number of matching types. + Total int64 `json:"total" toon:"total"` +} + +// ListIntegrationsRequest is generated from the Flashduty OpenAPI schema. +type ListIntegrationsRequest struct { + ListOptions + // Sort ascending when true, descending when false. + Asc bool `json:"asc,omitempty" toon:"asc,omitempty"` + // Filter by category. Accepts a comma-separated list. + Category string `json:"category,omitempty" toon:"category,omitempty"` + // Limit the result to integrations owned by your teams. + IsMyTeam bool `json:"is_my_team,omitempty" toon:"is_my_team,omitempty"` + // Filter by integration name. + Name string `json:"name,omitempty" toon:"name,omitempty"` + // Sort field. Defaults to `created_at`; `plugin_type` is sorted by the underlying plugin. + Orderby string `json:"orderby,omitempty" toon:"orderby,omitempty"` + // Filter by integration type. Accepts a comma-separated list. + PluginType string `json:"plugin_type,omitempty" toon:"plugin_type,omitempty"` + // Filter by source reference IDs. Each value must start with `c_` (channel), `a_` (account) or `w_`. + RefIDs []string `json:"ref_ids,omitempty" toon:"ref_ids,omitempty"` + // Filter by status. Accepts a comma-separated list. + Status string `json:"status,omitempty" toon:"status,omitempty"` + // Filter by team IDs. With `is_my_team`, the values narrow that set further. + TeamIDs []int64 `json:"team_ids,omitempty" toon:"team_ids,omitempty"` + // Deprecated. Merged into `plugin_type` when both are set. + Type string `json:"type,omitempty" toon:"type,omitempty"` +} + +// ListIntegrationsResponse is generated from the Flashduty OpenAPI schema. +type ListIntegrationsResponse struct { + ListOptions + // Integrations on the current page. + Items []IntegrationItem `json:"items" toon:"items"` + // Total number of matching integrations. + Total int64 `json:"total" toon:"total"` +} + // ListPastIncidentsRequest is generated from the Flashduty OpenAPI schema. type ListPastIncidentsRequest struct { // Reference incident ID (MongoDB ObjectID). @@ -6699,6 +7896,10 @@ type RemoteConfigRule struct { type RemoteConfigValues struct { // How Session Replay masks a page by default. DefaultPrivacyLevel *string `json:"defaultPrivacyLevel,omitempty" toon:"defaultPrivacyLevel,omitempty"` + // Keep sessions the session sample rate did not draw when they report an error; applies only to sessions that rate missed, so it does nothing alongside a rate of 100. + SessionOnError *bool `json:"sessionOnError,omitempty" toon:"sessionOnError,omitempty"` + // The same switch for Session Replay: un-sampled sessions still record and upload their recording only when the session errors. + SessionReplayOnError *bool `json:"sessionReplayOnError,omitempty" toon:"sessionReplayOnError,omitempty"` // Session Replay sampling rate (0-100). SessionReplaySampleRate *int64 `json:"sessionReplaySampleRate,omitempty" toon:"sessionReplaySampleRate,omitempty"` // Session sampling rate (0-100). @@ -7010,6 +8211,12 @@ type RoleUpsertResponse struct { RoleName string `json:"role_name" toon:"role_name"` } +// RotateIntegrationKeyResponse is generated from the Flashduty OpenAPI schema. +type RotateIntegrationKeyResponse struct { + // The new key. The previous key stops working immediately; this value cannot be read again later. + IntegrationKey string `json:"integration_key" toon:"integration_key"` +} + // RouteCase is generated from the Flashduty OpenAPI schema. type RouteCase struct { // Target channel IDs. Required when `routing_mode` is `standard` (or empty); returned as `null` for `name_mapping`. @@ -7917,7 +9124,7 @@ type RUMIssueItem struct { Status string `json:"status" toon:"status"` // Suspected root cause analysis, determined automatically (rules or AI) or set manually by a user. SuspectedCause RUMIssueItemSuspectedCause `json:"suspected_cause" toon:"suspected_cause"` - // ID of the team owning this issue, copied from the owning application's `team_id` at issue creation. + // ID of the team owning this issue. For `POST /rum/issue/info` this is the owning application's current `team_id`; `POST /rum/issue/list` and `POST /rum/issue/export` report the team recorded when the issue was first seen, which differs once the application moves to another team. TeamID int64 `json:"team_id" toon:"team_id"` // Time the issue was last updated, Unix timestamp in milliseconds. UpdatedAt TimestampMilli `json:"updated_at" toon:"updated_at"` @@ -8930,7 +10137,7 @@ type SessionGetResponse struct { // Opaque keyset cursor; pass back as search_after_ctx to fetch the next older page. Omitted when has_more_older is false. SearchAfterCtx string `json:"search_after_ctx" toon:"search_after_ctx"` Session SessionItem `json:"session" toon:"session"` - // Account-wide onboarding flag: true when the account has zero knowledge packs in any scope; not specific to this session. + // Account-wide onboarding flag: true when the account has no knowledge in any scope; not specific to this session. SuggestInit bool `json:"suggest_init" toon:"suggest_init"` } @@ -8984,6 +10191,8 @@ type SessionItem struct { // | `automation` | Created by an automation rule (unattended run) | // | `subagent` | Child session spawned by a parent's agent_dispatch (audit label; at runtime it executes on the web tool surface) | EntryKind string `json:"entry_kind" toon:"entry_kind"` + // Whether the session still has open tasks, used to tell a handed-off turn from a settled session. Best-effort: when the read fails the field is absent (`omitempty`), which callers must treat as "unknown", never as proof the session is idle. + HasOpenTasks bool `json:"has_open_tasks" toon:"has_open_tasks"` // True when there is assistant output the caller has not yet viewed. HasUnread bool `json:"has_unread" toon:"has_unread"` // True for incognito (non-persisted-memory) sessions. @@ -9053,6 +10262,8 @@ type SessionListRequest struct { Keyword string `json:"keyword,omitempty" toon:"keyword,omitempty"` // Sort field: `created_at` by creation time, `updated_at` by last update; defaults to `updated_at` when omitted. Orderby string `json:"orderby,omitempty" toon:"orderby,omitempty"` + // Filter by who started the session: returns only sessions started by these members (a session is kept when `person_id` matches any of them). Intersects with `scope` and `team_ids`, so it never widens what the caller is allowed to see. + PersonIDs []int64 `json:"person_ids,omitempty" toon:"person_ids,omitempty"` // Visibility scope: `all` (own personal + accessible team sessions), `personal`, or `team`; default `all`. Scope string `json:"scope,omitempty" toon:"scope,omitempty"` // Archive bucket: active (default) returns un-archived, archived returns archived, all returns both. @@ -9065,7 +10276,7 @@ type SessionListRequest struct { type SessionListResponse struct { // The page of sessions. Sessions []SessionItem `json:"sessions" toon:"sessions"` - // Account-wide onboarding flag: true when the account has zero knowledge packs in any scope; not dependent on this call's filters. + // Account-wide onboarding flag: true when the account has no knowledge in any scope; not dependent on this call's filters. SuggestInit bool `json:"suggest_init" toon:"suggest_init"` // Total number of sessions matching the filter (ignoring pagination). Total int64 `json:"total" toon:"total"` @@ -9920,6 +11131,8 @@ type TemplateCreateRequest struct { Dingtalk string `json:"dingtalk,omitempty" toon:"dingtalk,omitempty"` // DingTalk app message template source. DingtalkApp string `json:"dingtalk_app,omitempty" toon:"dingtalk_app,omitempty"` + // Show the Create War Room button on DingTalk app cards. + DingtalkAppWarRoomEnabled bool `json:"dingtalk_app_war_room_enabled,omitempty" toon:"dingtalk_app_war_room_enabled,omitempty"` // Email body template source (Go `html/template` syntax). Email string `json:"email,omitempty" toon:"email,omitempty"` // Feishu robot message template source. @@ -9940,6 +11153,8 @@ type TemplateCreateRequest struct { Slack string `json:"slack,omitempty" toon:"slack,omitempty"` // Slack app message template source. SlackApp string `json:"slack_app,omitempty" toon:"slack_app,omitempty"` + // Show the Create War Room button on Slack app cards. + SlackAppWarRoomEnabled bool `json:"slack_app_war_room_enabled,omitempty" toon:"slack_app_war_room_enabled,omitempty"` // SMS template source (Go `text/template` syntax). SMS string `json:"sms,omitempty" toon:"sms,omitempty"` // Team scope. 0 for account-wide. @@ -9992,6 +11207,8 @@ type TemplateItem struct { Dingtalk string `json:"dingtalk" toon:"dingtalk"` // DingTalk app message template source. DingtalkApp string `json:"dingtalk_app" toon:"dingtalk_app"` + // Whether DingTalk app cards show the Create War Room button. Hidden for closed incidents and when the incident has no responders. + DingtalkAppWarRoomEnabled bool `json:"dingtalk_app_war_room_enabled" toon:"dingtalk_app_war_room_enabled"` // Email body template source (Go `html/template` syntax). Email string `json:"email" toon:"email"` // Feishu robot message template source. @@ -10012,6 +11229,8 @@ type TemplateItem struct { Slack string `json:"slack" toon:"slack"` // Slack app message template source. SlackApp string `json:"slack_app" toon:"slack_app"` + // Whether Slack app cards show the Create War Room button. Hidden for closed incidents and when the incident has no responders. + SlackAppWarRoomEnabled bool `json:"slack_app_war_room_enabled" toon:"slack_app_war_room_enabled"` // SMS template source (Go `text/template` syntax). SMS string `json:"sms" toon:"sms"` // Template lifecycle status. `enabled` templates can be referenced by escalation policies for notifications; `disabled` templates are no longer used for new notifications; `deleted` templates are never returned by list endpoints. @@ -10077,6 +11296,8 @@ type TemplateUpdateRequest struct { Dingtalk *string `json:"dingtalk,omitempty" toon:"dingtalk,omitempty"` // DingTalk app message template source. Omit to keep the current content; send an empty string to clear it. DingtalkApp *string `json:"dingtalk_app,omitempty" toon:"dingtalk_app,omitempty"` + // When set, show or hide the Create War Room button on DingTalk app cards. Omit to keep the existing setting. + DingtalkAppWarRoomEnabled *bool `json:"dingtalk_app_war_room_enabled,omitempty" toon:"dingtalk_app_war_room_enabled,omitempty"` // Email body template source (Go `html/template` syntax). Omit to keep the current content; send an empty string to clear it. Email *string `json:"email,omitempty" toon:"email,omitempty"` // Feishu robot message template source. Omit to keep the current content; send an empty string to clear it. @@ -10097,6 +11318,8 @@ type TemplateUpdateRequest struct { Slack *string `json:"slack,omitempty" toon:"slack,omitempty"` // Slack app message template source. Omit to keep the current content; send an empty string to clear it. SlackApp *string `json:"slack_app,omitempty" toon:"slack_app,omitempty"` + // When set, show or hide the Create War Room button on Slack app cards. Omit to keep the existing setting. + SlackAppWarRoomEnabled *bool `json:"slack_app_war_room_enabled,omitempty" toon:"slack_app_war_room_enabled,omitempty"` // SMS template source (Go `text/template` syntax). Omit to keep the current content; send an empty string to clear it. SMS *string `json:"sms,omitempty" toon:"sms,omitempty"` // Team scope. 0 for account-wide. Omit to keep the template's current team. @@ -10317,6 +11540,20 @@ type UpdateInhibitRuleRequest struct { TargetFilters FilterGroup `json:"target_filters,omitempty" toon:"target_filters,omitempty"` } +// UpdateIntegrationRequest is generated from the Flashduty OpenAPI schema. +type UpdateIntegrationRequest struct { + // New description, at most 499 characters. + Description *string `json:"description,omitempty" toon:"description,omitempty"` + // Integration ID. + IntegrationID int64 `json:"integration_id" toon:"integration_id"` + // New name, 2–49 characters. + Name *string `json:"name,omitempty" toon:"name,omitempty"` + // Replacement configuration for the integration type. Sensitive entries left out, or sent back as the masked `******`, keep their stored value. + Settings map[string]any `json:"settings,omitempty" toon:"settings,omitempty"` + // New owning team ID; `0` clears the team assignment. + TeamID *int64 `json:"team_id,omitempty" toon:"team_id,omitempty"` +} + // UpdateRemoteConfigRequest is generated from the Flashduty OpenAPI schema. type UpdateRemoteConfigRequest struct { // RUM application ID. diff --git a/openapi/openapi.en.json b/openapi/openapi.en.json index 5c2bdd2..d7d57a3 100644 --- a/openapi/openapi.en.json +++ b/openapi/openapi.en.json @@ -5017,10 +5017,10 @@ "type": "object" }, "ContextResolvedItem": { - "description": "Snapshot of the three-tier knowledge-pack resolution for this session.", + "description": "Snapshot of the three-tier knowledge resolution for this session.", "properties": { "account_pack_id": { - "description": "Resolved account-scoped pack id.", + "description": "Resolved account-scope knowledge ID.", "type": "string" }, "incident_id": { @@ -5028,19 +5028,19 @@ "type": "string" }, "resolved_at_ms": { - "description": "Unix timestamp in milliseconds when the packs were resolved.", + "description": "Unix timestamp in milliseconds when the knowledge was resolved.", "format": "int64", "type": "integer" }, "team_pack_id": { - "description": "Resolved team-scoped pack id.", + "description": "Resolved team-scope knowledge ID.", "type": "string" }, "versions": { "additionalProperties": { "type": "integer" }, - "description": "Per-pack resolved version map.", + "description": "Resolved version map, one entry per knowledge.", "type": "object" } }, @@ -12829,18 +12829,18 @@ "type": "object" }, "KnowledgeFileDeleteRequest": { - "description": "File to remove from a knowledge pack.", + "description": "Knowledge file to remove.", "properties": { "force": { - "description": "Delete even when other pack files reference this file; the referrers are then returned as warnings instead of blocking the delete.", + "description": "Delete even when other knowledge files reference this file; the referrers are then returned as warnings instead of blocking the delete.", "type": "boolean" }, "pack_id": { - "description": "Knowledge pack ID; defaults to the caller's account-scope pack.", + "description": "Knowledge ID; defaults to the caller's account-scope knowledge.", "type": "string" }, "rel_path": { - "description": "Path of the file relative to the pack root.", + "description": "Path of the file relative to the knowledge root.", "type": "string" } }, @@ -12853,7 +12853,7 @@ "description": "Deletion result; empty unless warnings were raised.", "properties": { "warnings": { - "description": "Non-blocking warnings after deletion; `code=still_referenced_by` means the (force-)deleted file is still @ref-referenced by other files in the pack (`refs` lists the referrers). Absent when there are no warnings (omitempty).", + "description": "Non-blocking warnings after deletion; `code=still_referenced_by` means the (force-)deleted file is still @ref-referenced by other files in the knowledge (`refs` lists the referrers). Absent when there are no warnings (omitempty).", "items": { "$ref": "#/components/schemas/KnowledgeWarning" }, @@ -12866,11 +12866,11 @@ "description": "Which file to fetch.", "properties": { "pack_id": { - "description": "Knowledge pack ID; defaults to the caller's account-scope pack.", + "description": "Knowledge ID; defaults to the caller's account-scope knowledge.", "type": "string" }, "rel_path": { - "description": "Path of the file relative to the pack root.", + "description": "Path of the file relative to the knowledge root.", "type": "string" } }, @@ -12897,7 +12897,7 @@ "type": "object" }, "KnowledgeFileItem": { - "description": "Metadata of one file inside a knowledge pack. Content is fetched separately via file/get.", + "description": "Metadata of one knowledge file. Content is fetched separately via file/get.", "properties": { "checksum": { "description": "SHA-256 hex digest of the file content.", @@ -12912,11 +12912,11 @@ "type": "string" }, "pack_id": { - "description": "ID of the knowledge pack that contains the file.", + "description": "ID of the knowledge that contains the file.", "type": "string" }, "rel_path": { - "description": "Path relative to the pack root, e.g. `runbooks/restart.md`.", + "description": "Path relative to the knowledge root, e.g. `runbooks/restart.md`.", "type": "string" }, "size_bytes": { @@ -12948,7 +12948,7 @@ "type": "object" }, "KnowledgeFileListRequest": { - "description": "Which pack's files to list.", + "description": "Which knowledge's files to list.", "properties": { "limit": { "description": "Page size. Accepted but currently ignored — the response always contains the full file list.", @@ -12959,24 +12959,24 @@ "type": "integer" }, "pack_id": { - "description": "Knowledge pack ID; defaults to the caller's account-scope pack.", + "description": "Knowledge ID; defaults to the caller's account-scope knowledge.", "type": "string" } }, "type": "object" }, "KnowledgeFileListResponse": { - "description": "Files in the pack.", + "description": "Files in the knowledge.", "properties": { "files": { - "description": "Array of files in the specified knowledge pack; empty array when the pack has no files.", + "description": "Array of files in the specified knowledge; empty array when it has no files.", "items": { "$ref": "#/components/schemas/KnowledgeFileItem" }, "type": "array" }, "total": { - "description": "Total number of files in the pack.", + "description": "Total number of files in the knowledge.", "format": "int64", "type": "integer" } @@ -12999,11 +12999,11 @@ "type": "string" }, "pack_id": { - "description": "Knowledge pack ID; defaults to the caller's account-scope pack.", + "description": "Knowledge ID; defaults to the caller's account-scope knowledge.", "type": "string" }, "rel_path": { - "description": "Destination path relative to the pack root; existing files are overwritten.", + "description": "Destination path relative to the knowledge root; existing files are overwritten.", "type": "string" } }, @@ -13019,7 +13019,7 @@ "$ref": "#/components/schemas/KnowledgeFileItem" }, "warnings": { - "description": "Non-blocking warnings after a successful write; `code=unresolved_reference` means an @ref in the file content points to a file that does not exist in the pack. Absent when there are no warnings (omitempty).", + "description": "Non-blocking warnings after a successful write; `code=unresolved_reference` means an @ref in the file content points to a file that does not exist in the knowledge. Absent when there are no warnings (omitempty).", "items": { "$ref": "#/components/schemas/KnowledgeWarning" }, @@ -13032,15 +13032,15 @@ "type": "object" }, "KnowledgeGetRequest": { - "description": "No request fields — the account-scope pack is always targeted.", + "description": "No request fields — the account-scope knowledge is always targeted.", "properties": {}, "type": "object" }, "KnowledgeGetResponse": { - "description": "Account-scope pack metadata plus its file list.", + "description": "Account-scope knowledge metadata plus its file list.", "properties": { "files": { - "description": "Array of files in this knowledge pack; empty array when the pack has no files.", + "description": "Array of files in this knowledge; empty array when it has no files.", "items": { "$ref": "#/components/schemas/KnowledgeFileItem" }, @@ -13057,10 +13057,10 @@ "type": "object" }, "KnowledgePackDeleteRequest": { - "description": "Pack to delete.", + "description": "Knowledge to delete.", "properties": { "pack_id": { - "description": "Knowledge pack ID to delete.", + "description": "Knowledge ID to delete.", "type": "string" } }, @@ -13073,7 +13073,7 @@ "description": "Deletion result.", "properties": { "ok": { - "description": "True when the pack was deleted.", + "description": "True when the knowledge was deleted.", "type": "boolean" } }, @@ -13083,10 +13083,10 @@ "type": "object" }, "KnowledgePackEnsureRequest": { - "description": "Scope at which to ensure a knowledge pack exists.", + "description": "Scope at which to ensure knowledge exists.", "properties": { "scope": { - "description": "Scope of the pack to ensure. One of: `account` (account-level pack; scope_id is forced to the caller's account ID and only account admins may create it; first creation seeds a default DUTY.md), `team` (team-level pack; the `scope_id` team ID is required and the caller must belong to that team).", + "description": "Scope of the knowledge to ensure. One of: `account` (account-level knowledge; scope_id is forced to the caller's account ID and only account admins may create it; first creation seeds a default DUTY.md), `team` (team-level knowledge; the `scope_id` team ID is required and the caller must belong to that team).", "enum": [ "account", "team" @@ -13105,41 +13105,41 @@ "type": "object" }, "KnowledgePackItem": { - "description": "A knowledge pack — a versioned file tree staged into every AI SRE sandbox at session start. One pack exists per (account, scope, scope_id).", + "description": "Knowledge — a versioned file tree staged into every AI SRE sandbox at session start. One knowledge exists per (account, scope, scope_id).", "properties": { "account_id": { - "description": "Account that owns the pack.", + "description": "Account that owns the knowledge.", "format": "int64", "type": "integer" }, "can_edit": { - "description": "Whether the caller can edit this pack.", + "description": "Whether the caller can edit this knowledge.", "type": "boolean" }, "created_at_ms": { - "description": "Unix timestamp in milliseconds when the pack was created.", + "description": "Unix timestamp in milliseconds when the knowledge was created.", "format": "int64", "type": "integer" }, "created_by": { - "description": "Person ID of the member who created the pack.", + "description": "Person ID of the member who created the knowledge.", "format": "int64", "type": "integer" }, "duty_version": { - "description": "Pack version at which DUTY.md was last authored or re-affirmed. When `version` is greater, DUTY.md no longer reflects every file in the pack.", + "description": "Knowledge version at which DUTY.md was last authored or re-affirmed. When `version` is greater, DUTY.md no longer reflects every file in the knowledge.", "type": "integer" }, "file_count": { - "description": "Number of files in the pack.", + "description": "Number of files in the knowledge.", "type": "integer" }, "pack_id": { - "description": "Knowledge pack ID (`kpk_` prefix).", + "description": "Knowledge ID (`kpk_` prefix).", "type": "string" }, "scope": { - "description": "Pack scope. `channel` is a legacy scope; new packs are `account` or `team`.", + "description": "Knowledge scope. `channel` is a legacy scope; new knowledge is `account` or `team` scope.", "enum": [ "account", "team", @@ -13162,12 +13162,12 @@ "type": "integer" }, "updated_at_ms": { - "description": "Unix timestamp in milliseconds when the pack was last modified.", + "description": "Unix timestamp in milliseconds when the knowledge was last modified.", "format": "int64", "type": "integer" }, "version": { - "description": "Pack version, incremented on every file change.", + "description": "Knowledge version, incremented on every file change.", "type": "integer" } }, @@ -13188,10 +13188,10 @@ "type": "object" }, "KnowledgePackListRequest": { - "description": "Filter and pagination for the pack list.", + "description": "Filter and pagination for the knowledge list.", "properties": { "include_account": { - "description": "Include the account-scope pack; defaults to true.", + "description": "Include the account-scope knowledge; defaults to true.", "type": [ "boolean", "null" @@ -13206,12 +13206,12 @@ "type": "integer" }, "query": { - "description": "Case-insensitive substring filter over pack ID, scope, scope ID/account ID, and team name.", + "description": "Case-insensitive substring filter over knowledge ID, scope, scope ID/account ID, and team name.", "maxLength": 128, "type": "string" }, "scope": { - "description": "Restrict to one scope; `all` (default) overrides `include_account`. One of: `all` (account scope plus visible team scopes), `account` (account-level packs only), `team` (team-level packs only, can be combined with `team_ids`).", + "description": "Restrict to one scope; `all` (default) overrides `include_account`. One of: `all` (account scope plus visible team scopes), `account` (account-level knowledge only), `team` (team-level knowledge only, can be combined with `team_ids`).", "enum": [ "all", "account", @@ -13231,17 +13231,17 @@ "type": "object" }, "KnowledgePackListResponse": { - "description": "Visible packs and the total after filtering.", + "description": "Visible knowledge and the total after filtering.", "properties": { "packs": { - "description": "Array of visible knowledge packs after filtering (current page), used with `total` for pagination.", + "description": "Array of visible knowledge after filtering (current page), used with `total` for pagination.", "items": { "$ref": "#/components/schemas/KnowledgePackItem" }, "type": "array" }, "total": { - "description": "Total number of packs after filtering, before pagination.", + "description": "Total number of knowledge entries after filtering, before pagination.", "format": "int64", "type": "integer" } @@ -13253,14 +13253,14 @@ "type": "object" }, "KnowledgePackUpdateRequest": { - "description": "Move a knowledge pack to a different scope.", + "description": "Move knowledge to a different scope.", "properties": { "pack_id": { - "description": "Knowledge pack ID to update.", + "description": "Knowledge ID to update.", "type": "string" }, "scope": { - "description": "Destination scope; omit for a no-op that returns the current pack.", + "description": "Destination scope; omit for a no-op that returns the current knowledge.", "enum": [ "account", "team" @@ -13288,7 +13288,7 @@ "description": "Non-blocking annotation returned by file uploads and deletions, e.g. references that point at a removed file.", "properties": { "code": { - "description": "Warning code. One of: `unresolved_reference` (an @ref in the written file's content points to a file that does not exist in the pack; `ref` carries it), `still_referenced_by` (the deleted file is still @ref-referenced by other files in the pack; `refs` lists the referrers).", + "description": "Warning code. One of: `unresolved_reference` (an @ref in the written file's content points to a file that does not exist in the knowledge; `ref` carries it), `still_referenced_by` (the deleted file is still @ref-referenced by other files in the knowledge; `refs` lists the referrers).", "enum": [ "unresolved_reference", "still_referenced_by" @@ -13545,7 +13545,7 @@ "type": "array" }, "channel_name": { - "description": "Exact-match filter on channel name. Takes priority over `query` for name filtering.", + "description": "Exact-match filter on channel name. Takes priority over `query` for name filtering. Must be valid UTF-8 — invalid byte sequences are rejected with `InvalidParameter`.", "type": "string" }, "is_brief": { @@ -13588,7 +13588,7 @@ "type": "integer" }, "query": { - "description": "Case-insensitive regular expression matched against channel name and description; invalid regex syntax falls back to a literal match.", + "description": "Case-insensitive regular expression matched against channel name and description; invalid regex syntax falls back to a literal match. Must be valid UTF-8 — invalid byte sequences are rejected with `InvalidParameter`.", "type": "string" }, "team_ids": { @@ -17896,6 +17896,20 @@ "null" ] }, + "sessionOnError": { + "description": "Keep sessions the session sample rate did not draw when they report an error; applies only to sessions that rate missed, so it does nothing alongside a rate of 100.", + "type": [ + "boolean", + "null" + ] + }, + "sessionReplayOnError": { + "description": "The same switch for Session Replay: un-sampled sessions still record and upload their recording only when the session errors.", + "type": [ + "boolean", + "null" + ] + }, "sessionReplaySampleRate": { "description": "Session Replay sampling rate (0-100).", "maximum": 100, @@ -21147,7 +21161,7 @@ "type": "object" }, "team_id": { - "description": "ID of the team owning this issue, copied from the owning application's `team_id` at issue creation.", + "description": "ID of the team owning this issue. For `POST /rum/issue/info` this is the owning application's current `team_id`; `POST /rum/issue/list` and `POST /rum/issue/export` report the team recorded when the issue was first seen, which differs once the application moves to another team.", "format": "int64", "type": "integer" }, @@ -23757,7 +23771,7 @@ "$ref": "#/components/schemas/SessionItem" }, "suggest_init": { - "description": "Account-wide onboarding flag: true when the account has zero knowledge packs in any scope; not specific to this session.", + "description": "Account-wide onboarding flag: true when the account has no knowledge in any scope; not specific to this session.", "type": "boolean" }, "pending_messages": { @@ -23970,6 +23984,10 @@ "description": "Unix timestamp in milliseconds of the last session update.", "format": "int64", "type": "integer" + }, + "has_open_tasks": { + "type": "boolean", + "description": "Whether the session still has open tasks, used to tell a handed-off turn from a settled session. Best-effort: when the read fails the field is absent (`omitempty`), which callers must treat as \"unknown\", never as proof the session is idle." } }, "required": [ @@ -24093,6 +24111,14 @@ "type": "integer" }, "type": "array" + }, + "person_ids": { + "type": "array", + "items": { + "type": "integer", + "format": "int64" + }, + "description": "Filter by who started the session: returns only sessions started by these members (a session is kept when `person_id` matches any of them). Intersects with `scope` and `team_ids`, so it never widens what the caller is allowed to see." } }, "required": [ @@ -24111,7 +24137,7 @@ "type": "array" }, "suggest_init": { - "description": "Account-wide onboarding flag: true when the account has zero knowledge packs in any scope; not dependent on this call's filters.", + "description": "Account-wide onboarding flag: true when the account has no knowledge in any scope; not dependent on this call's filters.", "type": "boolean" }, "total": { @@ -26207,6 +26233,10 @@ "description": "DingTalk app message template source.", "type": "string" }, + "dingtalk_app_war_room_enabled": { + "type": "boolean", + "description": "Show the Create War Room button on DingTalk app cards." + }, "email": { "description": "Email body template source (Go `html/template` syntax).", "type": "string" @@ -26258,6 +26288,10 @@ "description": "Slack app message template source.", "type": "string" }, + "slack_app_war_room_enabled": { + "type": "boolean", + "description": "Show the Create War Room button on Slack app cards." + }, "sms": { "description": "SMS template source (Go `text/template` syntax).", "type": "string" @@ -26380,6 +26414,10 @@ "description": "DingTalk app message template source.", "type": "string" }, + "dingtalk_app_war_room_enabled": { + "type": "boolean", + "description": "Whether DingTalk app cards show the Create War Room button. Hidden for closed incidents and when the incident has no responders." + }, "email": { "description": "Email body template source (Go `html/template` syntax).", "type": "string" @@ -26430,6 +26468,10 @@ "description": "Slack app message template source.", "type": "string" }, + "slack_app_war_room_enabled": { + "type": "boolean", + "description": "Whether Slack app cards show the Create War Room button. Hidden for closed incidents and when the incident has no responders." + }, "sms": { "description": "SMS template source (Go `text/template` syntax).", "type": "string" @@ -26514,6 +26556,8 @@ "wecom_markdown_v2_enabled", "feishu_app_card_v2_preserve_blank_lines", "feishu_app_war_room_enabled", + "dingtalk_app_war_room_enabled", + "slack_app_war_room_enabled", "dingtalk_app", "wecom_app", "slack_app", @@ -26644,6 +26688,13 @@ "null" ] }, + "dingtalk_app_war_room_enabled": { + "type": [ + "boolean", + "null" + ], + "description": "When set, show or hide the Create War Room button on DingTalk app cards. Omit to keep the existing setting." + }, "email": { "description": "Email body template source (Go `html/template` syntax). Omit to keep the current content; send an empty string to clear it.", "type": [ @@ -26718,6 +26769,13 @@ "null" ] }, + "slack_app_war_room_enabled": { + "type": [ + "boolean", + "null" + ], + "description": "When set, show or hide the Create War Room button on Slack app cards. Omit to keep the existing setting." + }, "sms": { "description": "SMS template source (Go `text/template` syntax). Omit to keep the current content; send an empty string to clear it.", "type": [ @@ -29405,394 +29463,6090 @@ ] } } - } - }, - "securitySchemes": { - "AppKeyAuth": { - "description": "App key issued from the Flashduty console under Account → APP Keys. Required on every public API call. Keep it secret — it grants the same access as the owning account.", - "in": "query", - "name": "app_key", - "type": "apiKey" }, - "AutomationTriggerBearerAuth": { - "description": "Bearer token generated for one Automation HTTP POST trigger. This is not an app_key.", - "scheme": "bearer", - "type": "http" - } - } - }, - "info": { - "description": "Public HTTP API for the Flashduty incident management platform — incidents, notification templates, channels, schedules, monitors, RUM, and platform administration. Every operation is authenticated with an `app_key` query parameter issued from the Flashduty console under Account → APP Keys. Responses follow a uniform envelope: `{ request_id, data }` on success, `{ request_id, error }` on failure.", - "title": "Flashduty Open API", - "version": "1.0.0" - }, - "openapi": "3.1.0", - "paths": { - "/account/info": { - "post": { - "description": "Return the current account's profile and settings.", - "operationId": "account-read-info", - "requestBody": { - "content": { - "application/json": { - "example": {}, - "schema": { - "type": "object" - } - } - } - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "account_id": 1001, - "account_name": "acme", - "avatar": "https://cdn.flashcat.cloud/avatar/acme.png", - "country_code": "CN", - "created_at": 1716960000, - "domain": "acme", - "email": "ops@acme.example", - "extra_domains": [ - "acme-corp" - ], - "locale": "zh-CN", - "phone": "138****8000", - "restrictions": { - "allow_subdomain": true, - "email_domains": [ - "acme.example" - ], - "ips": [ - "203.0.113.0/24" - ] - }, - "time_zone": "Asia/Shanghai" - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/AccountInfo" - } - }, - "type": "object" - } - ] - } - } - }, - "description": "Success" + "DashboardDefinition": { + "type": "object", + "description": "Complete dashboard payload stored as a portable `dashboard.v1` document. Unknown keys, duplicate keys, NaN/Inf, over-range numbers and trailing values are rejected; the serialized form must stay within 1 MiB.", + "properties": { + "title": { + "type": "string", + "minLength": 1, + "maxLength": 189, + "description": "Dashboard title, 1–189 Unicode code points after trimming." }, - "400": { - "$ref": "#/components/responses/BadRequest" + "description": { + "type": "string", + "maxLength": 1024, + "description": "Optional description, at most 1024 Unicode code points." }, - "401": { - "$ref": "#/components/responses/Unauthorized" + "default_time_range": { + "$ref": "#/components/schemas/DashboardRelativeTimeRange" }, - "429": { - "$ref": "#/components/responses/TooManyRequests" + "refresh_interval": { + "type": "string", + "enum": [ + "off", + "30s", + "1m", + "5m" + ], + "description": "Auto-refresh cadence applied by the console: `off` disables auto-refresh; `30s` = every 30 seconds; `1m` = every minute; `5m` = every 5 minutes." }, - "500": { - "$ref": "#/components/responses/ServerError" + "variables": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardVariable" + }, + "maxItems": 20, + "description": "Dashboard variables, at most 20. Names must be unique within the definition and match the variable-name pattern." + }, + "tabs": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardTab" + }, + "minItems": 1, + "maxItems": 10, + "description": "Tabs, 1–10. Every tab title is unique and every tab or section ID must be a canonical UUIDv7 used only once across the definition." } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Get account detail", - "tags": [ - "Platform/Account" - ], - "x-mint": { - "content": "| Permission | Description |\n| --- | --- |\n| None | None — any valid app_key can call this operation. |\n\nFind this operation in the [Platform API reference](/en/api-reference/platform/account/account-read-info).", - "href": "/en/api-reference/platform/account/account-read-info", - "metadata": { - "sidebarTitle": "Get account detail" - } - } - } - }, - "/alert-event/list": { - "post": { - "description": "Return a cursor-paginated list of raw alert events across all alerts, with filtering by integration, channel, time range, and severity.", - "operationId": "alert-event-read-list", - "requestBody": { - "content": { - "application/json": { - "example": { - "end_time": 1712707200, - "limit": 20, - "severities": "Critical", - "start_time": 1712620800 - }, - "schema": { - "$ref": "#/components/schemas/AlertEventGlobalListRequest" - } - } + "required": [ + "title", + "default_time_range", + "refresh_interval", + "variables", + "tabs" + ] + }, + "DashboardRelativeTimeRange": { + "type": "object", + "description": "Relative time window. `from` is one of the fixed presets the validator accepts; `to` is always the literal string `now`.", + "properties": { + "from": { + "type": "string", + "enum": [ + "now-15m", + "now-30m", + "now-1h", + "now-3h", + "now-6h", + "now-12h", + "now-24h", + "now-7d" + ], + "description": "Start offset relative to `to`: `now-15m` = 15 minutes ago; `now-30m` = 30 minutes ago; `now-1h` = 1 hour ago; `now-3h` = 3 hours ago; `now-6h` = 6 hours ago; `now-12h` = 12 hours ago; `now-24h` = 24 hours ago; `now-7d` = 7 days ago." }, - "required": true + "to": { + "type": "string", + "enum": [ + "now" + ], + "description": "End of the window; only `now` is accepted." + } }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "has_next_page": false, - "items": [ - { - "alert_id": "663a1b2c3d4e5f6789abcdef", - "event_id": "663a1b2c3d4e5f6789abc001", - "event_severity": "Critical", - "event_time": 1712650000, - "title": "CPU usage > 90%" - } - ], - "total": 1 - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/AlertEventGlobalListResponse" - } - }, - "type": "object" - } - ] - } - } - }, - "description": "Success" + "required": [ + "from", + "to" + ] + }, + "DashboardTab": { + "type": "object", + "description": "A top-level tab. Panels can sit directly on the tab (`top_panels`) or inside sections.", + "properties": { + "id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 identifying the tab; unique across the definition." }, - "400": { - "$ref": "#/components/responses/BadRequest" + "title": { + "type": "string", + "minLength": 1, + "maxLength": 189, + "description": "Tab title, 1–189 Unicode code points. Unique among tabs." }, - "401": { - "$ref": "#/components/responses/Unauthorized" + "description": { + "type": "string", + "maxLength": 1024, + "description": "Optional tab description." }, - "429": { - "$ref": "#/components/responses/TooManyRequests" + "top_panels": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardPanel" + }, + "maxItems": 30, + "description": "Panels placed directly on the tab, at most 30." }, - "500": { - "$ref": "#/components/responses/ServerError" + "sections": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardSection" + }, + "maxItems": 10, + "description": "Sections on the tab, at most 10." } }, - "summary": "List raw alert events", - "tags": [ - "On-call/Alerts" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Results are filtered by the caller's channel data-access permissions.\n- `severities` is a comma-separated string, e.g. `\"Critical,Warning\"`.", - "href": "/en/api-reference/on-call/alerts/alert-event-read-list", - "metadata": { - "sidebarTitle": "List raw alert events" - } - } - } - }, - "/alert/event/list": { - "post": { - "description": "Return raw events for an alert with cursor or page-number pagination.", - "operationId": "alert-read-event-list", - "requestBody": { - "content": { - "application/json": { - "example": { - "alert_id": "663a1b2c3d4e5f6789abcdef", - "limit": 20 - }, - "schema": { - "$ref": "#/components/schemas/AlertEventListRequest" - } - } + "required": [ + "id", + "title", + "top_panels", + "sections" + ] + }, + "DashboardSection": { + "type": "object", + "description": "A collapsible group of panels inside a tab.", + "properties": { + "id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 identifying the section; unique across the definition." }, - "required": true - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "has_next_page": true, - "items": [ - { - "alert_id": "663a1b2c3d4e5f6789abcdef", - "event_id": "663a1b2c3d4e5f6789abc001", - "event_severity": "Critical", - "event_status": "Critical", - "event_time": 1712650000, - "labels": { - "host": "web-01" - }, - "title": "CPU usage > 90%" - } - ], - "search_after_ctx": "663a1b2c3d4e5f6789abc001", - "total": 57 - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/AlertEventListResponse" - } - }, - "type": "object" - } - ] - } - } + "title": { + "type": "string", + "minLength": 1, + "maxLength": 189, + "description": "Section title." + }, + "description": { + "type": "string", + "maxLength": 1024, + "description": "Optional section description." + }, + "collapsed": { + "type": "boolean", + "description": "Whether the section renders collapsed by default." + }, + "panels": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardPanel" }, - "description": "Success" + "maxItems": 30, + "description": "Panels in the section, at most 30." + } + }, + "required": [ + "id", + "title", + "collapsed", + "panels" + ] + }, + "DashboardPanel": { + "type": "object", + "description": "A single visualization. Panels must not overlap inside the same container; the 24-column grid is validated on save.", + "properties": { + "id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 identifying the panel; unique across the definition." }, - "400": { - "$ref": "#/components/responses/BadRequest" + "title": { + "type": "string", + "minLength": 1, + "maxLength": 189, + "description": "Panel title." }, - "401": { - "$ref": "#/components/responses/Unauthorized" + "description": { + "type": "string", + "maxLength": 1024, + "description": "Optional panel description." }, - "429": { - "$ref": "#/components/responses/TooManyRequests" + "grid": { + "$ref": "#/components/schemas/DashboardGridPosition" }, - "500": { - "$ref": "#/components/responses/ServerError" + "datasource_ref": { + "$ref": "#/components/schemas/DashboardDatasourceRef" + }, + "queries": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardPanelQuery" + }, + "maxItems": 26, + "description": "Queries in the panel. `time_series` accepts 1–26, `text` accepts none, every other kind accepts exactly one." + }, + "viz_config": { + "$ref": "#/components/schemas/DashboardVizConfig" } }, - "summary": "List events for an alert", - "tags": [ - "On-call/Alerts" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Results are newest-first by default. Set `asc=true` to read events oldest-first.\n- Use `limit` with `search_after_ctx` from the previous response to fetch the next page.\n- Classic page-number pagination is also supported with `p`, but `p * limit` must stay within 10,000 records.\n- Each alert can accumulate a large raw event history; prefer cursor pagination for hot alerts.", - "href": "/en/api-reference/on-call/alerts/alert-read-event-list", - "metadata": { - "sidebarTitle": "List events for an alert" - } - } - } - }, - "/alert/feed": { - "post": { - "description": "Return the activity feed (comments, state changes, merges, silence events) for a single alert, with page-based pagination.", - "operationId": "alert-read-feed", - "requestBody": { - "content": { - "application/json": { - "example": { - "alert_id": "663a1b2c3d4e5f6789abcdef", - "asc": false, - "limit": 20 - }, - "schema": { - "$ref": "#/components/schemas/AlertFeedRequest" - } - } + "required": [ + "id", + "title", + "grid", + "queries", + "viz_config" + ] + }, + "DashboardGridPosition": { + "type": "object", + "description": "24-column grid placement. `x` and `y` are zero-based; `x + w` must not exceed 24.", + "properties": { + "x": { + "type": "integer", + "minimum": 0, + "maximum": 23, + "description": "Zero-based column offset." }, - "required": true - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "has_next_page": false, - "items": [ - { - "created_at": 1712651000, - "creator_id": 80011, - "detail": { - "comment": "Investigating now." - }, - "ref_id": "663a1b2c3d4e5f6789abcdef", - "type": "a_comm" - } - ] - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/AlertFeedResponse" - } - }, - "type": "object" - } - ] - } - } - }, - "description": "Success" + "y": { + "type": "integer", + "minimum": 0, + "description": "Zero-based row offset." }, - "400": { - "$ref": "#/components/responses/BadRequest" + "w": { + "type": "integer", + "minimum": 1, + "maximum": 24, + "description": "Width in grid columns, 1–24." }, - "401": { - "$ref": "#/components/responses/Unauthorized" + "h": { + "type": "integer", + "minimum": 1, + "maximum": 100, + "description": "Height in grid rows, 1–100." + } + }, + "required": [ + "x", + "y", + "w", + "h" + ] + }, + "DashboardDatasourceRef": { + "type": "object", + "description": "Points a panel or query variable at a datasource — either a fixed ID or a datasource variable evaluated at render time.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "fixed", + "variable" + ], + "description": "`fixed` uses `datasource_id`; `variable` resolves `name` against a datasource variable." }, - "429": { - "$ref": "#/components/responses/TooManyRequests" + "datasource_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Datasource ID. Required when `kind` is `fixed`, forbidden when `kind` is `variable`." }, - "500": { - "$ref": "#/components/responses/ServerError" + "name": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_]{0,63}$", + "description": "Datasource variable name. Required when `kind` is `variable`, forbidden when `kind` is `fixed`." + }, + "datasource_type": { + "type": "string", + "pattern": "^[a-z][a-z0-9_]{0,63}$", + "description": "Datasource type identifier, e.g. `prometheus` or `victorialogs`." } }, - "summary": "List alert activity feed", - "tags": [ + "required": [ + "kind", + "datasource_type" + ] + }, + "DashboardPanelQuery": { + "type": "object", + "description": "One query inside a panel. `ref_id` labels the series in the panel and must be unique within the panel.", + "properties": { + "ref_id": { + "type": "string", + "pattern": "^[A-Z]$", + "description": "Single uppercase letter (A–Z) naming the query inside its panel." + }, + "query": { + "$ref": "#/components/schemas/DashboardQuery" + }, + "legend_alias": { + "type": "string", + "maxLength": 1024, + "description": "Optional legend label; supports the same variable templates as `expr`." + } + }, + "required": [ + "ref_id", + "query" + ] + }, + "DashboardVariable": { + "description": "A dashboard variable. Pick the arm with `kind`.", + "oneOf": [ + { + "$ref": "#/components/schemas/DashboardDatasourceVariable" + }, + { + "$ref": "#/components/schemas/DashboardCustomVariable" + }, + { + "$ref": "#/components/schemas/DashboardQueryVariable" + } + ], + "discriminator": { + "propertyName": "kind", + "mapping": { + "datasource": "#/components/schemas/DashboardDatasourceVariable", + "custom": "#/components/schemas/DashboardCustomVariable", + "query": "#/components/schemas/DashboardQueryVariable" + } + } + }, + "DashboardDatasourceVariable": { + "type": "object", + "description": "Datasource selector variable. Its candidates are the account's datasources of `datasource_type`.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "datasource" + ], + "description": "Variable kind discriminator; always `datasource`, selecting a datasource." + }, + "name": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_]{0,63}$", + "description": "Variable name used in `{{ }}` templates, at most 64 characters." + }, + "label": { + "type": "string", + "maxLength": 189, + "description": "Optional display label; falls back to `name`." + }, + "datasource_type": { + "type": "string", + "pattern": "^[a-z][a-z0-9_]{0,63}$", + "description": "Datasource type the candidates are drawn from." + }, + "name_patterns": { + "type": "array", + "items": { + "type": "string", + "minLength": 1, + "maxLength": 189 + }, + "maxItems": 10, + "description": "Wildcard patterns narrowing the candidates; empty means every datasource of the type." + }, + "default_datasource_id": { + "type": "integer", + "format": "uint64", + "description": "Default datasource ID. Without a usable default the runtime picks the first candidate by name, then ID." + } + }, + "required": [ + "kind", + "name", + "datasource_type" + ] + }, + "DashboardCustomVariable": { + "type": "object", + "description": "Variable whose candidates come from a fixed list supplied inline.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "custom" + ], + "description": "Variable kind discriminator; always `custom`, with candidates from a fixed list supplied inline." + }, + "name": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_]{0,63}$", + "description": "Variable name used in `{{ }}` templates, at most 64 characters." + }, + "label": { + "type": "string", + "maxLength": 189, + "description": "Optional display label; falls back to `name`." + }, + "selection": { + "$ref": "#/components/schemas/DashboardSelectionConfig" + }, + "options": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardCandidate" + }, + "minItems": 1, + "maxItems": 1000, + "description": "Candidate list, 1–1000 entries. Values must be non-empty, unique and must not be `$__all`." + }, + "default": { + "$ref": "#/components/schemas/DashboardSelection" + } + }, + "required": [ + "kind", + "name", + "selection", + "options" + ] + }, + "DashboardQueryVariable": { + "type": "object", + "description": "Variable whose candidates are resolved by running a query against a datasource.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "query" + ], + "description": "Variable kind discriminator; always `query`, with candidates resolved by running a query against a datasource." + }, + "name": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_]{0,63}$", + "description": "Variable name used in `{{ }}` templates, at most 64 characters." + }, + "label": { + "type": "string", + "maxLength": 189, + "description": "Optional display label; falls back to `name`." + }, + "selection": { + "$ref": "#/components/schemas/DashboardSelectionConfig" + }, + "default": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "datasource_ref": { + "$ref": "#/components/schemas/DashboardDatasourceRef" + }, + "variable_query": { + "$ref": "#/components/schemas/DashboardVariableQuery" + }, + "refresh": { + "type": "string", + "enum": [ + "on_dashboard_load", + "on_time_range_change" + ], + "description": "When the candidates are recomputed: `on_dashboard_load` = once when the dashboard loads; `on_time_range_change` = every time the time range changes." + } + }, + "required": [ + "kind", + "name", + "selection", + "datasource_ref", + "variable_query", + "refresh" + ] + }, + "DashboardSelectionConfig": { + "type": "object", + "description": "Selection cardinality for a variable.", + "properties": { + "mode": { + "type": "string", + "enum": [ + "single", + "multi" + ], + "description": "Selection cardinality: `single` makes the resolved selection hold exactly one value; `multi` allows multiple values." + }, + "include_all": { + "type": "boolean", + "description": "When true the variable also offers an `all` selection." + } + }, + "required": [ + "mode", + "include_all" + ] + }, + "DashboardSelection": { + "type": "object", + "description": "A concrete selection of variable values. An empty `values` array is valid wire input and means unresolved — the server never substitutes a default for it.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "values", + "all" + ], + "description": "`values` selects the listed entries, `all` selects everything (only allowed when `include_all` is true)." + }, + "values": { + "type": "array", + "items": { + "type": "string", + "minLength": 1, + "maxLength": 1024 + }, + "maxItems": 1000, + "description": "Selected values, unique and never `$__all`. Must be empty when `kind` is `all`." + } + }, + "required": [ + "kind" + ] + }, + "DashboardCandidate": { + "type": "object", + "description": "One selectable option of a custom variable.", + "properties": { + "text": { + "type": "string", + "minLength": 1, + "maxLength": 1024, + "description": "Label shown in the picker." + }, + "value": { + "type": "string", + "minLength": 1, + "maxLength": 1024, + "description": "Value substituted into templates." + } + }, + "required": [ + "text", + "value" + ] + }, + "DashboardVariableQuery": { + "description": "Variable query. Pick the arm with `kind`; the arm must match the referenced datasource type.", + "oneOf": [ + { + "$ref": "#/components/schemas/DashboardPrometheusVariableQuery" + }, + { + "$ref": "#/components/schemas/DashboardSQLVariableQuery" + }, + { + "$ref": "#/components/schemas/DashboardLogsVariableQuery" + } + ], + "discriminator": { + "propertyName": "kind", + "mapping": { + "prometheus": "#/components/schemas/DashboardPrometheusVariableQuery", + "sql": "#/components/schemas/DashboardSQLVariableQuery", + "logs": "#/components/schemas/DashboardLogsVariableQuery" + } + } + }, + "DashboardPrometheusVariableQuery": { + "type": "object", + "description": "Prometheus label-values query.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "prometheus" + ], + "description": "Query kind discriminator; always `prometheus`, a label-values query against Prometheus." + }, + "label": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_:.\\-]{0,189}$", + "description": "Label whose values become candidates." + }, + "metric": { + "type": "string", + "description": "Optional metric used to restrict the series considered." + }, + "label_filters": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardLabelFilter" + }, + "description": "Optional matchers narrowing the series before label values are read." + } + }, + "required": [ + "kind", + "label" + ] + }, + "DashboardLabelFilter": { + "type": "object", + "description": "Prometheus label matcher.", + "properties": { + "label": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_:.\\-]{0,189}$", + "description": "Label name." + }, + "op": { + "type": "string", + "enum": [ + "=", + "!=", + "=~", + "!~" + ], + "description": "Matcher operator: `=` = equals; `!=` = not equals; `=~` = regex match; `!~` = regex does-not-match." + }, + "value": { + "type": "string", + "minLength": 1, + "description": "Matcher value; may reference other variables through `{{ }}`." + } + }, + "required": [ + "label", + "op", + "value" + ] + }, + "DashboardSQLVariableQuery": { + "type": "object", + "description": "SQL query returning one column of candidates.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "sql" + ], + "description": "Query kind discriminator; always `sql`, a SQL query returning one column of candidates." + }, + "expr": { + "type": "string", + "description": "SQL statement; may reference other variables through `{{ }}`." + }, + "args": { + "type": "object", + "additionalProperties": { + "type": "string" + }, + "description": "Named query arguments; defaults to an empty object." + }, + "text_field": { + "type": "string", + "description": "Column used as the candidate label; defaults to the value column." + }, + "value_field": { + "type": "string", + "minLength": 1, + "description": "Column used as the candidate value." + } + }, + "required": [ + "kind", + "expr", + "args", + "value_field" + ] + }, + "DashboardLogsVariableQuery": { + "type": "object", + "description": "Logs query returning one field's values as candidates.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "logs" + ], + "description": "Query kind discriminator; always `logs`, a logs query returning one field's values as candidates." + }, + "expr": { + "type": "string", + "description": "Logs query expression; may reference other variables through `{{ }}`." + }, + "args": { + "type": "object", + "additionalProperties": { + "type": "string" + }, + "description": "Named query arguments; defaults to an empty object." + }, + "field": { + "type": "string", + "minLength": 1, + "description": "Log field whose values become candidates." + } + }, + "required": [ + "kind", + "expr", + "args", + "field" + ] + }, + "DashboardVizConfig": { + "description": "Visualization configuration. `kind` selects the arm and therefore which sibling config object is required; `time_series` also carries the shared numeric options.", + "oneOf": [ + { + "$ref": "#/components/schemas/DashboardTimeSeriesViz" + }, + { + "$ref": "#/components/schemas/DashboardTableViz" + }, + { + "$ref": "#/components/schemas/DashboardStatViz" + }, + { + "$ref": "#/components/schemas/DashboardBarViz" + }, + { + "$ref": "#/components/schemas/DashboardGaugeViz" + }, + { + "$ref": "#/components/schemas/DashboardLogsViz" + }, + { + "$ref": "#/components/schemas/DashboardTextViz" + } + ], + "discriminator": { + "propertyName": "kind", + "mapping": { + "time_series": "#/components/schemas/DashboardTimeSeriesViz", + "table": "#/components/schemas/DashboardTableViz", + "stat": "#/components/schemas/DashboardStatViz", + "bar": "#/components/schemas/DashboardBarViz", + "gauge": "#/components/schemas/DashboardGaugeViz", + "logs": "#/components/schemas/DashboardLogsViz", + "text": "#/components/schemas/DashboardTextViz" + } + } + }, + "DashboardTimeSeriesViz": { + "type": "object", + "description": "Time-series visualization.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "time_series" + ], + "description": "Visualization kind discriminator; always `time_series`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "unit": { + "type": "string", + "enum": [ + "unitless", + "ratio", + "percent", + "milliseconds", + "seconds", + "bytes", + "bits", + "count_per_second", + "bytes_per_second", + "bits_per_second" + ], + "description": "Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second." + }, + "decimals": { + "type": [ + "integer", + "null" + ], + "minimum": 0, + "description": "Fixed decimal places; omit or send null to let the renderer decide." + }, + "threshold": { + "$ref": "#/components/schemas/DashboardThreshold" + } + }, + "required": [ + "kind", + "options" + ] + }, + "DashboardTableViz": { + "type": "object", + "description": "Table visualization.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "table" + ], + "description": "Visualization kind discriminator; always `table`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "column_options": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardColumnOption" + }, + "description": "Per-column display overrides keyed by field name, at most 100 entries." + }, + "sort": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardFieldSort" + }, + "maxItems": 2, + "description": "Initial sort keys; fields must be unique." + }, + "link_columns": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardDataLink" + }, + "maxItems": 5, + "description": "Drill-down links rendered as table columns. Together with per-column links a table allows at most 5." + } + }, + "required": [ + "kind", + "options" + ] + }, + "DashboardStatViz": { + "type": "object", + "description": "Single-value (stat) visualization.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "stat" + ], + "description": "Visualization kind discriminator; always `stat`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "unit": { + "type": "string", + "enum": [ + "unitless", + "ratio", + "percent", + "milliseconds", + "seconds", + "bytes", + "bits", + "count_per_second", + "bytes_per_second", + "bits_per_second" + ], + "description": "Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second." + }, + "decimals": { + "type": [ + "integer", + "null" + ], + "minimum": 0, + "description": "Fixed decimal places; omit or send null to let the renderer decide." + }, + "threshold": { + "$ref": "#/components/schemas/DashboardThreshold" + }, + "value_fields": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Fields reduced to the displayed values." + }, + "reducer": { + "type": "string", + "enum": [ + "last_non_null", + "min", + "max", + "mean", + "sum" + ], + "description": "Reduction applied across the returned rows: `last_non_null` = most recent non-null value; `min` = minimum; `max` = maximum; `mean` = average; `sum` = sum." + } + }, + "required": [ + "kind", + "options", + "value_fields", + "reducer" + ] + }, + "DashboardBarViz": { + "type": "object", + "description": "Bar-chart visualization.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "bar" + ], + "description": "Visualization kind discriminator; always `bar`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "unit": { + "type": "string", + "enum": [ + "unitless", + "ratio", + "percent", + "milliseconds", + "seconds", + "bytes", + "bits", + "count_per_second", + "bytes_per_second", + "bits_per_second" + ], + "description": "Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second." + }, + "decimals": { + "type": [ + "integer", + "null" + ], + "minimum": 0, + "description": "Fixed decimal places; omit or send null to let the renderer decide." + }, + "threshold": { + "$ref": "#/components/schemas/DashboardThreshold" + }, + "category_field": { + "type": "string", + "description": "Field supplying the category axis." + }, + "value_fields": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Fields supplying the bar values." + }, + "data_link": { + "$ref": "#/components/schemas/DashboardDataLink" + } + }, + "required": [ + "kind", + "options", + "category_field", + "value_fields" + ] + }, + "DashboardGaugeViz": { + "type": "object", + "description": "Gauge visualization.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "gauge" + ], + "description": "Visualization kind discriminator; always `gauge`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "unit": { + "type": "string", + "enum": [ + "unitless", + "ratio", + "percent", + "milliseconds", + "seconds", + "bytes", + "bits", + "count_per_second", + "bytes_per_second", + "bits_per_second" + ], + "description": "Display unit for the panel's numeric values: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second." + }, + "decimals": { + "type": [ + "integer", + "null" + ], + "minimum": 0, + "description": "Fixed decimal places; omit or send null to let the renderer decide." + }, + "threshold": { + "$ref": "#/components/schemas/DashboardThreshold" + }, + "value_fields": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Fields reduced to the gauge value." + }, + "reducer": { + "type": "string", + "enum": [ + "last_non_null", + "min", + "max", + "mean", + "sum" + ], + "description": "Reduction applied across the returned rows: `last_non_null` = most recent non-null value; `min` = minimum; `max` = maximum; `mean` = average; `sum` = sum." + }, + "min": { + "type": [ + "number", + "null" + ], + "description": "Scale lower bound." + }, + "max": { + "type": [ + "number", + "null" + ], + "description": "Scale upper bound; must exceed `min` when both are set." + } + }, + "required": [ + "kind", + "options", + "value_fields", + "reducer" + ] + }, + "DashboardLogsViz": { + "type": "object", + "description": "Log-stream visualization.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "logs" + ], + "description": "Visualization kind discriminator; always `logs`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "display_fields": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Log fields rendered for each row." + } + }, + "required": [ + "kind", + "options" + ] + }, + "DashboardTextViz": { + "type": "object", + "description": "Markdown text panel.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "text" + ], + "description": "Visualization kind discriminator; always `text`." + }, + "options": { + "type": "object", + "additionalProperties": true, + "description": "Open options object for the chosen visualization kind; the only part of the definition that round-trips losslessly. Missing or null normalizes to `{}`." + }, + "markdown": { + "type": "string", + "maxLength": 65536, + "description": "Markdown body, at most 64 KiB. Only a restricted node set (headings, lists, tables, links, code) survives validation." + } + }, + "required": [ + "kind", + "options", + "markdown" + ] + }, + "DashboardThreshold": { + "type": "object", + "description": "Colour threshold for a numeric value. At least one of `warning`/`critical` is required, and with both set the pair must be ordered according to `mode`.", + "properties": { + "mode": { + "type": "string", + "enum": [ + "higher_is_worse", + "lower_is_worse" + ], + "description": "Direction of the comparison: `higher_is_worse` = values at or above the bound breach it; `lower_is_worse` = values at or below the bound breach it." + }, + "warning": { + "type": [ + "number", + "null" + ], + "description": "Warning bound; must be finite." + }, + "critical": { + "type": [ + "number", + "null" + ], + "description": "Critical bound; must be finite." + } + }, + "required": [ + "mode" + ] + }, + "DashboardColumnOption": { + "type": "object", + "description": "Per-column display override for a table.", + "properties": { + "display_name": { + "type": "string", + "description": "Header text replacing the raw field name." + }, + "hidden": { + "type": [ + "boolean", + "null" + ], + "description": "Hide the column; omit to keep it visible." + }, + "width_px": { + "type": [ + "integer", + "null" + ], + "minimum": 80, + "maximum": 1200, + "description": "Column width in pixels, 80–1200." + }, + "unit": { + "type": "string", + "enum": [ + "unitless", + "ratio", + "percent", + "milliseconds", + "seconds", + "bytes", + "bits", + "count_per_second", + "bytes_per_second", + "bits_per_second" + ], + "description": "Unit override for the column: `unitless` = raw number; `ratio` = fraction of 1; `percent` = percentage; `milliseconds` = duration in milliseconds; `seconds` = duration in seconds; `bytes` = size in bytes; `bits` = size in bits; `count_per_second` = per-second count; `bytes_per_second` = bytes per second; `bits_per_second` = bits per second." + }, + "threshold": { + "$ref": "#/components/schemas/DashboardThreshold" + }, + "threshold_display": { + "type": "string", + "enum": [ + "text", + "background" + ], + "description": "How the threshold is painted: `text` = colours the cell text; `background` = colours the cell background." + }, + "data_link": { + "$ref": "#/components/schemas/DashboardDataLink" + } + } + }, + "DashboardFieldSort": { + "type": "object", + "description": "A single sort key.", + "properties": { + "field": { + "type": "string", + "minLength": 1, + "description": "Field name to sort by." + }, + "direction": { + "type": "string", + "enum": [ + "asc", + "desc" + ], + "description": "Sort direction: `asc` = ascending; `desc` = descending." + } + }, + "required": [ + "field", + "direction" + ] + }, + "DashboardDataLink": { + "type": "object", + "description": "Drill-down link from a table column or bar panel into another dashboard. The target dashboard must exist and the mapping sources must match the source panel's shape.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Target dashboard ID." + }, + "target_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Optional tab, section or panel ID to focus in the target dashboard." + }, + "pass_time": { + "type": "boolean", + "description": "When true the current time range is forwarded to the target." + }, + "variable_mappings": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardLinkMapping" + }, + "description": "Maps target variable names to a source value such as a column or a source variable." + } + }, + "required": [ + "dashboard_id", + "pass_time", + "variable_mappings" + ] + }, + "DashboardLinkMapping": { + "type": "object", + "description": "One entry of a drill-down variable mapping.", + "properties": { + "source": { + "type": "string", + "enum": [ + "variable", + "row_column", + "category", + "series", + "value" + ], + "description": "Where the value comes from: `variable` = a dashboard variable; `row_column` = a table column (requires `column`); `category` = the bar category; `series` = the series name; `value` = the value itself. `category`, `series` and `value` are only valid for bar panels." + }, + "column": { + "type": "string", + "description": "Source column name; required when `source` is `row_column`." + }, + "name": { + "type": "string", + "description": "Source dashboard variable name; required when `source` is `variable`." + } + }, + "required": [ + "source" + ] + }, + "DashboardActor": { + "type": "object", + "description": "Account member recorded as the creator, updater or revision author.", + "properties": { + "id": { + "type": "integer", + "format": "uint64", + "description": "Member ID." + }, + "name": { + "type": "string", + "description": "Member display name." + } + }, + "required": [ + "id", + "name" + ] + }, + "DashboardResource": { + "type": "object", + "description": "A stored dashboard: its identity, revision counter, placement and full definition. `revision` increments on every accepted write and must be echoed back as `expected_revision` for the next mutation.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 assigned by the caller at creation time." + }, + "schema_version": { + "type": "string", + "enum": [ + "dashboard.v1" + ], + "description": "Wire schema version of `definition`; only `dashboard.v1` is accepted." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Current revision number." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "ID of the dashboard's folder." + }, + "folder_breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Folder names from the root down to `folder_id`." + }, + "definition": { + "$ref": "#/components/schemas/DashboardDefinition" + }, + "created_by": { + "$ref": "#/components/schemas/DashboardActor" + }, + "updated_by": { + "$ref": "#/components/schemas/DashboardActor" + }, + "created_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + }, + "updated_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "dashboard_id", + "schema_version", + "revision", + "folder_id", + "folder_breadcrumb", + "definition", + "created_by", + "updated_by", + "created_at", + "updated_at" + ] + }, + "DashboardListItem": { + "type": "object", + "description": "One row of a dashboard listing. Carries the summary fields only — call the get endpoint for the full definition.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder ID." + }, + "folder_breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Folder path from the root." + }, + "title": { + "type": "string", + "description": "Dashboard title." + }, + "description": { + "type": "string", + "description": "Dashboard description; empty when unset." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Current revision number." + }, + "updated_by": { + "$ref": "#/components/schemas/DashboardActor" + }, + "updated_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "dashboard_id", + "folder_id", + "folder_breadcrumb", + "title", + "revision", + "updated_by", + "updated_at" + ] + }, + "DashboardListOutput": { + "type": "object", + "description": "A page of dashboards plus the total matching count.", + "properties": { + "items": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardListItem" + }, + "description": "Dashboards in this page." + }, + "total": { + "type": "integer", + "format": "int64", + "description": "Total number of matching dashboards across all pages." + } + }, + "required": [ + "items", + "total" + ] + }, + "DashboardTrashItem": { + "type": "object", + "description": "One row of the trash listing.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder the dashboard sat in when deleted." + }, + "folder_breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Folder path from the root." + }, + "title": { + "type": "string", + "description": "Dashboard title." + }, + "description": { + "type": "string", + "description": "Dashboard description; empty when unset." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the dashboard had when deleted." + }, + "deleted_by": { + "$ref": "#/components/schemas/DashboardActor" + }, + "deleted_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "dashboard_id", + "folder_id", + "folder_breadcrumb", + "title", + "revision", + "deleted_by", + "deleted_at" + ] + }, + "DashboardTrashListOutput": { + "type": "object", + "description": "A page of deleted dashboards. Entries older than the 30-day retention window are purged.", + "properties": { + "items": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardTrashItem" + }, + "description": "Deleted dashboards in this page." + }, + "total": { + "type": "integer", + "format": "int64", + "description": "Total number of deleted dashboards." + } + }, + "required": [ + "items", + "total" + ] + }, + "DashboardUpdateOutput": { + "type": "object", + "description": "Result of an update or move. `changed` is false when the write was a no-op — the canonical serialized definition matched the stored one byte for byte, in which case `resource` still describes the unchanged dashboard.", + "properties": { + "changed": { + "type": "boolean", + "description": "Whether the stored dashboard actually changed." + }, + "resource": { + "$ref": "#/components/schemas/DashboardResource" + } + }, + "required": [ + "changed", + "resource" + ] + }, + "DashboardDeleteOutput": { + "type": "object", + "description": "Result of moving a dashboard to the trash.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision recorded for the deletion." + } + }, + "required": [ + "dashboard_id", + "revision" + ] + }, + "DashboardRevisionItem": { + "type": "object", + "description": "One entry of the revision history. The server keeps the most recent 20 revisions including the current one.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision number." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder the dashboard sat in at that revision." + }, + "message": { + "type": "string", + "maxLength": 1024, + "description": "Optional commit message; at most 1024 Unicode code points." + }, + "actor": { + "$ref": "#/components/schemas/DashboardActor" + }, + "created_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "dashboard_id", + "revision", + "folder_id", + "actor", + "created_at" + ] + }, + "DashboardRevisionListOutput": { + "type": "object", + "description": "Revision history, newest first.", + "properties": { + "items": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardRevisionItem" + }, + "description": "Revisions, at most 20." + } + }, + "required": [ + "items" + ] + }, + "DashboardRevisionResource": { + "type": "object", + "description": "A historical revision with its full definition.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "schema_version": { + "type": "string", + "enum": [ + "dashboard.v1" + ], + "description": "Wire schema version of `definition`; only `dashboard.v1` is accepted." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision number." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder the dashboard sat in at that revision." + }, + "definition": { + "$ref": "#/components/schemas/DashboardDefinition" + }, + "message": { + "type": "string", + "maxLength": 1024, + "description": "Optional commit message." + }, + "actor": { + "$ref": "#/components/schemas/DashboardActor" + }, + "created_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "dashboard_id", + "schema_version", + "revision", + "folder_id", + "definition", + "actor", + "created_at" + ] + }, + "DashboardOutline": { + "type": "object", + "description": "Structural outline of a dashboard — titles, breadcrumbs and visualization kinds, without queries or definitions. Pass `target_id` to narrow the outline to one tab, section or panel.", + "properties": { + "dashboard": { + "$ref": "#/components/schemas/DashboardOutlineInfo" + }, + "folder": { + "$ref": "#/components/schemas/DashboardOutlineFolder" + }, + "variables": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardOutlineVariable" + }, + "description": "Variable summaries." + }, + "tabs": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardOutlineTab" + }, + "description": "Tabs, narrowed by `target_id` when supplied." + } + }, + "required": [ + "dashboard", + "folder", + "variables", + "tabs" + ] + }, + "DashboardOutlineInfo": { + "type": "object", + "description": "Dashboard-level outline entry.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "title": { + "type": "string", + "description": "Dashboard title." + }, + "description": { + "type": "string", + "description": "Dashboard description; empty when unset." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Current revision number." + }, + "updated_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "dashboard_id", + "title", + "revision", + "updated_at" + ] + }, + "DashboardOutlineFolder": { + "type": "object", + "description": "Folder placement in an outline.", + "properties": { + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder ID." + }, + "breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Folder names from the root." + } + }, + "required": [ + "folder_id", + "breadcrumb" + ] + }, + "DashboardOutlineVariable": { + "type": "object", + "description": "Variable summary in an outline.", + "properties": { + "name": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_]{0,63}$", + "description": "Variable name." + }, + "label": { + "type": "string", + "description": "Display label; empty when unset." + }, + "kind": { + "type": "string", + "enum": [ + "datasource", + "custom", + "query" + ], + "description": "Variable kind: `datasource` = selects a datasource; `custom` = fixed inline list; `query` = resolved by running a query." + }, + "selection": { + "$ref": "#/components/schemas/DashboardSelectionConfig" + } + }, + "required": [ + "name", + "kind" + ] + }, + "DashboardOutlineTab": { + "type": "object", + "description": "Tab entry in an outline, with its breadcrumb.", + "properties": { + "id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Tab ID." + }, + "title": { + "type": "string", + "description": "Tab title." + }, + "description": { + "type": "string", + "description": "Tab description; empty when unset." + }, + "breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Dashboard title followed by the tab title." + }, + "top_panels": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardOutlinePanel" + }, + "description": "Panels placed directly on the tab." + }, + "sections": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardOutlineSection" + }, + "description": "Sections on the tab." + } + }, + "required": [ + "id", + "title", + "breadcrumb", + "top_panels", + "sections" + ] + }, + "DashboardOutlineSection": { + "type": "object", + "description": "Section entry in an outline.", + "properties": { + "id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Section ID." + }, + "title": { + "type": "string", + "description": "Section title." + }, + "description": { + "type": "string", + "description": "Section description; empty when unset." + }, + "breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Dashboard, tab and section titles." + }, + "panels": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardOutlinePanel" + }, + "description": "Panels in the section." + } + }, + "required": [ + "id", + "title", + "breadcrumb", + "panels" + ] + }, + "DashboardOutlinePanel": { + "type": "object", + "description": "Panel entry in an outline.", + "properties": { + "id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Panel ID." + }, + "title": { + "type": "string", + "description": "Panel title." + }, + "description": { + "type": "string", + "description": "Panel description; empty when unset." + }, + "breadcrumb": { + "type": "array", + "items": { + "type": "string" + }, + "description": "Full path of titles from the dashboard down to the panel." + }, + "viz_config": { + "$ref": "#/components/schemas/DashboardOutlineVizConfig" + }, + "datasource_type": { + "type": "string", + "description": "Datasource type the panel queries; empty when the panel has no datasource (text panels)." + } + }, + "required": [ + "id", + "title", + "breadcrumb", + "viz_config" + ] + }, + "DashboardOutlineVizConfig": { + "type": "object", + "description": "Visualization kind of an outlined panel.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "time_series", + "table", + "stat", + "bar", + "gauge", + "logs", + "text" + ], + "description": "Visualization kind: `time_series` = time series; `table` = table; `stat` = single value; `bar` = bar chart; `gauge` = gauge; `logs` = log stream; `text` = Markdown text." + } + }, + "required": [ + "kind" + ] + }, + "DashboardSort": { + "type": "object", + "description": "A sort key accepted by the listing endpoints. `field` must be one of the allowed fields for that endpoint and fields must be unique; at most two keys are accepted.", + "properties": { + "field": { + "type": "string", + "enum": [ + "title", + "updated_at", + "deleted_at" + ], + "description": "`title` is available everywhere; `updated_at` only on list/search, `deleted_at` only on the trash listing." + }, + "direction": { + "type": "string", + "enum": [ + "asc", + "desc" + ], + "description": "Sort direction: `asc` = ascending; `desc` = descending." + } + }, + "required": [ + "field", + "direction" + ] + }, + "DashboardCreateRequest": { + "type": "object", + "description": "Create a dashboard. The caller supplies the ID, so a retry after a timeout returns `DashboardIDConflict` rather than silently creating a second dashboard.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "schema_version": { + "type": "string", + "enum": [ + "dashboard.v1" + ], + "description": "Wire schema version; only `dashboard.v1` is accepted." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder the dashboard is created in. Must be a folder the caller can write." + }, + "definition": { + "$ref": "#/components/schemas/DashboardDefinition" + } + }, + "required": [ + "dashboard_id", + "schema_version", + "folder_id", + "definition" + ] + }, + "DashboardIDRequest": { + "type": "object", + "description": "Identifies a single dashboard.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + } + }, + "required": [ + "dashboard_id" + ] + }, + "DashboardOutlineRequest": { + "type": "object", + "description": "Request an outline, optionally narrowed to one tab, section or panel.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "target_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Optional tab, section or panel ID. When set, the response keeps only the branch that contains it, and an unknown ID returns `TargetNotFound`." + } + }, + "required": [ + "dashboard_id" + ] + }, + "DashboardUpdateRequest": { + "type": "object", + "description": "Replace a dashboard's definition. The whole definition is sent, not a patch; `expected_revision` makes the write compare-and-swap.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "schema_version": { + "type": "string", + "enum": [ + "dashboard.v1" + ], + "description": "Wire schema version; only `dashboard.v1` is accepted." + }, + "expected_revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision." + }, + "definition": { + "$ref": "#/components/schemas/DashboardDefinition" + }, + "message": { + "type": "string", + "maxLength": 1024, + "description": "Optional revision message, at most 1024 Unicode code points. Stored with the revision and never returned by this endpoint." + } + }, + "required": [ + "dashboard_id", + "schema_version", + "expected_revision", + "definition" + ] + }, + "DashboardMoveRequest": { + "type": "object", + "description": "Move a dashboard to another folder without touching its definition.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "expected_revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Destination folder ID." + } + }, + "required": [ + "dashboard_id", + "expected_revision", + "folder_id" + ] + }, + "DashboardDeleteRequest": { + "type": "object", + "description": "Move a dashboard to the trash. The definition is retained for 30 days so the delete can be undone with the restore endpoint.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "expected_revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision." + } + }, + "required": [ + "dashboard_id", + "expected_revision" + ] + }, + "DashboardRestoreRequest": { + "type": "object", + "description": "Restore a trashed dashboard, optionally into a different folder.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "expected_revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the caller last read. The write fails with `DashboardRevisionConflict` unless it still matches the stored revision." + }, + "folder_id": { + "type": [ + "integer", + "null" + ], + "format": "uint64", + "minimum": 1, + "description": "Destination folder. Omit to restore to the original folder; when the original folder is no longer writable the call fails with `RestoreFolderRequired` and you must pass one." + } + }, + "required": [ + "dashboard_id", + "expected_revision" + ] + }, + "DashboardRevisionGetRequest": { + "type": "object", + "description": "Fetch one historical revision.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision number to fetch." + } + }, + "required": [ + "dashboard_id", + "revision" + ] + }, + "DashboardListRequest": { + "type": "object", + "description": "List the dashboards in one folder. Unlike search, `folder_id` is required.", + "properties": { + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Folder whose dashboards are listed." + }, + "query": { + "type": "string", + "maxLength": 128, + "description": "Optional space-separated search words matched against title and description; at most 128 Unicode code points." + }, + "sort": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardSort" + }, + "maxItems": 2, + "description": "Sort keys; defaults to `updated_at` descending." + }, + "p": { + "type": "integer", + "minimum": 1, + "description": "Page number, 1-based. Defaults to 1." + }, + "limit": { + "type": "integer", + "minimum": 1, + "maximum": 100, + "description": "Page size, 1–100. Defaults to 20." + } + }, + "required": [ + "folder_id" + ] + }, + "DashboardSearchRequest": { + "type": "object", + "description": "Search dashboards across every folder the caller can read. The query must contain at least one word.", + "properties": { + "query": { + "type": "string", + "minLength": 1, + "maxLength": 128, + "description": "Space-separated search words; at least one word and at most 128 Unicode code points." + }, + "sort": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardSort" + }, + "maxItems": 2, + "description": "Sort keys; defaults to `updated_at` descending." + }, + "p": { + "type": "integer", + "minimum": 1, + "description": "Page number, 1-based. Defaults to 1." + }, + "limit": { + "type": "integer", + "minimum": 1, + "maximum": 100, + "description": "Page size, 1–100. Defaults to 20." + } + }, + "required": [ + "query" + ] + }, + "DashboardTrashListRequest": { + "type": "object", + "description": "List trashed dashboards. Defaults to `deleted_at` descending.", + "properties": { + "sort": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardSort" + }, + "maxItems": 2, + "description": "Sort keys; only `title` and `deleted_at` are accepted here." + }, + "p": { + "type": "integer", + "minimum": 1, + "description": "Page number, 1-based. Defaults to 1." + }, + "limit": { + "type": "integer", + "minimum": 1, + "maximum": 100, + "description": "Page size, 1–100. Defaults to 20." + } + } + }, + "DashboardAbsoluteTimeRange": { + "type": "object", + "description": "Absolute evaluation window. Both bounds are Unix timestamps in milliseconds, `from_ms` must be less than `to_ms`, and neither may exceed the JavaScript safe integer limit.", + "properties": { + "from_ms": { + "type": "integer", + "format": "int64", + "minimum": 0, + "description": "Unix timestamp in milliseconds." + }, + "to_ms": { + "type": "integer", + "format": "int64", + "minimum": 1, + "description": "Unix timestamp in milliseconds." + } + }, + "required": [ + "from_ms", + "to_ms" + ] + }, + "DashboardRuntimeError": { + "type": "object", + "description": "Per-variable or per-query failure. A failed arm does not fail the whole call.", + "properties": { + "reason": { + "type": "string", + "description": "Machine-readable failure reason. Observed values include `invalid_request`, `variable_invalid`, `panel_missing`, `field_missing`, `datasource_permission_denied`, `timeout`, `panel_deadline`, `panel_canceled`, `canceled`, `overloaded`, `source_too_large`, `edge_unavailable`, `edge_upgrade_required`, `edge_version_unknown`, `mixed_edge_versions` and `internal`." + }, + "message": { + "type": "string", + "description": "Human-readable detail for the failure." + } + }, + "required": [ + "reason", + "message" + ] + }, + "DashboardRuntimeDatasource": { + "type": "object", + "description": "The datasource a runtime query was bound to.", + "properties": { + "id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Datasource ID." + }, + "type": { + "type": "string", + "pattern": "^[a-z][a-z0-9_]{0,63}$", + "description": "Datasource type identifier." + }, + "name": { + "type": "string", + "description": "Datasource name." + } + }, + "required": [ + "id", + "type", + "name" + ] + }, + "DashboardResolvedVariable": { + "type": "object", + "description": "One resolved variable. An unreachable datasource, a bad expression or an empty result leaves `candidates` incomplete and fills `error` instead of failing the request.", + "properties": { + "name": { + "type": "string", + "pattern": "^[A-Za-z_][A-Za-z0-9_]{0,63}$", + "description": "Variable name." + }, + "kind": { + "type": "string", + "enum": [ + "datasource", + "custom", + "query" + ], + "description": "Variable kind: `datasource` = selects a datasource; `custom` = fixed inline list; `query` = resolved by running a query." + }, + "candidates": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardCandidate" + }, + "description": "Resolved candidates, at most 1000." + }, + "selection": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "datasource": { + "$ref": "#/components/schemas/DashboardRuntimeDatasource" + }, + "error": { + "$ref": "#/components/schemas/DashboardRuntimeError" + } + }, + "required": [ + "name", + "kind", + "candidates" + ] + }, + "DashboardVariablesResolveRequest": { + "type": "object", + "description": "Resolve every variable of a stored dashboard against a time range and the caller's current selections.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "variables": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections already made, keyed by variable name, at most 20 entries. Variables omitted here fall back to their stored defaults." + } + }, + "required": [ + "dashboard_id", + "time", + "variables" + ] + }, + "DashboardVariablesResolveResponse": { + "type": "object", + "description": "Resolved variables plus the effective selection for each name.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the resolution ran against." + }, + "variables": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardResolvedVariable" + }, + "description": "Resolved variables, in definition order." + }, + "selections": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Effective selections keyed by variable name; only variables that resolved successfully appear." + } + }, + "required": [ + "dashboard_id", + "revision", + "variables", + "selections" + ] + }, + "DashboardResolvedQuery": { + "type": "object", + "description": "One query bound to a concrete datasource with its variables substituted.", + "properties": { + "ref_id": { + "type": "string", + "pattern": "^[A-Z]$", + "description": "Panel-local query reference." + }, + "datasource": { + "$ref": "#/components/schemas/DashboardRuntimeDatasource" + }, + "mode": { + "type": "string", + "enum": [ + "range", + "instant", + "window" + ], + "description": "Evaluation mode: `range` = a stepped time series; `instant` = a single point in time; `window` = raw rows inside a bounded time window." + }, + "expr": { + "type": "string", + "description": "Expression with variable templates substituted." + }, + "args": { + "type": "object", + "additionalProperties": { + "type": "string" + }, + "description": "Query arguments; empty object when none." + }, + "min_step_seconds": { + "type": [ + "integer", + "null" + ], + "format": "int64", + "minimum": 1, + "description": "Minimum step in seconds; null when unset." + } + }, + "required": [ + "ref_id", + "datasource", + "mode", + "expr", + "args" + ] + }, + "DashboardResolvedPanelQueries": { + "type": "object", + "description": "Per-panel resolution result. `state` is `success` when every query resolved, `partial` when some did and `error` when none did.", + "properties": { + "panel_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Panel ID." + }, + "state": { + "type": "string", + "enum": [ + "success", + "partial", + "error" + ], + "description": "Aggregate state of the panel's queries: `success` = every query resolved; `partial` = some resolved; `error` = none resolved." + }, + "queries": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardResolvedQuery" + }, + "description": "Successfully resolved queries." + }, + "error": { + "$ref": "#/components/schemas/DashboardRuntimeError" + } + }, + "required": [ + "panel_id", + "state", + "queries" + ] + }, + "DashboardQueriesResolveRequest": { + "type": "object", + "description": "Resolve the queries of selected panels without executing them, so a client can preview datasource binding and variable substitution.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "panel_ids": { + "type": "array", + "items": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$" + }, + "minItems": 1, + "maxItems": 100, + "description": "Panels to resolve, 1–100 unique IDs. A panel that does not exist yields an `error` arm rather than failing the call." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "variables": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections keyed by variable name, at most 20 entries." + } + }, + "required": [ + "dashboard_id", + "panel_ids", + "time", + "variables" + ] + }, + "DashboardQueriesResolveResponse": { + "type": "object", + "description": "One entry per requested panel, in request order.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the resolution ran against." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "variables": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections that resolved successfully." + }, + "panels": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardResolvedPanelQueries" + }, + "description": "Per-panel results." + } + }, + "required": [ + "dashboard_id", + "revision", + "time", + "variables", + "panels" + ] + }, + "DashboardPanelRunBudget": { + "type": "object", + "description": "Execution accounting for a panel run.", + "properties": { + "max_concurrency": { + "type": "integer", + "minimum": 1, + "description": "Concurrency cap applied to the panel's queries." + }, + "execution_count": { + "type": "integer", + "minimum": 0, + "description": "Number of queries launched." + } + }, + "required": [ + "max_concurrency", + "execution_count" + ] + }, + "DashboardPanelRunRef": { + "type": "object", + "description": "Result of one query inside a panel run. The raw execution payload differs per datasource type and is passed through unmodified, so it is not schema-constrained here.", + "properties": { + "ref_id": { + "type": "string", + "pattern": "^[A-Z]$", + "description": "Panel-local query reference." + }, + "state": { + "type": "string", + "enum": [ + "success", + "error", + "incompatible" + ], + "description": "Per-query execution state: `success` = the query executed; `error` = the query failed; `incompatible` = the datasource accepted the call but the query mode or field selection does not fit the datasource type." + }, + "child_request_id": { + "type": "string", + "description": "Request ID of the underlying datasource execution; use it when tracing a single query." + }, + "execution": { + "type": "object", + "additionalProperties": true, + "description": "Datasource-specific execution payload, passed through unmodified." + }, + "error": { + "$ref": "#/components/schemas/DashboardRuntimeError" + } + }, + "required": [ + "ref_id", + "state" + ] + }, + "DashboardPanelRunRequest": { + "type": "object", + "description": "Execute one panel against the stored dashboard. Omit `revision` to run the current revision; send it to have stale responses rejected.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Canonical UUIDv7 of the dashboard." + }, + "panel_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Panel to execute." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision guard; when set it must equal the current revision." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "variables": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections keyed by variable name, at most 20 entries." + }, + "max_data_points": { + "type": [ + "integer", + "null" + ], + "minimum": 2, + "maximum": 5000, + "description": "Downsampling target, 2–5000 points; omit or send null for the server default of 100." + } + }, + "required": [ + "dashboard_id", + "panel_id", + "time", + "variables" + ] + }, + "DashboardPanelRunResponse": { + "type": "object", + "description": "Panel execution result. `run_state` aggregates the per-query states: `success` when all succeeded, `partial` when some did, otherwise `incompatible`, `cancelled` or `error`. The total response is capped at 8 MiB.", + "properties": { + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Dashboard ID." + }, + "panel_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Panel ID." + }, + "revision": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Revision the run executed against." + }, + "run_state": { + "type": "string", + "enum": [ + "success", + "partial", + "incompatible", + "cancelled", + "error" + ], + "description": "Aggregate state of the run: `success` = all queries succeeded; `partial` = some succeeded; `incompatible` = at least one query is incompatible with its datasource; `cancelled` = the run was cancelled; `error` = all queries failed." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "variables": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections that resolved successfully." + }, + "refs": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardPanelRunRef" + }, + "description": "One entry per query in the panel." + }, + "display": { + "$ref": "#/components/schemas/DashboardVizConfig" + }, + "budget": { + "$ref": "#/components/schemas/DashboardPanelRunBudget" + } + }, + "required": [ + "dashboard_id", + "panel_id", + "revision", + "run_state", + "time", + "variables", + "refs", + "display", + "budget" + ] + }, + "DashboardDraftContext": { + "type": "object", + "description": "Where an unsaved draft panel or variable set belongs. `existing` targets a stored dashboard, `new` a folder that does not contain one yet — the two are mutually exclusive.", + "properties": { + "kind": { + "type": "string", + "enum": [ + "existing", + "new" + ], + "description": "Draft context kind: `existing` = targets a stored dashboard (`dashboard_id` required); `new` = a folder that does not contain one yet (`folder_id` required)." + }, + "dashboard_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Required for `existing`, forbidden for `new`." + }, + "folder_id": { + "type": "integer", + "format": "uint64", + "minimum": 1, + "description": "Required for `new`, forbidden for `existing`." + } + }, + "required": [ + "kind" + ] + }, + "DashboardVariablesPreviewRequest": { + "type": "object", + "description": "Resolve a draft set of variables that is not stored in any dashboard yet.", + "properties": { + "context": { + "$ref": "#/components/schemas/DashboardDraftContext" + }, + "variables": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardVariable" + }, + "maxItems": 20, + "description": "Draft variables, at most 20." + }, + "selections": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections keyed by variable name, at most 20 entries." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + } + }, + "required": [ + "context", + "variables", + "selections", + "time" + ] + }, + "DashboardVariablesPreviewResponse": { + "type": "object", + "description": "Resolved draft variables. There is no `dashboard_id` because nothing is persisted.", + "properties": { + "variables": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardResolvedVariable" + }, + "description": "Resolved variables." + }, + "selections": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Effective selections keyed by variable name." + } + }, + "required": [ + "variables", + "selections" + ] + }, + "DashboardPanelPreviewRequest": { + "type": "object", + "description": "Execute a draft panel inline, without saving a dashboard revision. Subject to the same 1 MiB definition-size ceiling.", + "properties": { + "context": { + "$ref": "#/components/schemas/DashboardDraftContext" + }, + "panel": { + "$ref": "#/components/schemas/DashboardPanel" + }, + "variables": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardVariable" + }, + "maxItems": 20, + "description": "Draft variables the panel may reference." + }, + "selections": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections keyed by variable name." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "max_data_points": { + "type": [ + "integer", + "null" + ], + "minimum": 2, + "maximum": 5000, + "description": "Downsampling target, 2–5000 points." + } + }, + "required": [ + "context", + "panel", + "variables", + "selections", + "time" + ] + }, + "DashboardPanelPreviewResponse": { + "type": "object", + "description": "Draft panel execution result. Same shape as a stored panel run, minus the dashboard identity.", + "properties": { + "panel_id": { + "type": "string", + "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$", + "description": "Panel ID." + }, + "run_state": { + "type": "string", + "enum": [ + "success", + "partial", + "incompatible", + "cancelled", + "error" + ], + "description": "Aggregate state of the run: `success` = all queries succeeded; `partial` = some succeeded; `incompatible` = at least one query is incompatible with its datasource; `cancelled` = the run was cancelled; `error` = all queries failed." + }, + "time": { + "$ref": "#/components/schemas/DashboardAbsoluteTimeRange" + }, + "variables": { + "type": "object", + "additionalProperties": { + "$ref": "#/components/schemas/DashboardSelection" + }, + "description": "Selections that resolved successfully." + }, + "refs": { + "type": "array", + "items": { + "$ref": "#/components/schemas/DashboardPanelRunRef" + }, + "description": "One entry per query in the panel." + }, + "display": { + "$ref": "#/components/schemas/DashboardVizConfig" + }, + "budget": { + "$ref": "#/components/schemas/DashboardPanelRunBudget" + } + }, + "required": [ + "panel_id", + "run_state", + "time", + "variables", + "refs", + "display", + "budget" + ] + }, + "FolderItem": { + "type": "object", + "description": "A monitor folder (监控节点). Folders form a tree; `parent_path` is the comma-separated ancestor ID list, so the caller can rebuild the tree and search it client-side.", + "properties": { + "id": { + "type": "integer", + "format": "uint64", + "description": "Folder ID." + }, + "account_id": { + "type": "integer", + "format": "uint64", + "description": "Owning account ID." + }, + "parent_id": { + "type": "integer", + "format": "uint64", + "description": "Parent folder ID; 0 at the root." + }, + "parent_path": { + "type": "string", + "description": "Comma-separated ancestor IDs from the root, excluding this folder; empty at the root." + }, + "team_id": { + "type": "integer", + "format": "uint64", + "description": "Team the folder is scoped to; 0 when account-wide." + }, + "name": { + "type": "string", + "description": "Folder name." + }, + "note": { + "type": "string", + "description": "Free-form note." + }, + "creator_id": { + "type": "integer", + "format": "uint64", + "description": "Member ID of the creator." + }, + "creator_name": { + "type": "string", + "description": "Name of the creator." + }, + "updater_id": { + "type": "integer", + "format": "uint64", + "description": "Member ID of the last updater." + }, + "updater_name": { + "type": "string", + "description": "Name of the last updater." + }, + "created_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + }, + "updated_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds." + } + }, + "required": [ + "id", + "account_id", + "parent_id", + "parent_path", + "team_id", + "name", + "note", + "creator_id", + "creator_name", + "updater_id", + "updater_name", + "created_at", + "updated_at" + ] + }, + "IntegrationTypeListRequest": { + "type": "object", + "description": "Filter parameters for listing integration types.", + "properties": { + "p": { + "type": "integer", + "minimum": 1, + "default": 1, + "description": "Page number, 1-based." + }, + "limit": { + "type": "integer", + "minimum": 1, + "maximum": 100, + "default": 20, + "description": "Page size. Defaults to 20, maximum 100." + }, + "orderby": { + "type": "string", + "description": "Sort field. When omitted, types are returned in console ranking order.", + "enum": [ + "id", + "created_at", + "updated_at", + "name", + "type" + ] + }, + "category": { + "type": "string", + "description": "Filter by category. Accepts a comma-separated list, for example `event.alert,event.change`." + }, + "asc": { + "type": [ + "boolean", + "null" + ], + "default": true, + "description": "Sort ascending when `true` (the default); descending when `false`." + } + } + }, + "IntegrationTypeItem": { + "type": "object", + "description": "An integration type the account can configure.", + "required": [ + "plugin_type", + "plugin_type_name", + "plugin_type_logo_url", + "category", + "status", + "supports_api_create" + ], + "properties": { + "plugin_type": { + "type": "string", + "description": "Type identifier to pass as `plugin_type` when creating an integration.", + "example": "standard.alert" + }, + "plugin_type_name": { + "type": "string", + "description": "Display name of the type.", + "example": "Standard Alert" + }, + "plugin_type_logo_url": { + "type": "string", + "description": "Logo URL of the type." + }, + "category": { + "type": "string", + "description": "Category the type belongs to: `event.alert` alert events, `event.change` change events, `im` IM bots, `webhook` custom webhooks.", + "enum": [ + "event.alert", + "event.change", + "im", + "webhook" + ] + }, + "status": { + "type": "string", + "description": "Platform status of the type." + }, + "supports_api_create": { + "type": "boolean", + "description": "Whether `POST /integration/create` accepts this type." + } + } + }, + "ListIntegrationTypesResponse": { + "type": "object", + "description": "A page of integration types.", + "required": [ + "p", + "limit", + "total", + "items" + ], + "properties": { + "p": { + "type": "integer", + "description": "Page number echoed back." + }, + "limit": { + "type": "integer", + "description": "Page size echoed back." + }, + "total": { + "type": "integer", + "format": "int64", + "description": "Total number of matching types." + }, + "items": { + "type": "array", + "description": "Integration types on the current page.", + "items": { + "$ref": "#/components/schemas/IntegrationTypeItem" + } + } + } + }, + "ListIntegrationsRequest": { + "type": "object", + "description": "Filter parameters for listing integrations.", + "properties": { + "p": { + "type": "integer", + "minimum": 1, + "default": 1, + "description": "Page number, 1-based." + }, + "limit": { + "type": "integer", + "minimum": 1, + "maximum": 100, + "default": 100, + "description": "Page size. Defaults to 100, maximum 100." + }, + "orderby": { + "type": "string", + "description": "Sort field. Defaults to `created_at`; `plugin_type` is sorted by the underlying plugin.", + "enum": [ + "created_at", + "updated_at", + "name", + "plugin_type", + "status" + ] + }, + "category": { + "type": "string", + "description": "Filter by category. Accepts a comma-separated list." + }, + "type": { + "type": "string", + "description": "Deprecated. Merged into `plugin_type` when both are set." + }, + "plugin_type": { + "type": "string", + "description": "Filter by integration type. Accepts a comma-separated list." + }, + "status": { + "type": "string", + "description": "Filter by status. Accepts a comma-separated list." + }, + "name": { + "type": "string", + "description": "Filter by integration name." + }, + "ref_ids": { + "type": "array", + "description": "Filter by source reference IDs. Each value must start with `c_` (channel), `a_` (account) or `w_`.", + "items": { + "type": "string" + } + }, + "asc": { + "type": "boolean", + "description": "Sort ascending when true, descending when false." + }, + "is_my_team": { + "type": "boolean", + "description": "Limit the result to integrations owned by your teams." + }, + "team_ids": { + "type": "array", + "description": "Filter by team IDs. With `is_my_team`, the values narrow that set further.", + "items": { + "type": "integer", + "format": "int64" + } + } + } + }, + "IntegrationItem": { + "type": "object", + "description": "A configured integration. Timestamps are Unix epoch seconds.", + "required": [ + "integration_id", + "team_id", + "plugin_type", + "plugin_type_name", + "category", + "name", + "description", + "status", + "ref_id", + "created_at", + "updated_at", + "last_time" + ], + "properties": { + "integration_id": { + "type": "integer", + "format": "int64", + "description": "Integration ID." + }, + "team_id": { + "type": "integer", + "format": "int64", + "description": "ID of the team that owns the integration. `0` when it is not assigned to a team." + }, + "plugin_type": { + "type": "string", + "description": "Integration type, for example `standard.alert` or `zabbix.alert`." + }, + "plugin_type_name": { + "type": "string", + "description": "Display name of the integration type, in the language of the request." + }, + "category": { + "type": "string", + "enum": [ + "event.alert", + "event.change", + "im", + "webhook" + ], + "description": "Category the integration belongs to: `event.alert` alert events, `event.change` change events, `im` IM bots, `webhook` custom webhooks." + }, + "name": { + "type": "string", + "description": "Integration name." + }, + "description": { + "type": "string", + "description": "Free-form description." + }, + "status": { + "type": "string", + "enum": [ + "enabled", + "disabled" + ], + "description": "Lifecycle status: `enabled` while the integration accepts events, `disabled` when it is paused." + }, + "ref_id": { + "type": "string", + "description": "Source reference ID: `a_`-prefixed for an account-scoped integration, `c_`-prefixed when it is shared into a channel, `w_`-prefixed on legacy workspace-scoped integrations." + }, + "created_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds when the integration was created." + }, + "updated_at": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds when the integration was last updated." + }, + "last_time": { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds of the most recent event received. `0` when no event has arrived yet." + } + } + }, + "ListIntegrationsResponse": { + "type": "object", + "description": "A page of integrations.", + "required": [ + "p", + "limit", + "total", + "items" + ], + "properties": { + "p": { + "type": "integer", + "description": "Page number echoed back." + }, + "limit": { + "type": "integer", + "description": "Page size echoed back." + }, + "total": { + "type": "integer", + "format": "int64", + "description": "Total number of matching integrations." + }, + "items": { + "type": "array", + "description": "Integrations on the current page.", + "items": { + "$ref": "#/components/schemas/IntegrationItem" + } + } + } + }, + "GetIntegrationRequest": { + "type": "object", + "description": "Identifies one integration.", + "required": [ + "integration_id" + ], + "properties": { + "integration_id": { + "type": "integer", + "format": "int64", + "minimum": 1, + "description": "Integration ID.", + "example": 6113996590131 + } + } + }, + "IntegrationDetail": { + "type": "object", + "description": "A single integration with its full settings. Timestamps are Unix epoch seconds.", + "required": [ + "integration_id", + "team_id", + "plugin_type", + "plugin_type_name", + "category", + "name", + "description", + "status", + "ref_id", + "created_at", + "updated_at", + "last_time", + "settings" + ], + "properties": { + "integration_id": [ + { + "type": "integer", + "format": "int64", + "description": "Integration ID." + }, + true + ], + "team_id": [ + { + "type": "integer", + "format": "int64", + "description": "ID of the team that owns the integration. `0` when it is not assigned to a team." + }, + true + ], + "plugin_type": [ + { + "type": "string", + "description": "Integration type, for example `standard.alert` or `zabbix.alert`." + }, + true + ], + "plugin_type_name": [ + { + "type": "string", + "description": "Display name of the integration type, in the language of the request." + }, + true + ], + "category": [ + { + "type": "string", + "enum": [ + "event.alert", + "event.change", + "im", + "webhook" + ], + "description": "Category the integration belongs to." + }, + true + ], + "name": [ + { + "type": "string", + "description": "Integration name." + }, + true + ], + "description": [ + { + "type": "string", + "description": "Free-form description." + }, + true + ], + "status": [ + { + "type": "string", + "enum": [ + "enabled", + "disabled" + ], + "description": "Lifecycle status: `enabled` while the integration accepts events, `disabled` when it is paused." + }, + true + ], + "ref_id": [ + { + "type": "string", + "description": "Source reference ID: `a_`-prefixed for an account-scoped integration, `c_`-prefixed when it is shared into a channel." + }, + true + ], + "created_at": [ + { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds when the integration was created." + }, + true + ], + "updated_at": [ + { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds when the integration was last updated." + }, + true + ], + "last_time": [ + { + "type": "integer", + "format": "int64", + "description": "Unix timestamp in seconds of the most recent event received. `0` when no event has arrived yet." + }, + true + ], + "settings": { + "type": "object", + "additionalProperties": true, + "description": "Type-specific configuration. Sensitive values (endpoint, headers, secrets, passwords) are returned masked as `******`." + } + } + }, + "CreateIntegrationRequest": { + "type": "object", + "description": "Payload for creating an integration.", + "required": [ + "plugin_type" + ], + "properties": { + "plugin_type": { + "type": "string", + "description": "Integration type. Must be one listed by `POST /integration/type/list` with `supports_api_create: true`.", + "example": "standard.alert" + }, + "name": { + "type": "string", + "minLength": 2, + "maxLength": 49, + "description": "Integration name. 2–49 characters.", + "example": "Prod metrics alerts" + }, + "description": { + "type": "string", + "maxLength": 499, + "description": "Free-form description, at most 499 characters." + }, + "team_id": { + "type": "integer", + "format": "int64", + "minimum": 1, + "description": "Owning team ID.", + "example": 1467226103121 + }, + "settings": { + "type": "object", + "description": "Type-specific configuration; the accepted keys depend on `plugin_type`.", + "additionalProperties": true + } + } + }, + "CreateIntegrationResponse": { + "type": "object", + "description": "The created integration and its key.", + "required": [ + "integration_id", + "integration_key" + ], + "properties": { + "integration_id": { + "type": "integer", + "format": "int64", + "description": "ID of the new integration.", + "example": 6113996590131 + }, + "integration_key": { + "type": "string", + "description": "Key used to authenticate inbound pushes to this integration. Returned here only; fetch a new one with `POST /integration/key/rotate`.", + "example": "9f2c7d1b45a86e30f7b1c9d4a2e65738123" + } + } + }, + "UpdateIntegrationRequest": { + "type": "object", + "description": "Payload for updating an integration. Only the fields you send are changed.", + "required": [ + "integration_id" + ], + "properties": { + "integration_id": { + "type": "integer", + "format": "int64", + "minimum": 1, + "description": "Integration ID.", + "example": 6113996590131 + }, + "name": { + "type": [ + "string", + "null" + ], + "minLength": 2, + "maxLength": 49, + "description": "New name, 2–49 characters." + }, + "description": { + "type": [ + "string", + "null" + ], + "maxLength": 499, + "description": "New description, at most 499 characters." + }, + "team_id": { + "type": [ + "integer", + "null" + ], + "format": "int64", + "minimum": 0, + "description": "New owning team ID; `0` clears the team assignment." + }, + "settings": { + "type": [ + "object", + "null" + ], + "description": "Replacement configuration for the integration type. Sensitive entries left out, or sent back as the masked `******`, keep their stored value.", + "additionalProperties": true + } + } + }, + "IntegrationLifecycleRequest": { + "type": "object", + "description": "Identifies the integration to act on.", + "required": [ + "integration_id" + ], + "properties": { + "integration_id": { + "type": "integer", + "format": "int64", + "minimum": 1, + "description": "Integration ID.", + "example": 6113996590131 + } + } + }, + "RotateIntegrationKeyResponse": { + "type": "object", + "description": "The newly issued integration key.", + "required": [ + "integration_key" + ], + "properties": { + "integration_key": { + "type": "string", + "description": "The new key. The previous key stops working immediately; this value cannot be read again later.", + "example": "9f2c7d1b45a86e30f7b1c9d4a2e65738123" + } + } + } + }, + "securitySchemes": { + "AppKeyAuth": { + "description": "App key issued from the Flashduty console under Account → APP Keys. Required on every public API call. Keep it secret — it grants the same access as the owning account.", + "in": "query", + "name": "app_key", + "type": "apiKey" + }, + "AutomationTriggerBearerAuth": { + "description": "Bearer token generated for one Automation HTTP POST trigger. This is not an app_key.", + "scheme": "bearer", + "type": "http" + } + } + }, + "info": { + "description": "Public HTTP API for the Flashduty incident management platform — incidents, notification templates, channels, schedules, monitors, RUM, and platform administration. Every operation is authenticated with an `app_key` query parameter issued from the Flashduty console under Account → APP Keys. Responses follow a uniform envelope: `{ request_id, data }` on success, `{ request_id, error }` on failure.", + "title": "Flashduty Open API", + "version": "1.0.0" + }, + "openapi": "3.1.0", + "paths": { + "/account/info": { + "post": { + "description": "Return the current account's profile and settings.", + "operationId": "account-read-info", + "requestBody": { + "content": { + "application/json": { + "example": {}, + "schema": { + "type": "object" + } + } + } + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "account_id": 1001, + "account_name": "acme", + "avatar": "https://cdn.flashcat.cloud/avatar/acme.png", + "country_code": "CN", + "created_at": 1716960000, + "domain": "acme", + "email": "ops@acme.example", + "extra_domains": [ + "acme-corp" + ], + "locale": "zh-CN", + "phone": "138****8000", + "restrictions": { + "allow_subdomain": true, + "email_domains": [ + "acme.example" + ], + "ips": [ + "203.0.113.0/24" + ] + }, + "time_zone": "Asia/Shanghai" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AccountInfo" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Get account detail", + "tags": [ + "Platform/Account" + ], + "x-mint": { + "content": "| Permission | Description |\n| --- | --- |\n| None | None — any valid app_key can call this operation. |\n\nFind this operation in the [Platform API reference](/en/api-reference/platform/account/account-read-info).", + "href": "/en/api-reference/platform/account/account-read-info", + "metadata": { + "sidebarTitle": "Get account detail" + } + } + } + }, + "/alert-event/list": { + "post": { + "description": "Return a cursor-paginated list of raw alert events across all alerts, with filtering by integration, channel, time range, and severity.", + "operationId": "alert-event-read-list", + "requestBody": { + "content": { + "application/json": { + "example": { + "end_time": 1712707200, + "limit": 20, + "severities": "Critical", + "start_time": 1712620800 + }, + "schema": { + "$ref": "#/components/schemas/AlertEventGlobalListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "has_next_page": false, + "items": [ + { + "alert_id": "663a1b2c3d4e5f6789abcdef", + "event_id": "663a1b2c3d4e5f6789abc001", + "event_severity": "Critical", + "event_time": 1712650000, + "title": "CPU usage > 90%" + } + ], + "total": 1 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertEventGlobalListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List raw alert events", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Results are filtered by the caller's channel data-access permissions.\n- `severities` is a comma-separated string, e.g. `\"Critical,Warning\"`.", + "href": "/en/api-reference/on-call/alerts/alert-event-read-list", + "metadata": { + "sidebarTitle": "List raw alert events" + } + } + } + }, + "/alert/event/list": { + "post": { + "description": "Return raw events for an alert with cursor or page-number pagination.", + "operationId": "alert-read-event-list", + "requestBody": { + "content": { + "application/json": { + "example": { + "alert_id": "663a1b2c3d4e5f6789abcdef", + "limit": 20 + }, + "schema": { + "$ref": "#/components/schemas/AlertEventListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "has_next_page": true, + "items": [ + { + "alert_id": "663a1b2c3d4e5f6789abcdef", + "event_id": "663a1b2c3d4e5f6789abc001", + "event_severity": "Critical", + "event_status": "Critical", + "event_time": 1712650000, + "labels": { + "host": "web-01" + }, + "title": "CPU usage > 90%" + } + ], + "search_after_ctx": "663a1b2c3d4e5f6789abc001", + "total": 57 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertEventListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List events for an alert", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Results are newest-first by default. Set `asc=true` to read events oldest-first.\n- Use `limit` with `search_after_ctx` from the previous response to fetch the next page.\n- Classic page-number pagination is also supported with `p`, but `p * limit` must stay within 10,000 records.\n- Each alert can accumulate a large raw event history; prefer cursor pagination for hot alerts.", + "href": "/en/api-reference/on-call/alerts/alert-read-event-list", + "metadata": { + "sidebarTitle": "List events for an alert" + } + } + } + }, + "/alert/feed": { + "post": { + "description": "Return the activity feed (comments, state changes, merges, silence events) for a single alert, with page-based pagination.", + "operationId": "alert-read-feed", + "requestBody": { + "content": { + "application/json": { + "example": { + "alert_id": "663a1b2c3d4e5f6789abcdef", + "asc": false, + "limit": 20 + }, + "schema": { + "$ref": "#/components/schemas/AlertFeedRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "has_next_page": false, + "items": [ + { + "created_at": 1712651000, + "creator_id": 80011, + "detail": { + "comment": "Investigating now." + }, + "ref_id": "663a1b2c3d4e5f6789abcdef", + "type": "a_comm" + } + ] + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertFeedResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List alert activity feed", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Use `p` (page number, starting at 1) and `limit` (max 100, default 20) for pagination.\n- Set `asc` to `true` for chronological order.\n- Use `types` to filter by specific feed types (e.g. `a_comm`, `a_merge`).", + "href": "/en/api-reference/on-call/alerts/alert-read-feed", + "metadata": { + "sidebarTitle": "List alert activity feed" + } + } + } + }, + "/alert/info": { + "post": { + "description": "Return the full details of a single alert by its ID, including its associated incident and event count.", + "operationId": "alert-read-info", + "requestBody": { + "content": { + "application/json": { + "example": { + "alert_id": "663a1b2c3d4e5f6789abcdef" + }, + "schema": { + "$ref": "#/components/schemas/AlertInfoRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "alert_id": "663a1b2c3d4e5f6789abcdef", + "alert_severity": "Critical", + "alert_status": "Critical", + "event_cnt": 3, + "start_time": 1712650000, + "title": "CPU usage > 90%" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertItem" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Get alert detail", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- `alert_id` is an ObjectID hex string returned by `POST /alert/list` or `POST /alert-event/list`.", + "href": "/en/api-reference/on-call/alerts/alert-read-info", + "metadata": { + "sidebarTitle": "Get alert detail" + } + } + } + }, + "/alert/list": { + "post": { + "description": "Return a cursor-paginated list of alerts matching the given filters.", + "operationId": "alert-read-list", + "requestBody": { + "content": { + "application/json": { + "example": { + "end_time": 1712707200, + "is_active": true, + "limit": 20, + "start_time": 1712620800 + }, + "schema": { + "$ref": "#/components/schemas/AlertListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "has_next_page": false, + "items": [ + { + "account_id": 10023, + "alert_id": "663a1b2c3d4e5f6789abcdef", + "alert_severity": "Critical", + "alert_status": "Critical", + "channel_id": 20001, + "channel_name": "Production", + "created_at": 1712650000, + "end_time": 0, + "event_cnt": 3, + "ever_muted": false, + "integration_id": 10001, + "integration_name": "Prometheus", + "integration_type": "prometheus", + "labels": { + "host": "web-01" + }, + "last_time": 1712655000, + "start_time": 1712650000, + "title": "CPU usage > 90%", + "updated_at": 1712655000 + } + ], + "total": 1 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List alerts", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Both `start_time` and `end_time` are required Unix epoch seconds. Maximum span is 31 days.\n- Use `search_after_ctx` from the previous response to fetch the next page.\n- Results are filtered by the caller's channel data-access permissions.\n- Set `is_active` to `true` to retrieve only active (firing) alerts; `false` to retrieve resolved alerts.", + "href": "/en/api-reference/on-call/alerts/alert-read-list", + "metadata": { + "sidebarTitle": "List alerts" + } + } + } + }, + "/alert/list-by-ids": { + "post": { + "description": "Return the details of multiple alerts by their IDs in a single request. Note: this endpoint does not paginate — `total` and `has_next_page` are always `0`/`false` and `search_after_ctx` is never set.", + "operationId": "alert-read-list-by-ids", + "requestBody": { + "content": { + "application/json": { + "example": { + "alert_ids": [ + "663a1b2c3d4e5f6789abcdef" + ] + }, + "schema": { + "$ref": "#/components/schemas/AlertListByIDsRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "has_next_page": false, + "items": [ + { + "alert_id": "663a1b2c3d4e5f6789abcdef", + "title": "CPU usage > 90%" + } + ], + "total": 0 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List alerts by IDs", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- All provided `alert_ids` must belong to the caller's account; any invalid ID causes the entire request to fail.", + "href": "/en/api-reference/on-call/alerts/alert-read-list-by-ids", + "metadata": { + "sidebarTitle": "List alerts by IDs" + } + } + } + }, + "/alert/merge": { + "post": { + "description": "Associate one or more alerts with an existing incident. If a source alert previously belonged to a different incident and that incident becomes empty after the merge, it will be automatically closed.", + "operationId": "alert-write-merge", + "requestBody": { + "content": { + "application/json": { + "example": { + "alert_ids": [ + "663a1b2c3d4e5f6789abcdef" + ], + "incident_id": "663a000000000000deadbeef" + }, + "schema": { + "$ref": "#/components/schemas/AlertMergeRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Merge alerts into an incident", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- All `alert_ids` and the `incident_id` must belong to the caller's account.\n- Optionally set `title` and `owner_id` to update the target incident at the same time.", + "href": "/en/api-reference/on-call/alerts/alert-write-merge", + "metadata": { + "sidebarTitle": "Merge alerts into an incident" + } + } + } + }, + "/alert/pipeline/info": { + "post": { + "description": "Return the alert processing pipeline configured for a specific integration.", + "operationId": "alert-read-pipeline-info", + "requestBody": { + "content": { + "application/json": { + "example": { + "integration_id": 10001 + }, + "schema": { + "$ref": "#/components/schemas/AlertPipelineInfoRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "created_at": 1710000000, + "creator_id": 80011, + "integration_id": 10001, + "rules": [ + { + "if": [ + { + "key": "labels.env", + "oper": "IN", + "vals": [ + "prod" + ] + } + ], + "kind": "title_reset", + "settings": { + "title": "[TPL]{{.Labels.service}} / {{.Labels.check}}" + } + }, + { + "if": null, + "kind": "severity_reset", + "settings": { + "severity": "Warning" + } + } + ], + "status": "enabled", + "updated_at": 1712000000, + "updated_by": 80011 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertPipelineItem" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Get alert pipeline", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) |\n\n## Usage\n\n- Returns `null` data if no pipeline has been configured for the given integration.\n- Requires the caller to have access to the integration.", + "href": "/en/api-reference/on-call/alerts/alert-read-pipeline-info", + "metadata": { + "sidebarTitle": "Get alert pipeline" + } + } + } + }, + "/alert/pipeline/list": { + "post": { + "description": "Return the alert processing pipelines configured for multiple integrations.", + "operationId": "alert-read-pipeline-list", + "requestBody": { + "content": { + "application/json": { + "example": { + "integration_ids": [ + 10001, + 10002 + ] + }, + "schema": { + "$ref": "#/components/schemas/AlertPipelineListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "items": [ + { + "created_at": 1710000000, + "creator_id": 80011, + "integration_id": 10001, + "rules": [ + { + "if": [ + { + "key": "labels.cluster", + "oper": "IN", + "vals": [ + "prod-cn" + ] + } + ], + "kind": "alert_inhibit", + "settings": { + "equals": [ + "service" + ], + "source_filters": [ + { + "key": "alert_severity", + "oper": "IN", + "vals": [ + "Critical" + ] + } + ] + } + } + ], + "status": "enabled", + "updated_at": 1712000000, + "updated_by": 80011 + } + ] + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertPipelineListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List alert pipelines", + "tags": [ + "On-call/Alerts" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) |\n\n## Usage\n\n- All `integration_ids` must be accessible to the caller.", + "href": "/en/api-reference/on-call/alerts/alert-read-pipeline-list", + "metadata": { + "sidebarTitle": "List alert pipelines" + } + } + } + }, + "/alert/pipeline/upsert": { + "post": { + "description": "Set the alert processing pipeline for an integration. Replaces the existing configuration entirely.", + "operationId": "alert-write-pipeline-upsert", + "requestBody": { + "content": { + "application/json": { + "example": { + "integration_id": 10001, + "rules": [ + { + "if": [ + { + "key": "labels.env", + "oper": "IN", + "vals": [ + "prod" + ] + } + ], + "kind": "title_reset", + "settings": { + "title": "[TPL]{{.Labels.service}} / {{.Labels.check}}" + } + }, + { + "if": null, + "kind": "severity_reset", + "settings": { + "severity": "Warning" + } + } + ] + }, + "schema": { + "$ref": "#/components/schemas/AlertPipelineUpsertRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": null, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Create or update alert pipeline", + "tags": [ "On-call/Alerts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Use `p` (page number, starting at 1) and `limit` (max 100, default 20) for pagination.\n- Set `asc` to `true` for chronological order.\n- Use `types` to filter by specific feed types (e.g. `a_comm`, `a_merge`).", - "href": "/en/api-reference/on-call/alerts/alert-read-feed", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- Maximum 50 rules per pipeline.\n- Each rule has a `kind` (one of `title_reset`, `description_reset`, `severity_reset`, `alert_drop`, `alert_inhibit`), an optional `if` filter, and `settings` specific to the kind.\n- The `alert_inhibit` kind requires the Standard license or higher.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alerts/alert-write-pipeline-upsert", + "metadata": { + "sidebarTitle": "Create or update alert pipeline" + } + } + } + }, + "/audit/operation/list": { + "post": { + "description": "Return all operation names that are recorded in the audit log, for use as `operations` filter values.", + "operationId": "audit-read-operation-list", + "requestBody": { + "content": { + "application/json": { + "example": {}, + "schema": { + "$ref": "#/components/schemas/AuditOperationListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "items": [ + { + "name": "template:write:create", + "name_cn": "创建模板" + }, + { + "name": "template:write:delete", + "name_cn": "删除模板" + }, + { + "name": "incident:write:acknowledge", + "name_cn": "认领故障" + } + ] + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AuditOperationListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List auditable operation types", + "tags": [ + "Platform/Audit logs" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Audit Read** (`organization`) |\n\n## Usage\n\n- Use the `name` values from this response as `operations` filter values in `POST /audit/search`.\n- `name_cn` is the human-readable Chinese label shown in the console; `name` is the stable wire value to filter on.", + "href": "/en/api-reference/platform/audit-logs/audit-read-operation-list", + "metadata": { + "sidebarTitle": "List auditable operation types" + } + } + } + }, + "/audit/search": { + "post": { + "description": "Return a cursor-paginated list of audit log entries within a time range.", + "operationId": "audit-read-search", + "requestBody": { + "content": { + "application/json": { + "example": { + "end_time": 1712707200, + "limit": 20, + "operations": [ + "template:write:create", + "template:write:delete" + ], + "start_time": 1712620800 + }, + "schema": { + "$ref": "#/components/schemas/AuditSearchRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "docs": [ + { + "account_id": 10023, + "body": "{\"template_name\":\"Prod default\"}", + "created_at": 1712700123456, + "credential_id": 0, + "credential_type": "", + "ip": "203.0.113.42", + "is_dangerous": false, + "is_write": true, + "member_id": 80011, + "member_name": "Alice", + "operation": "template:write:create", + "operation_name": "创建模板", + "params": [], + "principal_kind": "member", + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + } + ], + "search_after_ctx": "", + "total": 2 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AuditSearchResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Search audit logs", + "tags": [ + "Platform/Audit logs" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Audit Read** (`organization`) |\n\n## Usage\n\n- Time range is required. Maximum span is 90 days. Both `start_time` and `end_time` are Unix epoch **seconds**.\n- Use `search_after_ctx` from the previous response to fetch the next page. The token is opaque — do not construct it manually.\n- The retention window depends on the account's license. Queries beyond the retention boundary silently return an empty result rather than an error.\n- `limit` accepts 0–99; omitting it (or 0) returns all matching rows in the window with no page-size cap. Rows are returned newest first.", + "href": "/en/api-reference/platform/audit-logs/audit-read-search", + "metadata": { + "sidebarTitle": "Search audit logs" + } + } + } + }, + "/calendar/create": { + "post": { + "description": "Create a personal service calendar. Each account is limited to 5 calendars unless the Flashcat-Break-Cal-Limit header is set.", + "operationId": "calendarCreate", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_name": "Production On-Call Calendar", + "description": "Calendar for production on-call team", + "timezone": "Asia/Shanghai", + "workdays": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "schema": { + "$ref": "#/components/schemas/CalendarCreateRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "cal_name": "API Test Calendar" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalendarCreateResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Create calendar", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/calendars/calendar-create", + "metadata": { + "sidebarTitle": "Create calendar" + } + } + } + }, + "/calendar/delete": { + "post": { + "description": "Delete a personal service calendar. The call fails when referenced by escalation or silence rules.", + "operationId": "calendarDelete", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM" + }, + "schema": { + "$ref": "#/components/schemas/CalendarIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalendarEmptyObject" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Delete calendar", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/calendars/calendar-delete", + "metadata": { + "sidebarTitle": "Delete calendar" + } + } + } + }, + "/calendar/event/delete": { + "post": { + "description": "Delete a calendar event by calendar ID and event ID.", + "operationId": "calEventDelete", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "event_id": "cale.KyG9XWTCU5CucbwukEVBQ4" + }, + "schema": { + "$ref": "#/components/schemas/CalEventIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalendarEmptyObject" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Delete calendar event", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/calendars/cal-event-delete", + "metadata": { + "sidebarTitle": "Delete calendar event" + } + } + } + }, + "/calendar/event/list": { + "post": { + "description": "Return events for a personal calendar within a year/month/day scope. When month and day are both omitted the whole year is returned.", + "operationId": "calEventList", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "month": 5, + "year": 2024 + }, + "schema": { + "$ref": "#/components/schemas/CalEventListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "items": [ + { + "account_id": 2451002751131, + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "created_at": 1775972034, + "creator_id": 2476444212131, + "description": "A test holiday event", + "end_at": "2026-05-02", + "event_id": "cale.KyG9XWTCU5CucbwukEVBQ4", + "is_off": true, + "start_at": "2026-05-01", + "summary": "Test Holiday", + "updated_at": 1775972034 + }, + { + "account_id": 2451002751131, + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "created_at": 0, + "creator_id": 2451002751131, + "description": "", + "end_at": "2026-05-03", + "event_id": "non_work.20260502", + "is_off": true, + "start_at": "2026-05-02", + "summary": "non-working day (Saturday)", + "updated_at": 0 + } + ], + "total": 11 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalEventListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List calendar events", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/calendars/cal-event-list", + "metadata": { + "sidebarTitle": "List calendar events" + } + } + } + }, + "/calendar/event/upsert": { + "post": { + "description": "Create or update a calendar event (holiday or workday override). Omit event_id to create a new event.", + "operationId": "calEventUpsert", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "description": "International Workers Day holiday", + "end_at": "2024-05-06", + "is_off": true, + "start_at": "2024-05-01", + "summary": "Labour Day" + }, + "schema": { + "$ref": "#/components/schemas/CalEventUpsertRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "event_id": "cale.KyG9XWTCU5CucbwukEVBQ4", + "summary": "Test Holiday" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalEventUpsertResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Upsert calendar event", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/calendars/cal-event-upsert", + "metadata": { + "sidebarTitle": "Upsert calendar event" + } + } + } + }, + "/calendar/info": { + "post": { + "description": "Return details of a service calendar.", + "operationId": "calendarInfo", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_id": "cal.eh9gvPtWeH3xXgKeVSRxRg" + }, + "schema": { + "$ref": "#/components/schemas/CalendarIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "account_id": 2451002751131, + "cal_id": "cal.eh9gvPtWeH3xXgKeVSRxRg", + "cal_name": "Stock Exchange Calendar", + "created_at": 1702455630, + "creator_id": 2476444212131, + "description": "A stock market trading calendar example", + "kind": "personal", + "status": "enabled", + "team_id": 2477033058131, + "timezone": "Asia/Shanghai", + "updated_at": 1775529526, + "updated_by": 3790925372131, + "workdays": [ + 0, + 1, + 2, + 3, + 4, + 5, + 6 + ] + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalendarItem" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Get calendar info", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/calendars/calendar-info", + "metadata": { + "sidebarTitle": "Get calendar info" + } + } + } + }, + "/calendar/list": { + "post": { + "description": "Return the list of service calendars visible to the current account.", + "operationId": "calendarList", + "requestBody": { + "content": { + "application/json": { + "example": { + "kind": "personal" + }, + "schema": { + "$ref": "#/components/schemas/CalendarListRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "items": [ + { + "account_id": 2451002751131, + "cal_id": "cal.eh9gvPtWeH3xXgKeVSRxRg", + "cal_name": "Stock Exchange Calendar", + "created_at": 1702455630, + "creator_id": 2476444212131, + "description": "A stock market trading calendar example", + "kind": "personal", + "status": "enabled", + "team_id": 2477033058131, + "timezone": "Asia/Shanghai", + "updated_at": 1775529526, + "updated_by": 3790925372131, + "workdays": [ + 0, + 1, + 2, + 3, + 4, + 5, + 6 + ] + }, + { + "account_id": 2451002751131, + "cal_id": "cal.VZYkchxJhGELSF4jzkUAud", + "cal_name": "HK Stock Exchange Calendar", + "created_at": 1702968470, + "creator_id": 2451002751131, + "description": "Hong Kong Stock Exchange trading days calendar", + "extra_cal_ids": [ + "zh-cn.china.official" + ], + "kind": "personal", + "status": "enabled", + "team_id": 0, + "timezone": "Asia/Shanghai", + "updated_at": 1775188967, + "updated_by": 3790925372131 + } + ], + "total": 8 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalendarListResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List calendars", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/calendars/calendar-list", + "metadata": { + "sidebarTitle": "List calendars" + } + } + } + }, + "/calendar/update": { + "post": { + "description": "Update a personal service calendar. Only non-null fields are updated.", + "operationId": "calendarUpdate", + "requestBody": { + "content": { + "application/json": { + "example": { + "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", + "cal_name": "Production On-Call Calendar (Updated)", + "timezone": "America/New_York", + "workdays": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "schema": { + "$ref": "#/components/schemas/CalendarUpdateRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/CalendarEmptyObject" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Update calendar", + "tags": [ + "On-call/Calendars" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/calendars/calendar-update", + "metadata": { + "sidebarTitle": "Update calendar" + } + } + } + }, + "/change/list": { + "post": { + "description": "Query change records within a time window, with filtering, search, and pagination.", + "operationId": "change-read-list", + "requestBody": { + "content": { + "application/json": { + "example": { + "asc": false, + "end_time": 1717046400, + "include_events": false, + "integration_ids": [ + 362 + ], + "limit": 10, + "orderby": "start_time", + "p": 1, + "start_time": 1716960000 + }, + "schema": { + "$ref": "#/components/schemas/ListChangeRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "has_next_page": false, + "items": [ + { + "account_id": 10001, + "change_id": "664a1b2c3d4e5f6a7b8c9d0e", + "change_key": "deploy-api-server-2311", + "change_status": "Done", + "channel_id": 5001, + "channel_name": "Production", + "channel_status": "enabled", + "description": "Rolling deploy to production cluster", + "end_time": 1716963000, + "integration_id": 362, + "integration_name": "GitHub Deploy", + "labels": { + "env": "prod", + "service": "api-server" + }, + "last_time": 1716962700, + "link": "https://github.com/acme/api-server/actions/runs/123", + "start_time": 1716962400, + "title": "Deploy api-server v2.3.1" + } + ], + "total": 1 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/ListChangeResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "List changes", + "tags": [ + "On-call/Changes" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", + "href": "/en/api-reference/on-call/changes/change-read-list", + "metadata": { + "sidebarTitle": "List changes" + } + } + } + }, + "/channel/create": { + "post": { + "description": "Create a new channel for incident management.", + "operationId": "channelCreate", + "requestBody": { + "content": { + "application/json": { + "example": { + "auto_resolve_mode": "trigger", + "auto_resolve_timeout": 86400, + "channel_name": "Production Alerts", + "description": "Handles all production environment alerts", + "group": { + "method": "p", + "time_window": 10, + "window_type": "tumbling" + }, + "team_id": 3521074710131 + }, + "schema": { + "$ref": "#/components/schemas/CreateChannelRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "channel_id": 6294542005131, + "channel_name": "API Test Channel" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/ChannelCreateResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Create channel", + "tags": [ + "On-call/Channels" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-create", + "metadata": { + "sidebarTitle": "Create channel" + } + } + } + }, + "/channel/delete": { + "post": { + "description": "Delete a channel. Only a `disabled` channel can be deleted; all of its escalation, silence, drop and inhibit rules are deleted with it. The call fails when an integration route still references the channel.", + "operationId": "channelDelete", + "requestBody": { + "content": { + "application/json": { + "example": { + "channel_id": 3521074710131 + }, + "schema": { + "$ref": "#/components/schemas/ChannelIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Delete channel", + "tags": [ + "On-call/Channels" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-delete", + "metadata": { + "sidebarTitle": "Delete channel" + } + } + } + }, + "/channel/disable": { + "post": { + "description": "Disable a channel to stop incident routing without deleting it; a disabled channel discards incoming events. Only an `enabled` channel can be disabled.", + "operationId": "channelDisable", + "requestBody": { + "content": { + "application/json": { + "example": { + "channel_id": 3521074710131 + }, + "schema": { + "$ref": "#/components/schemas/ChannelIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Disable channel", + "tags": [ + "On-call/Channels" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-disable", + "metadata": { + "sidebarTitle": "Disable channel" + } + } + } + }, + "/channel/enable": { + "post": { + "description": "Enable a channel to resume incident routing. Only a `disabled` channel can be enabled.", + "operationId": "channelEnable", + "requestBody": { + "content": { + "application/json": { + "example": { + "channel_id": 3521074710131 + }, + "schema": { + "$ref": "#/components/schemas/ChannelIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Enable channel", + "tags": [ + "On-call/Channels" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-enable", + "metadata": { + "sidebarTitle": "Enable channel" + } + } + } + }, + "/channel/escalate/rule/create": { + "post": { + "description": "Create an escalation rule defining who gets notified and when during an incident.", + "operationId": "channelEscalateRuleCreate", + "requestBody": { + "content": { + "application/json": { + "example": { + "channel_id": 3521074710131, + "description": "Notify primary on-call, then escalate to secondary after 30 minutes", + "layers": [ + { + "escalate_window": 30, + "force_escalate": false, + "max_times": 3, + "notify_step": 10, + "target": { + "by": { + "follow_preference": true + }, + "person_ids": [ + 3790925372131 + ] + } + } + ], + "rule_name": "On-call escalation", + "template_id": "6321aad26c12104586a88916" + }, + "schema": { + "$ref": "#/components/schemas/CreateEscalationRuleRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "rule_id": "69db2f72a0fe7db6448b1506", + "rule_name": "Test escalation rule" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/RuleCreateResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Create escalation rule", + "tags": [ + "On-call/Channels" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-create", + "metadata": { + "sidebarTitle": "Create escalation rule" + } + } + } + }, + "/channel/escalate/rule/delete": { + "post": { + "description": "Delete an escalation rule. Only a `disabled` rule can be deleted.", + "operationId": "channelEscalateRuleDelete", + "requestBody": { + "content": { + "application/json": { + "example": { + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" + }, + "schema": { + "$ref": "#/components/schemas/ChannelRuleIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Delete escalation rule", + "tags": [ + "On-call/Channels" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-delete", "metadata": { - "sidebarTitle": "List alert activity feed" + "sidebarTitle": "Delete escalation rule" } } } }, - "/alert/info": { + "/channel/escalate/rule/disable": { "post": { - "description": "Return the full details of a single alert by its ID, including its associated incident and event count.", - "operationId": "alert-read-info", + "description": "Disable an escalation rule without deleting it. Only an `enabled` rule can be disabled.", + "operationId": "channelEscalateRuleDisable", "requestBody": { "content": { "application/json": { "example": { - "alert_id": "663a1b2c3d4e5f6789abcdef" + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/AlertInfoRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -29803,14 +35557,7 @@ "content": { "application/json": { "example": { - "data": { - "alert_id": "663a1b2c3d4e5f6789abcdef", - "alert_severity": "Critical", - "alert_status": "Critical", - "event_cnt": 3, - "start_time": 1712650000, - "title": "CPU usage > 90%" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -29821,7 +35568,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AlertItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -29845,34 +35592,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get alert detail", + "summary": "Disable escalation rule", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- `alert_id` is an ObjectID hex string returned by `POST /alert/list` or `POST /alert-event/list`.", - "href": "/en/api-reference/on-call/alerts/alert-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-disable", "metadata": { - "sidebarTitle": "Get alert detail" + "sidebarTitle": "Disable escalation rule" } } } }, - "/alert/list": { + "/channel/escalate/rule/enable": { "post": { - "description": "Return a cursor-paginated list of alerts matching the given filters.", - "operationId": "alert-read-list", + "description": "Enable a disabled escalation rule. Only a `disabled` rule can be enabled.", + "operationId": "channelEscalateRuleEnable", "requestBody": { "content": { "application/json": { "example": { - "end_time": 1712707200, - "is_active": true, - "limit": 20, - "start_time": 1712620800 + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/AlertListRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -29883,34 +35628,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": false, - "items": [ - { - "account_id": 10023, - "alert_id": "663a1b2c3d4e5f6789abcdef", - "alert_severity": "Critical", - "alert_status": "Critical", - "channel_id": 20001, - "channel_name": "Production", - "created_at": 1712650000, - "end_time": 0, - "event_cnt": 3, - "ever_muted": false, - "integration_id": 10001, - "integration_name": "Prometheus", - "integration_type": "prometheus", - "labels": { - "host": "web-01" - }, - "last_time": 1712655000, - "start_time": 1712650000, - "title": "CPU usage > 90%", - "updated_at": 1712655000 - } - ], - "total": 1 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -29921,7 +35639,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AlertListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -29945,33 +35663,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List alerts", + "summary": "Enable escalation rule", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- Both `start_time` and `end_time` are required Unix epoch seconds. Maximum span is 31 days.\n- Use `search_after_ctx` from the previous response to fetch the next page.\n- Results are filtered by the caller's channel data-access permissions.\n- Set `is_active` to `true` to retrieve only active (firing) alerts; `false` to retrieve resolved alerts.", - "href": "/en/api-reference/on-call/alerts/alert-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-enable", "metadata": { - "sidebarTitle": "List alerts" + "sidebarTitle": "Enable escalation rule" } } } }, - "/alert/list-by-ids": { + "/channel/escalate/rule/info": { "post": { - "description": "Return the details of multiple alerts by their IDs in a single request. Note: this endpoint does not paginate — `total` and `has_next_page` are always `0`/`false` and `search_after_ctx` is never set.", - "operationId": "alert-read-list-by-ids", + "description": "Retrieve detailed information for a specific escalation rule.", + "operationId": "channelEscalateRuleInfo", "requestBody": { "content": { "application/json": { "example": { - "alert_ids": [ - "663a1b2c3d4e5f6789abcdef" - ] + "channel_id": 1001, + "rule_id": "6621b23f4a2c5e0012ab34d0" }, "schema": { - "$ref": "#/components/schemas/AlertListByIDsRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -29983,14 +35700,37 @@ "application/json": { "example": { "data": { - "has_next_page": false, - "items": [ + "account_id": 2451002751131, + "aggr_window": 0, + "channel_id": 6193426913131, + "created_at": 1773997289, + "description": "", + "filters": [], + "layers": [ { - "alert_id": "663a1b2c3d4e5f6789abcdef", - "title": "CPU usage > 90%" + "escalate_window": 30, + "force_escalate": false, + "max_times": 1, + "notify_step": 10, + "target": { + "by": { + "follow_preference": true + }, + "person_ids": [ + 3790925372131 + ], + "webhooks": null + } } ], - "total": 0 + "priority": 0, + "rule_id": "69bd0ce95a238693176c1d66", + "rule_name": "Default", + "status": "enabled", + "template_id": "6321aad26c12104586a88916", + "time_filters": [], + "updated_at": 1773997289, + "updated_by": 3790925372131 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -30002,7 +35742,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AlertListResponse" + "$ref": "#/components/schemas/EscalateRuleItem" } }, "type": "object" @@ -30026,34 +35766,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List alerts by IDs", + "summary": "Get escalation rule detail", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- All provided `alert_ids` must belong to the caller's account; any invalid ID causes the entire request to fail.", - "href": "/en/api-reference/on-call/alerts/alert-read-list-by-ids", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-info", "metadata": { - "sidebarTitle": "List alerts by IDs" + "sidebarTitle": "Get escalation rule detail" } } } }, - "/alert/merge": { + "/channel/escalate/rule/list": { "post": { - "description": "Associate one or more alerts with an existing incident. If a source alert previously belonged to a different incident and that incident becomes empty after the merge, it will be automatically closed.", - "operationId": "alert-write-merge", + "description": "List all escalation rules for a channel.", + "operationId": "channelEscalateRuleList", "requestBody": { "content": { "application/json": { "example": { - "alert_ids": [ - "663a1b2c3d4e5f6789abcdef" - ], - "incident_id": "663a000000000000deadbeef" + "channel_id": 1001 }, "schema": { - "$ref": "#/components/schemas/AlertMergeRequest" + "$ref": "#/components/schemas/ChannelScopedListRequest" } } }, @@ -30064,7 +35801,43 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "account_id": 2451002751131, + "aggr_window": 0, + "channel_id": 6193426913131, + "created_at": 1773997289, + "description": "", + "filters": [], + "layers": [ + { + "escalate_window": 30, + "force_escalate": false, + "max_times": 1, + "notify_step": 10, + "target": { + "by": { + "follow_preference": true + }, + "person_ids": [ + 3790925372131 + ], + "webhooks": null + } + } + ], + "priority": 0, + "rule_id": "69bd0ce95a238693176c1d66", + "rule_name": "Default", + "status": "enabled", + "template_id": "6321aad26c12104586a88916", + "time_filters": [], + "updated_at": 1773997289, + "updated_by": 3790925372131 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30075,7 +35848,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ListEscalationRulesResponse" } }, "type": "object" @@ -30099,31 +35872,51 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Merge alerts into an incident", + "summary": "List escalation rules", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |\n\n## Usage\n\n- All `alert_ids` and the `incident_id` must belong to the caller's account.\n- Optionally set `title` and `owner_id` to update the target incident at the same time.", - "href": "/en/api-reference/on-call/alerts/alert-write-merge", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-list", "metadata": { - "sidebarTitle": "Merge alerts into an incident" + "sidebarTitle": "List escalation rules" } } } }, - "/alert/pipeline/info": { + "/channel/escalate/rule/update": { "post": { - "description": "Return the alert processing pipeline configured for a specific integration.", - "operationId": "alert-read-pipeline-info", + "description": "Update an existing escalation rule configuration.", + "operationId": "channelEscalateRuleUpdate", "requestBody": { "content": { "application/json": { "example": { - "integration_id": 10001 + "channel_id": 1001, + "layers": [ + { + "target": { + "by": { + "critical": [ + "voice" + ], + "warning": [ + "sms" + ] + }, + "person_ids": [ + 42 + ] + } + } + ], + "rule_id": "6621b23f4a2c5e0012ab34d0", + "rule_name": "Default escalation", + "template_id": "6621b23f4a2c5e0012ab34d1" }, "schema": { - "$ref": "#/components/schemas/AlertPipelineInfoRequest" + "$ref": "#/components/schemas/UpdateEscalationRuleRequest" } } }, @@ -30134,38 +35927,7 @@ "content": { "application/json": { "example": { - "data": { - "created_at": 1710000000, - "creator_id": 80011, - "integration_id": 10001, - "rules": [ - { - "if": [ - { - "key": "labels.env", - "oper": "IN", - "vals": [ - "prod" - ] - } - ], - "kind": "title_reset", - "settings": { - "title": "[TPL]{{.Labels.service}} / {{.Labels.check}}" - } - }, - { - "if": null, - "kind": "severity_reset", - "settings": { - "severity": "Warning" - } - } - ], - "status": "enabled", - "updated_at": 1712000000, - "updated_by": 80011 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30176,7 +35938,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AlertPipelineItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -30200,34 +35962,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get alert pipeline", + "summary": "Update escalation rule", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) |\n\n## Usage\n\n- Returns `null` data if no pipeline has been configured for the given integration.\n- Requires the caller to have access to the integration.", - "href": "/en/api-reference/on-call/alerts/alert-read-pipeline-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-escalate-rule-update", "metadata": { - "sidebarTitle": "Get alert pipeline" + "sidebarTitle": "Update escalation rule" } } } }, - "/alert/pipeline/list": { + "/channel/info": { "post": { - "description": "Return the alert processing pipelines configured for multiple integrations.", - "operationId": "alert-read-pipeline-list", + "description": "Retrieve detailed information for a specific channel.", + "operationId": "channelInfo", "requestBody": { "content": { "application/json": { "example": { - "integration_ids": [ - 10001, - 10002 - ] + "channel_id": 1001 }, "schema": { - "$ref": "#/components/schemas/AlertPipelineListRequest" + "$ref": "#/components/schemas/ChannelInfoRequest" } } }, @@ -30239,44 +35998,10 @@ "application/json": { "example": { "data": { - "items": [ - { - "created_at": 1710000000, - "creator_id": 80011, - "integration_id": 10001, - "rules": [ - { - "if": [ - { - "key": "labels.cluster", - "oper": "IN", - "vals": [ - "prod-cn" - ] - } - ], - "kind": "alert_inhibit", - "settings": { - "equals": [ - "service" - ], - "source_filters": [ - { - "key": "alert_severity", - "oper": "IN", - "vals": [ - "Critical" - ] - } - ] - } - } - ], - "status": "enabled", - "updated_at": 1712000000, - "updated_by": 80011 - } - ] + "channel_id": 1001, + "channel_name": "Production Alerts", + "status": "enabled", + "team_id": 10 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -30288,7 +36013,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AlertPipelineListResponse" + "$ref": "#/components/schemas/ChannelItem" } }, "type": "object" @@ -30312,55 +36037,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List alert pipelines", + "summary": "Get channel detail", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) |\n\n## Usage\n\n- All `integration_ids` must be accessible to the caller.", - "href": "/en/api-reference/on-call/alerts/alert-read-pipeline-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-info", "metadata": { - "sidebarTitle": "List alert pipelines" + "sidebarTitle": "Get channel detail" } } } }, - "/alert/pipeline/upsert": { + "/channel/infos": { "post": { - "description": "Set the alert processing pipeline for an integration. Replaces the existing configuration entirely.", - "operationId": "alert-write-pipeline-upsert", + "description": "Retrieve multiple channels by their IDs.", + "operationId": "channelInfos", "requestBody": { "content": { "application/json": { "example": { - "integration_id": 10001, - "rules": [ - { - "if": [ - { - "key": "labels.env", - "oper": "IN", - "vals": [ - "prod" - ] - } - ], - "kind": "title_reset", - "settings": { - "title": "[TPL]{{.Labels.service}} / {{.Labels.check}}" - } - }, - { - "if": null, - "kind": "severity_reset", - "settings": { - "severity": "Warning" - } - } + "channel_ids": [ + 1001, + 1002 ] }, "schema": { - "$ref": "#/components/schemas/AlertPipelineUpsertRequest" + "$ref": "#/components/schemas/ChannelInfosRequest" } } }, @@ -30371,7 +36075,15 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "items": [ + { + "channel_id": 1001, + "channel_name": "Production Alerts", + "status": "enabled" + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30382,7 +36094,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ChannelInfosResponse" } }, "type": "object" @@ -30406,29 +36118,60 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create or update alert pipeline", + "summary": "Batch get channels", "tags": [ - "On-call/Alerts" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- Maximum 50 rules per pipeline.\n- Each rule has a `kind` (one of `title_reset`, `description_reset`, `severity_reset`, `alert_drop`, `alert_inhibit`), an optional `if` filter, and `settings` specific to the kind.\n- The `alert_inhibit` kind requires the Standard license or higher.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alerts/alert-write-pipeline-upsert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-infos", "metadata": { - "sidebarTitle": "Create or update alert pipeline" + "sidebarTitle": "Batch get channels" } } } }, - "/audit/operation/list": { + "/channel/inhibit/rule/create": { "post": { - "description": "Return all operation names that are recorded in the audit log, for use as `operations` filter values.", - "operationId": "audit-read-operation-list", + "description": "Create an inhibit rule to suppress lower-priority alerts when higher-priority ones are firing.", + "operationId": "channelInhibitRuleCreate", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "channel_id": 3521074710131, + "description": "When a Critical alert fires, suppress matching Info alerts", + "equals": [ + "labels.cluster", + "labels.service" + ], + "is_directly_discard": false, + "rule_name": "Suppress Info when Critical fires", + "source_filters": [ + [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Critical" + ] + } + ] + ], + "target_filters": [ + [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Info" + ] + } + ] + ] + }, "schema": { - "$ref": "#/components/schemas/AuditOperationListRequest" + "$ref": "#/components/schemas/CreateInhibitRuleRequest" } } }, @@ -30438,22 +36181,10 @@ "200": { "content": { "application/json": { - "example": { - "data": { - "items": [ - { - "name": "template:write:create", - "name_cn": "创建模板" - }, - { - "name": "template:write:delete", - "name_cn": "删除模板" - }, - { - "name": "incident:write:acknowledge", - "name_cn": "认领故障" - } - ] + "example": { + "data": { + "rule_id": "69db2f69a0fe7db6448b1504", + "rule_name": "Test inhibit rule" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -30465,7 +36196,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AuditOperationListResponse" + "$ref": "#/components/schemas/RuleCreateResponse" } }, "type": "object" @@ -30489,37 +36220,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List auditable operation types", + "summary": "Create inhibit rule", "tags": [ - "Platform/Audit logs" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Audit Read** (`organization`) |\n\n## Usage\n\n- Use the `name` values from this response as `operations` filter values in `POST /audit/search`.\n- `name_cn` is the human-readable Chinese label shown in the console; `name` is the stable wire value to filter on.", - "href": "/en/api-reference/platform/audit-logs/audit-read-operation-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-create", "metadata": { - "sidebarTitle": "List auditable operation types" + "sidebarTitle": "Create inhibit rule" } } } }, - "/audit/search": { + "/channel/inhibit/rule/delete": { "post": { - "description": "Return a cursor-paginated list of audit log entries within a time range.", - "operationId": "audit-read-search", + "description": "Delete an inhibit rule. Only a `disabled` rule can be deleted.", + "operationId": "channelInhibitRuleDelete", "requestBody": { "content": { "application/json": { "example": { - "end_time": 1712707200, - "limit": 20, - "operations": [ - "template:write:create", - "template:write:delete" - ], - "start_time": 1712620800 + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/AuditSearchRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -30530,29 +36256,7 @@ "content": { "application/json": { "example": { - "data": { - "docs": [ - { - "account_id": 10023, - "body": "{\"template_name\":\"Prod default\"}", - "created_at": 1712700123456, - "credential_id": 0, - "credential_type": "", - "ip": "203.0.113.42", - "is_dangerous": false, - "is_write": true, - "member_id": 80011, - "member_name": "Alice", - "operation": "template:write:create", - "operation_name": "创建模板", - "params": [], - "principal_kind": "member", - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - } - ], - "search_after_ctx": "", - "total": 2 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30563,7 +36267,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AuditSearchResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -30587,40 +36291,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Search audit logs", + "summary": "Delete inhibit rule", "tags": [ - "Platform/Audit logs" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Audit Read** (`organization`) |\n\n## Usage\n\n- Time range is required. Maximum span is 90 days. Both `start_time` and `end_time` are Unix epoch **seconds**.\n- Use `search_after_ctx` from the previous response to fetch the next page. The token is opaque — do not construct it manually.\n- The retention window depends on the account's license. Queries beyond the retention boundary silently return an empty result rather than an error.\n- `limit` accepts 0–99; omitting it (or 0) returns all matching rows in the window with no page-size cap. Rows are returned newest first.", - "href": "/en/api-reference/platform/audit-logs/audit-read-search", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-delete", "metadata": { - "sidebarTitle": "Search audit logs" + "sidebarTitle": "Delete inhibit rule" } } } }, - "/calendar/create": { + "/channel/inhibit/rule/disable": { "post": { - "description": "Create a personal service calendar. Each account is limited to 5 calendars unless the Flashcat-Break-Cal-Limit header is set.", - "operationId": "calendarCreate", + "description": "Disable an inhibit rule without deleting it. Only an `enabled` rule can be disabled.", + "operationId": "channelInhibitRuleDisable", "requestBody": { "content": { "application/json": { "example": { - "cal_name": "Production On-Call Calendar", - "description": "Calendar for production on-call team", - "timezone": "Asia/Shanghai", - "workdays": [ - 1, - 2, - 3, - 4, - 5 - ] + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/CalendarCreateRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -30631,10 +36327,7 @@ "content": { "application/json": { "example": { - "data": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "cal_name": "API Test Calendar" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30645,7 +36338,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalendarCreateResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -30669,31 +36362,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create calendar", + "summary": "Disable inhibit rule", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/calendars/calendar-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-disable", "metadata": { - "sidebarTitle": "Create calendar" + "sidebarTitle": "Disable inhibit rule" } } } }, - "/calendar/delete": { + "/channel/inhibit/rule/enable": { "post": { - "description": "Delete a personal service calendar. The call fails when referenced by escalation or silence rules.", - "operationId": "calendarDelete", + "description": "Enable a disabled inhibit rule. Only a `disabled` rule can be enabled.", + "operationId": "channelInhibitRuleEnable", "requestBody": { "content": { "application/json": { "example": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM" + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/CalendarIDRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -30715,7 +36409,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalendarEmptyObject" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -30739,32 +36433,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete calendar", + "summary": "Enable inhibit rule", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/calendars/calendar-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-enable", "metadata": { - "sidebarTitle": "Delete calendar" + "sidebarTitle": "Enable inhibit rule" } } } }, - "/calendar/event/delete": { + "/channel/inhibit/rule/list": { "post": { - "description": "Delete a calendar event by calendar ID and event ID.", - "operationId": "calEventDelete", + "description": "List all inhibit rules configured for a channel.", + "operationId": "channelInhibitRuleList", "requestBody": { "content": { "application/json": { "example": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "event_id": "cale.KyG9XWTCU5CucbwukEVBQ4" + "channel_id": 1001 }, "schema": { - "$ref": "#/components/schemas/CalEventIDRequest" + "$ref": "#/components/schemas/ChannelScopedListRequest" } } }, @@ -30775,7 +36468,48 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "account_id": 2451002751131, + "channel_id": 5967964835131, + "created_at": 1773979184, + "description": "", + "equals": [ + "data_source_id", + "labels._account_id" + ], + "is_directly_discard": false, + "rule_id": "69bcc630b9e63df36603e425", + "rule_name": "Suppress downstream alerts", + "source_filters": [ + [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Info" + ] + } + ] + ], + "status": "enabled", + "target_filters": [ + [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Info" + ] + } + ] + ], + "updated_at": 1773979184, + "updated_by": 3790925372131 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30786,7 +36520,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalendarEmptyObject" + "$ref": "#/components/schemas/ListInhibitRulesResponse" } }, "type": "object" @@ -30810,33 +36544,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete calendar event", + "summary": "List inhibit rules", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/calendars/cal-event-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-list", "metadata": { - "sidebarTitle": "Delete calendar event" + "sidebarTitle": "List inhibit rules" } } } }, - "/calendar/event/list": { + "/channel/inhibit/rule/update": { "post": { - "description": "Return events for a personal calendar within a year/month/day scope. When month and day are both omitted the whole year is returned.", - "operationId": "calEventList", + "description": "Update an existing inhibit rule configuration.", + "operationId": "channelInhibitRuleUpdate", "requestBody": { "content": { "application/json": { "example": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "month": 5, - "year": 2024 + "channel_id": 1001, + "equals": [ + "labels.cluster" + ], + "rule_id": "6621b23f4a2c5e0012ab34ce", + "rule_name": "Suppress downstream" }, "schema": { - "$ref": "#/components/schemas/CalEventListRequest" + "$ref": "#/components/schemas/UpdateInhibitRuleRequest" } } }, @@ -30847,37 +36584,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 2451002751131, - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "created_at": 1775972034, - "creator_id": 2476444212131, - "description": "A test holiday event", - "end_at": "2026-05-02", - "event_id": "cale.KyG9XWTCU5CucbwukEVBQ4", - "is_off": true, - "start_at": "2026-05-01", - "summary": "Test Holiday", - "updated_at": 1775972034 - }, - { - "account_id": 2451002751131, - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "created_at": 0, - "creator_id": 2451002751131, - "description": "", - "end_at": "2026-05-03", - "event_id": "non_work.20260502", - "is_off": true, - "start_at": "2026-05-02", - "summary": "non-working day (Saturday)", - "updated_at": 0 - } - ], - "total": 11 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -30888,7 +36595,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalEventListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -30912,36 +36619,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List calendar events", + "summary": "Update inhibit rule", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/calendars/cal-event-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-update", "metadata": { - "sidebarTitle": "List calendar events" + "sidebarTitle": "Update inhibit rule" } } } }, - "/calendar/event/upsert": { + "/channel/list": { "post": { - "description": "Create or update a calendar event (holiday or workday override). Omit event_id to create a new event.", - "operationId": "calEventUpsert", + "description": "List channels accessible to the current user with optional filters.", + "operationId": "channelList", "requestBody": { "content": { "application/json": { "example": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "description": "International Workers Day holiday", - "end_at": "2024-05-06", - "is_off": true, - "start_at": "2024-05-01", - "summary": "Labour Day" + "asc": false, + "limit": 20, + "orderby": "created_at", + "p": 1 }, "schema": { - "$ref": "#/components/schemas/CalEventUpsertRequest" + "$ref": "#/components/schemas/ListChannelsRequest" } } }, @@ -30953,9 +36658,15 @@ "application/json": { "example": { "data": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "event_id": "cale.KyG9XWTCU5CucbwukEVBQ4", - "summary": "Test Holiday" + "has_next_page": true, + "items": [ + { + "channel_id": 1001, + "channel_name": "Production Alerts", + "status": "enabled" + } + ], + "total": 42 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -30967,7 +36678,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalEventUpsertResponse" + "$ref": "#/components/schemas/ListChannelsResponse" } }, "type": "object" @@ -30991,31 +36702,49 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Upsert calendar event", + "summary": "List channels", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/calendars/cal-event-upsert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-list", "metadata": { - "sidebarTitle": "Upsert calendar event" + "sidebarTitle": "List channels" } } } }, - "/calendar/info": { + "/channel/silence/rule/create": { "post": { - "description": "Return details of a service calendar.", - "operationId": "calendarInfo", + "description": "Create a silence rule to suppress notifications matching specified conditions.", + "operationId": "channelSilenceRuleCreate", "requestBody": { "content": { "application/json": { "example": { - "cal_id": "cal.eh9gvPtWeH3xXgKeVSRxRg" + "channel_id": 3521074710131, + "description": "Silence all Info alerts during planned maintenance", + "filters": [ + [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Info" + ] + } + ] + ], + "is_directly_discard": false, + "rule_name": "Maintenance window silence", + "time_filter": { + "end_time": 1773414000, + "start_time": 1773388800 + } }, "schema": { - "$ref": "#/components/schemas/CalendarIDRequest" + "$ref": "#/components/schemas/CreateSilenceRuleRequest" } } }, @@ -31027,27 +36756,8 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "cal_id": "cal.eh9gvPtWeH3xXgKeVSRxRg", - "cal_name": "Stock Exchange Calendar", - "created_at": 1702455630, - "creator_id": 2476444212131, - "description": "A stock market trading calendar example", - "kind": "personal", - "status": "enabled", - "team_id": 2477033058131, - "timezone": "Asia/Shanghai", - "updated_at": 1775529526, - "updated_by": 3790925372131, - "workdays": [ - 0, - 1, - 2, - 3, - 4, - 5, - 6 - ] + "rule_id": "69db2f66a0fe7db6448b1503", + "rule_name": "Test silence rule" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -31059,7 +36769,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalendarItem" + "$ref": "#/components/schemas/RuleCreateResponse" } }, "type": "object" @@ -31083,31 +36793,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get calendar info", + "summary": "Create silence rule", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/calendars/calendar-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-silence-rule-create", "metadata": { - "sidebarTitle": "Get calendar info" + "sidebarTitle": "Create silence rule" } } } }, - "/calendar/list": { + "/channel/silence/rule/delete": { "post": { - "description": "Return the list of service calendars visible to the current account.", - "operationId": "calendarList", + "description": "Delete a silence rule. Only a `disabled` rule can be deleted.", + "operationId": "channelSilenceRuleDelete", "requestBody": { "content": { "application/json": { "example": { - "kind": "personal" + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/CalendarListRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -31118,51 +36829,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 2451002751131, - "cal_id": "cal.eh9gvPtWeH3xXgKeVSRxRg", - "cal_name": "Stock Exchange Calendar", - "created_at": 1702455630, - "creator_id": 2476444212131, - "description": "A stock market trading calendar example", - "kind": "personal", - "status": "enabled", - "team_id": 2477033058131, - "timezone": "Asia/Shanghai", - "updated_at": 1775529526, - "updated_by": 3790925372131, - "workdays": [ - 0, - 1, - 2, - 3, - 4, - 5, - 6 - ] - }, - { - "account_id": 2451002751131, - "cal_id": "cal.VZYkchxJhGELSF4jzkUAud", - "cal_name": "HK Stock Exchange Calendar", - "created_at": 1702968470, - "creator_id": 2451002751131, - "description": "Hong Kong Stock Exchange trading days calendar", - "extra_cal_ids": [ - "zh-cn.china.official" - ], - "kind": "personal", - "status": "enabled", - "team_id": 0, - "timezone": "Asia/Shanghai", - "updated_at": 1775188967, - "updated_by": 3790925372131 - } - ], - "total": 8 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -31173,7 +36840,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalendarListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -31197,40 +36864,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List calendars", + "summary": "Delete silence rule", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/calendars/calendar-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-silence-rule-delete", "metadata": { - "sidebarTitle": "List calendars" + "sidebarTitle": "Delete silence rule" } } } }, - "/calendar/update": { + "/channel/silence/rule/disable": { "post": { - "description": "Update a personal service calendar. Only non-null fields are updated.", - "operationId": "calendarUpdate", + "description": "Disable a silence rule without deleting it. Only an `enabled` rule can be disabled.", + "operationId": "channelSilenceRuleDisable", "requestBody": { "content": { "application/json": { "example": { - "cal_id": "cal.QiNvtdKs4Wj52kZhT3LafM", - "cal_name": "Production On-Call Calendar (Updated)", - "timezone": "America/New_York", - "workdays": [ - 1, - 2, - 3, - 4, - 5 - ] + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/CalendarUpdateRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -31252,7 +36911,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CalendarEmptyObject" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -31276,40 +36935,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update calendar", + "summary": "Disable silence rule", "tags": [ - "On-call/Calendars" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Calendars Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/calendars/calendar-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-silence-rule-disable", "metadata": { - "sidebarTitle": "Update calendar" + "sidebarTitle": "Disable silence rule" } } } }, - "/change/list": { + "/channel/silence/rule/enable": { "post": { - "description": "Query change records within a time window, with filtering, search, and pagination.", - "operationId": "change-read-list", + "description": "Enable a disabled silence rule. Only a `disabled` rule can be enabled.", + "operationId": "channelSilenceRuleEnable", "requestBody": { "content": { "application/json": { "example": { - "asc": false, - "end_time": 1717046400, - "include_events": false, - "integration_ids": [ - 362 - ], - "limit": 10, - "orderby": "start_time", - "p": 1, - "start_time": 1716960000 + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/ListChangeRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -31320,33 +36971,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": false, - "items": [ - { - "account_id": 10001, - "change_id": "664a1b2c3d4e5f6a7b8c9d0e", - "change_key": "deploy-api-server-2311", - "change_status": "Done", - "channel_id": 5001, - "channel_name": "Production", - "channel_status": "enabled", - "description": "Rolling deploy to production cluster", - "end_time": 1716963000, - "integration_id": 362, - "integration_name": "GitHub Deploy", - "labels": { - "env": "prod", - "service": "api-server" - }, - "last_time": 1716962700, - "link": "https://github.com/acme/api-server/actions/runs/123", - "start_time": 1716962400, - "title": "Deploy api-server v2.3.1" - } - ], - "total": 1 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -31357,7 +36982,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListChangeResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -31381,40 +37006,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List changes", + "summary": "Enable silence rule", "tags": [ - "On-call/Changes" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", - "href": "/en/api-reference/on-call/changes/change-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-silence-rule-enable", "metadata": { - "sidebarTitle": "List changes" + "sidebarTitle": "Enable silence rule" } } } }, - "/channel/create": { + "/channel/silence/rule/list": { "post": { - "description": "Create a new channel for incident management.", - "operationId": "channelCreate", + "description": "List all silence rules configured for a channel.", + "operationId": "channelSilenceRuleList", "requestBody": { "content": { "application/json": { "example": { - "auto_resolve_mode": "trigger", - "auto_resolve_timeout": 86400, - "channel_name": "Production Alerts", - "description": "Handles all production environment alerts", - "group": { - "method": "p", - "time_window": 10, - "window_type": "tumbling" - }, - "team_id": 3521074710131 + "channel_id": 1001 }, "schema": { - "$ref": "#/components/schemas/CreateChannelRequest" + "$ref": "#/components/schemas/ChannelScopedListRequest" } } }, @@ -31426,8 +37042,38 @@ "application/json": { "example": { "data": { - "channel_id": 6294542005131, - "channel_name": "API Test Channel" + "items": [ + { + "account_id": 2451002751131, + "channel_id": 5967964835131, + "created_at": 1773388838, + "description": "", + "filters": [ + [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Info" + ] + } + ] + ], + "from_incident_id": "000000000000000000000000", + "is_directly_discard": true, + "is_effective": false, + "rule_id": "69b3c426b4a6f5abf1f54873", + "rule_name": "Silence Info alerts", + "status": "enabled", + "time_filter": { + "end_time": 1773414000, + "start_time": 1773388800 + }, + "time_filters": [], + "updated_at": 1773388838, + "updated_by": 3790925372131 + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -31439,7 +37085,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ChannelCreateResponse" + "$ref": "#/components/schemas/ListSilenceRulesResponse" } }, "type": "object" @@ -31463,31 +37109,48 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create channel", + "summary": "List silence rules", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-silence-rule-list", "metadata": { - "sidebarTitle": "Create channel" + "sidebarTitle": "List silence rules" } } } }, - "/channel/delete": { + "/channel/silence/rule/update": { "post": { - "description": "Delete a channel. Only a `disabled` channel can be deleted; all of its escalation, silence, drop and inhibit rules are deleted with it. The call fails when an integration route still references the channel.", - "operationId": "channelDelete", + "description": "Update an existing silence rule configuration.", + "operationId": "channelSilenceRuleUpdate", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131 + "channel_id": 1001, + "filters": [ + [ + { + "key": "labels.service", + "oper": "IN", + "vals": [ + "billing" + ] + } + ] + ], + "rule_id": "6621b23f4a2c5e0012ab34cd", + "rule_name": "Mute during maintenance", + "time_filter": { + "end_time": 1710086400, + "start_time": 1710000000 + } }, "schema": { - "$ref": "#/components/schemas/ChannelIDRequest" + "$ref": "#/components/schemas/UpdateSilenceRuleRequest" } } }, @@ -31533,31 +37196,45 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete channel", + "summary": "Update silence rule", "tags": [ "On-call/Channels" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-delete", + "href": "/en/api-reference/on-call/channels/channel-silence-rule-update", "metadata": { - "sidebarTitle": "Delete channel" + "sidebarTitle": "Update silence rule" } } } }, - "/channel/disable": { + "/channel/unsubscribe/rule/create": { "post": { - "description": "Disable a channel to stop incident routing without deleting it; a disabled channel discards incoming events. Only an `enabled` channel can be disabled.", - "operationId": "channelDisable", + "description": "Create a drop rule to filter out unwanted alerts before they become incidents.", + "operationId": "channelUnsubscribeRuleCreate", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131 + "channel_id": 3521074710131, + "description": "Discard all alerts from the test environment before they create incidents", + "filters": [ + [ + { + "key": "labels.env", + "oper": "IN", + "vals": [ + "test", + "dev" + ] + } + ] + ], + "rule_name": "Drop test environment alerts" }, "schema": { - "$ref": "#/components/schemas/ChannelIDRequest" + "$ref": "#/components/schemas/CreateDropRuleRequest" } } }, @@ -31568,7 +37245,10 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "rule_id": "69db2f6ba0fe7db6448b1505", + "rule_name": "Test drop rule" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -31579,7 +37259,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/RuleCreateResponse" } }, "type": "object" @@ -31603,31 +37283,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable channel", + "summary": "Create drop rule", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-create", "metadata": { - "sidebarTitle": "Disable channel" + "sidebarTitle": "Create drop rule" } } } }, - "/channel/enable": { + "/channel/unsubscribe/rule/delete": { "post": { - "description": "Enable a channel to resume incident routing. Only a `disabled` channel can be enabled.", - "operationId": "channelEnable", + "description": "Delete a drop rule. Only a `disabled` rule can be deleted.", + "operationId": "channelUnsubscribeRuleDelete", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131 + "channel_id": 3521074710131, + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/ChannelIDRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -31673,50 +37354,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable channel", + "summary": "Delete drop rule", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-delete", "metadata": { - "sidebarTitle": "Enable channel" + "sidebarTitle": "Delete drop rule" } } } }, - "/channel/escalate/rule/create": { + "/channel/unsubscribe/rule/disable": { "post": { - "description": "Create an escalation rule defining who gets notified and when during an incident.", - "operationId": "channelEscalateRuleCreate", + "description": "Disable a drop rule without deleting it. Only an `enabled` rule can be disabled.", + "operationId": "channelUnsubscribeRuleDisable", "requestBody": { "content": { "application/json": { "example": { "channel_id": 3521074710131, - "description": "Notify primary on-call, then escalate to secondary after 30 minutes", - "layers": [ - { - "escalate_window": 30, - "force_escalate": false, - "max_times": 3, - "notify_step": 10, - "target": { - "by": { - "follow_preference": true - }, - "person_ids": [ - 3790925372131 - ] - } - } - ], - "rule_name": "On-call escalation", - "template_id": "6321aad26c12104586a88916" + "rule_id": "6621b23f4a2c5e0012ab34cd" }, "schema": { - "$ref": "#/components/schemas/CreateEscalationRuleRequest" + "$ref": "#/components/schemas/ChannelRuleIDRequest" } } }, @@ -31727,10 +37390,7 @@ "content": { "application/json": { "example": { - "data": { - "rule_id": "69db2f72a0fe7db6448b1506", - "rule_name": "Test escalation rule" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -31741,7 +37401,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleCreateResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -31765,23 +37425,23 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create escalation rule", + "summary": "Disable drop rule", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-disable", "metadata": { - "sidebarTitle": "Create escalation rule" + "sidebarTitle": "Disable drop rule" } } } }, - "/channel/escalate/rule/delete": { + "/channel/unsubscribe/rule/enable": { "post": { - "description": "Delete an escalation rule. Only a `disabled` rule can be deleted.", - "operationId": "channelEscalateRuleDelete", + "description": "Enable a disabled drop rule. Only a `disabled` rule can be enabled.", + "operationId": "channelUnsubscribeRuleEnable", "requestBody": { "content": { "application/json": { @@ -31836,32 +37496,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete escalation rule", + "summary": "Enable drop rule", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-enable", "metadata": { - "sidebarTitle": "Delete escalation rule" + "sidebarTitle": "Enable drop rule" } } } }, - "/channel/escalate/rule/disable": { + "/channel/unsubscribe/rule/list": { "post": { - "description": "Disable an escalation rule without deleting it. Only an `enabled` rule can be disabled.", - "operationId": "channelEscalateRuleDisable", + "description": "List drop rules for a channel.", + "operationId": "channelUnsubscribeRuleList", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "channel_id": 1001 }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/ChannelScopedListRequest" } } }, @@ -31872,7 +37531,32 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "account_id": 2451002751131, + "channel_id": 5967964835131, + "created_at": 1773978928, + "description": "", + "filters": [ + [ + { + "key": "data_source_id", + "oper": "IN", + "vals": [ + "6113996590131" + ] + } + ] + ], + "rule_id": "69bcc530b9e63df36603e421", + "rule_name": "Drop test alerts", + "status": "enabled", + "updated_at": 1773978928, + "updated_by": 3790925372131 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -31883,7 +37567,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ListDropRulesResponse" } }, "type": "object" @@ -31907,32 +37591,44 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable escalation rule", + "summary": "List drop rules", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-list", "metadata": { - "sidebarTitle": "Disable escalation rule" + "sidebarTitle": "List drop rules" } } } }, - "/channel/escalate/rule/enable": { + "/channel/unsubscribe/rule/update": { "post": { - "description": "Enable a disabled escalation rule. Only a `disabled` rule can be enabled.", - "operationId": "channelEscalateRuleEnable", + "description": "Update an existing drop rule configuration.", + "operationId": "channelUnsubscribeRuleUpdate", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "channel_id": 1001, + "filters": [ + [ + { + "key": "labels.env", + "oper": "IN", + "vals": [ + "test" + ] + } + ] + ], + "rule_id": "6621b23f4a2c5e0012ab34cf", + "rule_name": "Drop test alerts" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/UpdateDropRuleRequest" } } }, @@ -31978,32 +37674,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable escalation rule", + "summary": "Update drop rule", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-update", "metadata": { - "sidebarTitle": "Enable escalation rule" + "sidebarTitle": "Update drop rule" } } } }, - "/channel/escalate/rule/info": { + "/channel/update": { "post": { - "description": "Retrieve detailed information for a specific escalation rule.", - "operationId": "channelEscalateRuleInfo", + "description": "Update an existing channel's configuration and settings.", + "operationId": "channelUpdate", "requestBody": { "content": { "application/json": { "example": { "channel_id": 1001, - "rule_id": "6621b23f4a2c5e0012ab34d0" + "channel_name": "Production Alerts (v2)", + "description": "Updated description" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/UpdateChannelRequest" } } }, @@ -32015,37 +37712,7 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "aggr_window": 0, - "channel_id": 6193426913131, - "created_at": 1773997289, - "description": "", - "filters": [], - "layers": [ - { - "escalate_window": 30, - "force_escalate": false, - "max_times": 1, - "notify_step": 10, - "target": { - "by": { - "follow_preference": true - }, - "person_ids": [ - 3790925372131 - ], - "webhooks": null - } - } - ], - "priority": 0, - "rule_id": "69bd0ce95a238693176c1d66", - "rule_name": "Default", - "status": "enabled", - "template_id": "6321aad26c12104586a88916", - "time_filters": [], - "updated_at": 1773997289, - "updated_by": 3790925372131 + "external_report_token": "" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -32057,7 +37724,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EscalateRuleItem" + "$ref": "#/components/schemas/UpdateChannelResponse" } }, "type": "object" @@ -32081,31 +37748,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get escalation rule detail", + "summary": "Update channel", "tags": [ "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/channel-update", "metadata": { - "sidebarTitle": "Get escalation rule detail" + "sidebarTitle": "Update channel" } } } }, - "/channel/escalate/rule/list": { + "/datasource/im/person/try-link": { "post": { - "description": "List all escalation rules for a channel.", - "operationId": "channelEscalateRuleList", + "description": "Try to automatically link unbound members to their IM accounts for one integration.", + "operationId": "datasourceImPersonTryLink", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001 + "integration_id": 6113996590131 }, "schema": { - "$ref": "#/components/schemas/ChannelScopedListRequest" + "$ref": "#/components/schemas/TryLinkPersonRequest" } } }, @@ -32117,40 +37784,8 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "aggr_window": 0, - "channel_id": 6193426913131, - "created_at": 1773997289, - "description": "", - "filters": [], - "layers": [ - { - "escalate_window": 30, - "force_escalate": false, - "max_times": 1, - "notify_step": 10, - "target": { - "by": { - "follow_preference": true - }, - "person_ids": [ - 3790925372131 - ], - "webhooks": null - } - } - ], - "priority": 0, - "rule_id": "69bd0ce95a238693176c1d66", - "rule_name": "Default", - "status": "enabled", - "template_id": "6321aad26c12104586a88916", - "time_filters": [], - "updated_at": 1773997289, - "updated_by": 3790925372131 - } + "new_linked_person_ids": [ + 5348648172131 ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" @@ -32163,7 +37798,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListEscalationRulesResponse" + "$ref": "#/components/schemas/TryLinkPersonResponse" } }, "type": "object" @@ -32187,51 +37822,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List escalation rules", + "summary": "Attempt IM person linking", "tags": [ - "On-call/Channels" + "On-call/Integrations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- The server uses member email and phone values to find matching users in DingTalk, Feishu, or WeCom.\n- When no member can be linked, the response either carries an empty `new_linked_person_ids` array or omits the `data` field entirely.", + "href": "/en/api-reference/on-call/integrations/datasource-im-person-try-link", "metadata": { - "sidebarTitle": "List escalation rules" + "sidebarTitle": "Attempt IM person linking" } } } }, - "/channel/escalate/rule/update": { + "/datasource/im/war-room-enabled/list": { "post": { - "description": "Update an existing escalation rule configuration.", - "operationId": "channelEscalateRuleUpdate", + "description": "List IM integrations that have the war-room feature enabled for the account.", + "operationId": "im-war-room-enabled-list", "requestBody": { "content": { "application/json": { - "example": { - "channel_id": 1001, - "layers": [ - { - "target": { - "by": { - "critical": [ - "voice" - ], - "warning": [ - "sms" - ] - }, - "person_ids": [ - 42 - ] - } - } - ], - "rule_id": "6621b23f4a2c5e0012ab34d0", - "rule_name": "Default escalation", - "template_id": "6621b23f4a2c5e0012ab34d1" - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/UpdateEscalationRuleRequest" + "type": "object" } } }, @@ -32242,7 +37855,35 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "account_id": 10001, + "category": "im", + "created_at": 1716962400, + "creator_id": 20001, + "data_source_id": 362, + "description": "Feishu war-room integration", + "exclusive_data_source_id": 0, + "integration_id": 362, + "integration_key": "ik_8f3a2b1c9d0e", + "last_time": 0, + "name": "Feishu Ops", + "no_editable": false, + "plugin_id": 101, + "plugin_type": "feishu", + "plugin_type_name": "Feishu", + "ref_id": "", + "settings": { + "war_room_enabled": true + }, + "status": "enabled", + "team_id": 0, + "updated_at": 1716962700, + "updated_by": 20001 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -32253,7 +37894,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ListWarRoomEnabledResponse" } }, "type": "object" @@ -32277,31 +37918,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update escalation rule", + "summary": "List war-room-enabled IM integrations", "tags": [ - "On-call/Channels" + "On-call/IM integrations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-escalate-rule-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", + "href": "/en/api-reference/on-call/integrations/im-war-room-enabled-list", "metadata": { - "sidebarTitle": "Update escalation rule" + "sidebarTitle": "List war-room-enabled IM integrations" } } } }, - "/channel/info": { + "/enrichment/info": { "post": { - "description": "Retrieve detailed information for a specific channel.", - "operationId": "channelInfo", + "description": "Return the enrichment rule set configured for a specific integration.", + "operationId": "enrichment-read-info", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001 + "integration_id": 5001 }, "schema": { - "$ref": "#/components/schemas/ChannelInfoRequest" + "$ref": "#/components/schemas/EnrichmentInfoRequest" } } }, @@ -32313,10 +37954,23 @@ "application/json": { "example": { "data": { - "channel_id": 1001, - "channel_name": "Production Alerts", + "created_at": 1710000000, + "creator_id": 80011, + "integration_id": 5001, + "rules": [ + { + "kind": "extraction", + "settings": { + "override": true, + "pattern": "^(prod|staging|dev).*$", + "result_label": "environment", + "source_field": "labels.env" + } + } + ], "status": "enabled", - "team_id": 10 + "updated_at": 1710000000, + "updated_by": 80011 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -32328,7 +37982,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ChannelItem" + "$ref": "#/components/schemas/EnrichmentItem" } }, "type": "object" @@ -32352,34 +38006,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get channel detail", + "summary": "Get enrichment rules", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) or **Channels Manage** (`on-call`) or **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- Returns `null` if no enrichment rules have been configured for the integration.", + "href": "/en/api-reference/on-call/alert-enrichment/enrichment-read-info", "metadata": { - "sidebarTitle": "Get channel detail" + "sidebarTitle": "Get enrichment rules" } } } }, - "/channel/infos": { + "/enrichment/list": { "post": { - "description": "Retrieve multiple channels by their IDs.", - "operationId": "channelInfos", + "description": "Return the enrichment rule sets for a list of integration IDs.", + "operationId": "enrichment-read-list", "requestBody": { "content": { "application/json": { "example": { - "channel_ids": [ - 1001, - 1002 + "integration_ids": [ + 5001, + 5002 ] }, "schema": { - "$ref": "#/components/schemas/ChannelInfosRequest" + "$ref": "#/components/schemas/EnrichmentListRequest" } } }, @@ -32393,9 +38047,13 @@ "data": { "items": [ { - "channel_id": 1001, - "channel_name": "Production Alerts", - "status": "enabled" + "created_at": 1710000000, + "creator_id": 80011, + "integration_id": 5001, + "rules": [], + "status": "enabled", + "updated_at": 1710000000, + "updated_by": 80011 } ] }, @@ -32409,7 +38067,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ChannelInfosResponse" + "$ref": "#/components/schemas/EnrichmentListResponse" } }, "type": "object" @@ -32433,60 +38091,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Batch get channels", + "summary": "List enrichment rules", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-infos", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/alert-enrichment/enrichment-read-list", "metadata": { - "sidebarTitle": "Batch get channels" + "sidebarTitle": "List enrichment rules" } } } }, - "/channel/inhibit/rule/create": { + "/enrichment/mapping/api/create": { "post": { - "description": "Create an inhibit rule to suppress lower-priority alerts when higher-priority ones are firing.", - "operationId": "channelInhibitRuleCreate", + "description": "Create a new external HTTP API endpoint used to enrich alerts via HTTP lookup.", + "operationId": "mapping-api-write-create", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "description": "When a Critical alert fires, suppress matching Info alerts", - "equals": [ - "labels.cluster", - "labels.service" - ], - "is_directly_discard": false, - "rule_name": "Suppress Info when Critical fires", - "source_filters": [ - [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Critical" - ] - } - ] - ], - "target_filters": [ - [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Info" - ] - } - ] - ] + "api_name": "CMDB API", + "description": "Query CMDB for host metadata", + "headers": { + "X-Token": "mytoken" + }, + "insecure_skip_verify": false, + "retry_count": 1, + "timeout": 2, + "url": "https://cmdb.example.com/api/lookup" }, "schema": { - "$ref": "#/components/schemas/CreateInhibitRuleRequest" + "$ref": "#/components/schemas/MappingAPICreateRequest" } } }, @@ -32498,8 +38135,8 @@ "application/json": { "example": { "data": { - "rule_id": "69db2f69a0fe7db6448b1504", - "rule_name": "Test inhibit rule" + "api_id": "665f1a2b3c4d5e6f7a8b9c02", + "api_name": "CMDB API" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -32511,7 +38148,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleCreateResponse" + "$ref": "#/components/schemas/MappingAPICreateResponse" } }, "type": "object" @@ -32535,32 +38172,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create inhibit rule", + "summary": "Create mapping API", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- `url` must start with `http://` or `https://` and cannot resolve to an internal IP (in SaaS mode).\n- `timeout` is the HTTP read timeout in seconds (1–3, default 2).\n- `retry_count` is the number of retries on failure (0–1, default 0).\n- Headers with security-sensitive names (e.g. `authorization`, `cookie`) are rejected in SaaS mode.\n- An account can have at most 50 mapping APIs.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-write-create", "metadata": { - "sidebarTitle": "Create inhibit rule" + "sidebarTitle": "Create mapping API" } } } }, - "/channel/inhibit/rule/delete": { + "/enrichment/mapping/api/delete": { "post": { - "description": "Delete an inhibit rule. Only a `disabled` rule can be deleted.", - "operationId": "channelInhibitRuleDelete", + "description": "Delete a mapping API. Deletion is blocked if the API is referenced by any enrichment rule.", + "operationId": "mapping-api-write-delete", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "api_id": "665f1a2b3c4d5e6f7a8b9c02" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/MappingAPIIDRequest" } } }, @@ -32606,32 +38242,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete inhibit rule", + "summary": "Delete mapping API", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- If the API is still referenced, the response returns HTTP 400 with a `refs` list.\n- Only the API creator, account admin, or team member can delete the API.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-write-delete", "metadata": { - "sidebarTitle": "Delete inhibit rule" + "sidebarTitle": "Delete mapping API" } } } }, - "/channel/inhibit/rule/disable": { + "/enrichment/mapping/api/info": { "post": { - "description": "Disable an inhibit rule without deleting it. Only an `enabled` rule can be disabled.", - "operationId": "channelInhibitRuleDisable", + "description": "Return detail of a single mapping API by its ID.", + "operationId": "mapping-api-read-info", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "api_id": "665f1a2b3c4d5e6f7a8b9c02" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/MappingAPIIDRequest" } } }, @@ -32642,7 +38277,18 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "api_id": "665f1a2b3c4d5e6f7a8b9c02", + "api_name": "CMDB API", + "created_at": 1710000000, + "creator_id": 80011, + "insecure_skip_verify": false, + "retry_count": 1, + "status": "enabled", + "timeout": 2, + "updated_at": 1710000000, + "url": "https://cmdb.example.com/api/lookup" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -32653,7 +38299,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/MappingAPIItem" } }, "type": "object" @@ -32677,32 +38323,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable inhibit rule", + "summary": "Get mapping API detail", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `null` if the API does not exist.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-read-info", "metadata": { - "sidebarTitle": "Disable inhibit rule" + "sidebarTitle": "Get mapping API detail" } } } }, - "/channel/inhibit/rule/enable": { + "/enrichment/mapping/api/list": { "post": { - "description": "Enable a disabled inhibit rule. Only a `disabled` rule can be enabled.", - "operationId": "channelInhibitRuleEnable", + "description": "Return all mapping APIs configured for the account.", + "operationId": "mapping-api-read-list", "requestBody": { "content": { "application/json": { - "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/EmptyRequest" } } }, @@ -32713,7 +38356,28 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "api_id": "665f1a2b3c4d5e6f7a8b9c02", + "api_name": "CMDB API", + "created_at": 1710000000, + "creator_id": 80011, + "description": "Query CMDB for host metadata", + "headers": { + "Authorization": "Bearer eyJhbGciOiJIUzI1NiJ9.example-token" + }, + "insecure_skip_verify": false, + "retry_count": 1, + "status": "enabled", + "team_id": 0, + "timeout": 2, + "updated_at": 1710000000, + "url": "https://cmdb.example.com/api/lookup" + } + ], + "total": 1 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -32724,7 +38388,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/MappingAPIListResponse" } }, "type": "object" @@ -32748,31 +38412,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable inhibit rule", + "summary": "List mapping APIs", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-read-list", "metadata": { - "sidebarTitle": "Enable inhibit rule" + "sidebarTitle": "List mapping APIs" } } } }, - "/channel/inhibit/rule/list": { + "/enrichment/mapping/api/update": { "post": { - "description": "List all inhibit rules configured for a channel.", - "operationId": "channelInhibitRuleList", + "description": "Update configuration of an existing mapping API.", + "operationId": "mapping-api-write-update", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001 + "api_id": "665f1a2b3c4d5e6f7a8b9c02", + "retry_count": 1, + "timeout": 3 }, "schema": { - "$ref": "#/components/schemas/ChannelScopedListRequest" + "$ref": "#/components/schemas/MappingAPIUpdateRequest" } } }, @@ -32783,48 +38449,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 2451002751131, - "channel_id": 5967964835131, - "created_at": 1773979184, - "description": "", - "equals": [ - "data_source_id", - "labels._account_id" - ], - "is_directly_discard": false, - "rule_id": "69bcc630b9e63df36603e425", - "rule_name": "Suppress downstream alerts", - "source_filters": [ - [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Info" - ] - } - ] - ], - "status": "enabled", - "target_filters": [ - [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Info" - ] - } - ] - ], - "updated_at": 1773979184, - "updated_by": 3790925372131 - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -32835,7 +38460,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListInhibitRulesResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -32859,36 +38484,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List inhibit rules", + "summary": "Update mapping API", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Only the API creator, account admin, or team member can update the API.\n- All updatable fields are optional — only provided fields are changed.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-write-update", "metadata": { - "sidebarTitle": "List inhibit rules" + "sidebarTitle": "Update mapping API" } } } }, - "/channel/inhibit/rule/update": { + "/enrichment/mapping/data/delete": { "post": { - "description": "Update an existing inhibit rule configuration.", - "operationId": "channelInhibitRuleUpdate", + "description": "Delete up to 100 mapping data rows by their keys.", + "operationId": "mapping-data-write-delete", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001, - "equals": [ - "labels.cluster" + "keys": [ + "server01", + "server02" ], - "rule_id": "6621b23f4a2c5e0012ab34ce", - "rule_name": "Suppress downstream" + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/UpdateInhibitRuleRequest" + "$ref": "#/components/schemas/MappingDataDeleteRequest" } } }, @@ -32934,34 +38558,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update inhibit rule", + "summary": "Delete mapping data rows", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-inhibit-rule-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-delete", "metadata": { - "sidebarTitle": "Update inhibit rule" + "sidebarTitle": "Delete mapping data rows" } } } }, - "/channel/list": { + "/enrichment/mapping/data/download": { "post": { - "description": "List channels accessible to the current user with optional filters.", - "operationId": "channelList", + "description": "Export all data rows of a mapping schema as a CSV file download.", + "operationId": "mapping-data-read-download", "requestBody": { "content": { "application/json": { "example": { - "asc": false, - "limit": 20, - "orderby": "created_at", - "p": 1 + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/ListChannelsRequest" + "$ref": "#/components/schemas/MappingSchemaIDRequest" } } }, @@ -32970,39 +38591,16 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": { - "has_next_page": true, - "items": [ - { - "channel_id": 1001, - "channel_name": "Production Alerts", - "status": "enabled" - } - ], - "total": 42 - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/octet-stream": { + "example": "host,owner,team\nserver01,alice,sre\nserver02,bob,backend\n", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/ListChannelsResponse" - } - }, - "type": "object" - } - ] + "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=.csv`). The header row lists the schema's source_labels followed by result_labels in order; each subsequent row is one mapping document.", + "format": "binary", + "type": "string" } } }, - "description": "Success" + "description": "Success. CSV attachment stream, not a JSON envelope." }, "400": { "$ref": "#/components/responses/BadRequest" @@ -33017,49 +38615,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List channels", + "summary": "Download mapping data as CSV", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- The response is a CSV file with `Content-Disposition: attachment` header.\n- The CSV header row matches the schema's source and result labels in order.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-read-download", "metadata": { - "sidebarTitle": "List channels" + "sidebarTitle": "Download mapping data as CSV" } } } }, - "/channel/silence/rule/create": { + "/enrichment/mapping/data/list": { "post": { - "description": "Create a silence rule to suppress notifications matching specified conditions.", - "operationId": "channelSilenceRuleCreate", + "description": "Return paginated mapping data rows for a schema, with optional exact-match filtering on source label values.", + "operationId": "mapping-data-read-list", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "description": "Silence all Info alerts during planned maintenance", - "filters": [ - [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Info" - ] - } - ] - ], - "is_directly_discard": false, - "rule_name": "Maintenance window silence", - "time_filter": { - "end_time": 1773414000, - "start_time": 1773388800 - } + "asc": false, + "limit": 20, + "orderby": "updated_at", + "p": 1, + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/CreateSilenceRuleRequest" + "$ref": "#/components/schemas/MappingDataListRequest" } } }, @@ -33071,8 +38655,21 @@ "application/json": { "example": { "data": { - "rule_id": "69db2f66a0fe7db6448b1503", - "rule_name": "Test silence rule" + "has_next_page": false, + "items": [ + { + "created_at": 1710000000, + "fields": { + "host": "server01", + "owner": "alice", + "service": "api", + "team": "sre" + }, + "key": "server01", + "updated_at": 1710000000 + } + ], + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -33084,7 +38681,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleCreateResponse" + "$ref": "#/components/schemas/MappingDataListResponse" } }, "type": "object" @@ -33108,32 +38705,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create silence rule", + "summary": "List mapping data", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-silence-rule-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- If `query` is provided, all source labels must be specified — partial source label queries are rejected.\n- Pagination uses cursor-based (`search_after_ctx`) or page-based (`p`, `limit`) navigation. `limit` defaults to 20, max 100.\n- The `search_after_ctx` token from a response can be passed back to retrieve the next page.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-read-list", "metadata": { - "sidebarTitle": "Create silence rule" + "sidebarTitle": "List mapping data" } } } }, - "/channel/silence/rule/delete": { + "/enrichment/mapping/data/truncate": { "post": { - "description": "Delete a silence rule. Only a `disabled` rule can be deleted.", - "operationId": "channelSilenceRuleDelete", + "description": "Delete all data rows in a mapping schema.", + "operationId": "mapping-data-write-truncate", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/MappingSchemaIDRequest" } } }, @@ -33179,32 +38775,63 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete silence rule", + "summary": "Truncate mapping data", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-silence-rule-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- This is an irreversible bulk-delete operation.\n- High-risk operation. Console JWT callers must pass a second-factor code; `app_key` callers bypass the MFA prompt but remain audited — treat the key as a secret.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-truncate", "metadata": { - "sidebarTitle": "Delete silence rule" + "sidebarTitle": "Truncate mapping data" } } } }, - "/channel/silence/rule/disable": { + "/enrichment/mapping/data/upload": { "post": { - "description": "Disable a silence rule without deleting it. Only an `enabled` rule can be disabled.", - "operationId": "channelSilenceRuleDisable", + "description": "Upload a CSV file to bulk-load mapping data. By default the existing data is truncated before loading the new rows.", + "operationId": "mapping-data-write-upload", + "parameters": [ + { + "description": "ID of the target mapping schema (ObjectID hex).", + "example": "665f1a2b3c4d5e6f7a8b9c01", + "in": "query", + "name": "schema_id", + "required": true, + "schema": { + "pattern": "^[0-9a-fA-F]{24}$", + "type": "string" + } + }, + { + "description": "Pass `TRUE` (case-insensitive) to append instead of replacing. When omitted and the schema already has data, the server truncates existing rows before importing.", + "in": "query", + "name": "do_not_truncate_first", + "required": false, + "schema": { + "enum": [ + "TRUE" + ], + "type": "string" + } + } + ], "requestBody": { "content": { - "application/json": { - "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" - }, + "multipart/form-data": { "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "properties": { + "file": { + "description": "CSV file, max 100 MB. The header row must include all of the schema's source/result label names.", + "format": "binary", + "type": "string" + } + }, + "required": [ + "file" + ], + "type": "object" } } }, @@ -33250,32 +38877,45 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable silence rule", + "summary": "Upload mapping data via CSV", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-silence-rule-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **20 requests/minute**; **2 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- The request must use `Content-Type: multipart/form-data`. The file field name is `file` and `schema_id` is a query parameter.\n- CSV header row must include all source and result label names.\n- Maximum file size: 100 MB.\n- By default the schema's existing data is truncated before import. Pass query param `do_not_truncate_first=TRUE` to append instead.\n- Duplicate source label value combinations in the CSV cause a 400 error.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-upload", "metadata": { - "sidebarTitle": "Disable silence rule" + "sidebarTitle": "Upload mapping data via CSV" } } } }, - "/channel/silence/rule/enable": { + "/enrichment/mapping/data/upsert": { "post": { - "description": "Enable a disabled silence rule. Only a `disabled` rule can be enabled.", - "operationId": "channelSilenceRuleEnable", + "description": "Insert or update up to 1000 data rows in a mapping schema. Each row must contain all source and result labels.", + "operationId": "mapping-data-write-upsert", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "docs": [ + { + "host": "server01", + "owner": "alice", + "service": "api", + "team": "sre" + }, + { + "host": "server02", + "owner": "bob", + "service": "gateway", + "team": "platform" + } + ], + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/MappingDataUpsertRequest" } } }, @@ -33286,7 +38926,12 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "keys": [ + "server01", + "server02" + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -33297,7 +38942,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/MappingDataUpsertResponse" } }, "type": "object" @@ -33321,31 +38966,40 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable silence rule", + "summary": "Upsert mapping data rows", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-silence-rule-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Each doc must contain values for all labels defined in `source_labels` and `result_labels`.\n- Values for unknown labels are silently dropped.\n- Each value must be at most 2048 characters.\n- Upsert is keyed on the combination of source label values — existing rows with the same source key are updated.\n- A schema can hold at most 10,000 rows by default.\n- The operation is locked per schema; concurrent upserts to the same schema may fail with `ErrRequestTooFrequently`.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-upsert", "metadata": { - "sidebarTitle": "Enable silence rule" + "sidebarTitle": "Upsert mapping data rows" } } } }, - "/channel/silence/rule/list": { + "/enrichment/mapping/schema/create": { "post": { - "description": "List all silence rules configured for a channel.", - "operationId": "channelSilenceRuleList", + "description": "Create a new mapping schema defining source lookup labels and the result labels to populate. Requires a Pro plan.", + "operationId": "mapping-schema-write-create", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001 + "description": "Enrich alerts with CMDB data", + "result_labels": [ + "owner", + "team", + "service" + ], + "schema_name": "CMDB Lookup", + "source_labels": [ + "host" + ] }, "schema": { - "$ref": "#/components/schemas/ChannelScopedListRequest" + "$ref": "#/components/schemas/MappingSchemaCreateRequest" } } }, @@ -33357,38 +39011,8 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "channel_id": 5967964835131, - "created_at": 1773388838, - "description": "", - "filters": [ - [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Info" - ] - } - ] - ], - "from_incident_id": "000000000000000000000000", - "is_directly_discard": true, - "is_effective": false, - "rule_id": "69b3c426b4a6f5abf1f54873", - "rule_name": "Silence Info alerts", - "status": "enabled", - "time_filter": { - "end_time": 1773414000, - "start_time": 1773388800 - }, - "time_filters": [], - "updated_at": 1773388838, - "updated_by": 3790925372131 - } - ] + "schema_id": "665f1a2b3c4d5e6f7a8b9c01", + "schema_name": "CMDB Lookup" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -33400,7 +39024,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListSilenceRulesResponse" + "$ref": "#/components/schemas/MappingSchemaCreateResponse" } }, "type": "object" @@ -33424,48 +39048,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List silence rules", + "summary": "Create mapping schema", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-silence-rule-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Schema names must be unique within an account.\n- `source_labels` (1–3 labels) are used as lookup keys; `result_labels` (1–10 labels) are the labels written on match.\n- Label names must match `^[a-zA-Z_][a-zA-Z0-9_]*$` and be unique within each list.\n- `source_labels` and `result_labels` must not overlap.\n- An account can have at most 20 mapping schemas.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-write-create", "metadata": { - "sidebarTitle": "List silence rules" + "sidebarTitle": "Create mapping schema" } } } }, - "/channel/silence/rule/update": { + "/enrichment/mapping/schema/delete": { "post": { - "description": "Update an existing silence rule configuration.", - "operationId": "channelSilenceRuleUpdate", + "description": "Delete a mapping schema and all its associated data. Deletion is blocked if the schema is referenced by any enrichment rule or webhook.", + "operationId": "mapping-schema-write-delete", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001, - "filters": [ - [ - { - "key": "labels.service", - "oper": "IN", - "vals": [ - "billing" - ] - } - ] - ], - "rule_id": "6621b23f4a2c5e0012ab34cd", - "rule_name": "Mute during maintenance", - "time_filter": { - "end_time": 1710086400, - "start_time": 1710000000 - } + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/UpdateSilenceRuleRequest" + "$ref": "#/components/schemas/MappingSchemaIDRequest" } } }, @@ -33511,45 +39118,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update silence rule", + "summary": "Delete mapping schema", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-silence-rule-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- If the schema is still referenced, the response returns HTTP 400 with a `refs` list of blocking references.\n- Only the schema creator, account admin, or team member can delete the schema.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.\n- High-risk operation. Console JWT callers must pass a second-factor code; `app_key` callers bypass the MFA prompt but remain audited — treat the key as a secret.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-write-delete", "metadata": { - "sidebarTitle": "Update silence rule" + "sidebarTitle": "Delete mapping schema" } } } }, - "/channel/unsubscribe/rule/create": { + "/enrichment/mapping/schema/info": { "post": { - "description": "Create a drop rule to filter out unwanted alerts before they become incidents.", - "operationId": "channelUnsubscribeRuleCreate", + "description": "Return detail of a single mapping schema by its ID.", + "operationId": "mapping-schema-read-info", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "description": "Discard all alerts from the test environment before they create incidents", - "filters": [ - [ - { - "key": "labels.env", - "oper": "IN", - "vals": [ - "test", - "dev" - ] - } - ] - ], - "rule_name": "Drop test environment alerts" + "schema_id": "665f1a2b3c4d5e6f7a8b9c01" }, "schema": { - "$ref": "#/components/schemas/CreateDropRuleRequest" + "$ref": "#/components/schemas/MappingSchemaIDRequest" } } }, @@ -33561,8 +39154,22 @@ "application/json": { "example": { "data": { - "rule_id": "69db2f6ba0fe7db6448b1505", - "rule_name": "Test drop rule" + "created_at": 1710000000, + "creator_id": 80011, + "description": "Enrich alerts with CMDB data", + "result_labels": [ + "owner", + "team", + "service" + ], + "schema_id": "665f1a2b3c4d5e6f7a8b9c01", + "schema_name": "CMDB Lookup", + "source_labels": [ + "host" + ], + "status": "enabled", + "team_id": 0, + "updated_at": 1710000000 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -33574,7 +39181,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleCreateResponse" + "$ref": "#/components/schemas/MappingSchemaItem" } }, "type": "object" @@ -33598,32 +39205,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create drop rule", + "summary": "Get mapping schema detail", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Returns `null` if the schema does not exist.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-read-info", "metadata": { - "sidebarTitle": "Create drop rule" + "sidebarTitle": "Get mapping schema detail" } } } }, - "/channel/unsubscribe/rule/delete": { + "/enrichment/mapping/schema/list": { "post": { - "description": "Delete a drop rule. Only a `disabled` rule can be deleted.", - "operationId": "channelUnsubscribeRuleDelete", + "description": "Return all mapping schemas for the account, sorted by creation time ascending.", + "operationId": "mapping-schema-read-list", "requestBody": { "content": { "application/json": { - "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/EmptyRequest" } } }, @@ -33634,7 +39238,29 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "created_at": 1710000000, + "creator_id": 80011, + "description": "Enrich alerts with CMDB data", + "result_labels": [ + "owner", + "team", + "service" + ], + "schema_id": "665f1a2b3c4d5e6f7a8b9c01", + "schema_name": "CMDB Lookup", + "source_labels": [ + "host" + ], + "status": "enabled", + "team_id": 0, + "updated_at": 1710000000 + } + ], + "total": 1 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -33645,7 +39271,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/MappingSchemaListResponse" } }, "type": "object" @@ -33669,32 +39295,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete drop rule", + "summary": "List mapping schemas", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) or **Channels Manage** (`on-call`) or **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-read-list", "metadata": { - "sidebarTitle": "Delete drop rule" + "sidebarTitle": "List mapping schemas" } } } }, - "/channel/unsubscribe/rule/disable": { + "/enrichment/mapping/schema/update": { "post": { - "description": "Disable a drop rule without deleting it. Only an `enabled` rule can be disabled.", - "operationId": "channelUnsubscribeRuleDisable", + "description": "Update the name, description, or owning team of a mapping schema. Source and result labels cannot be changed after creation.", + "operationId": "mapping-schema-write-update", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "description": "Updated description", + "schema_id": "665f1a2b3c4d5e6f7a8b9c01", + "schema_name": "CMDB Lookup v2" }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/MappingSchemaUpdateRequest" } } }, @@ -33740,32 +39367,50 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable drop rule", + "summary": "Update mapping schema", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Only the schema creator, account admin, or team member can update the schema.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-write-update", "metadata": { - "sidebarTitle": "Disable drop rule" + "sidebarTitle": "Update mapping schema" } } } }, - "/channel/unsubscribe/rule/enable": { + "/enrichment/upsert": { "post": { - "description": "Enable a disabled drop rule. Only a `disabled` rule can be enabled.", - "operationId": "channelUnsubscribeRuleEnable", + "description": "Create or fully replace the enrichment rule set for an integration. The entire `rules` array is replaced atomically.", + "operationId": "enrichment-write-upsert", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 3521074710131, - "rule_id": "6621b23f4a2c5e0012ab34cd" + "integration_id": 5001, + "rules": [ + { + "kind": "extraction", + "settings": { + "override": true, + "pattern": "(?Pprod|staging|dev)", + "result_label": "environment", + "source_field": "labels.env" + } + }, + { + "kind": "composition", + "settings": { + "override": false, + "result_label": "full_env", + "template": "{{.Labels.region}}-{{.Labels.environment}}" + } + } + ] }, "schema": { - "$ref": "#/components/schemas/ChannelRuleIDRequest" + "$ref": "#/components/schemas/EnrichmentUpsertRequest" } } }, @@ -33811,31 +39456,42 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable drop rule", + "summary": "Upsert enrichment rules", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) or **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- Enrichment rules are evaluated in order.\n- Each rule has a `kind`: `extraction` (regex/gjson extraction), `composition` (template-based label composition), `mapping` (lookup via mapping schema or API), or `drop` (remove labels).\n- The optional `if` field is an `AndFilters` condition: if it does not match, the rule is skipped.\n- For `kind: extraction`: `source_field` must be `title`, `description`, or a `labels.*` key; specify exactly one of `pattern` (RE2 regex — its capture groups are joined with a space and written to `result_label`) or `g_json` (GJson path).\n- For `kind: composition`: `template` is a Go text/template rendered against the event struct, e.g. `{{.Title}}`, `{{.Description}}`, `{{.Labels.key}}`.\n- For `kind: mapping`: `mapping_type` is `schema` (default) or `api`; provide `schema_id` or `api_id` accordingly.\n- For `kind: drop`: `drop_labels` lists the label keys to remove.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/alert-enrichment/enrichment-write-upsert", "metadata": { - "sidebarTitle": "Enable drop rule" + "sidebarTitle": "Upsert enrichment rules" } } } }, - "/channel/unsubscribe/rule/list": { + "/field/create": { "post": { - "description": "List drop rules for a channel.", - "operationId": "channelUnsubscribeRuleList", + "description": "Create a new incident custom field on the account.", + "operationId": "field-write-create", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001 + "default_value": "Medium", + "description": "Business severity tier.", + "display_name": "Severity Class", + "field_name": "severity_class", + "field_type": "single_select", + "options": [ + "Critical", + "High", + "Medium", + "Low" + ], + "value_type": "string" }, "schema": { - "$ref": "#/components/schemas/ChannelScopedListRequest" + "$ref": "#/components/schemas/CreateFieldRequest" } } }, @@ -33847,30 +39503,8 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "channel_id": 5967964835131, - "created_at": 1773978928, - "description": "", - "filters": [ - [ - { - "key": "data_source_id", - "oper": "IN", - "vals": [ - "6113996590131" - ] - } - ] - ], - "rule_id": "69bcc530b9e63df36603e421", - "rule_name": "Drop test alerts", - "status": "enabled", - "updated_at": 1773978928, - "updated_by": 3790925372131 - } - ] + "field_id": "66e9d3a4f7c2b04a1c8a91b3", + "field_name": "severity_class" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -33882,7 +39516,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListDropRulesResponse" + "$ref": "#/components/schemas/CreateFieldResponse" } }, "type": "object" @@ -33906,44 +39540,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List drop rules", + "summary": "Create field", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Maximum **15** custom fields per account.\n- `field_name` must match `^[a-zA-Z_][a-zA-Z0-9_]{0,39}$` and is immutable after creation; `display_name` must also be unique within the account.\n- Type-specific rules: `checkbox` requires `value_type=bool` and no `options`; `single_select`/`multi_select` require `value_type=string` and a non-empty unique `options` list; `text` requires `value_type=string` and no `options`.\n- Response contains only `field_id` and `field_name`; use `/field/info` to fetch the full object.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/alert-enrichment/field-write-create", "metadata": { - "sidebarTitle": "List drop rules" + "sidebarTitle": "Create field" } } } }, - "/channel/unsubscribe/rule/update": { + "/field/delete": { "post": { - "description": "Update an existing drop rule configuration.", - "operationId": "channelUnsubscribeRuleUpdate", + "description": "Delete an incident custom field and asynchronously strip it from existing incidents.", + "operationId": "field-write-delete", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001, - "filters": [ - [ - { - "key": "labels.env", - "oper": "IN", - "vals": [ - "test" - ] - } - ] - ], - "rule_id": "6621b23f4a2c5e0012ab34cf", - "rule_name": "Drop test alerts" + "field_id": "66e9d3a4f7c2b04a1c8a91b3" }, "schema": { - "$ref": "#/components/schemas/UpdateDropRuleRequest" + "$ref": "#/components/schemas/DeleteFieldRequest" } } }, @@ -33965,7 +39586,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "type": "object" } }, "type": "object" @@ -33977,7 +39598,41 @@ "description": "Success" }, "400": { - "$ref": "#/components/responses/BadRequest" + "content": { + "application/json": { + "examples": { + "fieldStillReferenced": { + "value": { + "data": { + "refs": [ + { + "href": "https://console.flashcat.cloud/forms/resolve", + "kind": "custom_form", + "name": "Resolve incident" + } + ] + }, + "error": { + "code": "ReferenceExist", + "message": "There still are associated resources, deletion is blocked." + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + } + } + }, + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/ErrorResponse" + }, + { + "$ref": "#/components/schemas/FieldDeleteReferenceError" + } + ] + } + } + }, + "description": "Invalid request or the field is still referenced by a custom form." }, "401": { "$ref": "#/components/responses/Unauthorized" @@ -33989,33 +39644,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update drop rule", + "summary": "Delete field", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/channels/channel-unsubscribe-rule-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- The field is marked deleted synchronously; clearing its values from historical incidents runs in the background and may take time on large datasets.\n- Re-creating a field with the same `field_name` is only allowed if `field_type` and `value_type` match the deleted entry.\n- Deletion is rejected with `ReferenceExist` and the referencing custom forms in `data.refs` until no form uses the field.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/alert-enrichment/field-write-delete", "metadata": { - "sidebarTitle": "Update drop rule" + "sidebarTitle": "Delete field" } } } }, - "/channel/update": { + "/field/info": { "post": { - "description": "Update an existing channel's configuration and settings.", - "operationId": "channelUpdate", + "description": "Return the configuration of a single incident custom field by ID.", + "operationId": "field-read-info", "requestBody": { "content": { "application/json": { "example": { - "channel_id": 1001, - "channel_name": "Production Alerts (v2)", - "description": "Updated description" + "field_id": "66e9d3a4f7c2b04a1c8a91b3" }, "schema": { - "$ref": "#/components/schemas/UpdateChannelRequest" + "$ref": "#/components/schemas/FieldInfoRequest" } } }, @@ -34027,7 +39680,25 @@ "application/json": { "example": { "data": { - "external_report_token": "" + "account_id": 80001, + "created_at": 1710000000, + "creator_id": 80011, + "default_value": "Medium", + "description": "Business severity tier.", + "display_name": "Severity Class", + "field_id": "66e9d3a4f7c2b04a1c8a91b3", + "field_name": "severity_class", + "field_type": "single_select", + "options": [ + "Critical", + "High", + "Medium", + "Low" + ], + "status": "enabled", + "updated_at": 1710000000, + "updated_by": 80011, + "value_type": "string" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -34039,7 +39710,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/UpdateChannelResponse" + "$ref": "#/components/schemas/FieldItem" } }, "type": "object" @@ -34063,31 +39734,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update channel", + "summary": "Get field detail", "tags": [ - "On-call/Channels" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/channel-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) or **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- An unknown `field_id` yields a 400 error. A soft-deleted field is still returned, with `status` = `deleted` and `deleted_at` set.\n- The shape of `options` and `default_value` varies by `field_type` — see the `FieldItem` schema.", + "href": "/en/api-reference/on-call/alert-enrichment/field-read-info", "metadata": { - "sidebarTitle": "Update channel" + "sidebarTitle": "Get field detail" } } } }, - "/datasource/im/person/try-link": { + "/field/list": { "post": { - "description": "Try to automatically link unbound members to their IM accounts for one integration.", - "operationId": "datasourceImPersonTryLink", + "description": "Return all incident custom fields configured for the account.", + "operationId": "field-read-list", "requestBody": { "content": { "application/json": { "example": { - "integration_id": 6113996590131 + "asc": false, + "orderby": "updated_at", + "query": "severity" }, "schema": { - "$ref": "#/components/schemas/TryLinkPersonRequest" + "$ref": "#/components/schemas/FieldListRequest" } } }, @@ -34099,8 +39772,28 @@ "application/json": { "example": { "data": { - "new_linked_person_ids": [ - 5348648172131 + "items": [ + { + "account_id": 80001, + "created_at": 1710000000, + "creator_id": 80011, + "default_value": "Medium", + "description": "Business severity tier.", + "display_name": "Severity Class", + "field_id": "66e9d3a4f7c2b04a1c8a91b3", + "field_name": "severity_class", + "field_type": "single_select", + "options": [ + "Critical", + "High", + "Medium", + "Low" + ], + "status": "enabled", + "updated_at": 1710000000, + "updated_by": 80011, + "value_type": "string" + } ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" @@ -34113,7 +39806,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/TryLinkPersonResponse" + "$ref": "#/components/schemas/FieldListResponse" } }, "type": "object" @@ -34137,29 +39830,40 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Attempt IM person linking", + "summary": "List fields", "tags": [ - "On-call/Integrations" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- The server uses member email and phone values to find matching users in DingTalk, Feishu, or WeCom.\n- When no member can be linked, the response either carries an empty `new_linked_person_ids` array or omits the `data` field entirely.", - "href": "/en/api-reference/on-call/integrations/datasource-im-person-try-link", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) or **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- All non-deleted fields are returned in a single response — there is no pagination and no `total` counter.\n- `query` matches against `field_name` only; invalid regular expressions are auto-escaped to a literal substring match.", + "href": "/en/api-reference/on-call/alert-enrichment/field-read-list", "metadata": { - "sidebarTitle": "Attempt IM person linking" + "sidebarTitle": "List fields" } } } }, - "/datasource/im/war-room-enabled/list": { + "/field/update": { "post": { - "description": "List IM integrations that have the war-room feature enabled for the account.", - "operationId": "im-war-room-enabled-list", + "description": "Update mutable attributes of an existing incident custom field.", + "operationId": "field-write-update", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "default_value": "Medium", + "description": "Business severity tier.", + "display_name": "Severity Class", + "field_id": "66e9d3a4f7c2b04a1c8a91b3", + "options": [ + "Critical", + "High", + "Medium", + "Low" + ] + }, "schema": { - "type": "object" + "$ref": "#/components/schemas/UpdateFieldRequest" } } }, @@ -34170,35 +39874,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 10001, - "category": "im", - "created_at": 1716962400, - "creator_id": 20001, - "data_source_id": 362, - "description": "Feishu war-room integration", - "exclusive_data_source_id": 0, - "integration_id": 362, - "integration_key": "ik_8f3a2b1c9d0e", - "last_time": 0, - "name": "Feishu Ops", - "no_editable": false, - "plugin_id": 101, - "plugin_type": "feishu", - "plugin_type_name": "Feishu", - "ref_id": "", - "settings": { - "war_room_enabled": true - }, - "status": "enabled", - "team_id": 0, - "updated_at": 1716962700, - "updated_by": 20001 - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -34209,7 +39885,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListWarRoomEnabledResponse" + "type": "object" } }, "type": "object" @@ -34233,31 +39909,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List war-room-enabled IM integrations", + "summary": "Update field", "tags": [ - "On-call/IM integrations" + "On-call/Alert enrichment" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", - "href": "/en/api-reference/on-call/integrations/im-war-room-enabled-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Only `display_name`, `description`, `options`, and `default_value` can be changed; `field_name`, `field_type`, and `value_type` are immutable.\n- `options` and `default_value` must remain consistent with the field's existing type — same rules as create.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/alert-enrichment/field-write-update", "metadata": { - "sidebarTitle": "List war-room-enabled IM integrations" + "sidebarTitle": "Update field" } } } }, - "/enrichment/info": { + "/incident/ack": { "post": { - "description": "Return the enrichment rule set configured for a specific integration.", - "operationId": "enrichment-read-info", + "description": "Acknowledge an incident to indicate you are actively working on it.", + "operationId": "incidentAck", "requestBody": { "content": { "application/json": { "example": { - "integration_id": 5001 + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ] }, "schema": { - "$ref": "#/components/schemas/EnrichmentInfoRequest" + "$ref": "#/components/schemas/AckIncidentRequest" } } }, @@ -34268,25 +39946,7 @@ "content": { "application/json": { "example": { - "data": { - "created_at": 1710000000, - "creator_id": 80011, - "integration_id": 5001, - "rules": [ - { - "kind": "extraction", - "settings": { - "override": true, - "pattern": "^(prod|staging|dev).*$", - "result_label": "environment", - "source_field": "labels.env" - } - } - ], - "status": "enabled", - "updated_at": 1710000000, - "updated_by": 80011 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -34297,7 +39957,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EnrichmentItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -34321,34 +39981,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get enrichment rules", + "summary": "Acknowledge incident", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) or **Channels Manage** (`on-call`) or **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- Returns `null` if no enrichment rules have been configured for the integration.", - "href": "/en/api-reference/on-call/alert-enrichment/enrichment-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- When an acknowledgement form applies, `custom_fields`, `summary`, and `images` must match its visible elements and required rules.\n- For a batch, form values are accepted only when every selected incident resolves to the same form; otherwise acknowledge incidents individually.\n- The legacy `values` and `custom_values` properties are rejected; use `custom_fields`.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-ack", "metadata": { - "sidebarTitle": "Get enrichment rules" + "sidebarTitle": "Acknowledge incident" } } } }, - "/enrichment/list": { + "/incident/alert/list": { "post": { - "description": "Return the enrichment rule sets for a list of integration IDs.", - "operationId": "enrichment-read-list", + "description": "List all alerts merged into a specific incident.", + "operationId": "incidentAlertList", "requestBody": { "content": { "application/json": { "example": { - "integration_ids": [ - 5001, - 5002 - ] + "incident_id": "69da451ef77b1b51f40e83ee", + "include_events": true, + "is_active": true, + "limit": 100, + "p": 1 }, "schema": { - "$ref": "#/components/schemas/EnrichmentListRequest" + "$ref": "#/components/schemas/ListIncidentAlertsRequest" } } }, @@ -34362,15 +40023,60 @@ "data": { "items": [ { - "created_at": 1710000000, - "creator_id": 80011, - "integration_id": 5001, - "rules": [], - "status": "enabled", - "updated_at": 1710000000, - "updated_by": 80011 + "account_id": 2451002751131, + "alert_id": "69da451df77b1b51f40e83de", + "alert_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", + "alert_severity": "Critical", + "alert_status": "Critical", + "channel_id": 2551105804131, + "channel_name": "Ops Channel", + "channel_status": "enabled", + "created_at": 1775912221, + "data_source_id": 2490562293131, + "data_source_name": "FlashMonit", + "data_source_ref_id": "a_2451002751131", + "data_source_type": "monit.alert", + "description": "", + "end_time": 0, + "event_cnt": 17, + "events": [ + { + "alert_id": "69da451df77b1b51f40e83de", + "event_id": "69da451df77b1b51f40e83df", + "event_severity": "Critical", + "event_status": "Critical", + "event_time": 1712650000, + "labels": { + "host": "web-01" + }, + "title": "CPU usage > 90%" + } + ], + "ever_muted": false, + "images": null, + "incident": { + "incident_id": "69da451ef77b1b51f40e83ee", + "progress": "Triggered", + "title": "CPU usage high - web-server-01" + }, + "integration_id": 2490562293131, + "integration_name": "FlashMonit", + "integration_ref_id": "a_2451002751131", + "integration_type": "monit.alert", + "labels": { + "check": "cpu_usage_high", + "resource": "web-server-01" + }, + "last_time": 1775969819, + "responder_email": "", + "responder_name": "", + "start_time": 1775912219, + "title": "CPU usage high - web-server-01", + "title_rule": "", + "updated_at": 1775969821 } - ] + ], + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -34382,7 +40088,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EnrichmentListResponse" + "$ref": "#/components/schemas/ListIncidentAlertsResponse" } }, "type": "object" @@ -34406,39 +40112,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List enrichment rules", + "summary": "List alerts of incident", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/alert-enrichment/enrichment-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- Set `include_events=true` only when you need a preview of each alert's raw events.\n- Event previews are capped at the 20 newest events per alert. Use `POST /alert/event/list` for a full paginated event history.\n- `event_cnt` still reports the total number of raw events merged into each alert.", + "href": "/en/api-reference/on-call/incidents/incident-alert-list", "metadata": { - "sidebarTitle": "List enrichment rules" + "sidebarTitle": "List alerts of incident" } } } }, - "/enrichment/mapping/api/create": { + "/incident/assign": { "post": { - "description": "Create a new external HTTP API endpoint used to enrich alerts via HTTP lookup.", - "operationId": "mapping-api-write-create", + "description": "Dispatch an incident to a specific escalation level or responder.", + "operationId": "incidentAssign", "requestBody": { "content": { "application/json": { "example": { - "api_name": "CMDB API", - "description": "Query CMDB for host metadata", - "headers": { - "X-Token": "mytoken" + "assigned_to": { + "person_ids": [ + 2476444212131 + ], + "type": "assign" }, - "insecure_skip_verify": false, - "retry_count": 1, - "timeout": 2, - "url": "https://cmdb.example.com/api/lookup" + "incident_id": "69da451ef77b1b51f40e83ee" }, "schema": { - "$ref": "#/components/schemas/MappingAPICreateRequest" + "$ref": "#/components/schemas/AssignIncidentRequest" } } }, @@ -34449,10 +40153,7 @@ "content": { "application/json": { "example": { - "data": { - "api_id": "665f1a2b3c4d5e6f7a8b9c02", - "api_name": "CMDB API" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -34463,7 +40164,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingAPICreateResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -34487,31 +40188,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create mapping API", + "summary": "Assign incident", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- `url` must start with `http://` or `https://` and cannot resolve to an internal IP (in SaaS mode).\n- `timeout` is the HTTP read timeout in seconds (1–3, default 2).\n- `retry_count` is the number of retries on failure (0–1, default 0).\n- Headers with security-sensitive names (e.g. `authorization`, `cookie`) are rejected in SaaS mode.\n- An account can have at most 50 mapping APIs.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-assign", "metadata": { - "sidebarTitle": "Create mapping API" + "sidebarTitle": "Assign incident" } } } }, - "/enrichment/mapping/api/delete": { + "/incident/comment": { "post": { - "description": "Delete a mapping API. Deletion is blocked if the API is referenced by any enrichment rule.", - "operationId": "mapping-api-write-delete", + "description": "Add a text comment to the incident timeline.", + "operationId": "incidentComment", "requestBody": { "content": { "application/json": { "example": { - "api_id": "665f1a2b3c4d5e6f7a8b9c02" + "comment": "Root cause identified. [@Jane Doe](flashduty://ref/member/2476444212131) please verify the fix.", + "comment_type_id": "6a5895d672a064bc2d3ddfc2", + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ] }, "schema": { - "$ref": "#/components/schemas/MappingAPIIDRequest" + "$ref": "#/components/schemas/CommentIncidentRequest" } } }, @@ -34557,31 +40262,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete mapping API", + "summary": "Add comment to incident", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- If the API is still referenced, the response returns HTTP 400 with a `refs` list.\n- Only the API creator, account admin, or team member can delete the API.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- To mention a member, embed a markdown link in `comment` in the form `[@Display Name](flashduty://ref/member/)`. Mentioned members receive a dedicated personal notification, which is not affected by `mute_reply`.\n- Plain `@name` text without the link syntax does not create a mention.\n- The server rewrites each mention's display label to the member's canonical name.", + "href": "/en/api-reference/on-call/incidents/incident-comment", "metadata": { - "sidebarTitle": "Delete mapping API" + "sidebarTitle": "Add comment to incident" } } } }, - "/enrichment/mapping/api/info": { + "/incident/comment-type/create": { "post": { - "description": "Return detail of a single mapping API by its ID.", - "operationId": "mapping-api-read-info", + "description": "Create a comment type that can be attached to incident comments.", + "operationId": "incidentCommentTypeCreate", "requestBody": { "content": { "application/json": { "example": { - "api_id": "665f1a2b3c4d5e6f7a8b9c02" + "color": "#30A46C", + "name": "Key finding" }, "schema": { - "$ref": "#/components/schemas/MappingAPIIDRequest" + "$ref": "#/components/schemas/CreateIncidentCommentTypeRequest" } } }, @@ -34593,16 +40299,18 @@ "application/json": { "example": { "data": { - "api_id": "665f1a2b3c4d5e6f7a8b9c02", - "api_name": "CMDB API", - "created_at": 1710000000, - "creator_id": 80011, - "insecure_skip_verify": false, - "retry_count": 1, - "status": "enabled", - "timeout": 2, - "updated_at": 1710000000, - "url": "https://cmdb.example.com/api/lookup" + "comment_type_id": "6a5895d672a064bc2d3ddfc2", + "item": { + "account_id": 2451002751131, + "color": "#30A46C", + "comment_type_id": "6a5895d672a064bc2d3ddfc2", + "created_at": 1784190422, + "creator_id": 5068740052131, + "name": "Key finding", + "position": 1, + "updated_at": 1784207748, + "updated_by": 5068740052131 + } }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -34614,7 +40322,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingAPIItem" + "$ref": "#/components/schemas/CreateIncidentCommentTypeResponse" } }, "type": "object" @@ -34638,29 +40346,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get mapping API detail", + "summary": "Create a comment type", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `null` if the API does not exist.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- The new type is appended to the end of the display ordering.\n- The name must be unique within the account (case-insensitive, after trimming whitespace).\n- An account can have at most 10 comment types.\n- This permission is admin-only by default; custom roles must be granted it explicitly.", + "href": "/en/api-reference/on-call/incidents/incident-comment-type-create", "metadata": { - "sidebarTitle": "Get mapping API detail" + "sidebarTitle": "Create a comment type" } } } }, - "/enrichment/mapping/api/list": { + "/incident/comment-type/delete": { "post": { - "description": "Return all mapping APIs configured for the account.", - "operationId": "mapping-api-read-list", + "description": "Delete a comment type. Comments that used it keep their text but lose the type label.", + "operationId": "incidentCommentTypeDelete", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "comment_type_id": "6a5895b572a064bc2d3ddfc0" + }, "schema": { - "$ref": "#/components/schemas/EmptyRequest" + "$ref": "#/components/schemas/DeleteIncidentCommentTypeRequest" } } }, @@ -34671,28 +40381,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "api_id": "665f1a2b3c4d5e6f7a8b9c02", - "api_name": "CMDB API", - "created_at": 1710000000, - "creator_id": 80011, - "description": "Query CMDB for host metadata", - "headers": { - "Authorization": "Bearer eyJhbGciOiJIUzI1NiJ9.example-token" - }, - "insecure_skip_verify": false, - "retry_count": 1, - "status": "enabled", - "team_id": 0, - "timeout": 2, - "updated_at": 1710000000, - "url": "https://cmdb.example.com/api/lookup" - } - ], - "total": 1 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -34703,7 +40392,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingAPIListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -34727,33 +40416,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List mapping APIs", + "summary": "Delete a comment type", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- Hard delete — the comment type is removed permanently and cannot be restored.\n- Existing comments that referenced the type lose the type label but are not otherwise affected.\n- This permission is admin-only by default; custom roles must be granted it explicitly.", + "href": "/en/api-reference/on-call/incidents/incident-comment-type-delete", "metadata": { - "sidebarTitle": "List mapping APIs" + "sidebarTitle": "Delete a comment type" } } } }, - "/enrichment/mapping/api/update": { + "/incident/comment-type/list": { "post": { - "description": "Update configuration of an existing mapping API.", - "operationId": "mapping-api-write-update", + "description": "Retrieve all comment types of the account, ordered by their display position.", + "operationId": "incidentCommentTypeList", "requestBody": { "content": { "application/json": { - "example": { - "api_id": "665f1a2b3c4d5e6f7a8b9c02", - "retry_count": 1, - "timeout": 3 - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/MappingAPIUpdateRequest" + "$ref": "#/components/schemas/ListIncidentCommentTypesRequest" } } }, @@ -34764,7 +40449,32 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "account_id": 2451002751131, + "color": "#30A46C", + "comment_type_id": "6a5895d672a064bc2d3ddfc2", + "created_at": 1784190422, + "creator_id": 5068740052131, + "name": "Key finding", + "position": 1, + "updated_at": 1784207748, + "updated_by": 5068740052131 + }, + { + "account_id": 2451002751131, + "color": "#998000", + "comment_type_id": "6a5895b572a064bc2d3ddfc0", + "created_at": 1784190389, + "creator_id": 5068740052131, + "name": "Hypothesis", + "position": 2, + "updated_at": 1785141535, + "updated_by": 3790925372131 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -34775,7 +40485,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ListIncidentCommentTypesResponse" } }, "type": "object" @@ -34799,35 +40509,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update mapping API", + "summary": "List comment types", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Only the API creator, account admin, or team member can update the API.\n- All updatable fields are optional — only provided fields are changed.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-api-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- Returns the full list in one call — there is no pagination.\n- An account can have at most 10 comment types.", + "href": "/en/api-reference/on-call/incidents/incident-comment-type-list", "metadata": { - "sidebarTitle": "Update mapping API" + "sidebarTitle": "List comment types" } } } }, - "/enrichment/mapping/data/delete": { + "/incident/comment-type/reorder": { "post": { - "description": "Delete up to 100 mapping data rows by their keys.", - "operationId": "mapping-data-write-delete", + "description": "Set the display order of all comment types by passing every type ID in the desired order.", + "operationId": "incidentCommentTypeReorder", "requestBody": { "content": { "application/json": { "example": { - "keys": [ - "server01", - "server02" - ], - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "comment_type_ids": [ + "6a5895b572a064bc2d3ddfc0", + "6a5895d672a064bc2d3ddfc2" + ] }, "schema": { - "$ref": "#/components/schemas/MappingDataDeleteRequest" + "$ref": "#/components/schemas/ReorderIncidentCommentTypesRequest" } } }, @@ -34873,31 +40582,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete mapping data rows", + "summary": "Reorder comment types", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- Full-set reorder — `comment_type_ids` must contain every comment type of the account, each exactly once, in the desired order.\n- Positions are reassigned starting from 1: the first ID in the array becomes position 1.\n- This permission is admin-only by default; custom roles must be granted it explicitly.", + "href": "/en/api-reference/on-call/incidents/incident-comment-type-reorder", "metadata": { - "sidebarTitle": "Delete mapping data rows" + "sidebarTitle": "Reorder comment types" } } } }, - "/enrichment/mapping/data/download": { + "/incident/comment-type/update": { "post": { - "description": "Export all data rows of a mapping schema as a CSV file download.", - "operationId": "mapping-data-read-download", + "description": "Update the name and/or color of an existing account comment type.", + "operationId": "incidentCommentTypeUpdate", "requestBody": { "content": { "application/json": { "example": { - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "color": "#B7791F", + "comment_type_id": "6a5895b572a064bc2d3ddfc0" }, "schema": { - "$ref": "#/components/schemas/MappingSchemaIDRequest" + "$ref": "#/components/schemas/UpdateIncidentCommentTypeRequest" } } }, @@ -34906,16 +40616,29 @@ "responses": { "200": { "content": { - "application/octet-stream": { - "example": "host,owner,team\nserver01,alice,sre\nserver02,bob,backend\n", + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { - "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=.csv`). The header row lists the schema's source_labels followed by result_labels in order; each subsequent row is one mapping document.", - "format": "binary", - "type": "string" + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] } } }, - "description": "Success. CSV attachment stream, not a JSON envelope." + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -34930,35 +40653,65 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Download mapping data as CSV", + "summary": "Update a comment type", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- The response is a CSV file with `Content-Disposition: attachment` header.\n- The CSV header row matches the schema's source and result labels in order.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-read-download", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- Partial update — only the provided fields are changed, but at least one of `name` or `color` must be provided.\n- The name must remain unique within the account (case-insensitive, after trimming whitespace).\n- This permission is admin-only by default; custom roles must be granted it explicitly.", + "href": "/en/api-reference/on-call/incidents/incident-comment-type-update", "metadata": { - "sidebarTitle": "Download mapping data as CSV" + "sidebarTitle": "Update a comment type" } } } }, - "/enrichment/mapping/data/list": { + "/incident/create": { "post": { - "description": "Return paginated mapping data rows for a schema, with optional exact-match filtering on source label values.", - "operationId": "mapping-data-read-list", + "description": "Manually create a new incident and assign responders.", + "operationId": "incidentCreate", "requestBody": { "content": { "application/json": { "example": { - "asc": false, - "limit": 20, - "orderby": "updated_at", - "p": 1, - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "assigned_to": { + "person_ids": [ + 2476444212131 + ] + }, + "channel_id": 2551105804131, + "incident_severity": "Critical", + "title": "Database connection timeout on prod-db-01" }, "schema": { - "$ref": "#/components/schemas/MappingDataListRequest" + "$ref": "#/components/schemas/CreateIncidentRequest" + } + }, + "multipart/form-data": { + "encoding": { + "data": { + "contentType": "application/json" + } + }, + "schema": { + "properties": { + "data": { + "description": "JSON-encoded CreateIncidentRequest payload.", + "type": "string" + }, + "images": { + "description": "Image files attached to the new incident.", + "items": { + "format": "binary", + "type": "string" + }, + "type": "array" + } + }, + "required": [ + "data" + ], + "type": "object" } } }, @@ -34970,21 +40723,8 @@ "application/json": { "example": { "data": { - "has_next_page": false, - "items": [ - { - "created_at": 1710000000, - "fields": { - "host": "server01", - "owner": "alice", - "service": "api", - "team": "sre" - }, - "key": "server01", - "updated_at": 1710000000 - } - ], - "total": 1 + "incident_id": "69db2ef1a0fe7db6448b14f1", + "title": "API test incident for docs" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -34996,7 +40736,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingDataListResponse" + "$ref": "#/components/schemas/CreateIncidentResponse" } }, "type": "object" @@ -35020,31 +40760,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List mapping data", + "summary": "Create incident", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- If `query` is provided, all source labels must be specified — partial source label queries are rejected.\n- Pagination uses cursor-based (`search_after_ctx`) or page-based (`p`, `limit`) navigation. `limit` defaults to 20, max 100.\n- The `search_after_ctx` token from a response can be passed back to retrieve the next page.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- When an account create form applies, its visible custom fields and required system values must be supplied.\n- To attach images, send `multipart/form-data` with the JSON request in `data` and files in `images`; the complete request must not exceed 50 MiB.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-create", "metadata": { - "sidebarTitle": "List mapping data" + "sidebarTitle": "Create incident" } } } }, - "/enrichment/mapping/data/truncate": { + "/incident/custom-action/do": { "post": { - "description": "Delete all data rows in a mapping schema.", - "operationId": "mapping-data-write-truncate", + "description": "Execute a custom action configured for an incident.", + "operationId": "incidentCustomActionDo", "requestBody": { "content": { "application/json": { "example": { - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "incident_id": "69da451ef77b1b51f40e83ee", + "integration_id": 2490562293131 }, "schema": { - "$ref": "#/components/schemas/MappingSchemaIDRequest" + "$ref": "#/components/schemas/DoIncidentCustomActionRequest" } } }, @@ -35055,7 +40796,9 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "message": "" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -35066,7 +40809,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/DoIncidentCustomActionResponse" } }, "type": "object" @@ -35090,63 +40833,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Truncate mapping data", + "summary": "Execute custom action", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- This is an irreversible bulk-delete operation.\n- High-risk operation. Console JWT callers must pass a second-factor code; `app_key` callers bypass the MFA prompt but remain audited — treat the key as a secret.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-truncate", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-custom-action-do", "metadata": { - "sidebarTitle": "Truncate mapping data" + "sidebarTitle": "Execute custom action" } } } }, - "/enrichment/mapping/data/upload": { + "/incident/disable-merge": { "post": { - "description": "Upload a CSV file to bulk-load mapping data. By default the existing data is truncated before loading the new rows.", - "operationId": "mapping-data-write-upload", - "parameters": [ - { - "description": "ID of the target mapping schema (ObjectID hex).", - "example": "665f1a2b3c4d5e6f7a8b9c01", - "in": "query", - "name": "schema_id", - "required": true, - "schema": { - "pattern": "^[0-9a-fA-F]{24}$", - "type": "string" - } - }, - { - "description": "Pass `TRUE` (case-insensitive) to append instead of replacing. When omitted and the schema already has data, the server truncates existing rows before importing.", - "in": "query", - "name": "do_not_truncate_first", - "required": false, - "schema": { - "enum": [ - "TRUE" - ], - "type": "string" - } - } - ], + "description": "Disable automatic merging for a specific incident.", + "operationId": "incidentDisableMerge", "requestBody": { "content": { - "multipart/form-data": { + "application/json": { + "example": { + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ] + }, "schema": { - "properties": { - "file": { - "description": "CSV file, max 100 MB. The header row must include all of the schema's source/result label names.", - "format": "binary", - "type": "string" - } - }, - "required": [ - "file" - ], - "type": "object" + "$ref": "#/components/schemas/DisableIncidentMergeRequest" } } }, @@ -35192,45 +40905,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Upload mapping data via CSV", + "summary": "Disable incident merge", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **20 requests/minute**; **2 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- The request must use `Content-Type: multipart/form-data`. The file field name is `file` and `schema_id` is a query parameter.\n- CSV header row must include all source and result label names.\n- Maximum file size: 100 MB.\n- By default the schema's existing data is truncated before import. Pass query param `do_not_truncate_first=TRUE` to append instead.\n- Duplicate source label value combinations in the CSV cause a 400 error.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-upload", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-disable-merge", "metadata": { - "sidebarTitle": "Upload mapping data via CSV" + "sidebarTitle": "Disable incident merge" } } } }, - "/enrichment/mapping/data/upsert": { + "/incident/feed": { "post": { - "description": "Insert or update up to 1000 data rows in a mapping schema. Each row must contain all source and result labels.", - "operationId": "mapping-data-write-upsert", + "description": "Retrieve the timeline feed for a specific incident, including state changes, comments and system events.", + "operationId": "incidentFeed", "requestBody": { "content": { "application/json": { "example": { - "docs": [ - { - "host": "server01", - "owner": "alice", - "service": "api", - "team": "sre" - }, - { - "host": "server02", - "owner": "bob", - "service": "gateway", - "team": "platform" - } - ], - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "incident_id": "69da451ef77b1b51f40e83ee", + "limit": 20, + "p": 1 }, "schema": { - "$ref": "#/components/schemas/MappingDataUpsertRequest" + "$ref": "#/components/schemas/ListIncidentFeedRequest" } } }, @@ -35242,9 +40943,60 @@ "application/json": { "example": { "data": { - "keys": [ - "server01", - "server02" + "has_next_page": true, + "items": [ + { + "account_id": 2451002751131, + "created_at": 1785495329402, + "creator_id": 5329873302131, + "detail": { + "assignee_ids": [ + 3790925372131, + 4756301322131 + ], + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "status": "open", + "title": "Follow-up: schedule database failover drill", + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + }, + "ref_id": "6a5f1e28807515413b384bce", + "type": "i_wi_created", + "updated_at": 1785495329402 + }, + { + "account_id": 2451002751131, + "created_at": 1785496333926, + "creator_id": 3790925372131, + "detail": { + "comment": "Root cause identified: connection pool exhaustion on the primary database.", + "comment_type": { + "color": "#30A46C", + "id": "6a5895d672a064bc2d3ddfc2", + "name": "Key finding" + }, + "comment_type_id": "6a5895d672a064bc2d3ddfc2" + }, + "ref_id": "6a5f1e28807515413b384bce", + "type": "i_comm", + "updated_at": 1785496333926 + }, + { + "account_id": 2451002751131, + "created_at": 1785496384806, + "creator_id": 3790925372131, + "detail": { + "from_status": "open", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "title": "Follow-up: schedule database failover drill", + "to_status": "done", + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + }, + "ref_id": "6a5f1e28807515413b384bce", + "type": "i_wi_completed", + "updated_at": 1785496384806 + } ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" @@ -35257,7 +41009,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingDataUpsertResponse" + "$ref": "#/components/schemas/ListIncidentFeedResponse" } }, "type": "object" @@ -35281,40 +41033,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Upsert mapping data rows", + "summary": "Get incident timeline", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Each doc must contain values for all labels defined in `source_labels` and `result_labels`.\n- Values for unknown labels are silently dropped.\n- Each value must be at most 2048 characters.\n- Upsert is keyed on the combination of source label values — existing rows with the same source key are updated.\n- A schema can hold at most 10,000 rows by default.\n- The operation is locked per schema; concurrent upserts to the same schema may fail with `ErrRequestTooFrequently`.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-data-write-upsert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- For `i_comm` entries, `detail.comment_type` is resolved from the current account-level comment type definition at read time, so it reflects the type's latest name and color.", + "href": "/en/api-reference/on-call/incidents/incident-feed", "metadata": { - "sidebarTitle": "Upsert mapping data rows" + "sidebarTitle": "Get incident timeline" } } } }, - "/enrichment/mapping/schema/create": { + "/incident/field/reset": { "post": { - "description": "Create a new mapping schema defining source lookup labels and the result labels to populate. Requires a Pro plan.", - "operationId": "mapping-schema-write-create", + "description": "Update a custom field value on an incident.", + "operationId": "incidentFieldReset", "requestBody": { "content": { "application/json": { "example": { - "description": "Enrich alerts with CMDB data", - "result_labels": [ - "owner", - "team", - "service" - ], - "schema_name": "CMDB Lookup", - "source_labels": [ - "host" - ] + "field_name": "affected_service", + "field_value": "payment-service", + "incident_id": "69da451ef77b1b51f40e83ee" }, "schema": { - "$ref": "#/components/schemas/MappingSchemaCreateRequest" + "$ref": "#/components/schemas/ResetIncidentFieldRequest" } } }, @@ -35325,10 +41070,7 @@ "content": { "application/json": { "example": { - "data": { - "schema_id": "665f1a2b3c4d5e6f7a8b9c01", - "schema_name": "CMDB Lookup" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -35339,7 +41081,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingSchemaCreateResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -35363,31 +41105,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create mapping schema", + "summary": "Update incident custom field", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Schema names must be unique within an account.\n- `source_labels` (1–3 labels) are used as lookup keys; `result_labels` (1–10 labels) are the labels written on match.\n- Label names must match `^[a-zA-Z_][a-zA-Z0-9_]*$` and be unique within each list.\n- `source_labels` and `result_labels` must not overlap.\n- An account can have at most 20 mapping schemas.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-field-reset", "metadata": { - "sidebarTitle": "Create mapping schema" + "sidebarTitle": "Update incident custom field" } } } }, - "/enrichment/mapping/schema/delete": { + "/incident/info": { "post": { - "description": "Delete a mapping schema and all its associated data. Deletion is blocked if the schema is referenced by any enrichment rule or webhook.", - "operationId": "mapping-schema-write-delete", + "description": "Retrieve detailed information for a single incident including timeline, alerts, responders and custom fields.", + "operationId": "incidentInfo", "requestBody": { "content": { "application/json": { "example": { - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "incident_id": "69da451ef77b1b51f40e83ee" }, "schema": { - "$ref": "#/components/schemas/MappingSchemaIDRequest" + "$ref": "#/components/schemas/IncidentInfoRequest" } } }, @@ -35398,7 +41140,85 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "account_id": 2451002751131, + "account_locale": "", + "account_name": "", + "account_time_zone": "", + "ack_time": 0, + "active_alert_cnt": 1, + "ai_summary": "", + "alert_cnt": 1, + "alert_event_cnt": 17, + "assigned_to": { + "assigned_at": 1775972128, + "escalate_rule_id": "000000000000000000000000", + "escalate_rule_name": "", + "id": "MvQfH9Dc8eNS8k79jmrWn6", + "layer_idx": 0, + "person_ids": [ + 2476444212131 + ], + "type": "assign" + }, + "channel_id": 2551105804131, + "channel_name": "Ops Channel", + "channel_status": "enabled", + "close_time": 0, + "closer_id": 0, + "created_at": 1775912222, + "creator_id": 0, + "dedup_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", + "description": "", + "detail_url": "https://app.flashcat.cloud/incident/detail/69da451ef77b1b51f40e83ee", + "end_time": 0, + "equals_md5": "", + "ever_muted": false, + "fields": {}, + "frequency": "frequent", + "group_method": "n", + "images": null, + "impact": "", + "incident_id": "69da451ef77b1b51f40e83ee", + "incident_severity": "Critical", + "incident_status": "Critical", + "integration_id": 2490562293131, + "integration_ids": [ + 2490562293131 + ], + "integration_type": "monit.alert", + "integration_types": [ + "monit.alert" + ], + "labels": { + "check": "cpu_usage_high", + "env": "production", + "resource": "web-server-01" + }, + "last_time": 1775969819, + "manual_overrides": [ + "title" + ], + "num": "0E83EE", + "owner_id": 0, + "post_mortem_id": "", + "progress": "Triggered", + "resolution": "", + "responders": [ + { + "acknowledged_at": 0, + "assigned_at": 1775972128, + "person_id": 2476444212131 + } + ], + "root_cause": "", + "silence_url": "https://app.flashcat.cloud/channel/detail/2551105804131?tab=alertSuppression&fromIncidentId=69da451ef77b1b51f40e83ee", + "snoozed_before": 0, + "start_time": 1775912219, + "team_id": 2477033058131, + "title": "CPU usage high - web-server-01", + "updated_at": 1775972145 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -35409,7 +41229,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/IncidentInfo" } }, "type": "object" @@ -35433,31 +41253,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete mapping schema", + "summary": "Get incident detail", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- If the schema is still referenced, the response returns HTTP 400 with a `refs` list of blocking references.\n- Only the schema creator, account admin, or team member can delete the schema.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.\n- High-risk operation. Console JWT callers must pass a second-factor code; `app_key` callers bypass the MFA prompt but remain audited — treat the key as a secret.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-info", "metadata": { - "sidebarTitle": "Delete mapping schema" + "sidebarTitle": "Get incident detail" } } } }, - "/enrichment/mapping/schema/info": { + "/incident/list": { "post": { - "description": "Return detail of a single mapping schema by its ID.", - "operationId": "mapping-schema-read-info", + "description": "Query a paginated list of incidents with filters by channel, severity, status, responder, and time range.", + "operationId": "incidentList", "requestBody": { "content": { "application/json": { "example": { - "schema_id": "665f1a2b3c4d5e6f7a8b9c01" + "channel_ids": [ + 2551105804131 + ], + "end_time": 1712000000, + "incident_severity": "Critical,Warning", + "limit": 20, + "p": 1, + "progress": "Triggered,Processing", + "start_time": 1711900800 }, "schema": { - "$ref": "#/components/schemas/MappingSchemaIDRequest" + "$ref": "#/components/schemas/ListIncidentsRequest" } } }, @@ -35469,22 +41297,90 @@ "application/json": { "example": { "data": { - "created_at": 1710000000, - "creator_id": 80011, - "description": "Enrich alerts with CMDB data", - "result_labels": [ - "owner", - "team", - "service" - ], - "schema_id": "665f1a2b3c4d5e6f7a8b9c01", - "schema_name": "CMDB Lookup", - "source_labels": [ - "host" + "has_next_page": true, + "items": [ + { + "account_id": 2451002751131, + "account_locale": "", + "account_name": "", + "account_time_zone": "", + "ack_time": 0, + "active_alert_cnt": 1, + "ai_summary": "", + "alert_cnt": 1, + "alert_event_cnt": 17, + "assigned_to": { + "assigned_at": 1775972128, + "escalate_rule_id": "000000000000000000000000", + "escalate_rule_name": "", + "id": "MvQfH9Dc8eNS8k79jmrWn6", + "layer_idx": 0, + "person_ids": [ + 2476444212131 + ], + "type": "assign" + }, + "channel_id": 2551105804131, + "channel_name": "Ops Channel", + "channel_status": "enabled", + "close_time": 0, + "closer_id": 0, + "created_at": 1775912222, + "creator_id": 0, + "dedup_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", + "description": "", + "detail_url": "https://app.flashcat.cloud/incident/detail/69da451ef77b1b51f40e83ee", + "end_time": 0, + "equals_md5": "", + "ever_muted": false, + "fields": {}, + "frequency": "frequent", + "group_method": "n", + "images": null, + "impact": "", + "incident_id": "69da451ef77b1b51f40e83ee", + "incident_severity": "Critical", + "incident_status": "Critical", + "integration_id": 2490562293131, + "integration_ids": [ + 2490562293131 + ], + "integration_type": "monit.alert", + "integration_types": [ + "monit.alert" + ], + "labels": { + "check": "cpu_usage_high", + "env": "production", + "resource": "web-server-01" + }, + "last_time": 1775969819, + "manual_overrides": [ + "title" + ], + "num": "0E83EE", + "owner_id": 0, + "post_mortem_id": "", + "progress": "Triggered", + "resolution": "", + "responders": [ + { + "acknowledged_at": 0, + "assigned_at": 1775972128, + "person_id": 2476444212131 + } + ], + "root_cause": "", + "silence_url": "https://app.flashcat.cloud/channel/detail/2551105804131?tab=alertSuppression&fromIncidentId=69da451ef77b1b51f40e83ee", + "snoozed_before": 0, + "start_time": 1775912219, + "team_id": 2477033058131, + "title": "CPU usage high - web-server-01", + "updated_at": 1775972145 + } ], - "status": "enabled", - "team_id": 0, - "updated_at": 1710000000 + "search_after_ctx": "69da451ef77b1b51f40e83eb", + "total": 88 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -35496,7 +41392,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingSchemaItem" + "$ref": "#/components/schemas/IncidentListResponse" } }, "type": "object" @@ -35520,29 +41416,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get mapping schema detail", + "summary": "List incidents", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Returns `null` if the schema does not exist.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-list", "metadata": { - "sidebarTitle": "Get mapping schema detail" + "sidebarTitle": "List incidents" } } } }, - "/enrichment/mapping/schema/list": { + "/incident/list-by-ids": { "post": { - "description": "Return all mapping schemas for the account, sorted by creation time ascending.", - "operationId": "mapping-schema-read-list", + "description": "Retrieve multiple incidents by their IDs in a single request.", + "operationId": "incidentListByIds", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "incident_ids": [ + "69da451ef77b1b51f40e83ee", + "69da451ef77b1b51f40e83ef" + ] + }, "schema": { - "$ref": "#/components/schemas/EmptyRequest" + "$ref": "#/components/schemas/ListIncidentsByIdsRequest" } } }, @@ -35554,27 +41455,74 @@ "application/json": { "example": { "data": { + "has_next_page": false, "items": [ { - "created_at": 1710000000, - "creator_id": 80011, - "description": "Enrich alerts with CMDB data", - "result_labels": [ - "owner", - "team", - "service" + "account_id": 2451002751131, + "account_locale": "", + "account_name": "", + "account_time_zone": "", + "ack_time": 0, + "active_alert_cnt": 1, + "ai_summary": "", + "alert_cnt": 1, + "alert_event_cnt": 17, + "assigned_to": { + "assigned_at": 0, + "escalate_rule_id": "000000000000000000000000", + "escalate_rule_name": "", + "id": "", + "layer_idx": 0, + "type": "" + }, + "channel_id": 2551105804131, + "channel_name": "Ops Channel", + "channel_status": "enabled", + "close_time": 0, + "closer_id": 0, + "created_at": 1775912222, + "creator_id": 0, + "dedup_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", + "description": "", + "detail_url": "https://app.flashcat.cloud/incident/detail/69da451ef77b1b51f40e83ee", + "end_time": 0, + "equals_md5": "", + "ever_muted": false, + "fields": {}, + "frequency": "frequent", + "group_method": "n", + "images": null, + "impact": "", + "incident_id": "69da451ef77b1b51f40e83ee", + "incident_severity": "Critical", + "incident_status": "Critical", + "integration_id": 2490562293131, + "integration_ids": [ + 2490562293131 ], - "schema_id": "665f1a2b3c4d5e6f7a8b9c01", - "schema_name": "CMDB Lookup", - "source_labels": [ - "host" + "integration_type": "monit.alert", + "integration_types": [ + "monit.alert" ], - "status": "enabled", - "team_id": 0, - "updated_at": 1710000000 + "labels": {}, + "last_time": 1775969819, + "manual_overrides": null, + "num": "0E83EE", + "owner_id": 0, + "post_mortem_id": "", + "progress": "Triggered", + "resolution": "", + "responders": [], + "root_cause": "", + "silence_url": "https://app.flashcat.cloud/channel/detail/2551105804131?tab=alertSuppression&fromIncidentId=69da451ef77b1b51f40e83ee", + "snoozed_before": 0, + "start_time": 1775912219, + "team_id": 2477033058131, + "title": "CPU usage high - web-server-01", + "updated_at": 1775972145 } ], - "total": 1 + "total": 2 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -35586,7 +41534,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MappingSchemaListResponse" + "$ref": "#/components/schemas/IncidentListResponse" } }, "type": "object" @@ -35610,33 +41558,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List mapping schemas", + "summary": "List incidents by IDs", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Read** (`on-call`) or **Channels Manage** (`on-call`) or **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) or **Mappings Read** (`on-call`) or **Mappings Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-list-by-ids", "metadata": { - "sidebarTitle": "List mapping schemas" + "sidebarTitle": "List incidents by IDs" } } } }, - "/enrichment/mapping/schema/update": { + "/incident/merge": { "post": { - "description": "Update the name, description, or owning team of a mapping schema. Source and result labels cannot be changed after creation.", - "operationId": "mapping-schema-write-update", + "description": "Merge one or more incidents into a target incident.", + "operationId": "incidentMerge", "requestBody": { "content": { "application/json": { "example": { - "description": "Updated description", - "schema_id": "665f1a2b3c4d5e6f7a8b9c01", - "schema_name": "CMDB Lookup v2" + "comment": "Merging related database connectivity incidents into one.", + "source_incident_ids": [ + "69da451ef77b1b51f40e83ef", + "69da451ef77b1b51f40e83f0" + ], + "target_incident_id": "69da451ef77b1b51f40e83ee" }, "schema": { - "$ref": "#/components/schemas/MappingSchemaUpdateRequest" + "$ref": "#/components/schemas/MergeIncidentsRequest" } } }, @@ -35682,50 +41633,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update mapping schema", + "summary": "Merge incidents", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Mappings Manage** (`on-call`) |\n\n## Usage\n\n- Only the schema creator, account admin, or team member can update the schema.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alert-enrichment/mapping-schema-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-merge", "metadata": { - "sidebarTitle": "Update mapping schema" + "sidebarTitle": "Merge incidents" } } } }, - "/enrichment/upsert": { + "/incident/past/list": { "post": { - "description": "Create or fully replace the enrichment rule set for an integration. The entire `rules` array is replaced atomically.", - "operationId": "enrichment-write-upsert", + "description": "List historical incidents related to the current incident for reference during triage.", + "operationId": "incidentPastList", "requestBody": { "content": { "application/json": { "example": { - "integration_id": 5001, - "rules": [ - { - "kind": "extraction", - "settings": { - "override": true, - "pattern": "(?Pprod|staging|dev)", - "result_label": "environment", - "source_field": "labels.env" - } - }, - { - "kind": "composition", - "settings": { - "override": false, - "result_label": "full_env", - "template": "{{.Labels.region}}-{{.Labels.environment}}" - } - } - ] + "incident_id": "69da451ef77b1b51f40e83ee", + "limit": 5 }, "schema": { - "$ref": "#/components/schemas/EnrichmentUpsertRequest" + "$ref": "#/components/schemas/ListPastIncidentsRequest" } } }, @@ -35736,7 +41669,9 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -35747,7 +41682,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ListPastIncidentsResponse" } }, "type": "object" @@ -35771,42 +41706,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Upsert enrichment rules", + "summary": "List past incidents", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Channels Manage** (`on-call`) or **Integrations Manage** (`on-call`) |\n\n## Usage\n\n- Enrichment rules are evaluated in order.\n- Each rule has a `kind`: `extraction` (regex/gjson extraction), `composition` (template-based label composition), `mapping` (lookup via mapping schema or API), or `drop` (remove labels).\n- The optional `if` field is an `AndFilters` condition: if it does not match, the rule is skipped.\n- For `kind: extraction`: `source_field` must be `title`, `description`, or a `labels.*` key; specify exactly one of `pattern` (RE2 regex — its capture groups are joined with a space and written to `result_label`) or `g_json` (GJson path).\n- For `kind: composition`: `template` is a Go text/template rendered against the event struct, e.g. `{{.Title}}`, `{{.Description}}`, `{{.Labels.key}}`.\n- For `kind: mapping`: `mapping_type` is `schema` (default) or `api`; provide `schema_id` or `api_id` accordingly.\n- For `kind: drop`: `drop_labels` lists the label keys to remove.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/alert-enrichment/enrichment-write-upsert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **20 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-past-list", "metadata": { - "sidebarTitle": "Upsert enrichment rules" + "sidebarTitle": "List past incidents" } } } }, - "/field/create": { + "/incident/post-mortem/basics/reset": { "post": { - "description": "Create a new incident custom field on the account.", - "operationId": "field-write-create", + "description": "Replace the incident facts stored in a post-mortem report.", + "operationId": "postmortem-write-reset-basics", "requestBody": { "content": { "application/json": { "example": { - "default_value": "Medium", - "description": "Business severity tier.", - "display_name": "Severity Class", - "field_name": "severity_class", - "field_type": "single_select", - "options": [ - "Critical", - "High", - "Medium", - "Low" - ], - "value_type": "string" + "incidents_earliest_start_seconds": 1761133512, + "incidents_highest_severity": "Warning", + "incidents_latest_close_seconds": 1761133632, + "incidents_total_duration_seconds": 120, + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "responder_ids": [ + 3790925372131 + ] }, "schema": { - "$ref": "#/components/schemas/CreateFieldRequest" + "$ref": "#/components/schemas/ResetPostMortemBasicsRequest" } } }, @@ -35817,10 +41748,7 @@ "content": { "application/json": { "example": { - "data": { - "field_id": "66e9d3a4f7c2b04a1c8a91b3", - "field_name": "severity_class" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -35831,7 +41759,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CreateFieldResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -35855,31 +41783,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create field", + "summary": "Update post-mortem basics", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Maximum **15** custom fields per account.\n- `field_name` must match `^[a-zA-Z_][a-zA-Z0-9_]{0,39}$` and is immutable after creation; `display_name` must also be unique within the account.\n- Type-specific rules: `checkbox` requires `value_type=bool` and no `options`; `single_select`/`multi_select` require `value_type=string` and a non-empty unique `options` list; `text` requires `value_type=string` and no `options`.\n- Response contains only `field_id` and `field_name`; use `/field/info` to fetch the full object.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/alert-enrichment/field-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-basics", "metadata": { - "sidebarTitle": "Create field" + "sidebarTitle": "Update post-mortem basics" } } } }, - "/field/delete": { + "/incident/post-mortem/content/reset": { "post": { - "description": "Delete an incident custom field and asynchronously strip it from existing incidents.", - "operationId": "field-write-delete", + "description": "Replace the body of a drafting post-mortem report with Markdown.", + "operationId": "incident-post-mortem-write-reset-content", "requestBody": { "content": { "application/json": { "example": { - "field_id": "66e9d3a4f7c2b04a1c8a91b3" + "expected_revision": 11, + "idempotency_key": "postmortem-reset-8104935102-11", + "markdown": "# Database saturation incident\n\nThe database pool was exhausted; added saturation alert.", + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e" }, "schema": { - "$ref": "#/components/schemas/DeleteFieldRequest" + "$ref": "#/components/schemas/ResetPostMortemContentRequest" } } }, @@ -35890,7 +41821,15 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "generation": 2, + "markdown_bytes": 88, + "markdown_sha256": "70d764e77e68f8fbfa14d72a235ac07b0110768b8380c8e3436459ebaf02a7c0", + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "previous_generation": 1, + "previous_revision": 11, + "revision": 12 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -35901,7 +41840,7 @@ { "properties": { "data": { - "type": "object" + "$ref": "#/components/schemas/PostMortemContentResetResponse" } }, "type": "object" @@ -35913,44 +41852,74 @@ "description": "Success" }, "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, + "409": { "content": { "application/json": { - "examples": { - "fieldStillReferenced": { - "value": { - "data": { - "refs": [ - { - "href": "https://console.flashcat.cloud/forms/resolve", - "kind": "custom_form", - "name": "Resolve incident" - } - ] - }, - "error": { - "code": "ReferenceExist", - "message": "There still are associated resources, deletion is blocked." - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - } - } + "example": { + "error": { + "code": "Conflict", + "message": "expected_revision conflict: request has 11 but current revision is 12" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { - "oneOf": [ - { - "$ref": "#/components/schemas/ErrorResponse" + "properties": { + "error": { + "properties": { + "code": { + "enum": [ + "Conflict" + ], + "type": "string" + }, + "message": { + "type": "string" + } + }, + "required": [ + "code", + "message" + ], + "type": "object" }, - { - "$ref": "#/components/schemas/FieldDeleteReferenceError" + "request_id": { + "type": "string" } - ] + }, + "required": [ + "request_id", + "error" + ], + "type": "object" } } }, - "description": "Invalid request or the field is still referenced by a custom form." + "description": "The report is not drafting, the revision is stale, or the idempotency key was reused for a different request." }, - "401": { - "$ref": "#/components/responses/Unauthorized" + "413": { + "content": { + "application/json": { + "example": { + "error": { + "code": "EntityTooLarge", + "message": "markdown exceeds maximum size" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Markdown content exceeds the 4 MiB limit." }, "429": { "$ref": "#/components/responses/TooManyRequests" @@ -35959,31 +41928,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete field", + "summary": "Reset post-mortem content", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- The field is marked deleted synchronously; clearing its values from historical incidents runs in the background and may take time on large datasets.\n- Re-creating a field with the same `field_name` is only allowed if `field_type` and `value_type` match the deleted entry.\n- Deletion is rejected with `ReferenceExist` and the referencing custom forms in `data.refs` until no form uses the field.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/alert-enrichment/field-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Edit access to the target report is required. |\n\n## Usage\n\n- The report must be drafting and its current revision must equal `expected_revision`; otherwise the API returns `409 Conflict`.\n- Reuse an `idempotency_key` only for the same report, revision, and Markdown content; different reuse returns `409 Conflict`.\n- A successful reset disconnects the previous collaboration (Yjs) room. Reconnect to the new generation room `post-mortem-{accountId}-{postMortemId}-g{N}` (generation 0 has no `-g` suffix). The reset cannot be rolled back.\n- Markdown content is limited to 4 MiB.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/incident-post-mortem-write-reset-content", "metadata": { - "sidebarTitle": "Delete field" + "sidebarTitle": "Reset post-mortem content" } } } }, - "/field/info": { + "/incident/post-mortem/delete": { "post": { - "description": "Return the configuration of a single incident custom field by ID.", - "operationId": "field-read-info", + "description": "Delete a post-mortem report.", + "operationId": "incidentPostMortemDelete", "requestBody": { "content": { "application/json": { "example": { - "field_id": "66e9d3a4f7c2b04a1c8a91b3" + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e" }, "schema": { - "$ref": "#/components/schemas/FieldInfoRequest" + "$ref": "#/components/schemas/DeletePostMortemRequest" } } }, @@ -35994,27 +41963,7 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 80001, - "created_at": 1710000000, - "creator_id": 80011, - "default_value": "Medium", - "description": "Business severity tier.", - "display_name": "Severity Class", - "field_id": "66e9d3a4f7c2b04a1c8a91b3", - "field_name": "severity_class", - "field_type": "single_select", - "options": [ - "Critical", - "High", - "Medium", - "Low" - ], - "status": "enabled", - "updated_at": 1710000000, - "updated_by": 80011, - "value_type": "string" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -36025,7 +41974,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/FieldItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -36049,33 +41998,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get field detail", + "summary": "Delete post-mortem", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) or **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- An unknown `field_id` yields a 400 error. A soft-deleted field is still returned, with `status` = `deleted` and `deleted_at` set.\n- The shape of `options` and `default_value` varies by `field_type` — see the `FieldItem` schema.", - "href": "/en/api-reference/on-call/alert-enrichment/field-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-post-mortem-delete", "metadata": { - "sidebarTitle": "Get field detail" + "sidebarTitle": "Delete post-mortem" } } } }, - "/field/list": { + "/incident/post-mortem/follow-ups/reset": { "post": { - "description": "Return all incident custom fields configured for the account.", - "operationId": "field-read-list", + "description": "Replace the follow-up action items on a post-mortem report.", + "operationId": "postmortem-write-reset-follow-ups", "requestBody": { "content": { "application/json": { "example": { - "asc": false, - "orderby": "updated_at", - "query": "severity" + "follow_ups": "- Add database saturation alert\n- Review cache TTL rollout", + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e" }, "schema": { - "$ref": "#/components/schemas/FieldListRequest" + "$ref": "#/components/schemas/ResetPostMortemFollowUpsRequest" } } }, @@ -36086,31 +42034,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 80001, - "created_at": 1710000000, - "creator_id": 80011, - "default_value": "Medium", - "description": "Business severity tier.", - "display_name": "Severity Class", - "field_id": "66e9d3a4f7c2b04a1c8a91b3", - "field_name": "severity_class", - "field_type": "single_select", - "options": [ - "Critical", - "High", - "Medium", - "Low" - ], - "status": "enabled", - "updated_at": 1710000000, - "updated_by": 80011, - "value_type": "string" - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -36121,7 +42045,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/FieldListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -36145,51 +42069,78 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List fields", + "summary": "Update post-mortem follow-ups", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) or **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- All non-deleted fields are returned in a single response — there is no pagination and no `total` counter.\n- `query` matches against `field_name` only; invalid regular expressions are auto-escaped to a literal substring match.", - "href": "/en/api-reference/on-call/alert-enrichment/field-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-follow-ups", "metadata": { - "sidebarTitle": "List fields" + "sidebarTitle": "Update post-mortem follow-ups" } } } }, - "/field/update": { - "post": { - "description": "Update mutable attributes of an existing incident custom field.", - "operationId": "field-write-update", - "requestBody": { - "content": { - "application/json": { - "example": { - "default_value": "Medium", - "description": "Business severity tier.", - "display_name": "Severity Class", - "field_id": "66e9d3a4f7c2b04a1c8a91b3", - "options": [ - "Critical", - "High", - "Medium", - "Low" - ] - }, - "schema": { - "$ref": "#/components/schemas/UpdateFieldRequest" - } + "/incident/post-mortem/info": { + "get": { + "description": "Retrieve a post-mortem report by its `post_mortem_id`. List reports via `/incident/post-mortem/list` first — each row carries the incident it covers — then fetch the full report here by that id.", + "operationId": "incidentPostMortemInfo", + "parameters": [ + { + "description": "Post-mortem ID. Deterministic hash derived from account ID and the set of linked incident IDs.", + "in": "query", + "name": "post_mortem_id", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { "content": { "application/json": { "example": { - "data": {}, + "data": { + "basics": { + "incidents_earliest_start_seconds": 1761133512, + "incidents_highest_severity": "Warning", + "incidents_latest_close_seconds": 1761133632, + "incidents_total_duration_seconds": 120, + "responders": [ + { + "acknowledged_at": 0, + "assigned_at": 1761133515, + "person_id": 3790925372131 + } + ] + }, + "content": { + "content": "{\"type\":\"doc\",\"content\":[]}" + }, + "follow_ups": "", + "meta": { + "account_id": 2451002751131, + "author_ids": [ + 2477273692131 + ], + "channel_id": 3047621227131, + "channel_name": "Ops Channel", + "created_at_seconds": 1773900354, + "incident_ids": [ + "69bb9233331067560c718ecd" + ], + "is_private": false, + "media_count": 0, + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "status": "published", + "team_id": 2477033058131, + "template_id": "post_mortem_default_tmpl_en-us", + "title": "Postmortem1", + "updated_at_seconds": 1773909012 + } + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -36200,7 +42151,7 @@ { "properties": { "data": { - "type": "object" + "$ref": "#/components/schemas/PostMortemItem" } }, "type": "object" @@ -36224,33 +42175,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update field", + "summary": "Get post-mortem", "tags": [ - "On-call/Alert enrichment" + "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Only `display_name`, `description`, `options`, and `default_value` can be changed; `field_name`, `field_type`, and `value_type` are immutable.\n- `options` and `default_value` must remain consistent with the field's existing type — same rules as create.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/alert-enrichment/field-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-post-mortem-info", "metadata": { - "sidebarTitle": "Update field" + "sidebarTitle": "Get post-mortem" } } } }, - "/incident/ack": { + "/incident/post-mortem/init": { "post": { - "description": "Acknowledge an incident to indicate you are actively working on it.", - "operationId": "incidentAck", + "description": "Create a post-mortem draft from one or more incidents and a template.", + "operationId": "postmortem-write-init", "requestBody": { "content": { "application/json": { "example": { "incident_ids": [ - "69da451ef77b1b51f40e83ee" - ] + "69bb9233331067560c718ecd" + ], + "template_id": "post_mortem_default_tmpl_en-us" }, "schema": { - "$ref": "#/components/schemas/AckIncidentRequest" + "$ref": "#/components/schemas/InitPostMortemRequest" } } }, @@ -36261,7 +42213,45 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "basics": { + "incidents_earliest_start_seconds": 1761133512, + "incidents_highest_severity": "Warning", + "incidents_latest_close_seconds": 1761133632, + "incidents_total_duration_seconds": 120, + "responders": [ + { + "acknowledged_at": 0, + "assigned_at": 1761133515, + "person_id": 3790925372131 + } + ] + }, + "content": { + "content": "{\"type\":\"doc\",\"content\":[]}" + }, + "follow_ups": "", + "meta": { + "account_id": 2451002751131, + "author_ids": [ + 2477273692131 + ], + "channel_id": 3047621227131, + "channel_name": "Ops Channel", + "created_at_seconds": 1773900354, + "incident_ids": [ + "69bb9233331067560c718ecd" + ], + "is_private": false, + "media_count": 0, + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "status": "published", + "team_id": 2477033058131, + "template_id": "post_mortem_default_tmpl_en-us", + "title": "Postmortem1", + "updated_at_seconds": 1773909012 + } + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -36272,7 +42262,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/PostMortemItem" } }, "type": "object" @@ -36296,35 +42286,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Acknowledge incident", + "summary": "Initialize post-mortem", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- When an acknowledgement form applies, `custom_fields`, `summary`, and `images` must match its visible elements and required rules.\n- For a batch, form values are accepted only when every selected incident resolves to the same form; otherwise acknowledge incidents individually.\n- The legacy `values` and `custom_values` properties are rejected; use `custom_fields`.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-ack", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Links at most 10 incidents to one post-mortem report.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-init", "metadata": { - "sidebarTitle": "Acknowledge incident" + "sidebarTitle": "Initialize post-mortem" } } } }, - "/incident/alert/list": { + "/incident/post-mortem/list": { "post": { - "description": "List all alerts merged into a specific incident.", - "operationId": "incidentAlertList", + "description": "List post-mortem reports with optional filters.", + "operationId": "incidentPostMortemList", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "include_events": true, - "is_active": true, - "limit": 100, - "p": 1 + "limit": 20, + "p": 1, + "status": "published" }, "schema": { - "$ref": "#/components/schemas/ListIncidentAlertsRequest" + "$ref": "#/components/schemas/ListPostMortemsRequest" } } }, @@ -36336,62 +42324,30 @@ "application/json": { "example": { "data": { + "has_next_page": false, "items": [ { "account_id": 2451002751131, - "alert_id": "69da451df77b1b51f40e83de", - "alert_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", - "alert_severity": "Critical", - "alert_status": "Critical", - "channel_id": 2551105804131, + "author_ids": [ + 2477273692131 + ], + "channel_id": 3047621227131, "channel_name": "Ops Channel", - "channel_status": "enabled", - "created_at": 1775912221, - "data_source_id": 2490562293131, - "data_source_name": "FlashMonit", - "data_source_ref_id": "a_2451002751131", - "data_source_type": "monit.alert", - "description": "", - "end_time": 0, - "event_cnt": 17, - "events": [ - { - "alert_id": "69da451df77b1b51f40e83de", - "event_id": "69da451df77b1b51f40e83df", - "event_severity": "Critical", - "event_status": "Critical", - "event_time": 1712650000, - "labels": { - "host": "web-01" - }, - "title": "CPU usage > 90%" - } + "created_at_seconds": 1773900354, + "incident_ids": [ + "69bb9233331067560c718ecd" ], - "ever_muted": false, - "images": null, - "incident": { - "incident_id": "69da451ef77b1b51f40e83ee", - "progress": "Triggered", - "title": "CPU usage high - web-server-01" - }, - "integration_id": 2490562293131, - "integration_name": "FlashMonit", - "integration_ref_id": "a_2451002751131", - "integration_type": "monit.alert", - "labels": { - "check": "cpu_usage_high", - "resource": "web-server-01" - }, - "last_time": 1775969819, - "responder_email": "", - "responder_name": "", - "start_time": 1775912219, - "title": "CPU usage high - web-server-01", - "title_rule": "", - "updated_at": 1775969821 + "is_private": false, + "media_count": 0, + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "status": "published", + "team_id": 2477033058131, + "template_id": "post_mortem_default_tmpl_en-us", + "title": "Postmortem1", + "updated_at_seconds": 1773909012 } ], - "total": 1 + "total": 3 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -36403,7 +42359,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListIncidentAlertsResponse" + "$ref": "#/components/schemas/ListPostMortemsResponse" } }, "type": "object" @@ -36427,37 +42383,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List alerts of incident", + "summary": "List post-mortems", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- Set `include_events=true` only when you need a preview of each alert's raw events.\n- Event previews are capped at the 20 newest events per alert. Use `POST /alert/event/list` for a full paginated event history.\n- `event_cnt` still reports the total number of raw events merged into each alert.", - "href": "/en/api-reference/on-call/incidents/incident-alert-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-post-mortem-list", "metadata": { - "sidebarTitle": "List alerts of incident" + "sidebarTitle": "List post-mortems" } } } }, - "/incident/assign": { + "/incident/post-mortem/status/reset": { "post": { - "description": "Dispatch an incident to a specific escalation level or responder.", - "operationId": "incidentAssign", + "description": "Set a post-mortem report to drafting or published.", + "operationId": "postmortem-write-reset-status", "requestBody": { "content": { "application/json": { "example": { - "assigned_to": { - "person_ids": [ - 2476444212131 - ], - "type": "assign" - }, - "incident_id": "69da451ef77b1b51f40e83ee" + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "status": "published" }, "schema": { - "$ref": "#/components/schemas/AssignIncidentRequest" + "$ref": "#/components/schemas/ResetPostMortemStatusRequest" } } }, @@ -36503,35 +42454,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Assign incident", + "summary": "Update post-mortem status", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-assign", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-status", "metadata": { - "sidebarTitle": "Assign incident" + "sidebarTitle": "Update post-mortem status" } } } }, - "/incident/comment": { + "/incident/post-mortem/template/delete": { "post": { - "description": "Add a text comment to the incident timeline.", - "operationId": "incidentComment", + "description": "Delete a custom post-mortem template.", + "operationId": "postmortem-write-delete-template", "requestBody": { "content": { "application/json": { "example": { - "comment": "Root cause identified. [@Jane Doe](flashduty://ref/member/2476444212131) please verify the fix.", - "comment_type_id": "6a5895d672a064bc2d3ddfc2", - "incident_ids": [ - "69da451ef77b1b51f40e83ee" - ] + "template_id": "post_mortem_custom_tmpl_01" }, "schema": { - "$ref": "#/components/schemas/CommentIncidentRequest" + "$ref": "#/components/schemas/DeletePostMortemTemplateRequest" } } }, @@ -36577,55 +42524,49 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Add comment to incident", + "summary": "Delete post-mortem template", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- To mention a member, embed a markdown link in `comment` in the form `[@Display Name](flashduty://ref/member/)`. Mentioned members receive a dedicated personal notification, which is not affected by `mute_reply`.\n- Plain `@name` text without the link syntax does not create a mention.\n- The server rewrites each mention's display label to the member's canonical name.", - "href": "/en/api-reference/on-call/incidents/incident-comment", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-delete-template", "metadata": { - "sidebarTitle": "Add comment to incident" + "sidebarTitle": "Delete post-mortem template" } } } }, - "/incident/comment-type/create": { - "post": { - "description": "Create a comment type that can be attached to incident comments.", - "operationId": "incidentCommentTypeCreate", - "requestBody": { - "content": { - "application/json": { - "example": { - "color": "#30A46C", - "name": "Key finding" - }, - "schema": { - "$ref": "#/components/schemas/CreateIncidentCommentTypeRequest" - } + "/incident/post-mortem/template/info": { + "get": { + "description": "Return one post-mortem template by ID.", + "operationId": "postmortem-read-template-info", + "parameters": [ + { + "description": "Template ID.", + "in": "query", + "name": "template_id", + "required": true, + "schema": { + "type": "string" } - }, - "required": true - }, + } + ], "responses": { "200": { "content": { "application/json": { "example": { "data": { - "comment_type_id": "6a5895d672a064bc2d3ddfc2", - "item": { - "account_id": 2451002751131, - "color": "#30A46C", - "comment_type_id": "6a5895d672a064bc2d3ddfc2", - "created_at": 1784190422, - "creator_id": 5068740052131, - "name": "Key finding", - "position": 1, - "updated_at": 1784207748, - "updated_by": 5068740052131 - } + "account_id": 2451002751131, + "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", + "content_markdown": "## Summary\nDescribe what happened.", + "created_at_seconds": 1773900000, + "description": "Default sections for post-mortem reports.", + "name": "Default post-mortem report", + "team_id": 2477033058131, + "template_id": "post_mortem_default_tmpl_en-us", + "updated_at_seconds": 1773903600 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -36637,7 +42578,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CreateIncidentCommentTypeResponse" + "$ref": "#/components/schemas/PostMortemTemplate" } }, "type": "object" @@ -36661,99 +42602,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create a comment type", + "summary": "Get post-mortem template detail", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- The new type is appended to the end of the display ordering.\n- The name must be unique within the account (case-insensitive, after trimming whitespace).\n- An account can have at most 10 comment types.\n- This permission is admin-only by default; custom roles must be granted it explicitly.", - "href": "/en/api-reference/on-call/incidents/incident-comment-type-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/postmortem-read-template-info", "metadata": { - "sidebarTitle": "Create a comment type" + "sidebarTitle": "Get post-mortem template detail" } } } }, - "/incident/comment-type/delete": { + "/incident/post-mortem/template/list": { "post": { - "description": "Delete a comment type. Comments that used it keep their text but lose the type label.", - "operationId": "incidentCommentTypeDelete", + "description": "Return built-in and custom post-mortem templates for the account.", + "operationId": "postmortem-read-list-templates", "requestBody": { "content": { "application/json": { "example": { - "comment_type_id": "6a5895b572a064bc2d3ddfc0" + "asc": false, + "limit": 20, + "order_by": "created_at_seconds", + "p": 1 }, "schema": { - "$ref": "#/components/schemas/DeleteIncidentCommentTypeRequest" - } - } - }, - "required": true - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/EmptyResponse" - } - }, - "type": "object" - } - ] - } - } - }, - "description": "Success" - }, - "400": { - "$ref": "#/components/responses/BadRequest" - }, - "401": { - "$ref": "#/components/responses/Unauthorized" - }, - "429": { - "$ref": "#/components/responses/TooManyRequests" - }, - "500": { - "$ref": "#/components/responses/ServerError" - } - }, - "summary": "Delete a comment type", - "tags": [ - "On-call/Incidents" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- Hard delete — the comment type is removed permanently and cannot be restored.\n- Existing comments that referenced the type lose the type label but are not otherwise affected.\n- This permission is admin-only by default; custom roles must be granted it explicitly.", - "href": "/en/api-reference/on-call/incidents/incident-comment-type-delete", - "metadata": { - "sidebarTitle": "Delete a comment type" - } - } - } - }, - "/incident/comment-type/list": { - "post": { - "description": "Retrieve all comment types of the account, ordered by their display position.", - "operationId": "incidentCommentTypeList", - "requestBody": { - "content": { - "application/json": { - "example": {}, - "schema": { - "$ref": "#/components/schemas/ListIncidentCommentTypesRequest" + "$ref": "#/components/schemas/ListPostMortemTemplatesRequest" } } }, @@ -36765,30 +42641,21 @@ "application/json": { "example": { "data": { + "has_next_page": false, "items": [ { "account_id": 2451002751131, - "color": "#30A46C", - "comment_type_id": "6a5895d672a064bc2d3ddfc2", - "created_at": 1784190422, - "creator_id": 5068740052131, - "name": "Key finding", - "position": 1, - "updated_at": 1784207748, - "updated_by": 5068740052131 - }, - { - "account_id": 2451002751131, - "color": "#998000", - "comment_type_id": "6a5895b572a064bc2d3ddfc0", - "created_at": 1784190389, - "creator_id": 5068740052131, - "name": "Hypothesis", - "position": 2, - "updated_at": 1785141535, - "updated_by": 3790925372131 + "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", + "content_markdown": "## Summary\nDescribe what happened.", + "created_at_seconds": 1773900000, + "description": "Default sections for post-mortem reports.", + "name": "Default post-mortem report", + "team_id": 2477033058131, + "template_id": "post_mortem_default_tmpl_en-us", + "updated_at_seconds": 1773903600 } - ] + ], + "total": 2 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -36800,7 +42667,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListIncidentCommentTypesResponse" + "$ref": "#/components/schemas/ListPostMortemTemplatesResponse" } }, "type": "object" @@ -36824,34 +42691,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List comment types", + "summary": "List post-mortem templates", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- Returns the full list in one call — there is no pagination.\n- An account can have at most 10 comment types.", - "href": "/en/api-reference/on-call/incidents/incident-comment-type-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/postmortem-read-list-templates", "metadata": { - "sidebarTitle": "List comment types" + "sidebarTitle": "List post-mortem templates" } } } }, - "/incident/comment-type/reorder": { + "/incident/post-mortem/template/upsert": { "post": { - "description": "Set the display order of all comment types by passing every type ID in the desired order.", - "operationId": "incidentCommentTypeReorder", + "description": "Create a custom post-mortem template or update an existing one.", + "operationId": "postmortem-write-upsert-template", "requestBody": { "content": { "application/json": { "example": { - "comment_type_ids": [ - "6a5895b572a064bc2d3ddfc0", - "6a5895d672a064bc2d3ddfc2" - ] + "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", + "content_markdown": "## Summary\nDescribe what happened.", + "description": "Template for production incident reviews.", + "name": "Production incident template", + "team_id": 2477033058131 }, "schema": { - "$ref": "#/components/schemas/ReorderIncidentCommentTypesRequest" + "$ref": "#/components/schemas/UpsertPostMortemTemplateRequest" } } }, @@ -36862,7 +42730,17 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "account_id": 2451002751131, + "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", + "content_markdown": "## Summary\nDescribe what happened.", + "created_at_seconds": 1773900000, + "description": "Default sections for post-mortem reports.", + "name": "Default post-mortem report", + "team_id": 2477033058131, + "template_id": "post_mortem_default_tmpl_en-us", + "updated_at_seconds": 1773903600 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -36873,7 +42751,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/PostMortemTemplate" } }, "type": "object" @@ -36897,32 +42775,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Reorder comment types", + "summary": "Create or update post-mortem template", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- Full-set reorder — `comment_type_ids` must contain every comment type of the account, each exactly once, in the desired order.\n- Positions are reassigned starting from 1: the first ID in the array becomes position 1.\n- This permission is admin-only by default; custom roles must be granted it explicitly.", - "href": "/en/api-reference/on-call/incidents/incident-comment-type-reorder", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-upsert-template", "metadata": { - "sidebarTitle": "Reorder comment types" + "sidebarTitle": "Create or update post-mortem template" } } } }, - "/incident/comment-type/update": { + "/incident/post-mortem/title/reset": { "post": { - "description": "Update the name and/or color of an existing account comment type.", - "operationId": "incidentCommentTypeUpdate", + "description": "Replace the title of a post-mortem report.", + "operationId": "postmortem-write-reset-title", "requestBody": { "content": { "application/json": { "example": { - "color": "#B7791F", - "comment_type_id": "6a5895b572a064bc2d3ddfc0" + "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", + "title": "Production API latency incident" }, "schema": { - "$ref": "#/components/schemas/UpdateIncidentCommentTypeRequest" + "$ref": "#/components/schemas/ResetPostMortemTitleRequest" } } }, @@ -36968,65 +42846,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update a comment type", + "summary": "Update post-mortem title", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Comment Types Manage** (`on-call`) |\n\n## Usage\n\n- Partial update — only the provided fields are changed, but at least one of `name` or `color` must be provided.\n- The name must remain unique within the account (case-insensitive, after trimming whitespace).\n- This permission is admin-only by default; custom roles must be granted it explicitly.", - "href": "/en/api-reference/on-call/incidents/incident-comment-type-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-title", "metadata": { - "sidebarTitle": "Update a comment type" + "sidebarTitle": "Update post-mortem title" } } } }, - "/incident/create": { + "/incident/remove": { "post": { - "description": "Manually create a new incident and assign responders.", - "operationId": "incidentCreate", - "requestBody": { - "content": { - "application/json": { - "example": { - "assigned_to": { - "person_ids": [ - 2476444212131 - ] - }, - "channel_id": 2551105804131, - "incident_severity": "Critical", - "title": "Database connection timeout on prod-db-01" - }, - "schema": { - "$ref": "#/components/schemas/CreateIncidentRequest" - } - }, - "multipart/form-data": { - "encoding": { - "data": { - "contentType": "application/json" - } - }, - "schema": { - "properties": { - "data": { - "description": "JSON-encoded CreateIncidentRequest payload.", - "type": "string" - }, - "images": { - "description": "Image files attached to the new incident.", - "items": { - "format": "binary", - "type": "string" - }, - "type": "array" - } - }, - "required": [ - "data" - ], - "type": "object" + "description": "Permanently delete an incident and all associated data.", + "operationId": "incidentRemove", + "requestBody": { + "content": { + "application/json": { + "example": { + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ] + }, + "schema": { + "$ref": "#/components/schemas/RemoveIncidentRequest" } } }, @@ -37037,10 +42883,7 @@ "content": { "application/json": { "example": { - "data": { - "incident_id": "69db2ef1a0fe7db6448b14f1", - "title": "API test incident for docs" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -37051,7 +42894,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CreateIncidentResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -37075,32 +42918,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create incident", + "summary": "Delete an incident", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- When an account create form applies, its visible custom fields and required system values must be supplied.\n- To attach images, send `multipart/form-data` with the JSON request in `data` and files in `images`; the complete request must not exceed 50 MiB.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-remove", "metadata": { - "sidebarTitle": "Create incident" + "sidebarTitle": "Delete an incident" } } } }, - "/incident/custom-action/do": { + "/incident/reopen": { "post": { - "description": "Execute a custom action configured for an incident.", - "operationId": "incidentCustomActionDo", + "description": "Reopen a previously resolved incident.", + "operationId": "incidentReopen", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "integration_id": 2490562293131 + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ], + "reason": "Monitoring detected the issue recurred after the initial fix." }, "schema": { - "$ref": "#/components/schemas/DoIncidentCustomActionRequest" + "$ref": "#/components/schemas/ReopenIncidentRequest" } } }, @@ -37111,9 +42956,7 @@ "content": { "application/json": { "example": { - "data": { - "message": "" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -37124,7 +42967,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DoIncidentCustomActionResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -37148,33 +42991,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Execute custom action", + "summary": "Reopen incident", "tags": [ "On-call/Incidents" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-custom-action-do", + "href": "/en/api-reference/on-call/incidents/incident-reopen", "metadata": { - "sidebarTitle": "Execute custom action" + "sidebarTitle": "Reopen incident" } } } }, - "/incident/disable-merge": { + "/incident/reset": { "post": { - "description": "Disable automatic merging for a specific incident.", - "operationId": "incidentDisableMerge", + "description": "Update one or more editable fields of an incident in a single call, including title, description, impact, root cause, resolution, and severity. At least one field must be provided.", + "operationId": "incidentReset", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" - ] + "incident_id": "69da451ef77b1b51f40e83ee", + "incident_severity": "Critical", + "title": "Database connection timeout - prod-db-01 primary" }, "schema": { - "$ref": "#/components/schemas/DisableIncidentMergeRequest" + "$ref": "#/components/schemas/UpdateIncidentFieldsRequest" } } }, @@ -37220,33 +43063,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable incident merge", + "summary": "Update incident fields", "tags": [ "On-call/Incidents" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-disable-merge", + "href": "/en/api-reference/on-call/incidents/incident-reset", "metadata": { - "sidebarTitle": "Disable incident merge" + "sidebarTitle": "Update incident fields" } } } }, - "/incident/feed": { + "/incident/resolve": { "post": { - "description": "Retrieve the timeline feed for a specific incident, including state changes, comments and system events.", - "operationId": "incidentFeed", + "description": "Mark an incident as resolved.", + "operationId": "incidentResolve", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "limit": 20, - "p": 1 + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ], + "resolution": "Deployed hotfix v2.3.1 and restarted the affected service.", + "root_cause": "Memory leak in the connection pool caused by a missing cleanup call." }, "schema": { - "$ref": "#/components/schemas/ListIncidentFeedRequest" + "$ref": "#/components/schemas/ResolveIncidentRequest" } } }, @@ -37257,63 +43102,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": true, - "items": [ - { - "account_id": 2451002751131, - "created_at": 1785495329402, - "creator_id": 5329873302131, - "detail": { - "assignee_ids": [ - 3790925372131, - 4756301322131 - ], - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "status": "open", - "title": "Follow-up: schedule database failover drill", - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - }, - "ref_id": "6a5f1e28807515413b384bce", - "type": "i_wi_created", - "updated_at": 1785495329402 - }, - { - "account_id": 2451002751131, - "created_at": 1785496333926, - "creator_id": 3790925372131, - "detail": { - "comment": "Root cause identified: connection pool exhaustion on the primary database.", - "comment_type": { - "color": "#30A46C", - "id": "6a5895d672a064bc2d3ddfc2", - "name": "Key finding" - }, - "comment_type_id": "6a5895d672a064bc2d3ddfc2" - }, - "ref_id": "6a5f1e28807515413b384bce", - "type": "i_comm", - "updated_at": 1785496333926 - }, - { - "account_id": 2451002751131, - "created_at": 1785496384806, - "creator_id": 3790925372131, - "detail": { - "from_status": "open", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "title": "Follow-up: schedule database failover drill", - "to_status": "done", - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - }, - "ref_id": "6a5f1e28807515413b384bce", - "type": "i_wi_completed", - "updated_at": 1785496384806 - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -37324,7 +43113,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListIncidentFeedResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -37348,33 +43137,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get incident timeline", + "summary": "Resolve incident", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- For `i_comm` entries, `detail.comment_type` is resolved from the current account-level comment type definition at read time, so it reflects the type's latest name and color.", - "href": "/en/api-reference/on-call/incidents/incident-feed", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- When a resolution form applies, `custom_fields`, `summary`, and `images` must match its visible elements and required rules.\n- For a batch, form values are accepted only when every selected incident resolves to the same form; otherwise resolve incidents individually.\n- The legacy `values` and `custom_values` properties are rejected; use `custom_fields`.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-resolve", "metadata": { - "sidebarTitle": "Get incident timeline" + "sidebarTitle": "Resolve incident" } } } }, - "/incident/field/reset": { + "/incident/responder/add": { "post": { - "description": "Update a custom field value on an incident.", - "operationId": "incidentFieldReset", + "description": "Add a responder to an existing incident.", + "operationId": "incidentResponderAdd", "requestBody": { "content": { "application/json": { "example": { - "field_name": "affected_service", - "field_value": "payment-service", - "incident_id": "69da451ef77b1b51f40e83ee" + "incident_id": "69da451ef77b1b51f40e83ee", + "person_ids": [ + 2476444212131, + 2476444212132 + ] }, "schema": { - "$ref": "#/components/schemas/ResetIncidentFieldRequest" + "$ref": "#/components/schemas/AddIncidentResponderRequest" } } }, @@ -37420,31 +43211,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update incident custom field", + "summary": "Add incident responder", "tags": [ "On-call/Incidents" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-field-reset", + "href": "/en/api-reference/on-call/incidents/incident-responder-add", "metadata": { - "sidebarTitle": "Update incident custom field" + "sidebarTitle": "Add incident responder" } } } }, - "/incident/info": { + "/incident/sdp/request/list": { "post": { - "description": "Retrieve detailed information for a single incident including timeline, alerts, responders and custom fields.", - "operationId": "incidentInfo", + "description": "List synchronization mappings between ServiceDeskPlus requests and Flashduty incidents.", + "operationId": "incident-service-desk-plus-request-read-list", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee" + "channel_ids": [ + 12345 + ], + "end_time": 1779600000, + "limit": 20, + "start_time": 1779513600, + "status": "success" }, "schema": { - "$ref": "#/components/schemas/IncidentInfoRequest" + "$ref": "#/components/schemas/ServiceDeskPlusRequestListRequest" } } }, @@ -37456,83 +43253,22 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "account_locale": "", - "account_name": "", - "account_time_zone": "", - "ack_time": 0, - "active_alert_cnt": 1, - "ai_summary": "", - "alert_cnt": 1, - "alert_event_cnt": 17, - "assigned_to": { - "assigned_at": 1775972128, - "escalate_rule_id": "000000000000000000000000", - "escalate_rule_name": "", - "id": "MvQfH9Dc8eNS8k79jmrWn6", - "layer_idx": 0, - "person_ids": [ - 2476444212131 - ], - "type": "assign" - }, - "channel_id": 2551105804131, - "channel_name": "Ops Channel", - "channel_status": "enabled", - "close_time": 0, - "closer_id": 0, - "created_at": 1775912222, - "creator_id": 0, - "dedup_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", - "description": "", - "detail_url": "https://app.flashcat.cloud/incident/detail/69da451ef77b1b51f40e83ee", - "end_time": 0, - "equals_md5": "", - "ever_muted": false, - "fields": {}, - "frequency": "frequent", - "group_method": "n", - "images": null, - "impact": "", - "incident_id": "69da451ef77b1b51f40e83ee", - "incident_severity": "Critical", - "incident_status": "Critical", - "integration_id": 2490562293131, - "integration_ids": [ - 2490562293131 - ], - "integration_type": "monit.alert", - "integration_types": [ - "monit.alert" - ], - "labels": { - "check": "cpu_usage_high", - "env": "production", - "resource": "web-server-01" - }, - "last_time": 1775969819, - "manual_overrides": [ - "title" - ], - "num": "0E83EE", - "owner_id": 0, - "post_mortem_id": "", - "progress": "Triggered", - "resolution": "", - "responders": [ + "has_next_page": false, + "items": [ { - "acknowledged_at": 0, - "assigned_at": 1775972128, - "person_id": 2476444212131 + "channel_id": 12345, + "channel_name": "Payments", + "created_at": 1779514631, + "incident_id": "685d7f4e51b9a9a6d4d0c123", + "incident_title": "Checkout API 5xx rate increased", + "integration_id": 98765, + "request_id": "100000000001", + "request_link": "https://servicedesk.example.com/app/itdesk/ui/requests/100000000001/details", + "status": "success" } ], - "root_cause": "", - "silence_url": "https://app.flashcat.cloud/channel/detail/2551105804131?tab=alertSuppression&fromIncidentId=69da451ef77b1b51f40e83ee", - "snoozed_before": 0, - "start_time": 1775912219, - "team_id": 2477033058131, - "title": "CPU usage high - web-server-01", - "updated_at": 1775972145 + "search_after_ctx": "", + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -37544,7 +43280,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/IncidentInfo" + "$ref": "#/components/schemas/ServiceDeskPlusRequestListResponse" } }, "type": "object" @@ -37568,39 +43304,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get incident detail", + "summary": "Get ServiceDeskPlus linked incidents", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- Use this endpoint to inspect synchronization mappings between ServiceDeskPlus requests and Flashduty incidents, including the external request link and sync status.\n- When `incident_id` is not provided, `start_time` and `end_time` are required Unix-second timestamps; the time window cannot exceed 30 days.\n- `status` accepts only `success` and `failed`, representing successful and failed synchronization records.\n- Results are sorted by the internal record ID. Set `asc` to `true` for ascending order; otherwise records are returned descending. Pass the returned `search_after_ctx` to continue pagination.", + "href": "/en/api-reference/on-call/incidents/incident-service-desk-plus-request-read-list", "metadata": { - "sidebarTitle": "Get incident detail" + "sidebarTitle": "Get ServiceDeskPlus linked incidents" } } } }, - "/incident/list": { + "/incident/snooze": { "post": { - "description": "Query a paginated list of incidents with filters by channel, severity, status, responder, and time range.", - "operationId": "incidentList", + "description": "Temporarily snooze notifications for an incident until a specified time.", + "operationId": "incidentSnooze", "requestBody": { "content": { "application/json": { "example": { - "channel_ids": [ - 2551105804131 + "incident_ids": [ + "69da451ef77b1b51f40e83ee" ], - "end_time": 1712000000, - "incident_severity": "Critical,Warning", - "limit": 20, - "p": 1, - "progress": "Triggered,Processing", - "start_time": 1711900800 + "minutes": 60 }, "schema": { - "$ref": "#/components/schemas/ListIncidentsRequest" + "$ref": "#/components/schemas/SnoozeIncidentRequest" } } }, @@ -37611,92 +43342,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": true, - "items": [ - { - "account_id": 2451002751131, - "account_locale": "", - "account_name": "", - "account_time_zone": "", - "ack_time": 0, - "active_alert_cnt": 1, - "ai_summary": "", - "alert_cnt": 1, - "alert_event_cnt": 17, - "assigned_to": { - "assigned_at": 1775972128, - "escalate_rule_id": "000000000000000000000000", - "escalate_rule_name": "", - "id": "MvQfH9Dc8eNS8k79jmrWn6", - "layer_idx": 0, - "person_ids": [ - 2476444212131 - ], - "type": "assign" - }, - "channel_id": 2551105804131, - "channel_name": "Ops Channel", - "channel_status": "enabled", - "close_time": 0, - "closer_id": 0, - "created_at": 1775912222, - "creator_id": 0, - "dedup_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", - "description": "", - "detail_url": "https://app.flashcat.cloud/incident/detail/69da451ef77b1b51f40e83ee", - "end_time": 0, - "equals_md5": "", - "ever_muted": false, - "fields": {}, - "frequency": "frequent", - "group_method": "n", - "images": null, - "impact": "", - "incident_id": "69da451ef77b1b51f40e83ee", - "incident_severity": "Critical", - "incident_status": "Critical", - "integration_id": 2490562293131, - "integration_ids": [ - 2490562293131 - ], - "integration_type": "monit.alert", - "integration_types": [ - "monit.alert" - ], - "labels": { - "check": "cpu_usage_high", - "env": "production", - "resource": "web-server-01" - }, - "last_time": 1775969819, - "manual_overrides": [ - "title" - ], - "num": "0E83EE", - "owner_id": 0, - "post_mortem_id": "", - "progress": "Triggered", - "resolution": "", - "responders": [ - { - "acknowledged_at": 0, - "assigned_at": 1775972128, - "person_id": 2476444212131 - } - ], - "root_cause": "", - "silence_url": "https://app.flashcat.cloud/channel/detail/2551105804131?tab=alertSuppression&fromIncidentId=69da451ef77b1b51f40e83ee", - "snoozed_before": 0, - "start_time": 1775912219, - "team_id": 2477033058131, - "title": "CPU usage high - web-server-01", - "updated_at": 1775972145 - } - ], - "search_after_ctx": "69da451ef77b1b51f40e83eb", - "total": 88 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -37707,7 +43353,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/IncidentListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -37731,34 +43377,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List incidents", + "summary": "Snooze incident", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-snooze", "metadata": { - "sidebarTitle": "List incidents" + "sidebarTitle": "Snooze incident" } } } }, - "/incident/list-by-ids": { + "/incident/unack": { "post": { - "description": "Retrieve multiple incidents by their IDs in a single request.", - "operationId": "incidentListByIds", + "description": "Remove the acknowledge status from an incident.", + "operationId": "incidentUnack", "requestBody": { "content": { "application/json": { "example": { "incident_ids": [ - "69da451ef77b1b51f40e83ee", - "69da451ef77b1b51f40e83ef" + "69da451ef77b1b51f40e83ee" ] }, "schema": { - "$ref": "#/components/schemas/ListIncidentsByIdsRequest" + "$ref": "#/components/schemas/UnackIncidentRequest" } } }, @@ -37769,76 +43414,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": false, - "items": [ - { - "account_id": 2451002751131, - "account_locale": "", - "account_name": "", - "account_time_zone": "", - "ack_time": 0, - "active_alert_cnt": 1, - "ai_summary": "", - "alert_cnt": 1, - "alert_event_cnt": 17, - "assigned_to": { - "assigned_at": 0, - "escalate_rule_id": "000000000000000000000000", - "escalate_rule_name": "", - "id": "", - "layer_idx": 0, - "type": "" - }, - "channel_id": 2551105804131, - "channel_name": "Ops Channel", - "channel_status": "enabled", - "close_time": 0, - "closer_id": 0, - "created_at": 1775912222, - "creator_id": 0, - "dedup_key": "100128:prom-203.0.113.107:A:1579244238440766834:anydata", - "description": "", - "detail_url": "https://app.flashcat.cloud/incident/detail/69da451ef77b1b51f40e83ee", - "end_time": 0, - "equals_md5": "", - "ever_muted": false, - "fields": {}, - "frequency": "frequent", - "group_method": "n", - "images": null, - "impact": "", - "incident_id": "69da451ef77b1b51f40e83ee", - "incident_severity": "Critical", - "incident_status": "Critical", - "integration_id": 2490562293131, - "integration_ids": [ - 2490562293131 - ], - "integration_type": "monit.alert", - "integration_types": [ - "monit.alert" - ], - "labels": {}, - "last_time": 1775969819, - "manual_overrides": null, - "num": "0E83EE", - "owner_id": 0, - "post_mortem_id": "", - "progress": "Triggered", - "resolution": "", - "responders": [], - "root_cause": "", - "silence_url": "https://app.flashcat.cloud/channel/detail/2551105804131?tab=alertSuppression&fromIncidentId=69da451ef77b1b51f40e83ee", - "snoozed_before": 0, - "start_time": 1775912219, - "team_id": 2477033058131, - "title": "CPU usage high - web-server-01", - "updated_at": 1775972145 - } - ], - "total": 2 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -37849,7 +43425,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/IncidentListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -37873,36 +43449,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List incidents by IDs", + "summary": "Unacknowledge incident", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-list-by-ids", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-unack", "metadata": { - "sidebarTitle": "List incidents by IDs" + "sidebarTitle": "Unacknowledge incident" } } } }, - "/incident/merge": { + "/incident/wake": { "post": { - "description": "Merge one or more incidents into a target incident.", - "operationId": "incidentMerge", + "description": "Cancel the snooze on an incident and resume notifications.", + "operationId": "incidentWake", "requestBody": { "content": { "application/json": { - "example": { - "comment": "Merging related database connectivity incidents into one.", - "source_incident_ids": [ - "69da451ef77b1b51f40e83ef", - "69da451ef77b1b51f40e83f0" - ], - "target_incident_id": "69da451ef77b1b51f40e83ee" + "example": { + "incident_ids": [ + "69da451ef77b1b51f40e83ee" + ] }, "schema": { - "$ref": "#/components/schemas/MergeIncidentsRequest" + "$ref": "#/components/schemas/WakeIncidentRequest" } } }, @@ -37948,32 +43521,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Merge incidents", + "summary": "Wake incident", "tags": [ "On-call/Incidents" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-merge", + "href": "/en/api-reference/on-call/incidents/incident-wake", "metadata": { - "sidebarTitle": "Merge incidents" + "sidebarTitle": "Wake incident" } } } }, - "/incident/past/list": { + "/incident/war-room/add-member": { "post": { - "description": "List historical incidents related to the current incident for reference during triage.", - "operationId": "incidentPastList", + "description": "Add one or more members to the IM war room bound to an incident integration.", + "operationId": "incident-write-add-war-room-member", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "limit": 5 + "chat_id": "oc_5ce6d572455d361153b7cb51da133945", + "integration_id": 362, + "member_ids": [ + 20001, + 20002 + ] }, "schema": { - "$ref": "#/components/schemas/ListPastIncidentsRequest" + "$ref": "#/components/schemas/AddWarRoomMemberRequest" } } }, @@ -37984,9 +43561,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [] - }, + "data": "ok", "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -37997,7 +43572,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListPastIncidentsResponse" + "description": "Returns the literal \"ok\" on success.", + "type": "string" } }, "type": "object" @@ -38021,38 +43597,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List past incidents", + "summary": "Add war-room member", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **20 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-past-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", + "href": "/en/api-reference/on-call/incidents/incident-write-add-war-room-member", "metadata": { - "sidebarTitle": "List past incidents" + "sidebarTitle": "Add war-room member" } } } }, - "/incident/post-mortem/basics/reset": { + "/incident/war-room/create": { "post": { - "description": "Replace the incident facts stored in a post-mortem report.", - "operationId": "postmortem-write-reset-basics", + "description": "Create a war room channel for collaborative incident response.", + "operationId": "incidentWarRoomCreate", "requestBody": { "content": { "application/json": { "example": { - "incidents_earliest_start_seconds": 1761133512, - "incidents_highest_severity": "Warning", - "incidents_latest_close_seconds": 1761133632, - "incidents_total_duration_seconds": 120, - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "responder_ids": [ - 3790925372131 - ] + "add_observers": true, + "incident_id": "69da451ef77b1b51f40e83ee", + "integration_id": 2490562293131 }, "schema": { - "$ref": "#/components/schemas/ResetPostMortemBasicsRequest" + "$ref": "#/components/schemas/CreateWarRoomRequest" } } }, @@ -38063,7 +43634,11 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "chat_id": "oc_a0553eda9014c2de1b3a8f75b4e0c000", + "chat_name": "Incident #0E83EE war room", + "share_link": "" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -38074,7 +43649,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/WarRoom" } }, "type": "object" @@ -38098,34 +43673,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update post-mortem basics", + "summary": "Create war room", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-basics", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-war-room-create", "metadata": { - "sidebarTitle": "Update post-mortem basics" + "sidebarTitle": "Create war room" } } } }, - "/incident/post-mortem/content/reset": { + "/incident/war-room/default-observers": { "post": { - "description": "Replace the body of a drafting post-mortem report with Markdown.", - "operationId": "incident-post-mortem-write-reset-content", + "description": "Return historical responders suggested as default observers when opening a war room.", + "operationId": "incident-read-get-war-room-default-observers", "requestBody": { "content": { "application/json": { "example": { - "expected_revision": 11, - "idempotency_key": "postmortem-reset-8104935102-11", - "markdown": "# Database saturation incident\n\nThe database pool was exhausted; added saturation alert.", - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e" + "incident_id": "664a1b2c3d4e5f6a7b8c9d0e" }, "schema": { - "$ref": "#/components/schemas/ResetPostMortemContentRequest" + "$ref": "#/components/schemas/GetWarRoomDefaultObserversRequest" } } }, @@ -38137,13 +43709,20 @@ "application/json": { "example": { "data": { - "generation": 2, - "markdown_bytes": 88, - "markdown_sha256": "70d764e77e68f8fbfa14d72a235ac07b0110768b8380c8e3436459ebaf02a7c0", - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "previous_generation": 1, - "previous_revision": 11, - "revision": 12 + "observers": [ + { + "account_id": 10001, + "as": "responder", + "avatar": "https://cdn.flashcat.cloud/avatar/20001.png", + "email": "alice@acme.com", + "locale": "zh-CN", + "person_id": 20001, + "person_name": "Alice Chen", + "phone": "+8613800000000", + "status": "active", + "time_zone": "Asia/Shanghai" + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -38155,7 +43734,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PostMortemContentResetResponse" + "$ref": "#/components/schemas/GetWarRoomDefaultObserversResponse" } }, "type": "object" @@ -38172,70 +43751,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, - "409": { - "content": { - "application/json": { - "example": { - "error": { - "code": "Conflict", - "message": "expected_revision conflict: request has 11 but current revision is 12" - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "properties": { - "error": { - "properties": { - "code": { - "enum": [ - "Conflict" - ], - "type": "string" - }, - "message": { - "type": "string" - } - }, - "required": [ - "code", - "message" - ], - "type": "object" - }, - "request_id": { - "type": "string" - } - }, - "required": [ - "request_id", - "error" - ], - "type": "object" - } - } - }, - "description": "The report is not drafting, the revision is stale, or the idempotency key was reused for a different request." - }, - "413": { - "content": { - "application/json": { - "example": { - "error": { - "code": "EntityTooLarge", - "message": "markdown exceeds maximum size" - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Markdown content exceeds the 4 MiB limit." - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -38243,31 +43758,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Reset post-mortem content", + "summary": "Get war-room default observers", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Edit access to the target report is required. |\n\n## Usage\n\n- The report must be drafting and its current revision must equal `expected_revision`; otherwise the API returns `409 Conflict`.\n- Reuse an `idempotency_key` only for the same report, revision, and Markdown content; different reuse returns `409 Conflict`.\n- A successful reset disconnects the previous collaboration (Yjs) room. Reconnect to the new generation room `post-mortem-{accountId}-{postMortemId}-g{N}` (generation 0 has no `-g` suffix). The reset cannot be rolled back.\n- Markdown content is limited to 4 MiB.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/incident-post-mortem-write-reset-content", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", + "href": "/en/api-reference/on-call/incidents/incident-read-get-war-room-default-observers", "metadata": { - "sidebarTitle": "Reset post-mortem content" + "sidebarTitle": "Get war-room default observers" } } } }, - "/incident/post-mortem/delete": { + "/incident/war-room/delete": { "post": { - "description": "Delete a post-mortem report.", - "operationId": "incidentPostMortemDelete", + "description": "Delete an incident war room.", + "operationId": "incidentWarRoomDelete", "requestBody": { "content": { "application/json": { "example": { - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e" + "incident_id": "69da451ef77b1b51f40e83ee", + "integration_id": 2490562293131 }, "schema": { - "$ref": "#/components/schemas/DeletePostMortemRequest" + "$ref": "#/components/schemas/DeleteWarRoomRequest" } } }, @@ -38313,32 +43829,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete post-mortem", + "summary": "Delete war room", "tags": [ "On-call/Incidents" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-post-mortem-delete", + "href": "/en/api-reference/on-call/incidents/incident-war-room-delete", "metadata": { - "sidebarTitle": "Delete post-mortem" + "sidebarTitle": "Delete war room" } } } }, - "/incident/post-mortem/follow-ups/reset": { + "/incident/war-room/detail": { "post": { - "description": "Replace the follow-up action items on a post-mortem report.", - "operationId": "postmortem-write-reset-follow-ups", + "description": "Retrieve the war room configuration and members for an incident.", + "operationId": "incidentWarRoomDetail", "requestBody": { "content": { "application/json": { "example": { - "follow_ups": "- Add database saturation alert\n- Review cache TTL rollout", - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e" + "chat_id": "oc_a0553eda9014c2de1b3a8f75b4e0c000", + "integration_id": 2490562293131 }, "schema": { - "$ref": "#/components/schemas/ResetPostMortemFollowUpsRequest" + "$ref": "#/components/schemas/GetWarRoomDetailRequest" } } }, @@ -38349,7 +43865,11 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "chat_id": "oc_a0553eda9014c2de1b3a8f75b4e0c000", + "chat_name": "Incident #0E83EE war room", + "share_link": "" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -38360,7 +43880,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/WarRoom" } }, "type": "object" @@ -38384,77 +43904,43 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update post-mortem follow-ups", + "summary": "Get war room detail", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-follow-ups", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", + "href": "/en/api-reference/on-call/incidents/incident-war-room-detail", "metadata": { - "sidebarTitle": "Update post-mortem follow-ups" + "sidebarTitle": "Get war room detail" } } } }, - "/incident/post-mortem/info": { - "get": { - "description": "Retrieve a post-mortem report by its `post_mortem_id`. List reports via `/incident/post-mortem/list` first — each row carries the incident it covers — then fetch the full report here by that id.", - "operationId": "incidentPostMortemInfo", - "parameters": [ - { - "description": "Post-mortem ID. Deterministic hash derived from account ID and the set of linked incident IDs.", - "in": "query", - "name": "post_mortem_id", - "required": true, - "schema": { - "type": "string" + "/incident/war-room/list": { + "post": { + "description": "List all war rooms associated with an incident.", + "operationId": "incidentWarRoomList", + "requestBody": { + "content": { + "application/json": { + "example": { + "incident_id": "69da451ef77b1b51f40e83ee" + }, + "schema": { + "$ref": "#/components/schemas/ListWarRoomsRequest" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "content": { "application/json": { "example": { "data": { - "basics": { - "incidents_earliest_start_seconds": 1761133512, - "incidents_highest_severity": "Warning", - "incidents_latest_close_seconds": 1761133632, - "incidents_total_duration_seconds": 120, - "responders": [ - { - "acknowledged_at": 0, - "assigned_at": 1761133515, - "person_id": 3790925372131 - } - ] - }, - "content": { - "content": "{\"type\":\"doc\",\"content\":[]}" - }, - "follow_ups": "", - "meta": { - "account_id": 2451002751131, - "author_ids": [ - 2477273692131 - ], - "channel_id": 3047621227131, - "channel_name": "Ops Channel", - "created_at_seconds": 1773900354, - "incident_ids": [ - "69bb9233331067560c718ecd" - ], - "is_private": false, - "media_count": 0, - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "status": "published", - "team_id": 2477033058131, - "template_id": "post_mortem_default_tmpl_en-us", - "title": "Postmortem1", - "updated_at_seconds": 1773909012 - } + "items": [] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -38466,7 +43952,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PostMortemItem" + "$ref": "#/components/schemas/ListWarRoomsResponse" } }, "type": "object" @@ -38490,34 +43976,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get post-mortem", + "summary": "List war rooms", "tags": [ "On-call/Incidents" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-post-mortem-info", + "href": "/en/api-reference/on-call/incidents/incident-war-room-list", "metadata": { - "sidebarTitle": "Get post-mortem" + "sidebarTitle": "List war rooms" } } } }, - "/incident/post-mortem/init": { + "/incident/work-item/assignees/reset": { "post": { - "description": "Create a post-mortem draft from one or more incidents and a template.", - "operationId": "postmortem-write-init", + "description": "Replace a work item's entire assignee set.", + "operationId": "incidentWorkItemResetAssignees", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69bb9233331067560c718ecd" + "assignee_ids": [ + 3790925372131, + 5068740052131 ], - "template_id": "post_mortem_default_tmpl_en-us" + "version": 2, + "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" }, "schema": { - "$ref": "#/components/schemas/InitPostMortemRequest" + "$ref": "#/components/schemas/ResetWorkItemAssigneesRequest" } } }, @@ -38529,45 +44017,47 @@ "application/json": { "example": { "data": { - "basics": { - "incidents_earliest_start_seconds": 1761133512, - "incidents_highest_severity": "Warning", - "incidents_latest_close_seconds": 1761133632, - "incidents_total_duration_seconds": 120, - "responders": [ + "added_assignee_ids": [ + 5068740052131 + ], + "item": { + "assignee_ids": [ + 3790925372131, + 4756301322131, + 5068740052131 + ], + "assignees": [ { - "acknowledged_at": 0, - "assigned_at": 1761133515, - "person_id": 3790925372131 + "id": 3790925372131, + "type": "person" + }, + { + "id": 4756301322131, + "type": "person" + }, + { + "id": 5068740052131, + "type": "person" } - ] - }, - "content": { - "content": "{\"type\":\"doc\",\"content\":[]}" - }, - "follow_ups": "", - "meta": { - "account_id": 2451002751131, - "author_ids": [ - 2477273692131 - ], - "channel_id": 3047621227131, - "channel_name": "Ops Channel", - "created_at_seconds": 1773900354, - "incident_ids": [ - "69bb9233331067560c718ecd" ], - "is_private": false, - "media_count": 0, - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "status": "published", - "team_id": 2477033058131, - "template_id": "post_mortem_default_tmpl_en-us", - "title": "Postmortem1", - "updated_at_seconds": 1773909012 - } + "created_at_seconds": 1785495329, + "created_by": 5329873302131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "done", + "title": "Follow-ups assigned to Bowen and Weili", + "updated_at_seconds": 1785496384, + "updated_by": 3790925372131, + "version": 2, + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + }, + "removed_assignee_ids": [ + 4756301322131 + ] }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -38577,7 +44067,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PostMortemItem" + "$ref": "#/components/schemas/WorkItemMutationResult" } }, "type": "object" @@ -38601,33 +44091,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Initialize post-mortem", + "summary": "Reset work item assignees", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Links at most 10 incidents to one post-mortem report.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-init", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Full replacement of the assignee set — an empty array clears all assignees.\n- Set either `assignees` or the legacy `assignee_ids`, not both (sending both returns an error). An `ai_sre` entry omits `id`.\n- Only newly added assignees are notified; removals never notify.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-reset-assignees", "metadata": { - "sidebarTitle": "Initialize post-mortem" + "sidebarTitle": "Reset work item assignees" } } } }, - "/incident/post-mortem/list": { + "/incident/work-item/complete": { "post": { - "description": "List post-mortem reports with optional filters.", - "operationId": "incidentPostMortemList", + "description": "Mark a work item as completed by setting a client-defined target status.", + "operationId": "incidentWorkItemComplete", "requestBody": { "content": { "application/json": { "example": { - "limit": 20, - "p": 1, - "status": "published" + "idempotency_key": "complete-wi-20260731-0001", + "target_status": "done", + "version": 2, + "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" }, "schema": { - "$ref": "#/components/schemas/ListPostMortemsRequest" + "$ref": "#/components/schemas/CompleteWorkItemRequest" } } }, @@ -38639,32 +44130,41 @@ "application/json": { "example": { "data": { - "has_next_page": false, - "items": [ - { - "account_id": 2451002751131, - "author_ids": [ - 2477273692131 - ], - "channel_id": 3047621227131, - "channel_name": "Ops Channel", - "created_at_seconds": 1773900354, - "incident_ids": [ - "69bb9233331067560c718ecd" - ], - "is_private": false, - "media_count": 0, - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "status": "published", - "team_id": 2477033058131, - "template_id": "post_mortem_default_tmpl_en-us", - "title": "Postmortem1", - "updated_at_seconds": 1773909012 - } - ], - "total": 3 + "item": { + "assignee_ids": [ + 3790925372131, + 4756301322131, + 5068740052131 + ], + "assignees": [ + { + "id": 3790925372131, + "type": "person" + }, + { + "id": 4756301322131, + "type": "person" + }, + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495329, + "created_by": 5329873302131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "done", + "title": "Follow-ups assigned to Bowen and Weili", + "updated_at_seconds": 1785496384, + "updated_by": 3790925372131, + "version": 2, + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + } }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -38674,7 +44174,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListPostMortemsResponse" + "$ref": "#/components/schemas/WorkItemMutationResult" } }, "type": "object" @@ -38698,32 +44198,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List post-mortems", + "summary": "Complete a work item", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-post-mortem-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Only current assignees can complete a work item.\n- `target_status` is a client-defined string — there is no fixed state machine.\n- The same `idempotency_key` with the same `target_status` replays idempotently; the same key with a different `target_status` returns an error.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-complete", "metadata": { - "sidebarTitle": "List post-mortems" + "sidebarTitle": "Complete a work item" } } } }, - "/incident/post-mortem/status/reset": { + "/incident/work-item/convert": { "post": { - "description": "Set a post-mortem report to drafting or published.", - "operationId": "postmortem-write-reset-status", + "description": "Convert an incident action item into a post-mortem follow-up in place.", + "operationId": "incidentWorkItemConvert", "requestBody": { "content": { "application/json": { "example": { - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "status": "published" + "idempotency_key": "convert-wi-20260731-0001", + "target_status": "open", + "version": 2, + "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" }, "schema": { - "$ref": "#/components/schemas/ResetPostMortemStatusRequest" + "$ref": "#/components/schemas/ConvertWorkItemRequest" } } }, @@ -38734,8 +44236,42 @@ "content": { "application/json": { "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "data": { + "item": { + "assignee_ids": [ + 3790925372131, + 4756301322131, + 5068740052131 + ], + "assignees": [ + { + "id": 3790925372131, + "type": "person" + }, + { + "id": 4756301322131, + "type": "person" + }, + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495329, + "created_by": 5329873302131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "done", + "title": "Follow-ups assigned to Bowen and Weili", + "updated_at_seconds": 1785496384, + "updated_by": 3790925372131, + "version": 2, + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + } + }, + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -38745,7 +44281,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/WorkItemMutationResult" } }, "type": "object" @@ -38769,31 +44305,40 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update post-mortem status", + "summary": "Convert a work item to a follow-up", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-status", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Converts an `action` item into a post-mortem `follow_up` in place — the `work_item_id` does not change.\n- Converting an item that is already a `follow_up` returns `idempotent_replay: true`.\n- If a post-mortem already exists for the incident, the converted item auto-binds to it.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-convert", "metadata": { - "sidebarTitle": "Update post-mortem status" + "sidebarTitle": "Convert a work item to a follow-up" } } } }, - "/incident/post-mortem/template/delete": { + "/incident/work-item/create": { "post": { - "description": "Delete a custom post-mortem template.", - "operationId": "postmortem-write-delete-template", + "description": "Create an action on an active incident or a follow-up on one of its post-mortems.", + "operationId": "incidentWorkItemCreate", "requestBody": { "content": { "application/json": { "example": { - "template_id": "post_mortem_custom_tmpl_01" + "assignee_ids": [ + 3790925372131 + ], + "description": "CPU saturation started right after the v2.14 rollout; roll back and watch the error rate.", + "idempotency_key": "create-wi-20260731-0001", + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "action", + "priority": "high", + "status": "open", + "title": "Roll back the v2.14 deployment on web-server-01" }, "schema": { - "$ref": "#/components/schemas/DeletePostMortemTemplateRequest" + "$ref": "#/components/schemas/CreateWorkItemRequest" } } }, @@ -38804,8 +44349,34 @@ "content": { "application/json": { "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "data": { + "added_assignee_ids": [ + 3790925372131 + ], + "item": { + "assignee_ids": [ + 3790925372131 + ], + "assignees": [ + { + "id": 3790925372131, + "type": "person" + } + ], + "created_at_seconds": 1785496400, + "created_by": 3790925372131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "action", + "source_kind": "native", + "status": "open", + "title": "Roll back the v2.14 deployment on web-server-01", + "updated_at_seconds": 1785496400, + "updated_by": 3790925372131, + "version": 1, + "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + } + }, + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -38815,7 +44386,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/WorkItemCreateResult" } }, "type": "object" @@ -38839,51 +44410,44 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete post-mortem template", + "summary": "Create a work item", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-delete-template", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- An `action` anchors to an active incident and must NOT set `post_mortem_id`; a `follow_up` REQUIRES the `post_mortem_id` of a post-mortem linked to `incident_id`.\n- Set either `assignees` or the legacy `assignee_ids`, not both. `assignees` entries are `{type, id?}` with `type` `person` or `ai_sre`; an `ai_sre` entry omits `id`. `assignee_ids` is equivalent to an all-`person` list. Sending both returns an error.\n- Person assignees must be active members who can already read the anchor incident or post-mortem — assignment never grants access.\n- Newly added assignees are notified.\n- Retrying with the same (`creator`, `idempotency_key`) replays the original item with `idempotent_replay: true` instead of creating a duplicate.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-create", "metadata": { - "sidebarTitle": "Delete post-mortem template" + "sidebarTitle": "Create a work item" } } } }, - "/incident/post-mortem/template/info": { - "get": { - "description": "Return one post-mortem template by ID.", - "operationId": "postmortem-read-template-info", - "parameters": [ - { - "description": "Template ID.", - "in": "query", - "name": "template_id", - "required": true, - "schema": { - "type": "string" + "/incident/work-item/delete": { + "post": { + "description": "Soft-delete a work item.", + "operationId": "incidentWorkItemDelete", + "requestBody": { + "content": { + "application/json": { + "example": { + "version": 2, + "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + }, + "schema": { + "$ref": "#/components/schemas/DeleteWorkItemRequest" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "content": { "application/json": { "example": { - "data": { - "account_id": 2451002751131, - "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", - "content_markdown": "## Summary\nDescribe what happened.", - "created_at_seconds": 1773900000, - "description": "Default sections for post-mortem reports.", - "name": "Default post-mortem report", - "team_id": 2477033058131, - "template_id": "post_mortem_default_tmpl_en-us", - "updated_at_seconds": 1773903600 - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "data": {}, + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -38893,7 +44457,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PostMortemTemplate" + "$ref": "#/components/schemas/WorkItemMutationResult" } }, "type": "object" @@ -38917,34 +44481,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get post-mortem template detail", + "summary": "Delete a work item", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/postmortem-read-template-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Soft delete — the item no longer appears in listings but is retained.\n- Optimistic locking — `version` must match the item's current version; a mismatch returns a conflict error.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-delete", "metadata": { - "sidebarTitle": "Get post-mortem template detail" + "sidebarTitle": "Delete a work item" } } } }, - "/incident/post-mortem/template/list": { + "/incident/work-item/list": { "post": { - "description": "Return built-in and custom post-mortem templates for the account.", - "operationId": "postmortem-read-list-templates", + "description": "List incident work items (actions and post-mortem follow-ups) with cursor pagination.", + "operationId": "incidentWorkItemList", "requestBody": { "content": { "application/json": { "example": { - "asc": false, - "limit": 20, - "order_by": "created_at_seconds", - "p": 1 + "incident_id": "6a5f1e28807515413b384bce", + "limit": 50 }, "schema": { - "$ref": "#/components/schemas/ListPostMortemTemplatesRequest" + "$ref": "#/components/schemas/ListWorkItemRequest" } } }, @@ -38956,23 +44518,68 @@ "application/json": { "example": { "data": { - "has_next_page": false, + "has_more": true, "items": [ { - "account_id": 2451002751131, - "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", - "content_markdown": "## Summary\nDescribe what happened.", - "created_at_seconds": 1773900000, - "description": "Default sections for post-mortem reports.", - "name": "Default post-mortem report", - "team_id": 2477033058131, - "template_id": "post_mortem_default_tmpl_en-us", - "updated_at_seconds": 1773903600 + "assignee_ids": [ + 3790925372131, + 4756301322131, + 5068740052131 + ], + "assignees": [ + { + "id": 3790925372131, + "type": "person" + }, + { + "id": 4756301322131, + "type": "person" + }, + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495329, + "created_by": 5329873302131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "done", + "title": "Follow-ups assigned to Bowen and Weili", + "updated_at_seconds": 1785496384, + "updated_by": 3790925372131, + "version": 2, + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + }, + { + "assignee_ids": [ + 5068740052131 + ], + "assignees": [ + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495164, + "created_by": 3790925372131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "open", + "title": "Check whether this to-do notifies Bowen", + "updated_at_seconds": 1785495164, + "updated_by": 3790925372131, + "version": 1, + "work_item_id": "wi_dMRYTeZHivE5vf87PQEeFX" } ], - "total": 2 + "next_cursor": "MTc4NTQ5NTE2NHx3aV9kTVJZVGVaSGl2RTV2Zjg3UFFFZUZY" }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -38982,7 +44589,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListPostMortemTemplatesResponse" + "$ref": "#/components/schemas/WorkItemListResult" } }, "type": "object" @@ -39006,35 +44613,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List post-mortem templates", + "summary": "List work items", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/postmortem-read-list-templates", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- At least one of `incident_id`, `post_mortem_id`, `assignee_id`, or `assignee_type` = `ai_sre` is required.\n- `assignee_type` = `ai_sre` lists items assigned to AI SRE and can be used on its own.\n- Cursor pagination sorted by `updated_at_seconds` descending — pass the previous response's `next_cursor` as `cursor` until `has_more` is false.\n- Listing by `incident_id` also includes follow-ups anchored on the incident's post-mortem.\n- Listing by `assignee_id` alone requires being that assignee or an account admin.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-list", "metadata": { - "sidebarTitle": "List post-mortem templates" + "sidebarTitle": "List work items" } } } }, - "/incident/post-mortem/template/upsert": { + "/incident/work-item/post-mortem/bind": { "post": { - "description": "Create a custom post-mortem template or update an existing one.", - "operationId": "postmortem-write-upsert-template", + "description": "Bulk-bind an incident's converted-but-unbound follow-ups to a post-mortem.", + "operationId": "incidentWorkItemBindPostMortem", "requestBody": { "content": { "application/json": { "example": { - "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", - "content_markdown": "## Summary\nDescribe what happened.", - "description": "Template for production incident reviews.", - "name": "Production incident template", - "team_id": 2477033058131 + "idempotency_key": "bind-wi-20260731-0001", + "incident_id": "6a5f1e28807515413b384bce", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63" }, "schema": { - "$ref": "#/components/schemas/UpsertPostMortemTemplateRequest" + "$ref": "#/components/schemas/BindWorkItemPostMortemRequest" } } }, @@ -39046,17 +44651,67 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "content": "[{\"type\":\"heading\",\"content\":\"Summary\"}]", - "content_markdown": "## Summary\nDescribe what happened.", - "created_at_seconds": 1773900000, - "description": "Default sections for post-mortem reports.", - "name": "Default post-mortem report", - "team_id": 2477033058131, - "template_id": "post_mortem_default_tmpl_en-us", - "updated_at_seconds": 1773903600 + "has_more": false, + "items": [ + { + "assignee_ids": [ + 3790925372131, + 4756301322131, + 5068740052131 + ], + "assignees": [ + { + "id": 3790925372131, + "type": "person" + }, + { + "id": 4756301322131, + "type": "person" + }, + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495329, + "created_by": 5329873302131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "done", + "title": "Follow-ups assigned to Bowen and Weili", + "updated_at_seconds": 1785496384, + "updated_by": 3790925372131, + "version": 2, + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + }, + { + "assignee_ids": [ + 5068740052131 + ], + "assignees": [ + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495164, + "created_by": 3790925372131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "open", + "title": "Check whether this to-do notifies Bowen", + "updated_at_seconds": 1785495164, + "updated_by": 3790925372131, + "version": 1, + "work_item_id": "wi_dMRYTeZHivE5vf87PQEeFX" + } + ] }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -39066,7 +44721,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PostMortemTemplate" + "$ref": "#/components/schemas/WorkItemListResult" } }, "type": "object" @@ -39090,32 +44745,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create or update post-mortem template", + "summary": "Bind work items to a post-mortem", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-upsert-template", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Binds ALL of the incident's converted-but-unbound follow-ups to the given post-mortem in one call.\n- `items` holds the newly bound batch; `next_cursor` and `has_more` are not set.\n- Idempotent by `idempotency_key` — retrying with the same key replays the original result.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-bind-post-mortem", "metadata": { - "sidebarTitle": "Create or update post-mortem template" + "sidebarTitle": "Bind work items to a post-mortem" } } } }, - "/incident/post-mortem/title/reset": { + "/incident/work-item/update": { "post": { - "description": "Replace the title of a post-mortem report.", - "operationId": "postmortem-write-reset-title", + "description": "Partially update a work item's title, description, status, or priority.", + "operationId": "incidentWorkItemUpdate", "requestBody": { "content": { "application/json": { "example": { - "post_mortem_id": "8104935102bf89dc01ac638a5261fe7e", - "title": "Production API latency incident" + "status": "in_progress", + "title": "Roll back the v2.14 deployment on web-server-01 and web-server-02", + "version": 1, + "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" }, "schema": { - "$ref": "#/components/schemas/ResetPostMortemTitleRequest" + "$ref": "#/components/schemas/UpdateWorkItemRequest" } } }, @@ -39126,8 +44783,42 @@ "content": { "application/json": { "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "data": { + "item": { + "assignee_ids": [ + 3790925372131, + 4756301322131, + 5068740052131 + ], + "assignees": [ + { + "id": 3790925372131, + "type": "person" + }, + { + "id": 4756301322131, + "type": "person" + }, + { + "id": 5068740052131, + "type": "person" + } + ], + "created_at_seconds": 1785495329, + "created_by": 5329873302131, + "incident_id": "6a5f1e28807515413b384bce", + "item_type": "follow_up", + "post_mortem_id": "51d65cd9525c369379ba471b5512df63", + "source_kind": "native", + "status": "done", + "title": "Follow-ups assigned to Bowen and Weili", + "updated_at_seconds": 1785496384, + "updated_by": 3790925372131, + "version": 2, + "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" + } + }, + "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -39137,7 +44828,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/WorkItemMutationResult" } }, "type": "object" @@ -39161,33 +44852,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update post-mortem title", + "summary": "Update a work item", "tags": [ "On-call/Incidents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/incidents/postmortem-write-reset-title", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Partial patch: omitted fields stay unchanged; an explicit `null` clears the field.\n- Optimistic locking — `version` must match the item's current version; a mismatch returns a conflict error.\n- Assignees, `item_type`, and the incident/post-mortem anchors cannot be changed here — use the dedicated endpoints.\n- Audited — changes are recorded in the audit log.", + "href": "/en/api-reference/on-call/incidents/incident-work-item-update", "metadata": { - "sidebarTitle": "Update post-mortem title" + "sidebarTitle": "Update a work item" } } } }, - "/incident/remove": { + "/insight/account": { "post": { - "description": "Permanently delete an incident and all associated data.", - "operationId": "incidentRemove", + "description": "Return aggregated incident insight metrics for the entire account.", + "operationId": "insightByAccount", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" - ] + "aggregate_unit": "day", + "end_time": 1712604800, + "severities": [ + "Critical", + "Warning" + ], + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/RemoveIncidentRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39198,7 +44893,34 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "acknowledgement_pct": 100, + "mean_seconds_to_ack": 1658854.5, + "mean_seconds_to_close": 1874757, + "noise_reduction_pct": 0, + "total_alert_cnt": 0, + "total_alert_event_cnt": 0, + "total_engaged_seconds": 3317709, + "total_incident_cnt": 2, + "total_incidents_acknowledged": 2, + "total_incidents_auto_closed": 0, + "total_incidents_closed": 2, + "total_incidents_escalated": 0, + "total_incidents_manually_closed": 2, + "total_incidents_manually_escalated": 0, + "total_incidents_reassigned": 2, + "total_incidents_timeout_closed": 0, + "total_incidents_timeout_escalated": 0, + "total_interruptions": 3, + "total_notifications": 6, + "total_seconds_to_ack": 3317709, + "total_seconds_to_close": 3749514, + "ts": 1740844800 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -39209,7 +44931,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/DimensionInsightResponse" } }, "type": "object" @@ -39233,34 +44955,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete an incident", + "summary": "Get account-level insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-remove", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-by-account", "metadata": { - "sidebarTitle": "Delete an incident" + "sidebarTitle": "Get account-level insight" } } } }, - "/incident/reopen": { + "/insight/alert/topk-by-label": { "post": { - "description": "Reopen a previously resolved incident.", - "operationId": "incidentReopen", + "description": "Return the top-K alert groups aggregated either by `check` or by `resource` label over the specified time range.", + "operationId": "insightTopkAlertsByLabel", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" - ], - "reason": "Monitoring detected the issue recurred after the initial fix." + "end_time": 1712604800, + "k": 10, + "label": "check", + "orderby": "total_alert_cnt", + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/ReopenIncidentRequest" + "$ref": "#/components/schemas/InsightTopkAlertByLabelRequest" } } }, @@ -39271,7 +44994,25 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "label": "cpu-high", + "total_alert_cnt": 312, + "total_alert_event_cnt": 987 + }, + { + "label": "disk-full", + "total_alert_cnt": 178, + "total_alert_event_cnt": 452 + }, + { + "label": "memory-oom", + "total_alert_cnt": 94, + "total_alert_event_cnt": 231 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -39282,7 +45023,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/InsightAlertByLabelResponse" } }, "type": "object" @@ -39306,33 +45047,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Reopen incident", + "summary": "Get top-K alerts grouped by check or resource", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-reopen", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-topk-alerts-by-label", "metadata": { - "sidebarTitle": "Reopen incident" + "sidebarTitle": "Get top-K alerts grouped by check or resource" } } } }, - "/incident/reset": { + "/insight/channel": { "post": { - "description": "Update one or more editable fields of an incident in a single call, including title, description, impact, root cause, resolution, and severity. At least one field must be provided.", - "operationId": "incidentReset", + "description": "Return insight metrics aggregated by channel.", + "operationId": "insightByChannel", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "incident_severity": "Critical", - "title": "Database connection timeout - prod-db-01 primary" + "aggregate_unit": "day", + "channel_ids": [ + 4321322010131 + ], + "end_time": 1712604800, + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/UpdateIncidentFieldsRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39343,7 +45087,36 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "acknowledgement_pct": 100, + "channel_id": 4321322010131, + "channel_name": "Production Alerts", + "mean_seconds_to_ack": 1658854.5, + "mean_seconds_to_close": 1874757, + "noise_reduction_pct": 0, + "total_alert_cnt": 0, + "total_alert_event_cnt": 0, + "total_engaged_seconds": 3317709, + "total_incident_cnt": 2, + "total_incidents_acknowledged": 2, + "total_incidents_auto_closed": 0, + "total_incidents_closed": 2, + "total_incidents_escalated": 0, + "total_incidents_manually_closed": 2, + "total_incidents_manually_escalated": 0, + "total_incidents_reassigned": 2, + "total_incidents_timeout_closed": 0, + "total_incidents_timeout_escalated": 0, + "total_interruptions": 3, + "total_notifications": 6, + "total_seconds_to_ack": 3317709, + "total_seconds_to_close": 3749514, + "ts": 1740844800 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -39354,7 +45127,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/DimensionInsightResponse" } }, "type": "object" @@ -39378,35 +45151,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update incident fields", + "summary": "Get channel insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-reset", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-by-channel", "metadata": { - "sidebarTitle": "Update incident fields" + "sidebarTitle": "Get channel insight" } } } }, - "/incident/resolve": { + "/insight/channel/export": { "post": { - "description": "Mark an incident as resolved.", - "operationId": "incidentResolve", + "description": "Export channel insight metrics as a CSV file — one row per channel (and per time/hour bucket when `aggregate_unit`/`split_hours` is used). The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. `time_zone` defaults to UTC. Rows without a valid channel ID are skipped. Valid `export_fields` keys: channel_id, channel_name, total_incident_cnt, total_incidents_acknowledged, total_incidents_closed, total_incidents_auto_closed, total_incidents_manually_closed, total_incidents_timeout_closed, total_incidents_escalated, total_incidents_manually_escalated, total_incidents_timeout_escalated, total_incidents_reassigned, total_interruptions, total_notifications, total_engaged_seconds, mean_seconds_to_ack, mean_seconds_to_close, noise_reduction_pct, acknowledgement_pct, total_alert_cnt, total_alert_event_cnt, hours. The `hours` column is included by default only when `split_hours` is true. For compatibility, incident-export column keys are also accepted but produce empty columns.", + "operationId": "insightChannelExport", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" + "channel_ids": [ + 4321322010131 ], - "resolution": "Deployed hotfix v2.3.1 and restarted the affected service.", - "root_cause": "Memory leak in the connection pool caused by a missing cleanup call." + "end_time": 1712604800, + "severities": [ + "Critical", + "Warning" + ], + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/ResolveIncidentRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39415,25 +45192,12 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/octet-stream": { + "example": "channel_id,channel_name,total_incident_cnt,total_incidents_closed\n4321322010131,Production Alerts,12,10\n", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/EmptyResponse" - } - }, - "type": "object" - } - ] + "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=channel_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full field set, or the keys given in `export_fields`.", + "format": "binary", + "type": "string" } } }, @@ -39452,35 +45216,44 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Resolve incident", + "summary": "Export channel insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- When a resolution form applies, `custom_fields`, `summary`, and `images` must match its visible elements and required rules.\n- For a batch, form values are accepted only when every selected incident resolves to the same form; otherwise resolve incidents individually.\n- The legacy `values` and `custom_values` properties are rejected; use `custom_fields`.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-resolve", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-channel-export", "metadata": { - "sidebarTitle": "Resolve incident" + "sidebarTitle": "Export channel insight" } } } }, - "/incident/responder/add": { + "/insight/incident/export": { "post": { - "description": "Add a responder to an existing incident.", - "operationId": "incidentResponderAdd", + "description": "Export the filtered incident analytics list as a CSV file. The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. CSV headers and formatted values use the request locale, falling back to the member locale and then the account locale. `time_zone` defaults to the account time zone, then `Asia/Shanghai`. Export stops after at most 100,000 rows. Valid `export_fields` keys: incident_id, title, severity, progress, channel_id, channel_name, team_id, team_name, created_at, alert_cnt, active_alert_cnt, alert_event_cnt, seconds_to_ack, seconds_to_close, closed_by, owner_id, owner_name, creator_id, creator_name, closer_id, closer_name, engaged_seconds, hours, notifications, interruptions, acknowledgements, ackers, assignments, reassignments, escalations, manual_escalations, timeout_escalations, assigned_to, raw_assigned_to, escalate_rule_name, responders, raw_responders, snooze_status, snoozed_before, ever_muted, frequency, is_rare, description, labels, fields. When `export_fields` is omitted, all columns are exported.", + "operationId": "insightIncidentExport", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "person_ids": [ - 2476444212131, - 2476444212132 - ] + "description_html_to_text": true, + "end_time": 1712604800, + "export_fields": [ + "incident_id", + "title", + "severity", + "created_at", + "seconds_to_close" + ], + "severities": [ + "Critical", + "Warning" + ], + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/AddIncidentResponderRequest" + "$ref": "#/components/schemas/InsightIncidentExportRequest" } } }, @@ -39489,25 +45262,12 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/octet-stream": { + "example": "incident_id,title,severity,created_at\n6a86b5d6f72de50ae1ce2ffb,CPU usage above 90%,Critical,2026-01-01 10:00:00 +0800 CST\n", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/EmptyResponse" - } - }, - "type": "object" - } - ] + "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=incident_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full incident field set, or the keys given in `export_fields`.", + "format": "binary", + "type": "string" } } }, @@ -39526,37 +45286,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Add incident responder", + "summary": "Export insight incidents", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-responder-add", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-incident-export", "metadata": { - "sidebarTitle": "Add incident responder" + "sidebarTitle": "Export insight incidents" } } } }, - "/incident/sdp/request/list": { + "/insight/incident/list": { "post": { - "description": "List synchronization mappings between ServiceDeskPlus requests and Flashduty incidents.", - "operationId": "incident-service-desk-plus-request-read-list", + "description": "Return a paged list of incidents with per-incident handling metrics used by the analytics dashboard.", + "operationId": "insightIncidentList", "requestBody": { "content": { "application/json": { "example": { - "channel_ids": [ - 12345 - ], - "end_time": 1779600000, + "end_time": 1712604800, "limit": 20, - "start_time": 1779513600, - "status": "success" + "p": 1, + "severities": [ + "Critical" + ], + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/ServiceDeskPlusRequestListRequest" + "$ref": "#/components/schemas/InsightIncidentListRequest" } } }, @@ -39568,22 +45328,60 @@ "application/json": { "example": { "data": { - "has_next_page": false, + "has_next_page": true, "items": [ { - "channel_id": 12345, - "channel_name": "Payments", - "created_at": 1779514631, - "incident_id": "685d7f4e51b9a9a6d4d0c123", - "incident_title": "Checkout API 5xx rate increased", - "integration_id": 98765, - "request_id": "100000000001", - "request_link": "https://servicedesk.example.com/app/itdesk/ui/requests/100000000001/details", - "status": "success" + "acknowledgements": 1, + "active_alert_cnt": 0, + "alert_cnt": 3, + "alert_event_cnt": 5, + "assigned_to": { + "assigned_at": 1787213270, + "escalate_rule_id": "66138789904a9027583dbc4e", + "escalate_rule_name": "On-call Policy", + "id": "b8tyUoRvCv4wsPndFRpmNL", + "layer_idx": 0, + "type": "assign" + }, + "assignments": 1, + "channel_id": 3047621227131, + "channel_name": "Production Alerts", + "closed_by": "manually", + "closer_id": 2477273692131, + "closer_name": "alice", + "created_at": 1787213270, + "creator_id": 2477273692131, + "creator_name": "alice", + "description": "CPU usage stayed above the threshold for 5 minutes", + "engaged_seconds": 1816, + "escalations": 0, + "hours": "work", + "incident_id": "6a86b5d6f72de50ae1ce2ffb", + "interruptions": 1, + "manual_escalations": 0, + "notifications": 2, + "progress": "Closed", + "reassignments": 0, + "responders": [ + { + "acknowledged_at": 1787213284, + "assigned_at": 1787213270, + "email": "alice@example.com", + "person_id": 2477273692131, + "person_name": "alice" + } + ], + "seconds_to_ack": 14, + "seconds_to_close": 1830, + "severity": "Critical", + "team_id": 2477033058131, + "team_name": "SRE Team", + "timeout_escalations": 0, + "title": "CPU usage above 90% on prod-web-01" } ], - "search_after_ctx": "", - "total": 1 + "search_after_ctx": "6a86b5d6f72de50ae1ce2ffb", + "total": 2363 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -39595,7 +45393,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ServiceDeskPlusRequestListResponse" + "$ref": "#/components/schemas/InsightIncidentListResponse" } }, "type": "object" @@ -39619,34 +45417,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get ServiceDeskPlus linked incidents", + "summary": "List insight incidents", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- Use this endpoint to inspect synchronization mappings between ServiceDeskPlus requests and Flashduty incidents, including the external request link and sync status.\n- When `incident_id` is not provided, `start_time` and `end_time` are required Unix-second timestamps; the time window cannot exceed 30 days.\n- `status` accepts only `success` and `failed`, representing successful and failed synchronization records.\n- Results are sorted by the internal record ID. Set `asc` to `true` for ascending order; otherwise records are returned descending. Pass the returned `search_after_ctx` to continue pagination.", - "href": "/en/api-reference/on-call/incidents/incident-service-desk-plus-request-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-incident-list", "metadata": { - "sidebarTitle": "Get ServiceDeskPlus linked incidents" + "sidebarTitle": "List insight incidents" } } } }, - "/incident/snooze": { + "/insight/responder": { "post": { - "description": "Temporarily snooze notifications for an incident until a specified time.", - "operationId": "incidentSnooze", + "description": "Return insight metrics aggregated by responder.", + "operationId": "insightByResponder", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" + "aggregate_unit": "day", + "end_time": 1712604800, + "responder_ids": [ + 3790925372131 ], - "minutes": 60 + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/SnoozeIncidentRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39657,7 +45457,27 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "acknowledgement_pct": 100, + "mean_seconds_to_ack": 2265624, + "responder_id": 3790925372131, + "responder_name": "alice", + "total_engaged_seconds": 10, + "total_incident_cnt": 1, + "total_incidents_acknowledged": 1, + "total_incidents_escalated": 0, + "total_incidents_manually_escalated": 0, + "total_incidents_reassigned": 0, + "total_incidents_timeout_escalated": 0, + "total_interruptions": 1, + "total_notifications": 2, + "total_seconds_to_ack": 2265624, + "ts": 1740844800 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -39668,7 +45488,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ResponderInsightResponse" } }, "type": "object" @@ -39692,33 +45512,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Snooze incident", + "summary": "Get responder insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-snooze", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-by-responder", "metadata": { - "sidebarTitle": "Snooze incident" + "sidebarTitle": "Get responder insight" } } } }, - "/incident/unack": { + "/insight/responder/export": { "post": { - "description": "Remove the acknowledge status from an incident.", - "operationId": "incidentUnack", + "description": "Export responder insight metrics as a CSV file — one row per responder (and per time/hour bucket when `aggregate_unit`/`split_hours` is used). The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. `time_zone` defaults to UTC. Rows without a valid responder ID are skipped. Valid `export_fields` keys: responder_id, responder_name, total_incident_cnt, total_incidents_acknowledged, total_incidents_reassigned, total_incidents_escalated, total_incidents_manually_escalated, total_incidents_timeout_escalated, total_interruptions, total_notifications, total_engaged_seconds, mean_seconds_to_ack, acknowledgement_pct, hours. The `hours` column is included by default only when `split_hours` is true. For compatibility, incident-export column keys are also accepted but produce empty columns.", + "operationId": "insightResponderExport", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" - ] + "end_time": 1712604800, + "responder_ids": [ + 3790925372131 + ], + "severities": [ + "Critical", + "Warning" + ], + "start_time": 1712000000 }, "schema": { - "$ref": "#/components/schemas/UnackIncidentRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39727,25 +45553,12 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/octet-stream": { + "example": "responder_id,responder_name,total_incident_cnt,total_incidents_acknowledged\n3790925372131,alice,5,4\n", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/EmptyResponse" - } - }, - "type": "object" - } - ] + "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=responder_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full field set, or the keys given in `export_fields`.", + "format": "binary", + "type": "string" } } }, @@ -39764,33 +45577,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Unacknowledge incident", + "summary": "Export responder insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-unack", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-responder-export", "metadata": { - "sidebarTitle": "Unacknowledge incident" + "sidebarTitle": "Export responder insight" } } } }, - "/incident/wake": { + "/insight/team": { "post": { - "description": "Cancel the snooze on an incident and resume notifications.", - "operationId": "incidentWake", + "description": "Return insight metrics aggregated by team.", + "operationId": "insightByTeam", "requestBody": { "content": { "application/json": { "example": { - "incident_ids": [ - "69da451ef77b1b51f40e83ee" + "aggregate_unit": "day", + "end_time": 1712604800, + "start_time": 1712000000, + "team_ids": [ + 4295771902131 ] }, "schema": { - "$ref": "#/components/schemas/WakeIncidentRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39801,7 +45617,36 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "items": [ + { + "acknowledgement_pct": 100, + "mean_seconds_to_ack": 1658854.5, + "mean_seconds_to_close": 1874757, + "noise_reduction_pct": 0, + "team_id": 4295771902131, + "team_name": "SRE Team", + "total_alert_cnt": 0, + "total_alert_event_cnt": 0, + "total_engaged_seconds": 3317709, + "total_incident_cnt": 2, + "total_incidents_acknowledged": 2, + "total_incidents_auto_closed": 0, + "total_incidents_closed": 2, + "total_incidents_escalated": 0, + "total_incidents_manually_closed": 2, + "total_incidents_manually_escalated": 0, + "total_incidents_reassigned": 2, + "total_incidents_timeout_closed": 0, + "total_incidents_timeout_escalated": 0, + "total_interruptions": 3, + "total_notifications": 6, + "total_seconds_to_ack": 3317709, + "total_seconds_to_close": 3749514, + "ts": 1740844800 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -39812,7 +45657,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/DimensionInsightResponse" } }, "type": "object" @@ -39836,36 +45681,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Wake incident", + "summary": "Get team insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-wake", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-by-team", "metadata": { - "sidebarTitle": "Wake incident" + "sidebarTitle": "Get team insight" } } } }, - "/incident/war-room/add-member": { + "/insight/team/export": { "post": { - "description": "Add one or more members to the IM war room bound to an incident integration.", - "operationId": "incident-write-add-war-room-member", + "description": "Export team insight metrics as a CSV file — one row per team (and per time/hour bucket when `aggregate_unit`/`split_hours` is used). The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. `time_zone` defaults to UTC. Rows without a valid team ID are skipped. Valid `export_fields` keys: team_id, team_name, total_incident_cnt, total_incidents_acknowledged, total_incidents_closed, total_incidents_auto_closed, total_incidents_manually_closed, total_incidents_timeout_closed, total_incidents_escalated, total_incidents_manually_escalated, total_incidents_timeout_escalated, total_incidents_reassigned, total_interruptions, total_notifications, total_engaged_seconds, mean_seconds_to_ack, mean_seconds_to_close, noise_reduction_pct, acknowledgement_pct, total_alert_cnt, total_alert_event_cnt, hours. The `hours` column is included by default only when `split_hours` is true. For compatibility, incident-export column keys are also accepted but produce empty columns.", + "operationId": "insightTeamExport", "requestBody": { "content": { "application/json": { "example": { - "chat_id": "oc_5ce6d572455d361153b7cb51da133945", - "integration_id": 362, - "member_ids": [ - 20001, - 20002 + "end_time": 1712604800, + "severities": [ + "Critical", + "Warning" + ], + "start_time": 1712000000, + "team_ids": [ + 4295771902131 ] }, "schema": { - "$ref": "#/components/schemas/AddWarRoomMemberRequest" + "$ref": "#/components/schemas/InsightQueryRequest" } } }, @@ -39874,26 +45722,12 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": "ok", - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/octet-stream": { + "example": "team_id,team_name,total_incident_cnt,total_incidents_closed\n4295771902131,SRE Team,12,10\n", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "description": "Returns the literal \"ok\" on success.", - "type": "string" - } - }, - "type": "object" - } - ] + "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=team_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full field set, or the keys given in `export_fields`.", + "format": "binary", + "type": "string" } } }, @@ -39912,33 +45746,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Add war-room member", + "summary": "Export team insight", "tags": [ - "On-call/Incidents" + "On-call/Analytics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", - "href": "/en/api-reference/on-call/incidents/incident-write-add-war-room-member", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", + "href": "/en/api-reference/on-call/analytics/insight-team-export", "metadata": { - "sidebarTitle": "Add war-room member" + "sidebarTitle": "Export team insight" } } } }, - "/incident/war-room/create": { + "/member/delete": { "post": { - "description": "Create a war room channel for collaborative incident response.", - "operationId": "incidentWarRoomCreate", + "description": "Remove a member from the organization by ID, email, phone, or name.", + "operationId": "memberDelete", "requestBody": { "content": { "application/json": { "example": { - "add_observers": true, - "incident_id": "69da451ef77b1b51f40e83ee", - "integration_id": 2490562293131 + "member_id": 5068740052131 }, "schema": { - "$ref": "#/components/schemas/CreateWarRoomRequest" + "$ref": "#/components/schemas/MemberDeleteRequest" } } }, @@ -39949,11 +45781,7 @@ "content": { "application/json": { "example": { - "data": { - "chat_id": "oc_a0553eda9014c2de1b3a8f75b4e0c000", - "chat_name": "Incident #0E83EE war room", - "share_link": "" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -39964,7 +45792,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WarRoom" + "$ref": "#/components/schemas/MemberEmptyObject" } }, "type": "object" @@ -39988,31 +45816,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create war room", + "summary": "Delete member", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-war-room-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |\n\n## Usage\n\n- By default (`is_force=false`), the system checks whether the member is referenced by other resources (e.g., escalation rules, schedules). If references exist, the API returns error code `ReferenceExist` with the reference list in `data.refs`. Set `is_force=true` to skip the reference check and force delete.\n- Members provisioned via SSO with `sso_user_non_editable=true` cannot be deleted through this API. Disable that SSO restriction first.\n- This operation is recorded in the audit log.", + "href": "/en/api-reference/platform/members/member-delete", "metadata": { - "sidebarTitle": "Create war room" + "sidebarTitle": "Delete member" } } } }, - "/incident/war-room/default-observers": { + "/member/info": { "post": { - "description": "Return historical responders suggested as default observers when opening a war room.", - "operationId": "incident-read-get-war-room-default-observers", + "description": "Return the profile of the member the credential belongs to. Requires a member-scoped credential — calls authenticated as the account principal (e.g. an account-level app key) are rejected with a 400.", + "operationId": "memberInfo", "requestBody": { "content": { "application/json": { - "example": { - "incident_id": "664a1b2c3d4e5f6a7b8c9d0e" - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/GetWarRoomDefaultObserversRequest" + "$ref": "#/components/schemas/MemberInfoRequest" } } }, @@ -40024,20 +45850,28 @@ "application/json": { "example": { "data": { - "observers": [ - { - "account_id": 10001, - "as": "responder", - "avatar": "https://cdn.flashcat.cloud/avatar/20001.png", - "email": "alice@acme.com", - "locale": "zh-CN", - "person_id": 20001, - "person_name": "Alice Chen", - "phone": "+8613800000000", - "status": "active", - "time_zone": "Asia/Shanghai" - } - ] + "account_avatar": "", + "account_email": "alice@example.com", + "account_id": 2451002751131, + "account_locale": "en-US", + "account_name": "Acme Corp", + "account_role_ids": [ + 6 + ], + "account_time_zone": "Asia/Shanghai", + "avatar": "/image/avatar1.png", + "country_code": "CN", + "created_at": 1701399971, + "domain": "acme", + "email": "alice@example.com", + "email_verified": true, + "is_external": false, + "locale": "zh-CN", + "member_id": 2476444212131, + "member_name": "Alice", + "phone": "+86185****0300", + "phone_verified": true, + "time_zone": "Asia/Shanghai" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -40049,7 +45883,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/GetWarRoomDefaultObserversResponse" + "$ref": "#/components/schemas/MemberInfoResponse" } }, "type": "object" @@ -40073,32 +45907,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get war-room default observers", + "summary": "Get current member info", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", - "href": "/en/api-reference/on-call/incidents/incident-read-get-war-room-default-observers", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — but the credential must belong to a member; account-principal credentials (e.g. an account-level app key) are rejected with a 400 |", + "href": "/en/api-reference/platform/members/member-info", "metadata": { - "sidebarTitle": "Get war-room default observers" + "sidebarTitle": "Get current member info" } } } }, - "/incident/war-room/delete": { + "/member/info/reset": { "post": { - "description": "Delete an incident war room.", - "operationId": "incidentWarRoomDelete", + "description": "Identify a member and reset the specified profile fields.", + "operationId": "memberResetInfo", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee", - "integration_id": 2490562293131 + "member_id": 2476444212131, + "updates": { + "locale": "zh-CN", + "member_name": "Alice Chen", + "time_zone": "Asia/Shanghai" + } }, "schema": { - "$ref": "#/components/schemas/DeleteWarRoomRequest" + "$ref": "#/components/schemas/MemberResetInfoRequest" } } }, @@ -40120,7 +45958,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/MemberEmptyObject" } }, "type": "object" @@ -40144,32 +45982,48 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete war room", + "summary": "Reset member info", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-war-room-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Identify the member with one of `member_id`, `member_name`, `email`, `phone`, or `ref_id`. If multiple identifiers are present, the server checks them in that order.\n- `updates.country_code` is an ISO 3166-1 alpha-2 region code (e.g. \"CN\", \"US\"). It is an independently updatable field: `updates.phone` is not required, and the new region is stored even when the phone is unchanged. An explicit empty string is rejected with a 400.\n- When `updates.phone` has no \"+\" prefix, it is parsed with `updates.country_code` as the region hint, falling back to the member's stored region and then to \"CN\". Legacy digit calling codes such as \"86\" remain accepted only as parsing hints — stored values are always ISO region codes.\n- The top-level `country_code` is only a parsing hint for the identifying `phone`; it is never stored.\n- Put the profile fields to write under `updates`: `member_name`, `password`, `phone`, `country_code`, `email`, `avatar`, `locale`, `time_zone`, or `ref_id`.\n- Members provisioned by SSO cannot be changed when SSO marks them as externally managed.\n- `updates` must carry at least one field; an object with every field omitted is rejected.", + "href": "/en/api-reference/platform/members/member-reset-info", "metadata": { - "sidebarTitle": "Delete war room" + "sidebarTitle": "Reset member info" } } } }, - "/incident/war-room/detail": { + "/member/invite": { "post": { - "description": "Retrieve the war room configuration and members for an incident.", - "operationId": "incidentWarRoomDetail", + "description": "Batch invite new members to the organization by email or phone.", + "operationId": "memberInvite", "requestBody": { "content": { "application/json": { "example": { - "chat_id": "oc_a0553eda9014c2de1b3a8f75b4e0c000", - "integration_id": 2490562293131 + "members": [ + { + "email": "charlie@example.com", + "locale": "en-US", + "member_name": "Charlie", + "role_ids": [ + 6 + ], + "time_zone": "Asia/Shanghai" + }, + { + "country_code": "CN", + "locale": "zh-CN", + "member_name": "Dave", + "phone": "13800138000", + "time_zone": "Asia/Shanghai" + } + ] }, "schema": { - "$ref": "#/components/schemas/GetWarRoomDetailRequest" + "$ref": "#/components/schemas/MemberInviteRequest" } } }, @@ -40181,9 +46035,16 @@ "application/json": { "example": { "data": { - "chat_id": "oc_a0553eda9014c2de1b3a8f75b4e0c000", - "chat_name": "Incident #0E83EE war room", - "share_link": "" + "items": [ + { + "member_id": 5068740052131, + "member_name": "Charlie" + }, + { + "member_id": 5068740052132, + "member_name": "Dave" + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -40195,7 +46056,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WarRoom" + "$ref": "#/components/schemas/MemberInviteResponse" } }, "type": "object" @@ -40219,31 +46080,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get war room detail", + "summary": "Invite members", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-war-room-detail", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |\n\n## Usage\n\n- `country_code` must be an ISO 3166-1 alpha-2 region code (e.g. \"CN\"). It is validated and normalized to upper case before storage; invalid values are rejected with a 400.\n- When a member's `phone` has no \"+\" prefix, it is parsed with that member's `country_code` as the region hint (defaults to \"CN\" when omitted).", + "href": "/en/api-reference/platform/members/member-invite", "metadata": { - "sidebarTitle": "Get war room detail" + "sidebarTitle": "Invite members" } } } }, - "/incident/war-room/list": { + "/member/list": { "post": { - "description": "List all war rooms associated with an incident.", - "operationId": "incidentWarRoomList", + "description": "Return a paginated list of organization members.", + "operationId": "memberList", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "69da451ef77b1b51f40e83ee" + "limit": 5, + "p": 1 }, "schema": { - "$ref": "#/components/schemas/ListWarRoomsRequest" + "$ref": "#/components/schemas/MemberListRequest" } } }, @@ -40255,7 +46117,50 @@ "application/json": { "example": { "data": { - "items": [] + "items": [ + { + "account_id": 2451002751131, + "account_role_ids": [ + 2, + 6 + ], + "avatar": "", + "country_code": "", + "created_at": 1752030749, + "email": "bob@example.com", + "email_verified": true, + "is_external": false, + "member_id": 5068740052131, + "member_name": "Bob", + "phone": "+86151****6519", + "phone_verified": true, + "ref_id": "", + "status": "enabled", + "updated_at": 1775962064 + }, + { + "account_id": 2451002751131, + "account_role_ids": [ + 6 + ], + "avatar": "/image/avatar1.png", + "country_code": "CN", + "created_at": 1701399971, + "email": "alice@example.com", + "email_verified": true, + "is_external": false, + "member_id": 2476444212131, + "member_name": "Alice", + "phone": "+86185****0300", + "phone_verified": true, + "ref_id": "", + "status": "enabled", + "updated_at": 1775809507 + } + ], + "limit": 5, + "p": 1, + "total": 148 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -40267,7 +46172,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListWarRoomsResponse" + "$ref": "#/components/schemas/MemberListResponse" } }, "type": "object" @@ -40291,36 +46196,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List war rooms", + "summary": "List members", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |", - "href": "/en/api-reference/on-call/incidents/incident-war-room-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/platform/members/member-list", "metadata": { - "sidebarTitle": "List war rooms" + "sidebarTitle": "List members" } } } }, - "/incident/work-item/assignees/reset": { + "/member/role/grant": { "post": { - "description": "Replace a work item's entire assignee set.", - "operationId": "incidentWorkItemResetAssignees", + "description": "Add role assignments to a member. Role IDs that do not exist are silently ignored; if none resolve, the call is a no-op success.", + "operationId": "memberGrantRole", "requestBody": { "content": { "application/json": { "example": { - "assignee_ids": [ - 3790925372131, - 5068740052131 - ], - "version": 2, - "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + "member_id": 5068740052131, + "role_ids": [ + 6 + ] }, "schema": { - "$ref": "#/components/schemas/ResetWorkItemAssigneesRequest" + "$ref": "#/components/schemas/MemberRoleGrantRequest" } } }, @@ -40331,48 +46234,8 @@ "content": { "application/json": { "example": { - "data": { - "added_assignee_ids": [ - 5068740052131 - ], - "item": { - "assignee_ids": [ - 3790925372131, - 4756301322131, - 5068740052131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - }, - { - "id": 4756301322131, - "type": "person" - }, - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495329, - "created_by": 5329873302131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "done", - "title": "Follow-ups assigned to Bowen and Weili", - "updated_at_seconds": 1785496384, - "updated_by": 3790925372131, - "version": 2, - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - }, - "removed_assignee_ids": [ - 4756301322131 - ] - }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -40382,7 +46245,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemMutationResult" + "$ref": "#/components/schemas/MemberEmptyObject" } }, "type": "object" @@ -40406,34 +46269,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Reset work item assignees", + "summary": "Grant role to member", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Full replacement of the assignee set — an empty array clears all assignees.\n- Set either `assignees` or the legacy `assignee_ids`, not both (sending both returns an error). An `ai_sre` entry omits `id`.\n- Only newly added assignees are notified; removals never notify.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-reset-assignees", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |", + "href": "/en/api-reference/platform/members/member-grant-role", "metadata": { - "sidebarTitle": "Reset work item assignees" + "sidebarTitle": "Grant role to member" } } } }, - "/incident/work-item/complete": { + "/member/role/revoke": { "post": { - "description": "Mark a work item as completed by setting a client-defined target status.", - "operationId": "incidentWorkItemComplete", + "description": "Remove role assignments from a member. Role IDs that do not exist are silently ignored; if none resolve, the call is a no-op success.", + "operationId": "memberRevokeRole", "requestBody": { "content": { "application/json": { "example": { - "idempotency_key": "complete-wi-20260731-0001", - "target_status": "done", - "version": 2, - "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + "member_id": 5068740052131, + "role_ids": [ + 6 + ] }, "schema": { - "$ref": "#/components/schemas/CompleteWorkItemRequest" + "$ref": "#/components/schemas/MemberRoleRevokeRequest" } } }, @@ -40444,42 +46307,8 @@ "content": { "application/json": { "example": { - "data": { - "item": { - "assignee_ids": [ - 3790925372131, - 4756301322131, - 5068740052131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - }, - { - "id": 4756301322131, - "type": "person" - }, - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495329, - "created_by": 5329873302131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "done", - "title": "Follow-ups assigned to Bowen and Weili", - "updated_at_seconds": 1785496384, - "updated_by": 3790925372131, - "version": 2, - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - } - }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -40489,7 +46318,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemMutationResult" + "$ref": "#/components/schemas/MemberEmptyObject" } }, "type": "object" @@ -40513,34 +46342,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Complete a work item", + "summary": "Revoke role from member", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Only current assignees can complete a work item.\n- `target_status` is a client-defined string — there is no fixed state machine.\n- The same `idempotency_key` with the same `target_status` replays idempotently; the same key with a different `target_status` returns an error.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-complete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |", + "href": "/en/api-reference/platform/members/member-revoke-role", "metadata": { - "sidebarTitle": "Complete a work item" + "sidebarTitle": "Revoke role from member" } } } }, - "/incident/work-item/convert": { + "/member/role/update": { "post": { - "description": "Convert an incident action item into a post-mortem follow-up in place.", - "operationId": "incidentWorkItemConvert", + "description": "Replace all role assignments for a member at once. Role IDs that do not exist are silently dropped; an empty `role_ids` resets the member to the built-in Viewer role (ID 8).", + "operationId": "memberUpdateRole", "requestBody": { "content": { "application/json": { "example": { - "idempotency_key": "convert-wi-20260731-0001", - "target_status": "open", - "version": 2, - "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + "member_id": 5068740052131, + "role_ids": [ + 2, + 6 + ] }, "schema": { - "$ref": "#/components/schemas/ConvertWorkItemRequest" + "$ref": "#/components/schemas/MemberRoleUpdateRequest" } } }, @@ -40551,42 +46381,8 @@ "content": { "application/json": { "example": { - "data": { - "item": { - "assignee_ids": [ - 3790925372131, - 4756301322131, - 5068740052131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - }, - { - "id": 4756301322131, - "type": "person" - }, - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495329, - "created_by": 5329873302131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "done", - "title": "Follow-ups assigned to Bowen and Weili", - "updated_at_seconds": 1785496384, - "updated_by": 3790925372131, - "version": 2, - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - } - }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -40596,7 +46392,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemMutationResult" + "$ref": "#/components/schemas/MemberEmptyObject" } }, "type": "object" @@ -40620,40 +46416,40 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Convert a work item to a follow-up", + "summary": "Update member roles", "tags": [ - "On-call/Incidents" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Converts an `action` item into a post-mortem `follow_up` in place — the `work_item_id` does not change.\n- Converting an item that is already a `follow_up` returns `idempotent_replay: true`.\n- If a post-mortem already exists for the incident, the converted item auto-binds to it.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-convert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |", + "href": "/en/api-reference/platform/members/member-update-role", "metadata": { - "sidebarTitle": "Convert a work item to a follow-up" + "sidebarTitle": "Update member roles" } } } }, - "/incident/work-item/create": { + "/monit/datasource/create": { "post": { - "description": "Create an action on an active incident or a follow-up on one of its post-mortems.", - "operationId": "incidentWorkItemCreate", + "description": "Create a new monitoring data source. The `payload` must include the type-specific configuration block. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", + "operationId": "monit-datasource-write-create", "requestBody": { "content": { "application/json": { "example": { - "assignee_ids": [ - 3790925372131 - ], - "description": "CPU saturation started right after the v2.14 rollout; roll back and watch the error rate.", - "idempotency_key": "create-wi-20260731-0001", - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "action", - "priority": "high", - "status": "open", - "title": "Roll back the v2.14 deployment on web-server-01" + "address": "http://prometheus.example.com:9090", + "edge_cluster_name": "default", + "name": "Prometheus Prod", + "note": "Production Prometheus", + "payload": { + "prometheus": { + "basic_auth_enabled": false + } + }, + "type_ident": "prometheus" }, "schema": { - "$ref": "#/components/schemas/CreateWorkItemRequest" + "$ref": "#/components/schemas/DataSourceUpsertRequest" } } }, @@ -40665,33 +46461,15 @@ "application/json": { "example": { "data": { - "added_assignee_ids": [ - 3790925372131 - ], - "item": { - "assignee_ids": [ - 3790925372131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - } - ], - "created_at_seconds": 1785496400, - "created_by": 3790925372131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "action", - "source_kind": "native", - "status": "open", - "title": "Roll back the v2.14 deployment on web-server-01", - "updated_at_seconds": 1785496400, - "updated_by": 3790925372131, - "version": 1, - "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" - } + "alerting_enabled": true, + "edge_cluster_name": "default", + "enabled": true, + "id": 10, + "name": "Prometheus Prod", + "type_ident": "prometheus", + "updated_at": 1712000000 }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -40701,7 +46479,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemCreateResult" + "$ref": "#/components/schemas/DataSourceItem" } }, "type": "object" @@ -40725,32 +46503,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create a work item", + "summary": "Create datasource", "tags": [ - "On-call/Incidents" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- An `action` anchors to an active incident and must NOT set `post_mortem_id`; a `follow_up` REQUIRES the `post_mortem_id` of a post-mortem linked to `incident_id`.\n- Set either `assignees` or the legacy `assignee_ids`, not both. `assignees` entries are `{type, id?}` with `type` `person` or `ai_sre`; an `ai_sre` entry omits `id`. `assignee_ids` is equivalent to an all-`person` list. Sending both returns an error.\n- Person assignees must be active members who can already read the anchor incident or post-mortem — assignment never grants access.\n- Newly added assignees are notified.\n- Retrying with the same (`creator`, `idempotency_key`) replays the original item with `idempotent_replay: true` instead of creating a duplicate.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Manage** (`monit`) |\n\n## Usage\n\n- `type_ident` must be one of: `prometheus`, `loki`, `mysql`, `oracle`, `postgres`, `clickhouse`, `elasticsearch`, `sls`, `tencent_cls`, `victorialogs`, `redis_node`, `redis_sentinel`, `mongodb_mongod`, `mongodb_mongos`, `kafka`.\n- `edge_cluster_name` specifies which Monitors edge cluster evaluates rules using this datasource.\n- For `elasticsearch`, set `payload.elasticsearch.deployment` to `cloud` or `self-managed`.\n- Every call is recorded in the account audit log. Use credential fields only for connection credentials.\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-write-create", "metadata": { - "sidebarTitle": "Create a work item" + "sidebarTitle": "Create datasource" } } } }, - "/incident/work-item/delete": { + "/monit/datasource/delete": { "post": { - "description": "Soft-delete a work item.", - "operationId": "incidentWorkItemDelete", + "description": "Delete a data source by ID. Alert rules referencing this datasource are not blocked: the datasource is removed from their monitoring scope and their open alerts on it are closed automatically.", + "operationId": "monit-datasource-write-delete", "requestBody": { "content": { "application/json": { "example": { - "version": 2, - "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + "id": 10 }, "schema": { - "$ref": "#/components/schemas/DeleteWorkItemRequest" + "$ref": "#/components/schemas/IDRequest" } } }, @@ -40762,7 +46539,7 @@ "application/json": { "example": { "data": {}, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -40772,7 +46549,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemMutationResult" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -40796,32 +46573,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete a work item", + "summary": "Delete datasource", "tags": [ - "On-call/Incidents" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Soft delete — the item no longer appears in listings but is retained.\n- Optimistic locking — `version` must match the item's current version; a mismatch returns a conflict error.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-write-delete", "metadata": { - "sidebarTitle": "Delete a work item" + "sidebarTitle": "Delete datasource" } } } }, - "/incident/work-item/list": { + "/monit/datasource/info": { "post": { - "description": "List incident work items (actions and post-mortem follow-ups) with cursor pagination.", - "operationId": "incidentWorkItemList", + "description": "Retrieve full details of a single data source by its ID, including the `payload` configuration with its configured connection and authentication settings; treat the response as sensitive and avoid logging or forwarding it. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", + "operationId": "monit-datasource-read-info", "requestBody": { "content": { "application/json": { "example": { - "incident_id": "6a5f1e28807515413b384bce", - "limit": 50 + "id": 10 }, "schema": { - "$ref": "#/components/schemas/ListWorkItemRequest" + "$ref": "#/components/schemas/IDRequest" } } }, @@ -40833,68 +46609,26 @@ "application/json": { "example": { "data": { - "has_more": true, - "items": [ - { - "assignee_ids": [ - 3790925372131, - 4756301322131, - 5068740052131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - }, - { - "id": 4756301322131, - "type": "person" - }, - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495329, - "created_by": 5329873302131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "done", - "title": "Follow-ups assigned to Bowen and Weili", - "updated_at_seconds": 1785496384, - "updated_by": 3790925372131, - "version": 2, - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - }, - { - "assignee_ids": [ - 5068740052131 - ], - "assignees": [ - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495164, - "created_by": 3790925372131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "open", - "title": "Check whether this to-do notifies Bowen", - "updated_at_seconds": 1785495164, - "updated_by": 3790925372131, - "version": 1, - "work_item_id": "wi_dMRYTeZHivE5vf87PQEeFX" + "account_id": 10023, + "address": "http://prometheus.example.com:9090", + "alerting_enabled": true, + "edge_cluster_name": "default", + "enabled": true, + "id": 10, + "name": "Prometheus Prod", + "note": "Production Prometheus", + "payload": { + "prometheus": { + "basic_auth_enabled": false, + "basic_auth_password": "", + "basic_auth_username": "", + "tls_skip_verify": false } - ], - "next_cursor": "MTc4NTQ5NTE2NHx3aV9kTVJZVGVaSGl2RTV2Zjg3UFFFZUZY" + }, + "type_ident": "prometheus", + "updated_at": 1712000000 }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -40904,7 +46638,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemListResult" + "$ref": "#/components/schemas/DataSourceItem" } }, "type": "object" @@ -40928,33 +46662,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List work items", + "summary": "Get datasource detail", "tags": [ - "On-call/Incidents" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Read** (`on-call`) |\n\n## Usage\n\n- At least one of `incident_id`, `post_mortem_id`, `assignee_id`, or `assignee_type` = `ai_sre` is required.\n- `assignee_type` = `ai_sre` lists items assigned to AI SRE and can be used on its own.\n- Cursor pagination sorted by `updated_at_seconds` descending — pass the previous response's `next_cursor` as `cursor` until `has_more` is false.\n- Listing by `incident_id` also includes follow-ups anchored on the incident's post-mortem.\n- Listing by `assignee_id` alone requires being that assignee or an account admin.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-info", "metadata": { - "sidebarTitle": "List work items" + "sidebarTitle": "Get datasource detail" } } } }, - "/incident/work-item/post-mortem/bind": { + "/monit/datasource/list": { "post": { - "description": "Bulk-bind an incident's converted-but-unbound follow-ups to a post-mortem.", - "operationId": "incidentWorkItemBindPostMortem", + "description": "Return all data sources for the current account. Optionally filter by `type_ident`. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", + "operationId": "monit-datasource-read-list", "requestBody": { "content": { "application/json": { "example": { - "idempotency_key": "bind-wi-20260731-0001", - "incident_id": "6a5f1e28807515413b384bce", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63" + "type": "prometheus" }, "schema": { - "$ref": "#/components/schemas/BindWorkItemPostMortemRequest" + "$ref": "#/components/schemas/DataSourceListRequest" } } }, @@ -40965,68 +46697,22 @@ "content": { "application/json": { "example": { - "data": { - "has_more": false, - "items": [ - { - "assignee_ids": [ - 3790925372131, - 4756301322131, - 5068740052131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - }, - { - "id": 4756301322131, - "type": "person" - }, - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495329, - "created_by": 5329873302131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "done", - "title": "Follow-ups assigned to Bowen and Weili", - "updated_at_seconds": 1785496384, - "updated_by": 3790925372131, - "version": 2, - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - }, - { - "assignee_ids": [ - 5068740052131 - ], - "assignees": [ - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495164, - "created_by": 3790925372131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "open", - "title": "Check whether this to-do notifies Bowen", - "updated_at_seconds": 1785495164, - "updated_by": 3790925372131, - "version": 1, - "work_item_id": "wi_dMRYTeZHivE5vf87PQEeFX" - } - ] - }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "data": [ + { + "account_id": 10023, + "address": "http://prometheus.example.com:9090", + "alerting_enabled": true, + "edge_cluster_name": "default", + "enabled": true, + "id": 10, + "name": "Prometheus Prod", + "note": "Production Prometheus", + "payload": null, + "type_ident": "prometheus", + "updated_at": 1712000000 + } + ], + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -41036,7 +46722,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemListResult" + "$ref": "#/components/schemas/DataSourceListResponse" } }, "type": "object" @@ -41060,34 +46746,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Bind work items to a post-mortem", + "summary": "List datasources", "tags": [ - "On-call/Incidents" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Binds ALL of the incident's converted-but-unbound follow-ups to the given post-mortem in one call.\n- `items` holds the newly bound batch; `next_cursor` and `has_more` are not set.\n- Idempotent by `idempotency_key` — retrying with the same key replays the original result.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-bind-post-mortem", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\n## Usage\n\n- Omit `type_ident` to return all types.\n- Sensitive credential fields (passwords, keys) are not returned in the list response.\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-list", "metadata": { - "sidebarTitle": "Bind work items to a post-mortem" + "sidebarTitle": "List datasources" } } } }, - "/incident/work-item/update": { + "/monit/datasource/sls/logstores": { "post": { - "description": "Partially update a work item's title, description, status, or priority.", - "operationId": "incidentWorkItemUpdate", + "description": "List logstores within an SLS project for the specified SLS datasource.", + "operationId": "monit-datasource-read-sls-logstores", "requestBody": { "content": { "application/json": { "example": { - "status": "in_progress", - "title": "Roll back the v2.14 deployment on web-server-01 and web-server-02", - "version": 1, - "work_item_id": "wi_9fK2mNqRtVwXyZaBcDeFgH" + "id": 10, + "offset": 0, + "project": "project-a", + "size": 50 }, "schema": { - "$ref": "#/components/schemas/UpdateWorkItemRequest" + "$ref": "#/components/schemas/SLSLogstoresRequest" } } }, @@ -41098,42 +46784,11 @@ "content": { "application/json": { "example": { - "data": { - "item": { - "assignee_ids": [ - 3790925372131, - 4756301322131, - 5068740052131 - ], - "assignees": [ - { - "id": 3790925372131, - "type": "person" - }, - { - "id": 4756301322131, - "type": "person" - }, - { - "id": 5068740052131, - "type": "person" - } - ], - "created_at_seconds": 1785495329, - "created_by": 5329873302131, - "incident_id": "6a5f1e28807515413b384bce", - "item_type": "follow_up", - "post_mortem_id": "51d65cd9525c369379ba471b5512df63", - "source_kind": "native", - "status": "done", - "title": "Follow-ups assigned to Bowen and Weili", - "updated_at_seconds": 1785496384, - "updated_by": 3790925372131, - "version": 2, - "work_item_id": "wi_68MHnkWBiyjrh6uhkxUyiZ" - } - }, - "request_id": "01J8XQ3E5Z7JM2NTFQ5YJ8P9R4" + "data": [ + "logstore-1", + "logstore-2" + ], + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -41143,7 +46798,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/WorkItemMutationResult" + "$ref": "#/components/schemas/SLSLogstoresResponse" } }, "type": "object" @@ -41167,37 +46822,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update a work item", + "summary": "List SLS logstores", "tags": [ - "On-call/Incidents" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Incidents Manage** (`on-call`) |\n\n## Usage\n\n- Requires the On-call Pro license.\n- Partial patch: omitted fields stay unchanged; an explicit `null` clears the field.\n- Optimistic locking — `version` must match the item's current version; a mismatch returns a conflict error.\n- Assignees, `item_type`, and the incident/post-mortem anchors cannot be changed here — use the dedicated endpoints.\n- Audited — changes are recorded in the audit log.", - "href": "/en/api-reference/on-call/incidents/incident-work-item-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\n## Usage\n\n- The datasource identified by `id` must be of type `sls`.\n- Supply `project` to select the SLS project whose logstores to list.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-sls-logstores", "metadata": { - "sidebarTitle": "Update a work item" + "sidebarTitle": "List SLS logstores" } } } }, - "/insight/account": { + "/monit/datasource/sls/projects": { "post": { - "description": "Return aggregated incident insight metrics for the entire account.", - "operationId": "insightByAccount", + "description": "List Alibaba Cloud SLS (Simple Log Service) projects available in the specified SLS datasource.", + "operationId": "monit-datasource-read-sls-projects", "requestBody": { "content": { "application/json": { "example": { - "aggregate_unit": "day", - "end_time": 1712604800, - "severities": [ - "Critical", - "Warning" - ], - "start_time": 1712000000 + "id": 10, + "offset": 0, + "query": "", + "size": 50 }, "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" + "$ref": "#/components/schemas/SLSProjectsRequest" } } }, @@ -41209,32 +46861,28 @@ "application/json": { "example": { "data": { - "items": [ + "count": 2, + "projects": [ { - "acknowledgement_pct": 100, - "mean_seconds_to_ack": 1658854.5, - "mean_seconds_to_close": 1874757, - "noise_reduction_pct": 0, - "total_alert_cnt": 0, - "total_alert_event_cnt": 0, - "total_engaged_seconds": 3317709, - "total_incident_cnt": 2, - "total_incidents_acknowledged": 2, - "total_incidents_auto_closed": 0, - "total_incidents_closed": 2, - "total_incidents_escalated": 0, - "total_incidents_manually_closed": 2, - "total_incidents_manually_escalated": 0, - "total_incidents_reassigned": 2, - "total_incidents_timeout_closed": 0, - "total_incidents_timeout_escalated": 0, - "total_interruptions": 3, - "total_notifications": 6, - "total_seconds_to_ack": 3317709, - "total_seconds_to_close": 3749514, - "ts": 1740844800 + "createTime": "1710000000", + "description": "Production logs", + "lastModifyTime": "1712000000", + "owner": "", + "projectName": "project-a", + "region": "cn-shanghai", + "status": "Normal" + }, + { + "createTime": "1710000000", + "description": "Staging logs", + "lastModifyTime": "1712000000", + "owner": "", + "projectName": "project-b", + "region": "cn-shanghai", + "status": "Normal" } - ] + ], + "total": 2 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -41246,7 +46894,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DimensionInsightResponse" + "$ref": "#/components/schemas/SLSProjectsResponse" } }, "type": "object" @@ -41270,35 +46918,50 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get account-level insight", + "summary": "List SLS projects", "tags": [ - "On-call/Analytics" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-by-account", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\n## Usage\n\n- The datasource identified by `id` must be of type `sls`.\n- Use `query` to filter projects by name prefix. Use `offset` and `size` for pagination.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-sls-projects", "metadata": { - "sidebarTitle": "Get account-level insight" + "sidebarTitle": "List SLS projects" } } } }, - "/insight/alert/topk-by-label": { + "/monit/datasource/tools/invoke": { "post": { - "description": "Return the top-K alert groups aggregated either by `check` or by `resource` label over the specified time range.", - "operationId": "insightTopkAlertsByLabel", + "description": "Execute one deterministic diagnostic or query tool against a configured datasource.", + "operationId": "monit-datasource-tools-invoke", "requestBody": { "content": { "application/json": { - "example": { - "end_time": 1712604800, - "k": 10, - "label": "check", - "orderby": "total_alert_cnt", - "start_time": 1712000000 - }, "schema": { - "$ref": "#/components/schemas/InsightTopkAlertByLabelRequest" + "$ref": "#/components/schemas/DatasourceToolInvokeRequest" + }, + "examples": { + "diagnostic": { + "value": { + "datasource_id": 10, + "params": {}, + "tool": "mysql.overview" + } + }, + "query": { + "value": { + "datasource_id": 24000, + "tool": "prometheus.query", + "params": { + "expr": "sum(rate(http_requests_total[5m]))", + "execution": { + "kind": "instant", + "to_ms": 1789000000000 + } + } + } + } } } }, @@ -41308,28 +46971,6 @@ "200": { "content": { "application/json": { - "example": { - "data": { - "items": [ - { - "label": "cpu-high", - "total_alert_cnt": 312, - "total_alert_event_cnt": 987 - }, - { - "label": "disk-full", - "total_alert_cnt": 178, - "total_alert_event_cnt": 452 - }, - { - "label": "memory-oom", - "total_alert_cnt": 94, - "total_alert_event_cnt": 231 - } - ] - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, "schema": { "allOf": [ { @@ -41338,60 +46979,195 @@ { "properties": { "data": { - "$ref": "#/components/schemas/InsightAlertByLabelResponse" + "$ref": "#/components/schemas/DatasourceToolResult" } }, "type": "object" } ] + }, + "examples": { + "diagnostic": { + "value": { + "data": { + "data": { + "version": "8.0.36" + }, + "datasource_id": 10, + "summary": "MySQL overview", + "tool": "mysql.overview" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + } + }, + "query": { + "value": { + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", + "data": { + "datasource_id": 24000, + "tool": "prometheus.query", + "data": { + "format": "explore_result.v1", + "result": { + "kind": "samples", + "samples": [ + { + "labels": { + "__name__": "up", + "instance": "10.101.214.50:7070" + }, + "value": 1 + } + ] + } + } + } + } + } + } + } + }, + "description": "Success" + }, + "400": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: invalid_request, tool_not_supported, datasource_error." + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "403": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: access_denied." + }, + "404": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: datasource_not_found." + }, + "409": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: datasource_disabled, datasource_in_use." + }, + "413": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: source_too_large, result_too_large." + }, + "429": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" } } }, - "description": "Success" + "description": "Standard HTTP error; error.reason: overloaded." }, - "400": { - "$ref": "#/components/responses/BadRequest" + "499": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: canceled." }, - "401": { - "$ref": "#/components/responses/Unauthorized" + "500": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: internal." }, - "429": { - "$ref": "#/components/responses/TooManyRequests" + "503": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: no_active_edge, edge_upgrade_required, mixed_edge_versions." }, - "500": { - "$ref": "#/components/responses/ServerError" + "504": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: timeout." } }, - "summary": "Get top-K alerts grouped by check or resource", + "summary": "Invoke datasource tool", "tags": [ - "On-call/Analytics" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-topk-alerts-by-label", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **2,000 requests/minute**; **32 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\nUse datasource IDs from `/monit/datasource/list`. Disabled datasources return `datasource_disabled`; `alerting_enabled=false` does not block tools. Errors use non-2xx HTTP status and `error.code`, `error.message`, `error.reason`. `tool_not_supported` indicates the selected executor does not provide this tool; it is not a vendor permission error. Never retry through another Edge or the legacy diagnose endpoint automatically.\n\n## Usage\n\n- Two tool families share this entry: diagnostic tools defined by the executing Edge (e.g. `mysql.overview`, `prometheus.metric_trends`) and query tools named `.query`. The tool prefix must match the datasource type.\n- Query tools require the Edge cluster to support Explore queries (protocol milestone v0.68.0); diagnostic tools require the v0.71.0 base invoke protocol. Unsupported clusters fail with `edge_upgrade_required`, `mixed_edge_versions`, or `edge_version_unknown`; never fall back to `/monit/query/data` or another endpoint automatically.\n- For query tools, `params` follows the per-datasource schema named in the `tool` field description. `expr` and `execution` are always required. `limit`/`direction` only bound raw-log retrieval, never SQL rows or scanned data. Unknown extension fields are tolerated but never executed or forwarded.\n- Query `data` is the complete Explore result: `format` is `explore_result.v1` and `result.kind` is `samples`, `frames`, or `logs`; log results keep `applied_limit` and `has_more`. Query results never synthesize `summary` or `truncated`.\n- Request body limit 128 KiB; complete success response limit 10 MiB for both families; diagnostic tool timeout at most 25 seconds.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-tools-invoke", "metadata": { - "sidebarTitle": "Get top-K alerts grouped by check or resource" + "sidebarTitle": "Invoke datasource tool" } } } }, - "/insight/channel": { + "/monit/datasource/update": { "post": { - "description": "Return insight metrics aggregated by channel.", - "operationId": "insightByChannel", + "description": "Update an existing data source. Supply `id` plus the fields to change. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", + "operationId": "monit-datasource-write-update", "requestBody": { "content": { "application/json": { "example": { - "aggregate_unit": "day", - "channel_ids": [ - 4321322010131 - ], - "end_time": 1712604800, - "start_time": 1712000000 + "address": "http://prometheus-v2.example.com:9090", + "edge_cluster_name": "default", + "id": 10, + "name": "Prometheus Prod v2", + "note": "Updated", + "payload": { + "prometheus": { + "basic_auth_enabled": false + } + }, + "type_ident": "prometheus" }, "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" + "$ref": "#/components/schemas/DataSourceUpsertRequest" } } }, @@ -41403,34 +47179,13 @@ "application/json": { "example": { "data": { - "items": [ - { - "acknowledgement_pct": 100, - "channel_id": 4321322010131, - "channel_name": "Production Alerts", - "mean_seconds_to_ack": 1658854.5, - "mean_seconds_to_close": 1874757, - "noise_reduction_pct": 0, - "total_alert_cnt": 0, - "total_alert_event_cnt": 0, - "total_engaged_seconds": 3317709, - "total_incident_cnt": 2, - "total_incidents_acknowledged": 2, - "total_incidents_auto_closed": 0, - "total_incidents_closed": 2, - "total_incidents_escalated": 0, - "total_incidents_manually_closed": 2, - "total_incidents_manually_escalated": 0, - "total_incidents_reassigned": 2, - "total_incidents_timeout_closed": 0, - "total_incidents_timeout_escalated": 0, - "total_interruptions": 3, - "total_notifications": 6, - "total_seconds_to_ack": 3317709, - "total_seconds_to_close": 3749514, - "ts": 1740844800 - } - ] + "alerting_enabled": true, + "edge_cluster_name": "default", + "enabled": true, + "id": 10, + "name": "Prometheus Prod v2", + "type_ident": "prometheus", + "updated_at": 1712100000 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -41442,7 +47197,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DimensionInsightResponse" + "$ref": "#/components/schemas/DataSourceItem" } }, "type": "object" @@ -41466,172 +47221,130 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get channel insight", + "summary": "Update datasource", "tags": [ - "On-call/Analytics" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-by-channel", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Use credential fields only for connection credentials.\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", + "href": "/en/api-reference/monitors/data-sources/monit-datasource-write-update", "metadata": { - "sidebarTitle": "Get channel insight" + "sidebarTitle": "Update datasource" } } } }, - "/insight/channel/export": { - "post": { - "description": "Export channel insight metrics as a CSV file — one row per channel (and per time/hour bucket when `aggregate_unit`/`split_hours` is used). The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. `time_zone` defaults to UTC. Rows without a valid channel ID are skipped. Valid `export_fields` keys: channel_id, channel_name, total_incident_cnt, total_incidents_acknowledged, total_incidents_closed, total_incidents_auto_closed, total_incidents_manually_closed, total_incidents_timeout_closed, total_incidents_escalated, total_incidents_manually_escalated, total_incidents_timeout_escalated, total_incidents_reassigned, total_interruptions, total_notifications, total_engaged_seconds, mean_seconds_to_ack, mean_seconds_to_close, noise_reduction_pct, acknowledgement_pct, total_alert_cnt, total_alert_event_cnt, hours. The `hours` column is included by default only when `split_hours` is true. For compatibility, incident-export column keys are also accepted but produce empty columns.", - "operationId": "insightChannelExport", - "requestBody": { - "content": { - "application/json": { - "example": { - "channel_ids": [ - 4321322010131 - ], - "end_time": 1712604800, - "severities": [ - "Critical", - "Warning" - ], - "start_time": 1712000000 - }, - "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" - } + "/monit/prometheus/api/v1/label/{label_name}/values": { + "get": { + "description": "Read label values from a Prometheus-compatible data source through the Monitors proxy.", + "operationId": "monit-prometheus-read-label-values", + "parameters": [ + { + "description": "Label name to enumerate values for, for example `job`.", + "in": "path", + "name": "label_name", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "description": "Data source ID to query. Must reference a Prometheus-compatible data source owned by the authenticated account.", + "in": "header", + "name": "X-DSID", + "required": true, + "schema": { + "type": "string" + } + } + ], "responses": { "200": { "content": { - "application/octet-stream": { - "example": "channel_id,channel_name,total_incident_cnt,total_incidents_closed\n4321322010131,Production Alerts,12,10\n", + "application/json": { + "example": { + "data": [ + "api", + "db", + "worker" + ], + "status": "success" + }, "schema": { - "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=channel_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full field set, or the keys given in `export_fields`.", - "format": "binary", - "type": "string" + "$ref": "#/components/schemas/PrometheusLabelValuesResponse" } } }, - "description": "Success" + "description": "Native Prometheus label-values response returned by the data source." }, "400": { - "$ref": "#/components/responses/BadRequest" + "content": { + "text/plain": { + "schema": { + "type": "string" + } + } + }, + "description": "The `X-DSID` header is missing or invalid, the data source does not exist, or it is not a Prometheus data source. Returned as `text/plain`." }, "401": { "$ref": "#/components/responses/Unauthorized" }, - "429": { - "$ref": "#/components/responses/TooManyRequests" - }, "500": { - "$ref": "#/components/responses/ServerError" - } - }, - "summary": "Export channel insight", - "tags": [ - "On-call/Analytics" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-channel-export", - "metadata": { - "sidebarTitle": "Export channel insight" - } - } - } - }, - "/insight/incident/export": { - "post": { - "description": "Export the filtered incident analytics list as a CSV file. The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. CSV headers and formatted values use the request locale, falling back to the member locale and then the account locale. `time_zone` defaults to the account time zone, then `Asia/Shanghai`. Export stops after at most 100,000 rows. Valid `export_fields` keys: incident_id, title, severity, progress, channel_id, channel_name, team_id, team_name, created_at, alert_cnt, active_alert_cnt, alert_event_cnt, seconds_to_ack, seconds_to_close, closed_by, owner_id, owner_name, creator_id, creator_name, closer_id, closer_name, engaged_seconds, hours, notifications, interruptions, acknowledgements, ackers, assignments, reassignments, escalations, manual_escalations, timeout_escalations, assigned_to, raw_assigned_to, escalate_rule_name, responders, raw_responders, snooze_status, snoozed_before, ever_muted, frequency, is_rare, description, labels, fields. When `export_fields` is omitted, all columns are exported.", - "operationId": "insightIncidentExport", - "requestBody": { - "content": { - "application/json": { - "example": { - "description_html_to_text": true, - "end_time": 1712604800, - "export_fields": [ - "incident_id", - "title", - "severity", - "created_at", - "seconds_to_close" - ], - "severities": [ - "Critical", - "Warning" - ], - "start_time": 1712000000 - }, - "schema": { - "$ref": "#/components/schemas/InsightIncidentExportRequest" + "content": { + "text/plain": { + "schema": { + "type": "string" + } } - } + }, + "description": "The data source lookup or the proxied request failed. Returned as `text/plain`." }, - "required": true - }, - "responses": { - "200": { + "503": { "content": { - "application/octet-stream": { - "example": "incident_id,title,severity,created_at\n6a86b5d6f72de50ae1ce2ffb,CPU usage above 90%,Critical,2026-01-01 10:00:00 +0800 CST\n", + "text/plain": { "schema": { - "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=incident_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full incident field set, or the keys given in `export_fields`.", - "format": "binary", "type": "string" } } }, - "description": "Success" - }, - "400": { - "$ref": "#/components/responses/BadRequest" - }, - "401": { - "$ref": "#/components/responses/Unauthorized" - }, - "429": { - "$ref": "#/components/responses/TooManyRequests" - }, - "500": { - "$ref": "#/components/responses/ServerError" + "description": "No monit-edge in the data source's cluster supports the data source resource proxy. Returned as `text/plain`; upgrade monit-edge." } }, - "summary": "Export insight incidents", + "summary": "List Prometheus label values", "tags": [ - "On-call/Analytics" + "Monitors/Data sources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-incident-export", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Any valid `app_key` (read-only; not gated by a specific permission class) |\n| Edge requirement | Supported deployments require **monit-edge v0.35.0 or later** |\n\n## Usage\n\n- Pass the target data source in the `X-DSID` header. It must be a Prometheus-compatible data source owned by the authenticated account; use `/monit/datasource/list` to obtain its ID.\n- The 200 body is the data source's native Prometheus HTTP API payload, **not** the standard `{ request_id, data }` envelope. Failures raised before the data source is reached are returned as `text/plain` with the matching 4xx or 5xx status.\n- When `X-DSID` is omitted, the request falls back to the platform's own Prometheus proxy. Send the header to query a specific data source.", + "href": "/en/api-reference/monitors/data-sources/monit-prometheus-read-label-values", "metadata": { - "sidebarTitle": "Export insight incidents" + "sidebarTitle": "List Prometheus label values" } } } }, - "/insight/incident/list": { + "/monit/query/explore": { "post": { - "description": "Return a paged list of incidents with per-incident handling metrics used by the analytics dashboard.", - "operationId": "insightIncidentList", + "description": "Run an Explore query against a configured data source and return frames, samples, or logs.", + "operationId": "monit-read-query-explore", "requestBody": { "content": { "application/json": { "example": { - "end_time": 1712604800, - "limit": 20, - "p": 1, - "severities": [ - "Critical" - ], - "start_time": 1712000000 + "args": {}, + "datasource_id": 101, + "execution": { + "from_ms": 1787187600000, + "kind": "range", + "max_data_points": 1200, + "min_step_seconds": 15, + "to_ms": 1787191200000 + }, + "expr": "rate(http_requests_total[5m])" }, "schema": { - "$ref": "#/components/schemas/InsightIncidentListRequest" + "$ref": "#/components/schemas/QueryExploreRequest" } } }, @@ -41643,60 +47356,40 @@ "application/json": { "example": { "data": { - "has_next_page": true, - "items": [ - { - "acknowledgements": 1, - "active_alert_cnt": 0, - "alert_cnt": 3, - "alert_event_cnt": 5, - "assigned_to": { - "assigned_at": 1787213270, - "escalate_rule_id": "66138789904a9027583dbc4e", - "escalate_rule_name": "On-call Policy", - "id": "b8tyUoRvCv4wsPndFRpmNL", - "layer_idx": 0, - "type": "assign" - }, - "assignments": 1, - "channel_id": 3047621227131, - "channel_name": "Production Alerts", - "closed_by": "manually", - "closer_id": 2477273692131, - "closer_name": "alice", - "created_at": 1787213270, - "creator_id": 2477273692131, - "creator_name": "alice", - "description": "CPU usage stayed above the threshold for 5 minutes", - "engaged_seconds": 1816, - "escalations": 0, - "hours": "work", - "incident_id": "6a86b5d6f72de50ae1ce2ffb", - "interruptions": 1, - "manual_escalations": 0, - "notifications": 2, - "progress": "Closed", - "reassignments": 0, - "responders": [ - { - "acknowledged_at": 1787213284, - "assigned_at": 1787213270, - "email": "alice@example.com", - "person_id": 2477273692131, - "person_name": "alice" - } - ], - "seconds_to_ack": 14, - "seconds_to_close": 1830, - "severity": "Critical", - "team_id": 2477033058131, - "team_name": "SRE Team", - "timeout_escalations": 0, - "title": "CPU usage above 90% on prod-web-01" - } - ], - "search_after_ctx": "6a86b5d6f72de50ae1ce2ffb", - "total": 2363 + "execution": { + "effective_step_seconds": 60, + "kind": "range" + }, + "format": "explore_result.v1", + "result": { + "frames": [ + { + "fields": [ + { + "name": "time", + "type": "time", + "values": [ + "2026-08-20T10:00:00Z", + "2026-08-20T10:01:00Z" + ] + }, + { + "labels": { + "job": "api" + }, + "name": "value", + "type": "float", + "values": [ + 1.25, + null + ] + } + ], + "kind": "time_series" + } + ], + "kind": "frames" + } }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -41708,7 +47401,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/InsightIncidentListResponse" + "$ref": "#/components/schemas/ExploreData" } }, "type": "object" @@ -41720,48 +47413,128 @@ "description": "Success" }, "400": { - "$ref": "#/components/responses/BadRequest" + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: invalid_request." }, "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: access_denied." + }, + "404": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: datasource_not_found." + }, + "413": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: source_too_large, result_too_large." + }, "429": { - "$ref": "#/components/responses/TooManyRequests" + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: overloaded." + }, + "499": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: canceled." }, "500": { - "$ref": "#/components/responses/ServerError" + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: internal." + }, + "503": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: no_active_edge, edge_upgrade_required, mixed_edge_versions, edge_unavailable." + }, + "504": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "Standard HTTP error; error.reason: timeout." } }, - "summary": "List insight incidents", + "summary": "Run Explore query", "tags": [ - "On-call/Analytics" + "Monitors/Diagnostics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-incident-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **16 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n| Edge requirement | Supported deployments require **monit-edge v0.68.0 or later** |\n\n## Usage\n\n- Use this endpoint when you need the data source's native result shape; `/monit/query/data` returns the stable `query_result.v1` contract instead. Dispatch on `data.result.kind` (`frames`, `samples`, or `logs`) here.\n- `execution.kind` decides which companion fields are accepted: `instant` needs only `to_ms`, `range` requires `from_ms`, `to_ms`, and `max_data_points`, and `window` takes `from_ms` and `to_ms`. `step_seconds` is not accepted; the step is derived from `max_data_points` and `min_step_seconds`.\n- `args` carries macro substitutions such as Grafana-style variables; every value is a string.\n- A `logs` result is capped at 1,000 entries and reports `applied_limit` plus `has_more`. Time-series and sample results are capped at 1,000 items each and the whole success response at 8 MiB.\n- Query execution may take up to 35 seconds across WebAPI forwarding and Edge execution. Configure client timeouts to at least 40 seconds.", + "href": "/en/api-reference/monitors/diagnostics/monit-read-query-explore", "metadata": { - "sidebarTitle": "List insight incidents" + "sidebarTitle": "Run Explore query" } } } }, - "/insight/responder": { + "/monit/query/data": { "post": { - "description": "Return insight metrics aggregated by responder.", - "operationId": "insightByResponder", + "description": "Run a synchronous ad-hoc query against a configured data source and return a stable `query_result.v1` result whose natural shape is frames, records, or samples. This public API requires monit-edge v0.65.0 or later.", + "operationId": "monit-read-query-data", "requestBody": { "content": { "application/json": { - "example": { - "aggregate_unit": "day", - "end_time": 1712604800, - "responder_ids": [ - 3790925372131 - ], - "start_time": 1712000000 + "example": { + "args": {}, + "delay_seconds": 0, + "ds_name": "prod-prom", + "ds_type": "prometheus", + "expr": "sum by (job) (rate(http_requests_total[5m]))" }, "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" + "$ref": "#/components/schemas/QueryDataRequest" } } }, @@ -41773,25 +47546,18 @@ "application/json": { "example": { "data": { - "items": [ - { - "acknowledgement_pct": 100, - "mean_seconds_to_ack": 2265624, - "responder_id": 3790925372131, - "responder_name": "alice", - "total_engaged_seconds": 10, - "total_incident_cnt": 1, - "total_incidents_acknowledged": 1, - "total_incidents_escalated": 0, - "total_incidents_manually_escalated": 0, - "total_incidents_reassigned": 0, - "total_incidents_timeout_escalated": 0, - "total_interruptions": 1, - "total_notifications": 2, - "total_seconds_to_ack": 2265624, - "ts": 1740844800 - } - ] + "format": "query_result.v1", + "result": { + "kind": "samples", + "samples": [ + { + "labels": { + "job": "api" + }, + "value": 1.25 + } + ] + } }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -41803,7 +47569,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ResponderInsightResponse" + "$ref": "#/components/schemas/QueryDataResponse" } }, "type": "object" @@ -41820,46 +47586,74 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, + "413": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "The request or final response exceeds its size limit." + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, + "499": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "The client canceled the query." + }, "500": { "$ref": "#/components/responses/ServerError" + }, + "503": { + "$ref": "#/components/responses/ServiceUnavailable" + }, + "504": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ErrorResponse" + } + } + }, + "description": "The query timed out." } }, - "summary": "Get responder insight", + "summary": "Query structured data", "tags": [ - "On-call/Analytics" + "Monitors/Diagnostics" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-by-responder", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **5 requests/second** per account |\n| Permissions | Any valid `app_key` (read-only; not gated by a specific permission class) |\n| Edge requirement | Supported deployments require **monit-edge v0.65.0 or later** |\n\n## Usage\n\n- Treat **monit-edge v0.65.0** as the minimum supported Edge version for this public API. WebAPI retains migration adapters for older Edge versions: query.v2 results may still preserve frames, records, or samples, while legacy rows can expose only the information they retained. These adapters do not change the support floor; older protocols lack query.v3 cancellation and error-lifecycle semantics, and data already lost by legacy rows cannot be recovered.\n- The public response format is always `query_result.v1` and is independent of the internal Edge query protocol. Dispatch on `result.kind` (`frames`, `records`, or `samples`); do not infer the result shape from `ds_type` or the Edge version.\n- A `frames` result may contain multiple table or time-series frames. Field values are columnar and all fields in one frame have the same length.\n- A `records` result may contain nested JSON and null records. Integer literals outside JavaScript's safe integer range are returned as decimal strings.\n- A `samples` result contains label sets and instant values. A value may be a number or one of the strings `NaN`, `+Inf`, and `-Inf`.\n- The final success response is limited to 8 MiB and query results are limited to 1,000 rows. Narrow the time range, reduce fields, or aggregate at the source when a request exceeds a limit.\n- Query failures use non-2xx HTTP status codes and the standard error envelope. Do not transparently fall back to the deprecated `/monit/query/rows` endpoint.\n- Query execution may take up to 35 seconds across WebAPI forwarding and Edge execution. Configure client timeouts to at least 40 seconds and propagate cancellation when the caller abandons a query.", + "href": "/en/api-reference/monitors/diagnostics/monit-read-query-data", "metadata": { - "sidebarTitle": "Get responder insight" + "sidebarTitle": "Query structured data" } } } }, - "/insight/responder/export": { + "/monit/rule/audit/detail": { "post": { - "description": "Export responder insight metrics as a CSV file — one row per responder (and per time/hour bucket when `aggregate_unit`/`split_hours` is used). The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. `time_zone` defaults to UTC. Rows without a valid responder ID are skipped. Valid `export_fields` keys: responder_id, responder_name, total_incident_cnt, total_incidents_acknowledged, total_incidents_reassigned, total_incidents_escalated, total_incidents_manually_escalated, total_incidents_timeout_escalated, total_interruptions, total_notifications, total_engaged_seconds, mean_seconds_to_ack, acknowledgement_pct, hours. The `hours` column is included by default only when `split_hours` is true. For compatibility, incident-export column keys are also accepted but produce empty columns.", - "operationId": "insightResponderExport", + "description": "Return the audit record (including the `content` field, a JSON string of the rule snapshot at that point in time).", + "operationId": "monit-rule-read-audit-detail", "requestBody": { "content": { "application/json": { "example": { - "end_time": 1712604800, - "responder_ids": [ - 3790925372131 - ], - "severities": [ - "Critical", - "Warning" - ], - "start_time": 1712000000 + "id": 9001 }, "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" + "$ref": "#/components/schemas/AuditRecordIDRequest" } } }, @@ -41868,12 +47662,34 @@ "responses": { "200": { "content": { - "application/octet-stream": { - "example": "responder_id,responder_name,total_incident_cnt,total_incidents_acknowledged\n3790925372131,alice,5,4\n", + "application/json": { + "example": { + "data": { + "account_id": 10023, + "action": "update", + "alert_rule_id": 50001, + "content": "{\"id\":50001,\"name\":\"CPU High\"}", + "created_at": 1712000000, + "creator_id": 80011, + "creator_name": "Alice", + "id": 9001 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { - "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=responder_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full field set, or the keys given in `export_fields`.", - "format": "binary", - "type": "string" + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/AlertRuleAudit" + } + }, + "type": "object" + } + ] } } }, @@ -41892,36 +47708,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Export responder insight", + "summary": "Get rule audit snapshot", "tags": [ - "On-call/Analytics" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-responder-export", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- Pass the audit record `id` (not the rule `id`) from `POST /monit/rule/audits`.\n- `content` is a JSON string — parse it to get the full rule snapshot.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-audit-detail", "metadata": { - "sidebarTitle": "Export responder insight" + "sidebarTitle": "Get rule audit snapshot" } } } }, - "/insight/team": { + "/monit/rule/audits": { "post": { - "description": "Return insight metrics aggregated by team.", - "operationId": "insightByTeam", + "description": "Return the change history (audit records) for an alert rule.", + "operationId": "monit-rule-read-audits", "requestBody": { "content": { "application/json": { "example": { - "aggregate_unit": "day", - "end_time": 1712604800, - "start_time": 1712000000, - "team_ids": [ - 4295771902131 - ] + "id": 50001 }, "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" + "$ref": "#/components/schemas/RuleIDRequest" } } }, @@ -41932,36 +47743,17 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "acknowledgement_pct": 100, - "mean_seconds_to_ack": 1658854.5, - "mean_seconds_to_close": 1874757, - "noise_reduction_pct": 0, - "team_id": 4295771902131, - "team_name": "SRE Team", - "total_alert_cnt": 0, - "total_alert_event_cnt": 0, - "total_engaged_seconds": 3317709, - "total_incident_cnt": 2, - "total_incidents_acknowledged": 2, - "total_incidents_auto_closed": 0, - "total_incidents_closed": 2, - "total_incidents_escalated": 0, - "total_incidents_manually_closed": 2, - "total_incidents_manually_escalated": 0, - "total_incidents_reassigned": 2, - "total_incidents_timeout_closed": 0, - "total_incidents_timeout_escalated": 0, - "total_interruptions": 3, - "total_notifications": 6, - "total_seconds_to_ack": 3317709, - "total_seconds_to_close": 3749514, - "ts": 1740844800 - } - ] - }, + "data": [ + { + "account_id": 10023, + "action": "update", + "alert_rule_id": 50001, + "created_at": 1712000000, + "creator_id": 80011, + "creator_name": "Alice", + "id": 9001 + } + ], "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -41972,7 +47764,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DimensionInsightResponse" + "$ref": "#/components/schemas/RuleAuditListResponse" } }, "type": "object" @@ -41996,39 +47788,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get team insight", + "summary": "List rule change history", "tags": [ - "On-call/Analytics" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-by-team", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-audits", "metadata": { - "sidebarTitle": "Get team insight" + "sidebarTitle": "List rule change history" } } } }, - "/insight/team/export": { + "/monit/rule/counter/channel": { "post": { - "description": "Export team insight metrics as a CSV file — one row per team (and per time/hour bucket when `aggregate_unit`/`split_hours` is used). The response is a CSV stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope. `time_zone` defaults to UTC. Rows without a valid team ID are skipped. Valid `export_fields` keys: team_id, team_name, total_incident_cnt, total_incidents_acknowledged, total_incidents_closed, total_incidents_auto_closed, total_incidents_manually_closed, total_incidents_timeout_closed, total_incidents_escalated, total_incidents_manually_escalated, total_incidents_timeout_escalated, total_incidents_reassigned, total_interruptions, total_notifications, total_engaged_seconds, mean_seconds_to_ack, mean_seconds_to_close, noise_reduction_pct, acknowledgement_pct, total_alert_cnt, total_alert_event_cnt, hours. The `hours` column is included by default only when `split_hours` is true. For compatibility, incident-export column keys are also accepted but produce empty columns.", - "operationId": "insightTeamExport", + "description": "Return an object mapping channel name to the number of rules routing alerts to that channel. If a channel name cannot be resolved, the channel ID (as a string) is used as the key.", + "operationId": "monit-rule-read-counter-channel", "requestBody": { "content": { "application/json": { - "example": { - "end_time": 1712604800, - "severities": [ - "Critical", - "Warning" - ], - "start_time": 1712000000, - "team_ids": [ - 4295771902131 - ] - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/InsightQueryRequest" + "$ref": "#/components/schemas/RuleEmptyRequest" } } }, @@ -42037,12 +47819,27 @@ "responses": { "200": { "content": { - "application/octet-stream": { - "example": "team_id,team_name,total_incident_cnt,total_incidents_closed\n4295771902131,SRE Team,12,10\n", + "application/json": { + "example": { + "data": { + "Production": 8 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { - "description": "CSV file stream (`Content-Type: application/octet-stream`, `Content-Disposition: attachment; filename=team_export_yyyyMMdd_HHmmss.csv`). The first row holds localized column headers. Columns default to the full field set, or the keys given in `export_fields`.", - "format": "binary", - "type": "string" + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/RuleCounterChannelResponse" + } + }, + "type": "object" + } + ] } } }, @@ -42061,31 +47858,29 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Export team insight", + "summary": "Get rule counts by channel", "tags": [ - "On-call/Analytics" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Analytics Read** (`on-call`) |", - "href": "/en/api-reference/on-call/analytics/insight-team-export", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-counter-channel", "metadata": { - "sidebarTitle": "Export team insight" + "sidebarTitle": "Get rule counts by channel" } } } }, - "/member/delete": { + "/monit/rule/counter/total": { "post": { - "description": "Remove a member from the organization by ID, email, phone, or name.", - "operationId": "memberDelete", + "description": "Return the stored time series of the total rule count across the account — one sample per `clock` timestamp.", + "operationId": "monit-rule-read-counter-total", "requestBody": { "content": { "application/json": { - "example": { - "member_id": 5068740052131 - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/MemberDeleteRequest" + "$ref": "#/components/schemas/RuleEmptyRequest" } } }, @@ -42096,7 +47891,14 @@ "content": { "application/json": { "example": { - "data": {}, + "data": [ + { + "account_id": 10023, + "clock": 1712000000, + "id": 1, + "num": 50 + } + ], "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -42107,7 +47909,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberEmptyObject" + "$ref": "#/components/schemas/RuleCounterTotalResponse" } }, "type": "object" @@ -42131,29 +47933,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete member", + "summary": "Get rule counter time series", "tags": [ - "Platform/Members" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |\n\n## Usage\n\n- By default (`is_force=false`), the system checks whether the member is referenced by other resources (e.g., escalation rules, schedules). If references exist, the API returns error code `ReferenceExist` with the reference list in `data.refs`. Set `is_force=true` to skip the reference check and force delete.\n- Members provisioned via SSO with `sso_user_non_editable=true` cannot be deleted through this API. Disable that SSO restriction first.\n- This operation is recorded in the audit log.", - "href": "/en/api-reference/platform/members/member-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- Each item is a historical snapshot: `num` is the total rule count at the given `clock` (Unix epoch seconds).", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-counter-total", "metadata": { - "sidebarTitle": "Delete member" + "sidebarTitle": "Get rule counter time series" } } } }, - "/member/info": { + "/monit/rule/delete": { "post": { - "description": "Return the profile of the member the credential belongs to. Requires a member-scoped credential — calls authenticated as the account principal (e.g. an account-level app key) are rejected with a 400.", - "operationId": "memberInfo", + "description": "Delete a single alert rule by its ID.", + "operationId": "monit-rule-write-delete", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "id": 50001 + }, "schema": { - "$ref": "#/components/schemas/MemberInfoRequest" + "$ref": "#/components/schemas/RuleIDRequest" } } }, @@ -42164,30 +47968,7 @@ "content": { "application/json": { "example": { - "data": { - "account_avatar": "", - "account_email": "alice@example.com", - "account_id": 2451002751131, - "account_locale": "en-US", - "account_name": "Acme Corp", - "account_role_ids": [ - 6 - ], - "account_time_zone": "Asia/Shanghai", - "avatar": "/image/avatar1.png", - "country_code": "CN", - "created_at": 1701399971, - "domain": "acme", - "email": "alice@example.com", - "email_verified": true, - "is_external": false, - "locale": "zh-CN", - "member_id": 2476444212131, - "member_name": "Alice", - "phone": "+86185****0300", - "phone_verified": true, - "time_zone": "Asia/Shanghai" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -42198,7 +47979,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberInfoResponse" + "$ref": "#/components/schemas/RuleEmptyResponse" } }, "type": "object" @@ -42222,36 +48003,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get current member info", + "summary": "Delete alert rule", "tags": [ - "Platform/Members" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — but the credential must belong to a member; account-principal credentials (e.g. an account-level app key) are rejected with a 400 |", - "href": "/en/api-reference/platform/members/member-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-delete", "metadata": { - "sidebarTitle": "Get current member info" + "sidebarTitle": "Delete alert rule" } } } }, - "/member/info/reset": { + "/monit/rule/delete/batch": { "post": { - "description": "Identify a member and reset the specified profile fields.", - "operationId": "memberResetInfo", + "description": "Delete multiple alert rules in a single request.", + "operationId": "monit-rule-write-delete-batch", "requestBody": { "content": { "application/json": { "example": { - "member_id": 2476444212131, - "updates": { - "locale": "zh-CN", - "member_name": "Alice Chen", - "time_zone": "Asia/Shanghai" - } + "ids": [ + 50001, + 50002 + ] }, "schema": { - "$ref": "#/components/schemas/MemberResetInfoRequest" + "$ref": "#/components/schemas/RuleIDsRequest" } } }, @@ -42273,7 +48052,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberEmptyObject" + "$ref": "#/components/schemas/RuleEmptyResponse" } }, "type": "object" @@ -42297,48 +48076,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Reset member info", + "summary": "Batch delete alert rules", "tags": [ - "Platform/Members" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Identify the member with one of `member_id`, `member_name`, `email`, `phone`, or `ref_id`. If multiple identifiers are present, the server checks them in that order.\n- `updates.country_code` is an ISO 3166-1 alpha-2 region code (e.g. \"CN\", \"US\"). It is an independently updatable field: `updates.phone` is not required, and the new region is stored even when the phone is unchanged. An explicit empty string is rejected with a 400.\n- When `updates.phone` has no \"+\" prefix, it is parsed with `updates.country_code` as the region hint, falling back to the member's stored region and then to \"CN\". Legacy digit calling codes such as \"86\" remain accepted only as parsing hints — stored values are always ISO region codes.\n- The top-level `country_code` is only a parsing hint for the identifying `phone`; it is never stored.\n- Put the profile fields to write under `updates`: `member_name`, `password`, `phone`, `country_code`, `email`, `avatar`, `locale`, `time_zone`, or `ref_id`.\n- Members provisioned by SSO cannot be changed when SSO marks them as externally managed.\n- `updates` must carry at least one field; an object with every field omitted is rejected.", - "href": "/en/api-reference/platform/members/member-reset-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **30 requests/minute**; **5 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-delete-batch", "metadata": { - "sidebarTitle": "Reset member info" + "sidebarTitle": "Batch delete alert rules" } } } }, - "/member/invite": { + "/monit/rule/list/basic": { "post": { - "description": "Batch invite new members to the organization by email or phone.", - "operationId": "memberInvite", + "description": "Return the basic information of all alert rules in a folder. For full rule details, call `POST /monit/rule/v2/info`.", + "operationId": "monit-rule-read-list", "requestBody": { "content": { "application/json": { "example": { - "members": [ - { - "email": "charlie@example.com", - "locale": "en-US", - "member_name": "Charlie", - "role_ids": [ - 6 - ], - "time_zone": "Asia/Shanghai" - }, - { - "country_code": "CN", - "locale": "zh-CN", - "member_name": "Dave", - "phone": "13800138000", - "time_zone": "Asia/Shanghai" - } - ] + "folder_id": 100 }, "schema": { - "$ref": "#/components/schemas/MemberInviteRequest" + "$ref": "#/components/schemas/RuleListRequest" } } }, @@ -42349,18 +48111,19 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "member_id": 5068740052131, - "member_name": "Charlie" - }, - { - "member_id": 5068740052132, - "member_name": "Dave" - } - ] - }, + "data": [ + { + "active_alert_count": 2, + "created_at": 1710000000, + "ds_type": "prometheus", + "enabled": true, + "folder_id": 100, + "id": 50001, + "name": "CPU High", + "runtime_state": "normal", + "triggered": true + } + ], "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -42371,7 +48134,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberInviteResponse" + "$ref": "#/components/schemas/RuleBasicListResponse" } }, "type": "object" @@ -42395,88 +48158,51 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Invite members", + "summary": "List alert rules", "tags": [ - "Platform/Members" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |\n\n## Usage\n\n- `country_code` must be an ISO 3166-1 alpha-2 region code (e.g. \"CN\"). It is validated and normalized to upper case before storage; invalid values are rejected with a 400.\n- When a member's `phone` has no \"+\" prefix, it is parsed with that member's `country_code` as the region hint (defaults to \"CN\" when omitted).", - "href": "/en/api-reference/platform/members/member-invite", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- Set `folder_id` to `0` to list all rules across all folders visible to the current user.\n- The `triggered` field indicates whether the rule has any currently active alerts.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-list", "metadata": { - "sidebarTitle": "Invite members" + "sidebarTitle": "List alert rules" } } } }, - "/member/list": { + "/monit/rule/move": { "post": { - "description": "Return a paginated list of organization members.", - "operationId": "memberList", + "description": "Move one or more alert rules to a different folder.", + "operationId": "monit-rule-write-move", "requestBody": { "content": { "application/json": { "example": { - "limit": 5, - "p": 1 + "dest_folder_id": 200, + "ids": [ + 50001, + 50002 + ] }, "schema": { - "$ref": "#/components/schemas/MemberListRequest" + "$ref": "#/components/schemas/RuleMoveRequest" } } }, "required": true }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "items": [ - { - "account_id": 2451002751131, - "account_role_ids": [ - 2, - 6 - ], - "avatar": "", - "country_code": "", - "created_at": 1752030749, - "email": "bob@example.com", - "email_verified": true, - "is_external": false, - "member_id": 5068740052131, - "member_name": "Bob", - "phone": "+86151****6519", - "phone_verified": true, - "ref_id": "", - "status": "enabled", - "updated_at": 1775962064 - }, - { - "account_id": 2451002751131, - "account_role_ids": [ - 6 - ], - "avatar": "/image/avatar1.png", - "country_code": "CN", - "created_at": 1701399971, - "email": "alice@example.com", - "email_verified": true, - "is_external": false, - "member_id": 2476444212131, - "member_name": "Alice", - "phone": "+86185****0300", - "phone_verified": true, - "ref_id": "", - "status": "enabled", - "updated_at": 1775809507 - } - ], - "limit": 5, - "p": 1, - "total": 148 - }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": [ + { + "message": "", + "name": "CPU High" + } + ], "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -42487,7 +48213,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberListResponse" + "$ref": "#/components/schemas/RuleNameMessageListResponse" } }, "type": "object" @@ -42511,34 +48237,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List members", + "summary": "Move alert rules to folder", "tags": [ - "Platform/Members" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/platform/members/member-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Rules whose names already exist in the destination folder are skipped. Inspect each result's `message` to identify conflicts.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-move", "metadata": { - "sidebarTitle": "List members" + "sidebarTitle": "Move alert rules to folder" } } } }, - "/member/role/grant": { + "/monit/rule/update/fields": { "post": { - "description": "Add role assignments to a member. Role IDs that do not exist are silently ignored; if none resolve, the call is a no-op success.", - "operationId": "memberGrantRole", + "description": "Update specific fields across multiple alert rules at once. Only the fields listed in `fields` are applied.", + "operationId": "monit-rule-write-fields-update", "requestBody": { "content": { "application/json": { "example": { - "member_id": 5068740052131, - "role_ids": [ - 6 + "enabled": false, + "fields": [ + "enabled" + ], + "ids": [ + 50001, + 50002 ] }, "schema": { - "$ref": "#/components/schemas/MemberRoleGrantRequest" + "$ref": "#/components/schemas/RuleFieldsUpdateRequest" } } }, @@ -42549,7 +48279,16 @@ "content": { "application/json": { "example": { - "data": {}, + "data": [ + { + "message": "", + "name": "CPU High" + }, + { + "message": "", + "name": "Disk High" + } + ], "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -42560,7 +48299,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberEmptyObject" + "$ref": "#/components/schemas/RuleNameMessageListResponse" } }, "type": "object" @@ -42584,65 +48323,256 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Grant role to member", + "summary": "Batch update rule fields", "tags": [ - "Platform/Members" + "Monitors/Alert rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |", - "href": "/en/api-reference/platform/members/member-grant-role", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Include the field names you want to update in the `fields` array, e.g. `[\"enabled\", \"channel_ids\"]`.\n- Only the specified fields are updated; others are left unchanged.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-fields-update", "metadata": { - "sidebarTitle": "Grant role to member" + "sidebarTitle": "Batch update rule fields" } } } }, - "/member/role/revoke": { + "/monit/rule/v2/info": { "post": { - "description": "Remove role assignments from a member. Role IDs that do not exist are silently ignored; if none resolve, the call is a no-op success.", - "operationId": "memberRevokeRole", + "operationId": "monit-rule-read-info-v2", + "summary": "Get alert rule detail (V2)", + "description": "Return the full V2 configuration of an alert rule by ID, including lifecycle v2 recovery and ending modes.", + "tags": [ + "Monitors/Alert rules" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- `id` is required and must not be `0`; otherwise the call returns `InvalidParameter`.\n- A missing rule returns `InvalidParameter` (`alert rule not found`).", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-info-v2", + "metadata": { + "sidebarTitle": "Get alert rule detail (V2)" + } + }, + "responses": { + "200": { + "description": "Success", + "content": { + "application/json": { + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "type": "object", + "properties": { + "data": { + "$ref": "#/components/schemas/AlertRuleV2" + } + } + } + ] + }, + "example": { + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", + "data": { + "id": 50001, + "account_id": 888, + "folder_id": 100, + "name": "CPU High", + "labels": {}, + "ds_type": "prometheus", + "ds_list": [ + "prometheus*" + ], + "ds_ids": [], + "enabled": true, + "debug_log_enabled": false, + "rule_configs": { + "queries": [ + { + "name": "A", + "expr": "100 - avg(cpu_usage_idle)" + } + ], + "check_threshold": { + "enabled": true, + "alerting_check_times": 3, + "alerting_window_size": 5, + "recovery_check_times": 2, + "critical": "$A > 90", + "warning": "$A > 80", + "recovery_mode": "condition_clear" + } + }, + "cron_pattern": "0 * * * * *", + "timezone": "Asia/Shanghai", + "delay_seconds": 0, + "enabled_times": [ + { + "days": [ + 1, + 2, + 3, + 4, + 5, + 6, + 0 + ], + "stime": "00:00", + "etime": "23:59" + } + ], + "annotations": {}, + "description_type": "text", + "description": "", + "channel_ids": [ + 20001 + ], + "repeat_interval": 3600, + "repeat_total": 3, + "investigation_targets": [], + "creator_id": 66, + "creator_name": "zhangsan", + "updater_id": 66, + "updater_name": "zhangsan", + "created_at": 1712000000, + "updated_at": 1712000000 + } + } + } + } + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, "requestBody": { + "required": true, "content": { "application/json": { - "example": { - "member_id": 5068740052131, - "role_ids": [ - 6 - ] - }, "schema": { - "$ref": "#/components/schemas/MemberRoleRevokeRequest" + "$ref": "#/components/schemas/RuleIDRequest" + }, + "example": { + "id": 50001 } } - }, - "required": true + } + } + } + }, + "/monit/rule/v2/create": { + "post": { + "operationId": "monit-rule-write-create-v2", + "summary": "Create alert rule (V2)", + "description": "Create a new V2 alert rule. Returns the created rule with its assigned ID.", + "tags": [ + "Monitors/Alert rules" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- `name`, `ds_type`, `enabled`, `cron_pattern`, and `rule_configs.queries` are required; either `ds_list` (supports wildcards) or `ds_ids` must be non-empty.\n- `enabled` must be passed explicitly (including `false`); omitting it returns `InvalidParameter`.\n- `id`, `account_id`, `creator_*`, `updater_*`, `created_at`, and `updated_at` are assigned by the server; client-supplied values are ignored.\n- `name` must be unique within `folder_id`; a duplicate returns `InvalidParameter`.\n- `channel_ids` can be empty; alerts will then route through the global integration.\n- The request body tolerates additional unknown fields (forward compatibility); they are ignored.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-create-v2", + "metadata": { + "sidebarTitle": "Create alert rule (V2)" + } }, "responses": { "200": { + "description": "Success", "content": { "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, "schema": { "allOf": [ { "$ref": "#/components/schemas/SuccessEnvelope" }, { + "type": "object", "properties": { "data": { - "$ref": "#/components/schemas/MemberEmptyObject" + "$ref": "#/components/schemas/AlertRuleV2" } - }, - "type": "object" + } } ] + }, + "example": { + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", + "data": { + "id": 50001, + "account_id": 888, + "folder_id": 100, + "name": "CPU High", + "labels": {}, + "ds_type": "prometheus", + "ds_list": [ + "prometheus*" + ], + "ds_ids": [], + "enabled": true, + "debug_log_enabled": false, + "rule_configs": { + "queries": [ + { + "name": "A", + "expr": "100 - avg(cpu_usage_idle)" + } + ], + "check_threshold": { + "enabled": true, + "alerting_check_times": 3, + "alerting_window_size": 5, + "recovery_check_times": 2, + "critical": "$A > 90", + "warning": "$A > 80", + "recovery_mode": "condition_clear" + } + }, + "cron_pattern": "0 * * * * *", + "timezone": "Asia/Shanghai", + "delay_seconds": 0, + "enabled_times": [ + { + "days": [ + 1, + 2, + 3, + 4, + 5, + 6, + 0 + ], + "stime": "00:00", + "etime": "23:59" + } + ], + "annotations": {}, + "description_type": "text", + "description": "", + "channel_ids": [ + 20001 + ], + "repeat_interval": 3600, + "repeat_total": 3, + "investigation_targets": [], + "creator_id": 66, + "creator_name": "zhangsan", + "updater_id": 66, + "updater_name": "zhangsan", + "created_at": 1712000000, + "updated_at": 1712000000 + } } } - }, - "description": "Success" + } }, "400": { "$ref": "#/components/responses/BadRequest" @@ -42657,35 +48587,219 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Revoke role from member", - "tags": [ - "Platform/Members" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |", - "href": "/en/api-reference/platform/members/member-revoke-role", - "metadata": { - "sidebarTitle": "Revoke role from member" + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AlertRuleV2" + }, + "example": { + "folder_id": 100, + "name": "CPU High", + "ds_type": "prometheus", + "ds_list": [ + "prometheus*" + ], + "enabled": true, + "cron_pattern": "0 * * * * *", + "channel_ids": [ + 20001 + ], + "rule_configs": { + "queries": [ + { + "name": "A", + "expr": "100 - avg(cpu_usage_idle)" + } + ], + "check_threshold": { + "enabled": true, + "alerting_check_times": 3, + "alerting_window_size": 5, + "recovery_check_times": 2, + "critical": "$A > 90", + "warning": "$A > 80", + "recovery_mode": "condition_clear" + } + } + } + } } } } }, - "/member/role/update": { + "/monit/rule/v2/update": { "post": { - "description": "Replace all role assignments for a member at once. Role IDs that do not exist are silently dropped; an empty `role_ids` resets the member to the built-in Viewer role (ID 8).", - "operationId": "memberUpdateRole", + "operationId": "monit-rule-write-update-v2", + "summary": "Update alert rule (V2)", + "description": "Replace an alert rule's V2 configuration in full by ID. Returns the updated rule.", + "tags": [ + "Monitors/Alert rules" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- `id` is required and the rule must already exist; otherwise the call returns `InvalidParameter`.\n- This is a full-field replacement: except for the cases below, fields you omit are stored as zero values. Fetch the full configuration via `/monit/rule/v2/info` before modifying it.\n- `enabled` must be passed explicitly (including `false`); omitting it returns `InvalidParameter`. Setting it to `false` clears the rule's active alerts.\n- `investigation_targets` is the exception: omit it to keep the current value, pass `[]` to clear, or pass a value to replace it entirely.\n- `folder_id` cannot be changed through this operation; use `/monit/rule/move` to move the rule to another folder.\n- `account_id`, `creator_*`, `updater_*`, `created_at`, and `updated_at` are maintained by the server; client-supplied values are ignored.\n- `name` must be unique within `folder_id`; a duplicate returns `InvalidParameter`.\n- The request body tolerates additional unknown fields (forward compatibility); they are ignored.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-update-v2", + "metadata": { + "sidebarTitle": "Update alert rule (V2)" + } + }, + "responses": { + "200": { + "description": "Success", + "content": { + "application/json": { + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "type": "object", + "properties": { + "data": { + "$ref": "#/components/schemas/AlertRuleV2" + } + } + } + ] + }, + "example": { + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", + "data": { + "id": 50001, + "account_id": 888, + "folder_id": 100, + "name": "CPU High", + "labels": {}, + "ds_type": "prometheus", + "ds_list": [ + "prometheus*" + ], + "ds_ids": [], + "enabled": true, + "debug_log_enabled": false, + "rule_configs": { + "queries": [ + { + "name": "A", + "expr": "100 - avg(cpu_usage_idle)" + } + ], + "check_threshold": { + "enabled": true, + "alerting_check_times": 3, + "alerting_window_size": 5, + "recovery_check_times": 2, + "critical": "$A > 95", + "warning": "$A > 80", + "recovery_mode": "condition_clear" + } + }, + "cron_pattern": "0 * * * * *", + "timezone": "Asia/Shanghai", + "delay_seconds": 0, + "enabled_times": [ + { + "days": [ + 1, + 2, + 3, + 4, + 5, + 6, + 0 + ], + "stime": "00:00", + "etime": "23:59" + } + ], + "annotations": {}, + "description_type": "text", + "description": "", + "channel_ids": [ + 20001 + ], + "repeat_interval": 3600, + "repeat_total": 3, + "investigation_targets": [], + "creator_id": 66, + "creator_name": "zhangsan", + "updater_id": 66, + "updater_name": "zhangsan", + "created_at": 1712000000, + "updated_at": 1712003600 + } + } + } + } + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, "requestBody": { + "required": true, "content": { "application/json": { - "example": { - "member_id": 5068740052131, - "role_ids": [ - 2, - 6 - ] + "schema": { + "$ref": "#/components/schemas/AlertRuleV2" }, + "example": { + "folder_id": 100, + "name": "CPU High", + "ds_type": "prometheus", + "ds_list": [ + "prometheus*" + ], + "enabled": true, + "cron_pattern": "0 * * * * *", + "channel_ids": [ + 20001 + ], + "rule_configs": { + "queries": [ + { + "name": "A", + "expr": "100 - avg(cpu_usage_idle)" + } + ], + "check_threshold": { + "enabled": true, + "alerting_check_times": 3, + "alerting_window_size": 5, + "recovery_check_times": 2, + "critical": "$A > 95", + "warning": "$A > 80", + "recovery_mode": "condition_clear" + } + }, + "id": 50001 + } + } + } + } + } + }, + "/oncall/license/list": { + "post": { + "description": "List people with active fixed or temporary On-call licenses in the current account.", + "operationId": "oncall-license-read-license-list", + "requestBody": { + "content": { + "application/json": { + "example": {}, "schema": { - "$ref": "#/components/schemas/MemberRoleUpdateRequest" + "$ref": "#/components/schemas/EmptyRequest" } } }, @@ -42696,8 +48810,28 @@ "content": { "application/json": { "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "data": { + "items": [ + { + "created_at": 1719792000, + "person_id": 80011, + "person_name": "Yuki Zhang", + "type": "fixed", + "updated_at": 1719878400, + "updated_by": 80001 + }, + { + "created_at": 0, + "person_id": 80012, + "person_name": "Alex Chen", + "type": "temporary", + "updated_at": 0, + "updated_by": 0 + } + ], + "total": 2 + }, + "request_id": "01J0D5Y31GY2TWAHRP3Q8K4M6N" }, "schema": { "allOf": [ @@ -42707,7 +48841,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/MemberEmptyObject" + "$ref": "#/components/schemas/LicenseListResponse" } }, "type": "object" @@ -42731,40 +48865,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update member roles", + "summary": "List On-call licenses", "tags": [ - "Platform/Members" + "On-call/Licenses" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Members Manage** (`organization`) |", - "href": "/en/api-reference/platform/members/member-update-role", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `items` contains only people with an active fixed or temporary On-call license.\n- For temporary licenses, `updated_by`, `created_at`, and `updated_at` are `0`.", + "href": "/en/api-reference/on-call/licenses/oncall-license-read-license-list", "metadata": { - "sidebarTitle": "Update member roles" + "sidebarTitle": "List On-call licenses" } } } }, - "/monit/datasource/create": { + "/person/infos": { "post": { - "description": "Create a new monitoring data source. The `payload` must include the type-specific configuration block. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", - "operationId": "monit-datasource-write-create", + "description": "Return profile information for a batch of person IDs (members or accounts).", + "operationId": "personInfos", "requestBody": { "content": { "application/json": { "example": { - "address": "http://prometheus.example.com:9090", - "edge_cluster_name": "default", - "name": "Prometheus Prod", - "note": "Production Prometheus", - "payload": { - "prometheus": { - "basic_auth_enabled": false - } - }, - "type_ident": "prometheus" + "person_ids": [ + 2476444212131, + 3790925372131 + ] }, "schema": { - "$ref": "#/components/schemas/DataSourceUpsertRequest" + "$ref": "#/components/schemas/PersonInfosRequest" } } }, @@ -42776,13 +48904,31 @@ "application/json": { "example": { "data": { - "alerting_enabled": true, - "edge_cluster_name": "default", - "enabled": true, - "id": 10, - "name": "Prometheus Prod", - "type_ident": "prometheus", - "updated_at": 1712000000 + "items": [ + { + "account_id": 2451002751131, + "as": "member", + "avatar": "/image/avatar1.png", + "email": "alice@example.com", + "email_verified": true, + "locale": "zh-CN", + "person_id": 2476444212131, + "person_name": "Alice", + "phone_verified": false, + "status": "enabled", + "time_zone": "Asia/Shanghai" + }, + { + "account_id": 2451002751131, + "as": "member", + "email": "bob@example.com", + "email_verified": true, + "person_id": 3790925372131, + "person_name": "Bob", + "phone_verified": false, + "status": "enabled" + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -42794,7 +48940,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DataSourceItem" + "$ref": "#/components/schemas/PersonInfosResponse" } }, "type": "object" @@ -42818,31 +48964,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create datasource", + "summary": "Batch get persons", "tags": [ - "Monitors/Data sources" + "Platform/Members" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Manage** (`monit`) |\n\n## Usage\n\n- `type_ident` must be one of: `prometheus`, `loki`, `mysql`, `oracle`, `postgres`, `clickhouse`, `elasticsearch`, `sls`, `tencent_cls`, `victorialogs`, `redis_node`, `redis_sentinel`, `mongodb_mongod`, `mongodb_mongos`, `kafka`.\n- `edge_cluster_name` specifies which Monitors edge cluster evaluates rules using this datasource.\n- For `elasticsearch`, set `payload.elasticsearch.deployment` to `cloud` or `self-managed`.\n- Every call is recorded in the account audit log. Use credential fields only for connection credentials.\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/platform/members/person-infos", "metadata": { - "sidebarTitle": "Create datasource" + "sidebarTitle": "Batch get persons" } } } }, - "/monit/datasource/delete": { + "/role/delete": { "post": { - "description": "Delete a data source by ID. Alert rules referencing this datasource are not blocked: the datasource is removed from their monitoring scope and their open alerts on it are closed automatically.", - "operationId": "monit-datasource-write-delete", + "description": "Delete a custom role. While members still hold the role, the call fails with `ReferenceExist` unless `is_force` is true.", + "operationId": "role-write-delete", "requestBody": { "content": { "application/json": { "example": { - "id": 10 + "role_id": 150 }, "schema": { - "$ref": "#/components/schemas/IDRequest" + "$ref": "#/components/schemas/RoleDeleteRequest" } } }, @@ -42864,7 +49010,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/PlatformEmptyObject" } }, "type": "object" @@ -42881,6 +49027,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -42888,31 +49037,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete datasource", + "summary": "Delete a role", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Built-in roles are synthetic and are never deleted; the call is a no-op for them.\n- While any member still holds the role, the default (`is_force=false`) call fails with error code `ReferenceExist` and the holders listed in `data.refs`. Set `is_force=true` to revoke the role from all holders and delete it in one call.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/roles-permissions/role-write-delete", "metadata": { - "sidebarTitle": "Delete datasource" + "sidebarTitle": "Delete a role" } } } }, - "/monit/datasource/info": { + "/role/disable": { "post": { - "description": "Retrieve full details of a single data source by its ID, including the `payload` configuration with its configured connection and authentication settings; treat the response as sensitive and avoid logging or forwarding it. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", - "operationId": "monit-datasource-read-info", + "description": "Disable a custom role to prevent it from granting permissions.", + "operationId": "role-write-disable", "requestBody": { "content": { "application/json": { "example": { - "id": 10 + "role_id": 150 }, "schema": { - "$ref": "#/components/schemas/IDRequest" + "$ref": "#/components/schemas/RoleIDRequest" } } }, @@ -42923,26 +49072,7 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 10023, - "address": "http://prometheus.example.com:9090", - "alerting_enabled": true, - "edge_cluster_name": "default", - "enabled": true, - "id": 10, - "name": "Prometheus Prod", - "note": "Production Prometheus", - "payload": { - "prometheus": { - "basic_auth_enabled": false, - "basic_auth_password": "", - "basic_auth_username": "", - "tls_skip_verify": false - } - }, - "type_ident": "prometheus", - "updated_at": 1712000000 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -42953,7 +49083,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DataSourceItem" + "$ref": "#/components/schemas/PlatformEmptyObject" } }, "type": "object" @@ -42970,6 +49100,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -42977,31 +49110,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get datasource detail", + "summary": "Disable a role", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Members who held this role lose its permissions immediately.\n- Built-in roles always remain enabled; enabling or disabling them is a silent no-op.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/roles-permissions/role-write-disable", "metadata": { - "sidebarTitle": "Get datasource detail" + "sidebarTitle": "Disable a role" } } } }, - "/monit/datasource/list": { + "/role/enable": { "post": { - "description": "Return all data sources for the current account. Optionally filter by `type_ident`. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", - "operationId": "monit-datasource-read-list", + "description": "Re-enable a previously disabled custom role.", + "operationId": "role-write-enable", "requestBody": { "content": { "application/json": { "example": { - "type": "prometheus" + "role_id": 150 }, "schema": { - "$ref": "#/components/schemas/DataSourceListRequest" + "$ref": "#/components/schemas/RoleIDRequest" } } }, @@ -43012,21 +49145,7 @@ "content": { "application/json": { "example": { - "data": [ - { - "account_id": 10023, - "address": "http://prometheus.example.com:9090", - "alerting_enabled": true, - "edge_cluster_name": "default", - "enabled": true, - "id": 10, - "name": "Prometheus Prod", - "note": "Production Prometheus", - "payload": null, - "type_ident": "prometheus", - "updated_at": 1712000000 - } - ], + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -43037,7 +49156,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DataSourceListResponse" + "$ref": "#/components/schemas/PlatformEmptyObject" } }, "type": "object" @@ -43054,6 +49173,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -43061,34 +49183,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List datasources", + "summary": "Enable a role", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\n## Usage\n\n- Omit `type_ident` to return all types.\n- Sensitive credential fields (passwords, keys) are not returned in the list response.\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Built-in roles always remain enabled; enabling or disabling them is a silent no-op.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/roles-permissions/role-write-enable", "metadata": { - "sidebarTitle": "List datasources" + "sidebarTitle": "Enable a role" } } } }, - "/monit/datasource/sls/logstores": { + "/role/info": { "post": { - "description": "List logstores within an SLS project for the specified SLS datasource.", - "operationId": "monit-datasource-read-sls-logstores", + "description": "Return the detail of a single role by its ID.", + "operationId": "role-read-info", "requestBody": { "content": { "application/json": { "example": { - "id": 10, - "offset": 0, - "project": "project-a", - "size": 50 + "role_id": 2 }, "schema": { - "$ref": "#/components/schemas/SLSLogstoresRequest" + "$ref": "#/components/schemas/RoleInfoRequest" } } }, @@ -43099,10 +49218,20 @@ "content": { "application/json": { "example": { - "data": [ - "logstore-1", - "logstore-2" - ], + "data": { + "created_at": 1700000000, + "description": "Account admin with all permissions.", + "editable": false, + "permission_ids": [ + 101, + 102, + 201 + ], + "role_id": 2, + "role_name": "Account Admin", + "status": "enabled", + "updated_at": 1700000000 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -43113,7 +49242,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/SLSLogstoresResponse" + "$ref": "#/components/schemas/RoleItem" } }, "type": "object" @@ -43137,34 +49266,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List SLS logstores", + "summary": "Get role detail", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\n## Usage\n\n- The datasource identified by `id` must be of type `sls`.\n- Supply `project` to select the SLS project whose logstores to list.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-sls-logstores", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/platform/roles-permissions/role-read-info", "metadata": { - "sidebarTitle": "List SLS logstores" + "sidebarTitle": "Get role detail" } } } }, - "/monit/datasource/sls/projects": { + "/role/list": { "post": { - "description": "List Alibaba Cloud SLS (Simple Log Service) projects available in the specified SLS datasource.", - "operationId": "monit-datasource-read-sls-projects", + "description": "Return all custom and built-in roles for the current account.", + "operationId": "role-read-list", "requestBody": { "content": { "application/json": { "example": { - "id": 10, - "offset": 0, - "query": "", - "size": 50 + "asc": false, + "orderby": "created_at" }, "schema": { - "$ref": "#/components/schemas/SLSProjectsRequest" + "$ref": "#/components/schemas/RoleListRequest" } } }, @@ -43176,28 +49303,19 @@ "application/json": { "example": { "data": { - "count": 2, - "projects": [ - { - "createTime": "1710000000", - "description": "Production logs", - "lastModifyTime": "1712000000", - "owner": "", - "projectName": "project-a", - "region": "cn-shanghai", - "status": "Normal" - }, + "items": [ { - "createTime": "1710000000", - "description": "Staging logs", - "lastModifyTime": "1712000000", - "owner": "", - "projectName": "project-b", - "region": "cn-shanghai", - "status": "Normal" + "created_at": 1700000000, + "description": "", + "editable": false, + "permission_ids": [], + "role_id": 2, + "role_name": "Account Admin", + "status": "enabled", + "updated_at": 1700000000 } ], - "total": 2 + "total": 3 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -43209,7 +49327,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/SLSProjectsResponse" + "$ref": "#/components/schemas/RoleListResponse" } }, "type": "object" @@ -43233,50 +49351,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List SLS projects", + "summary": "List roles", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\n## Usage\n\n- The datasource identified by `id` must be of type `sls`.\n- Use `query` to filter projects by name prefix. Use `offset` and `size` for pagination.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-read-sls-projects", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Built-in roles (`editable: false`) cannot be modified or deleted.", + "href": "/en/api-reference/platform/roles-permissions/role-read-list", "metadata": { - "sidebarTitle": "List SLS projects" + "sidebarTitle": "List roles" } } } }, - "/monit/datasource/tools/invoke": { + "/role/member/grant": { "post": { - "description": "Execute one deterministic diagnostic or query tool against a configured datasource.", - "operationId": "monit-datasource-tools-invoke", + "description": "Assign a role to one or more members, giving them its permissions.", + "operationId": "role-write-grant-role", "requestBody": { "content": { "application/json": { - "schema": { - "$ref": "#/components/schemas/DatasourceToolInvokeRequest" + "example": { + "member_ids": [ + 80011, + 80012 + ], + "role_id": 150 }, - "examples": { - "diagnostic": { - "value": { - "datasource_id": 10, - "params": {}, - "tool": "mysql.overview" - } - }, - "query": { - "value": { - "datasource_id": 24000, - "tool": "prometheus.query", - "params": { - "expr": "sum(rate(http_requests_total[5m]))", - "execution": { - "kind": "instant", - "to_ms": 1789000000000 - } - } - } - } + "schema": { + "$ref": "#/components/schemas/RoleGrantRequest" } } }, @@ -43286,6 +49389,10 @@ "200": { "content": { "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { "allOf": [ { @@ -43294,195 +49401,61 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DatasourceToolResult" + "$ref": "#/components/schemas/PlatformEmptyObject" } }, "type": "object" } ] - }, - "examples": { - "diagnostic": { - "value": { - "data": { - "data": { - "version": "8.0.36" - }, - "datasource_id": 10, - "summary": "MySQL overview", - "tool": "mysql.overview" - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - } - }, - "query": { - "value": { - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", - "data": { - "datasource_id": 24000, - "tool": "prometheus.query", - "data": { - "format": "explore_result.v1", - "result": { - "kind": "samples", - "samples": [ - { - "labels": { - "__name__": "up", - "instance": "10.101.214.50:7070" - }, - "value": 1 - } - ] - } - } - } - } - } } } }, "description": "Success" }, "400": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: invalid_request, tool_not_supported, datasource_error." + "$ref": "#/components/responses/BadRequest" }, "401": { "$ref": "#/components/responses/Unauthorized" }, "403": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: access_denied." - }, - "404": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: datasource_not_found." - }, - "409": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: datasource_disabled, datasource_in_use." - }, - "413": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: source_too_large, result_too_large." + "$ref": "#/components/responses/Forbidden" }, "429": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: overloaded." - }, - "499": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: canceled." + "$ref": "#/components/responses/TooManyRequests" }, "500": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: internal." - }, - "503": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: no_active_edge, edge_upgrade_required, mixed_edge_versions." - }, - "504": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: timeout." + "$ref": "#/components/responses/ServerError" } }, - "summary": "Invoke datasource tool", + "summary": "Grant role to members", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **2,000 requests/minute**; **32 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n\nUse datasource IDs from `/monit/datasource/list`. Disabled datasources return `datasource_disabled`; `alerting_enabled=false` does not block tools. Errors use non-2xx HTTP status and `error.code`, `error.message`, `error.reason`. `tool_not_supported` indicates the selected executor does not provide this tool; it is not a vendor permission error. Never retry through another Edge or the legacy diagnose endpoint automatically.\n\n## Usage\n\n- Two tool families share this entry: diagnostic tools defined by the executing Edge (e.g. `mysql.overview`, `prometheus.metric_trends`) and query tools named `.query`. The tool prefix must match the datasource type.\n- Query tools require the Edge cluster to support Explore queries (protocol milestone v0.68.0); diagnostic tools require the v0.71.0 base invoke protocol. Unsupported clusters fail with `edge_upgrade_required`, `mixed_edge_versions`, or `edge_version_unknown`; never fall back to `/monit/query/data` or another endpoint automatically.\n- For query tools, `params` follows the per-datasource schema named in the `tool` field description. `expr` and `execution` are always required. `limit`/`direction` only bound raw-log retrieval, never SQL rows or scanned data. Unknown extension fields are tolerated but never executed or forwarded.\n- Query `data` is the complete Explore result: `format` is `explore_result.v1` and `result.kind` is `samples`, `frames`, or `logs`; log results keep `applied_limit` and `has_more`. Query results never synthesize `summary` or `truncated`.\n- Request body limit 128 KiB; complete success response limit 10 MiB for both families; diagnostic tool timeout at most 25 seconds.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-tools-invoke", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Members who already have the role are silently skipped.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/roles-permissions/role-write-grant-role", "metadata": { - "sidebarTitle": "Invoke datasource tool" + "sidebarTitle": "Grant role to members" } } } }, - "/monit/datasource/update": { + "/role/member/revoke": { "post": { - "description": "Update an existing data source. Supply `id` plus the fields to change. Supports diagnostic types redis_node, redis_sentinel, mongodb_mongod, mongodb_mongos and kafka; enabled and alerting_enabled are independent.", - "operationId": "monit-datasource-write-update", + "description": "Remove a role from one or more members, revoking the permissions it granted.", + "operationId": "role-write-revoke-role", "requestBody": { "content": { "application/json": { "example": { - "address": "http://prometheus-v2.example.com:9090", - "edge_cluster_name": "default", - "id": 10, - "name": "Prometheus Prod v2", - "note": "Updated", - "payload": { - "prometheus": { - "basic_auth_enabled": false - } - }, - "type_ident": "prometheus" + "member_ids": [ + 80011 + ], + "role_id": 150 }, "schema": { - "$ref": "#/components/schemas/DataSourceUpsertRequest" + "$ref": "#/components/schemas/RoleGrantRequest" } } }, @@ -43493,15 +49466,7 @@ "content": { "application/json": { "example": { - "data": { - "alerting_enabled": true, - "edge_cluster_name": "default", - "enabled": true, - "id": 10, - "name": "Prometheus Prod v2", - "type_ident": "prometheus", - "updated_at": 1712100000 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -43512,7 +49477,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/DataSourceItem" + "$ref": "#/components/schemas/PlatformEmptyObject" } }, "type": "object" @@ -43529,6 +49494,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -43536,130 +49504,112 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update datasource", + "summary": "Revoke role from members", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Datasources Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Use credential fields only for connection credentials.\n\nSee the request/response schemas for all supported types and credential handling. Diagnostic-only types cannot enable alerting. On create omitted enabled defaults to true; on update omission preserves the current value. Explicit null for enabled or alerting_enabled is invalid. Diagnostic passwords and Kafka private keys are omitted from responses unless they are environment references; omit these secrets on update to preserve them, or send an empty string to clear. Other datasource credentials may be returned and must be handled as sensitive.", - "href": "/en/api-reference/monitors/data-sources/monit-datasource-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Members who don't have the role are silently skipped.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/roles-permissions/role-write-revoke-role", "metadata": { - "sidebarTitle": "Update datasource" + "sidebarTitle": "Revoke role from members" } } } }, - "/monit/prometheus/api/v1/label/{label_name}/values": { - "get": { - "description": "Read label values from a Prometheus-compatible data source through the Monitors proxy.", - "operationId": "monit-prometheus-read-label-values", - "parameters": [ - { - "description": "Label name to enumerate values for, for example `job`.", - "in": "path", - "name": "label_name", - "required": true, - "schema": { - "type": "string" + "/role/permission/factor/list": { + "post": { + "description": "Return all permission factors (API, button, menu, URL, visit) granted to the calling member, optionally filtered by type. Requires a member-scoped credential — calls authenticated as the account principal (e.g. an account-level app key) are rejected with a 400, because the account principal implicitly holds every permission.", + "operationId": "role-read-list-permission-factor", + "requestBody": { + "content": { + "application/json": { + "example": { + "factor_types": [ + "api" + ] + }, + "schema": { + "$ref": "#/components/schemas/PermissionFactorListRequest" + } } }, - { - "description": "Data source ID to query. Must reference a Prometheus-compatible data source owned by the authenticated account.", - "in": "header", - "name": "X-DSID", - "required": true, - "schema": { - "type": "string" - } - } - ], + "required": true + }, "responses": { "200": { "content": { "application/json": { "example": { "data": [ - "api", - "db", - "worker" + { + "factor_name": "template:read:info", + "factor_type": "api", + "source": "system" + } ], - "status": "success" + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { - "$ref": "#/components/schemas/PrometheusLabelValuesResponse" + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/PermissionFactorListResponse" + } + }, + "type": "object" + } + ] } } }, - "description": "Native Prometheus label-values response returned by the data source." + "description": "Success" }, "400": { - "content": { - "text/plain": { - "schema": { - "type": "string" - } - } - }, - "description": "The `X-DSID` header is missing or invalid, the data source does not exist, or it is not a Prometheus data source. Returned as `text/plain`." + "$ref": "#/components/responses/BadRequest" }, "401": { "$ref": "#/components/responses/Unauthorized" }, - "500": { - "content": { - "text/plain": { - "schema": { - "type": "string" - } - } - }, - "description": "The data source lookup or the proxied request failed. Returned as `text/plain`." + "429": { + "$ref": "#/components/responses/TooManyRequests" }, - "503": { - "content": { - "text/plain": { - "schema": { - "type": "string" - } - } - }, - "description": "No monit-edge in the data source's cluster supports the data source resource proxy. Returned as `text/plain`; upgrade monit-edge." + "500": { + "$ref": "#/components/responses/ServerError" } }, - "summary": "List Prometheus label values", + "summary": "List permission factors", "tags": [ - "Monitors/Data sources" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Any valid `app_key` (read-only; not gated by a specific permission class) |\n| Edge requirement | Supported deployments require **monit-edge v0.35.0 or later** |\n\n## Usage\n\n- Pass the target data source in the `X-DSID` header. It must be a Prometheus-compatible data source owned by the authenticated account; use `/monit/datasource/list` to obtain its ID.\n- The 200 body is the data source's native Prometheus HTTP API payload, **not** the standard `{ request_id, data }` envelope. Failures raised before the data source is reached are returned as `text/plain` with the matching 4xx or 5xx status.\n- When `X-DSID` is omitted, the request falls back to the platform's own Prometheus proxy. Send the header to query a specific data source.", - "href": "/en/api-reference/monitors/data-sources/monit-prometheus-read-label-values", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — but the credential must belong to a member; account-principal credentials (e.g. an account-level app key) are rejected with a 400 |\n\n## Usage\n\n- Permission factors are the fine-grained controls that make up each permission.\n- `factor_types` accepts: `api`, `button`, `visit`, `menu`, `url`.", + "href": "/en/api-reference/platform/roles-permissions/role-read-list-permission-factor", "metadata": { - "sidebarTitle": "List Prometheus label values" + "sidebarTitle": "List permission factors" } } } }, - "/monit/query/explore": { + "/role/permission/list": { "post": { - "description": "Run an Explore query against a configured data source and return frames, samples, or logs.", - "operationId": "monit-read-query-explore", + "description": "Return all available permissions, optionally filtered to those granted to specific roles.", + "operationId": "role-read-list-permission", "requestBody": { "content": { "application/json": { "example": { - "args": {}, - "datasource_id": 101, - "execution": { - "from_ms": 1787187600000, - "kind": "range", - "max_data_points": 1200, - "min_step_seconds": 15, - "to_ms": 1787191200000 - }, - "expr": "rate(http_requests_total[5m])" + "role_ids": [ + 150 + ], + "with_all": true }, "schema": { - "$ref": "#/components/schemas/QueryExploreRequest" + "$ref": "#/components/schemas/RolePermissionListRequest" } } }, @@ -43671,40 +49621,19 @@ "application/json": { "example": { "data": { - "execution": { - "effective_step_seconds": 60, - "kind": "range" - }, - "format": "explore_result.v1", - "result": { - "frames": [ - { - "fields": [ - { - "name": "time", - "type": "time", - "values": [ - "2026-08-20T10:00:00Z", - "2026-08-20T10:01:00Z" - ] - }, - { - "labels": { - "job": "api" - }, - "name": "value", - "type": "float", - "values": [ - 1.25, - null - ] - } - ], - "kind": "time_series" - } - ], - "kind": "frames" - } + "items": [ + { + "class": "On-call", + "description": "View notification templates", + "id": 501, + "is_granted": true, + "permission_name": "Templates Read", + "permission_type": "read", + "scope": "on-call", + "source": "system", + "status": "enabled" + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -43716,7 +49645,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ExploreData" + "$ref": "#/components/schemas/RolePermissionListResponse" } }, "type": "object" @@ -43728,128 +49657,48 @@ "description": "Success" }, "400": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: invalid_request." + "$ref": "#/components/responses/BadRequest" }, "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: access_denied." - }, - "404": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: datasource_not_found." - }, - "413": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: source_too_large, result_too_large." - }, "429": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: overloaded." - }, - "499": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: canceled." + "$ref": "#/components/responses/TooManyRequests" }, "500": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: internal." - }, - "503": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: no_active_edge, edge_upgrade_required, mixed_edge_versions, edge_unavailable." - }, - "504": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "Standard HTTP error; error.reason: timeout." + "$ref": "#/components/responses/ServerError" } }, - "summary": "Run Explore query", + "summary": "List permissions", "tags": [ - "Monitors/Diagnostics" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **16 requests/second** per account |\n| Permissions | **Datasources Read** (`monit`) |\n| Edge requirement | Supported deployments require **monit-edge v0.68.0 or later** |\n\n## Usage\n\n- Use this endpoint when you need the data source's native result shape; `/monit/query/data` returns the stable `query_result.v1` contract instead. Dispatch on `data.result.kind` (`frames`, `samples`, or `logs`) here.\n- `execution.kind` decides which companion fields are accepted: `instant` needs only `to_ms`, `range` requires `from_ms`, `to_ms`, and `max_data_points`, and `window` takes `from_ms` and `to_ms`. `step_seconds` is not accepted; the step is derived from `max_data_points` and `min_step_seconds`.\n- `args` carries macro substitutions such as Grafana-style variables; every value is a string.\n- A `logs` result is capped at 1,000 entries and reports `applied_limit` plus `has_more`. Time-series and sample results are capped at 1,000 items each and the whole success response at 8 MiB.\n- Query execution may take up to 35 seconds across WebAPI forwarding and Edge execution. Configure client timeouts to at least 40 seconds.", - "href": "/en/api-reference/monitors/diagnostics/monit-read-query-explore", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Pass `role_ids` to filter permissions to those granted to those roles.\n- Pass `with_all: true` to include all permissions regardless of role filter, with `is_granted` set to indicate which are granted to the specified roles.", + "href": "/en/api-reference/platform/roles-permissions/role-read-list-permission", "metadata": { - "sidebarTitle": "Run Explore query" + "sidebarTitle": "List permissions" } } } }, - "/monit/query/data": { + "/role/upsert": { "post": { - "description": "Run a synchronous ad-hoc query against a configured data source and return a stable `query_result.v1` result whose natural shape is frames, records, or samples. This public API requires monit-edge v0.65.0 or later.", - "operationId": "monit-read-query-data", + "description": "Create a new custom role or update an existing one. Pass `role_id` to update.", + "operationId": "role-write-upsert", "requestBody": { "content": { "application/json": { "example": { - "args": {}, - "delay_seconds": 0, - "ds_name": "prod-prom", - "ds_type": "prometheus", - "expr": "sum by (job) (rate(http_requests_total[5m]))" + "description": "Manage on-call rotations and incidents.", + "permission_ids": [ + 501, + 502 + ], + "role_name": "On-call Manager" }, "schema": { - "$ref": "#/components/schemas/QueryDataRequest" + "$ref": "#/components/schemas/RoleUpsertRequest" } } }, @@ -43861,18 +49710,8 @@ "application/json": { "example": { "data": { - "format": "query_result.v1", - "result": { - "kind": "samples", - "samples": [ - { - "labels": { - "job": "api" - }, - "value": 1.25 - } - ] - } + "role_id": 150, + "role_name": "On-call Manager" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -43884,7 +49723,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/QueryDataResponse" + "$ref": "#/components/schemas/RoleUpsertResponse" } }, "type": "object" @@ -43904,71 +49743,38 @@ "403": { "$ref": "#/components/responses/Forbidden" }, - "413": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "The request or final response exceeds its size limit." - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, - "499": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "The client canceled the query." - }, "500": { "$ref": "#/components/responses/ServerError" - }, - "503": { - "$ref": "#/components/responses/ServiceUnavailable" - }, - "504": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorResponse" - } - } - }, - "description": "The query timed out." } }, - "summary": "Query structured data", + "summary": "Create or update a role", "tags": [ - "Monitors/Diagnostics" + "Platform/Roles & permissions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **5 requests/second** per account |\n| Permissions | Any valid `app_key` (read-only; not gated by a specific permission class) |\n| Edge requirement | Supported deployments require **monit-edge v0.65.0 or later** |\n\n## Usage\n\n- Treat **monit-edge v0.65.0** as the minimum supported Edge version for this public API. WebAPI retains migration adapters for older Edge versions: query.v2 results may still preserve frames, records, or samples, while legacy rows can expose only the information they retained. These adapters do not change the support floor; older protocols lack query.v3 cancellation and error-lifecycle semantics, and data already lost by legacy rows cannot be recovered.\n- The public response format is always `query_result.v1` and is independent of the internal Edge query protocol. Dispatch on `result.kind` (`frames`, `records`, or `samples`); do not infer the result shape from `ds_type` or the Edge version.\n- A `frames` result may contain multiple table or time-series frames. Field values are columnar and all fields in one frame have the same length.\n- A `records` result may contain nested JSON and null records. Integer literals outside JavaScript's safe integer range are returned as decimal strings.\n- A `samples` result contains label sets and instant values. A value may be a number or one of the strings `NaN`, `+Inf`, and `-Inf`.\n- The final success response is limited to 8 MiB and query results are limited to 1,000 rows. Narrow the time range, reduce fields, or aggregate at the source when a request exceeds a limit.\n- Query failures use non-2xx HTTP status codes and the standard error envelope. Do not transparently fall back to the deprecated `/monit/query/rows` endpoint.\n- Query execution may take up to 35 seconds across WebAPI forwarding and Edge execution. Configure client timeouts to at least 40 seconds and propagate cancellation when the caller abandons a query.", - "href": "/en/api-reference/monitors/diagnostics/monit-read-query-data", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Omit `role_id` (or set to 0) to create; pass an existing ID to update.\n- `role_name` must be 1–39 characters and unique within the account.\n- `permission_ids` sets the full permission set for the role, replacing any previous assignment.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/roles-permissions/role-write-upsert", "metadata": { - "sidebarTitle": "Query structured data" + "sidebarTitle": "Create or update a role" } } } }, - "/monit/rule/audit/detail": { + "/route/info": { "post": { - "description": "Return the audit record (including the `content` field, a JSON string of the rule snapshot at that point in time).", - "operationId": "monit-rule-read-audit-detail", + "description": "Retrieve the routing rule configuration for a specific integration. Returns null when the integration has no routing rule configured.", + "operationId": "routeInfo", "requestBody": { "content": { "application/json": { "example": { - "id": 9001 + "integration_id": 6113996590131 }, "schema": { - "$ref": "#/components/schemas/AuditRecordIDRequest" + "$ref": "#/components/schemas/RouteInfoRequest" } } }, @@ -43980,14 +49786,51 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "action": "update", - "alert_rule_id": 50001, - "content": "{\"id\":50001,\"name\":\"CPU High\"}", - "created_at": 1712000000, - "creator_id": 80011, - "creator_name": "Alice", - "id": 9001 + "cases": [ + { + "channel_ids": [ + 2533748993131 + ], + "fallthrough": false, + "if": [ + { + "key": "labels.check", + "oper": "IN", + "vals": [ + "cpu.idle<20%" + ] + } + ], + "routing_mode": "standard" + }, + { + "channel_ids": null, + "fallthrough": false, + "if": [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Warning" + ] + } + ], + "name_mapping_label": "labels.service", + "routing_mode": "name_mapping" + } + ], + "created_at": 1774606136, + "creator_id": 3790925372131, + "default": { + "channel_ids": [ + 3521074710131 + ] + }, + "integration_id": 6113996590131, + "status": "enabled", + "updated_at": 1774606136, + "updated_by": 3790925372131, + "version": 6 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -43999,7 +49842,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AlertRuleAudit" + "$ref": "#/components/schemas/RouteItem" } }, "type": "object" @@ -44023,31 +49866,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get rule audit snapshot", + "summary": "Get routing rule detail", "tags": [ - "Monitors/Alert rules" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- Pass the audit record `id` (not the rule `id`) from `POST /monit/rule/audits`.\n- `content` is a JSON string — parse it to get the full rule snapshot.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-audit-detail", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/route-info", "metadata": { - "sidebarTitle": "Get rule audit snapshot" + "sidebarTitle": "Get routing rule detail" } } } }, - "/monit/rule/audits": { + "/route/list": { "post": { - "description": "Return the change history (audit records) for an alert rule.", - "operationId": "monit-rule-read-audits", + "description": "Return routing rules for the specified integrations. Integrations without a configured rule are omitted from the response.", + "operationId": "routeList", "requestBody": { "content": { "application/json": { "example": { - "id": 50001 + "integration_ids": [ + 6113996590131, + 6113996590132 + ] }, "schema": { - "$ref": "#/components/schemas/RuleIDRequest" + "$ref": "#/components/schemas/ListRoutesRequest" } } }, @@ -44058,17 +49904,42 @@ "content": { "application/json": { "example": { - "data": [ - { - "account_id": 10023, - "action": "update", - "alert_rule_id": 50001, - "created_at": 1712000000, - "creator_id": 80011, - "creator_name": "Alice", - "id": 9001 - } - ], + "data": { + "items": [ + { + "cases": [ + { + "channel_ids": [ + 2533748993131 + ], + "fallthrough": false, + "if": [ + { + "key": "labels.check", + "oper": "IN", + "vals": [ + "cpu.idle<20%" + ] + } + ], + "routing_mode": "standard" + } + ], + "created_at": 1774606136, + "creator_id": 3790925372131, + "default": { + "channel_ids": [ + 3521074710131 + ] + }, + "integration_id": 6113996590131, + "status": "enabled", + "updated_at": 1774606136, + "updated_by": 3790925372131, + "version": 6 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44079,7 +49950,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleAuditListResponse" + "$ref": "#/components/schemas/ListRoutesResponse" } }, "type": "object" @@ -44103,29 +49974,54 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List rule change history", + "summary": "List routing rules", "tags": [ - "Monitors/Alert rules" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-audits", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/route-list", "metadata": { - "sidebarTitle": "List rule change history" + "sidebarTitle": "List routing rules" } } } }, - "/monit/rule/counter/channel": { + "/route/upsert": { "post": { - "description": "Return an object mapping channel name to the number of rules routing alerts to that channel. If a channel name cannot be resolved, the channel ID (as a string) is used as the key.", - "operationId": "monit-rule-read-counter-channel", + "description": "Create or update routing rules for an integration to direct alerts to specific channels. At least one of `cases` or `default` must be provided.", + "operationId": "routeUpsert", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "cases": [ + { + "channel_ids": [ + 3521074710131 + ], + "fallthrough": false, + "if": [ + { + "key": "severity", + "oper": "IN", + "vals": [ + "Critical" + ] + } + ], + "routing_mode": "standard" + } + ], + "default": { + "channel_ids": [ + 3521074710131 + ] + }, + "integration_id": 6113996590131 + }, "schema": { - "$ref": "#/components/schemas/RuleEmptyRequest" + "$ref": "#/components/schemas/UpsertRouteRequest" } } }, @@ -44136,9 +50032,7 @@ "content": { "application/json": { "example": { - "data": { - "Production": 8 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44149,7 +50043,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleCounterChannelResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -44173,29 +50067,51 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get rule counts by channel", + "summary": "Upsert routing rule", "tags": [ - "Monitors/Alert rules" + "On-call/Channels" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-counter-channel", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/channels/route-upsert", "metadata": { - "sidebarTitle": "Get rule counts by channel" + "sidebarTitle": "Upsert routing rule" } } } }, - "/monit/rule/counter/total": { + "/rum/application/create": { "post": { - "description": "Return the stored time series of the total rule count across the account — one sample per `clock` timestamp.", - "operationId": "monit-rule-read-counter-total", + "description": "Create a new RUM application. Returns the generated `application_id` and `client_token`.", + "operationId": "rum-application-write-create", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "application_name": "My Web App", + "is_private": false, + "links": { + "enabled": true, + "systems": [ + { + "enabled": true, + "event_types": [ + "crash", + "error" + ], + "icon_color": "#0F766E", + "icon_text": "S3", + "id": "s3-crash-logs", + "name": "S3 Crash Logs", + "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" + } + ] + }, + "team_id": 2477033058131, + "type": "browser" + }, "schema": { - "$ref": "#/components/schemas/RuleEmptyRequest" + "$ref": "#/components/schemas/RumApplicationCreateRequest" } } }, @@ -44206,14 +50122,11 @@ "content": { "application/json": { "example": { - "data": [ - { - "account_id": 10023, - "clock": 1712000000, - "id": 1, - "num": 50 - } - ], + "data": { + "application_id": "qLpu24Dz4CAzWsESPbJYWA", + "application_name": "My Web App", + "client_token": "e090078724855a4ca168c3884880dfbc131" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44224,7 +50137,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleCounterTotalResponse" + "$ref": "#/components/schemas/RumApplicationCreateResponse" } }, "type": "object" @@ -44248,31 +50161,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get rule counter time series", + "summary": "Create application", "tags": [ - "Monitors/Alert rules" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- Each item is a historical snapshot: `num` is the total rule count at the given `clock` (Unix epoch seconds).", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-counter-total", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- `type` must be one of: `browser`, `ios`, `android`, `react-native`, `flutter`, `kotlin-multiplatform`, `roku`, `unity`, `miniprogram`, `harmony`, `electron`.\n- `links.systems[].url` must start with `http` or `https`; `${var}` tokens are resolved from RUM event context.\n- `links.systems[].event_types` accepts: `crash`, `error`, `view`, `action`, `resource`, `session`, `all`.\n- `client_token` is auto-generated and used to initialize the RUM SDK.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/applications/rum-application-write-create", "metadata": { - "sidebarTitle": "Get rule counter time series" + "sidebarTitle": "Create application" } } } }, - "/monit/rule/delete": { + "/rum/application/delete": { "post": { - "description": "Delete a single alert rule by its ID.", - "operationId": "monit-rule-write-delete", + "description": "Delete a RUM application by `application_id`.", + "operationId": "rum-application-write-delete", "requestBody": { "content": { "application/json": { "example": { - "id": 50001 + "application_id": "qLpu24Dz4CAzWsESPbJYWA" }, "schema": { - "$ref": "#/components/schemas/RuleIDRequest" + "$ref": "#/components/schemas/RumApplicationIDRequest" } } }, @@ -44294,7 +50207,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleEmptyResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -44318,34 +50231,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete alert rule", + "summary": "Delete application", "tags": [ - "Monitors/Alert rules" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/applications/rum-application-write-delete", "metadata": { - "sidebarTitle": "Delete alert rule" + "sidebarTitle": "Delete application" } } } }, - "/monit/rule/delete/batch": { + "/rum/application/info": { "post": { - "description": "Delete multiple alert rules in a single request.", - "operationId": "monit-rule-write-delete-batch", + "description": "Retrieve full details of a single RUM application by `application_id`.", + "operationId": "rum-application-read-info", "requestBody": { "content": { "application/json": { "example": { - "ids": [ - 50001, - 50002 - ] + "application_id": "WoyQQ3BohkdtPivubEvE8o" }, "schema": { - "$ref": "#/components/schemas/RuleIDsRequest" + "$ref": "#/components/schemas/RumApplicationIDRequest" } } }, @@ -44356,7 +50266,51 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "account_id": 2451002751131, + "alerting": { + "channel_ids": [ + 2490121812131 + ], + "enabled": true, + "integration_id": 4759595678131 + }, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "application_name": "flashcat-rum", + "client_token": "a3cea433a8685a398cdfd68f54a45e06131", + "created_at": 1746673831462, + "created_by": 4441703362131, + "is_private": true, + "links": { + "enabled": true, + "systems": [ + { + "enabled": true, + "event_types": [ + "crash", + "error" + ], + "icon_color": "#0F766E", + "icon_text": "S3", + "id": "s3-crash-logs", + "name": "S3 Crash Logs", + "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" + } + ] + }, + "no_geo": false, + "no_ip": true, + "status": "enabled", + "team_id": 2477033058131, + "tracing": { + "enabled": false, + "endpoint": "", + "open_type": "" + }, + "type": "browser", + "updated_at": 1773398630657, + "updated_by": 3790925372131 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44367,7 +50321,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleEmptyResponse" + "$ref": "#/components/schemas/RumApplicationItem" } }, "type": "object" @@ -44391,31 +50345,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Batch delete alert rules", + "summary": "Get application detail", "tags": [ - "Monitors/Alert rules" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **30 requests/minute**; **5 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-delete-batch", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/rum/applications/rum-application-read-info", "metadata": { - "sidebarTitle": "Batch delete alert rules" + "sidebarTitle": "Get application detail" } } } }, - "/monit/rule/list/basic": { + "/rum/application/infos": { "post": { - "description": "Return the basic information of all alert rules in a folder. For full rule details, call `POST /monit/rule/v2/info`.", - "operationId": "monit-rule-read-list", + "description": "Retrieve details for multiple RUM applications by their IDs in one request.", + "operationId": "rum-application-read-infos", "requestBody": { "content": { "application/json": { "example": { - "folder_id": 100 + "application_ids": [ + "eWbr4xk3ZRnLabRa6unqwD", + "WoyQQ3BohkdtPivubEvE8o" + ] }, "schema": { - "$ref": "#/components/schemas/RuleListRequest" + "$ref": "#/components/schemas/RumApplicationInfosRequest" } } }, @@ -44426,19 +50383,88 @@ "content": { "application/json": { "example": { - "data": [ - { - "active_alert_count": 2, - "created_at": 1710000000, - "ds_type": "prometheus", - "enabled": true, - "folder_id": 100, - "id": 50001, - "name": "CPU High", - "runtime_state": "normal", - "triggered": true - } - ], + "data": { + "items": [ + { + "account_id": 2451002751131, + "alerting": { + "channel_ids": [ + 5962711836131, + 5967875767131 + ], + "enabled": true, + "integration_id": 4759595678131 + }, + "application_id": "eWbr4xk3ZRnLabRa6unqwD", + "application_name": "Flashduty DEV", + "client_token": "ce8d1be90fc6534f89ce36ebf526765e131", + "created_at": 1742958482000, + "created_by": 2476444212131, + "is_private": false, + "links": { + "enabled": false, + "systems": [] + }, + "no_geo": false, + "no_ip": false, + "status": "enabled", + "team_id": 2477033058131, + "tracing": { + "enabled": true, + "endpoint": "https://www.tracing.com/${trace_id}", + "open_type": "popup" + }, + "type": "browser", + "updated_at": 1772096392711, + "updated_by": 3122470302131 + }, + { + "account_id": 2451002751131, + "alerting": { + "channel_ids": [ + 2490121812131 + ], + "enabled": true, + "integration_id": 4759595678131 + }, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "application_name": "flashcat-rum", + "client_token": "a3cea433a8685a398cdfd68f54a45e06131", + "created_at": 1746673831462, + "created_by": 4441703362131, + "is_private": true, + "links": { + "enabled": true, + "systems": [ + { + "enabled": true, + "event_types": [ + "crash", + "error" + ], + "icon_color": "#0F766E", + "icon_text": "S3", + "id": "s3-crash-logs", + "name": "S3 Crash Logs", + "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" + } + ] + }, + "no_geo": false, + "no_ip": true, + "status": "enabled", + "team_id": 2477033058131, + "tracing": { + "enabled": false, + "endpoint": "", + "open_type": "" + }, + "type": "browser", + "updated_at": 1773398630657, + "updated_by": 3790925372131 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44449,7 +50475,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleBasicListResponse" + "$ref": "#/components/schemas/RumApplicationInfosResponse" } }, "type": "object" @@ -44473,35 +50499,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List alert rules", + "summary": "Batch get applications", "tags": [ - "Monitors/Alert rules" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- Set `folder_id` to `0` to list all rules across all folders visible to the current user.\n- The `triggered` field indicates whether the rule has any currently active alerts.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Maximum 200 IDs per request.", + "href": "/en/api-reference/rum/applications/rum-application-read-infos", "metadata": { - "sidebarTitle": "List alert rules" + "sidebarTitle": "Batch get applications" } } } }, - "/monit/rule/move": { + "/rum/application/list": { "post": { - "description": "Move one or more alert rules to a different folder.", - "operationId": "monit-rule-write-move", + "description": "Return a paginated list of RUM applications accessible to the current user.", + "operationId": "rum-application-read-list", "requestBody": { "content": { "application/json": { "example": { - "dest_folder_id": 200, - "ids": [ - 50001, - 50002 - ] + "is_my_team": false, + "limit": 20, + "p": 1, + "query": "" }, "schema": { - "$ref": "#/components/schemas/RuleMoveRequest" + "$ref": "#/components/schemas/RumApplicationListRequest" } } }, @@ -44512,12 +50537,90 @@ "content": { "application/json": { "example": { - "data": [ - { - "message": "", - "name": "CPU High" - } - ], + "data": { + "has_next_page": true, + "items": [ + { + "account_id": 2451002751131, + "alerting": { + "channel_ids": [ + 2490121812131 + ], + "enabled": true, + "integration_id": 4759595678131 + }, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "application_name": "flashcat-rum", + "client_token": "a3cea433a8685a398cdfd68f54a45e06131", + "created_at": 1746673831462, + "created_by": 4441703362131, + "is_private": true, + "links": { + "enabled": true, + "systems": [ + { + "enabled": true, + "event_types": [ + "crash", + "error" + ], + "icon_color": "#0F766E", + "icon_text": "S3", + "id": "s3-crash-logs", + "name": "S3 Crash Logs", + "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" + } + ] + }, + "no_geo": false, + "no_ip": true, + "status": "enabled", + "team_id": 2477033058131, + "tracing": { + "enabled": false, + "endpoint": "", + "open_type": "" + }, + "type": "browser", + "updated_at": 1773398630657, + "updated_by": 3790925372131 + }, + { + "account_id": 2451002751131, + "alerting": { + "channel_ids": [ + 5962711836131, + 5967875767131 + ], + "enabled": true, + "integration_id": 4759595678131 + }, + "application_id": "eWbr4xk3ZRnLabRa6unqwD", + "application_name": "Flashduty DEV", + "client_token": "ce8d1be90fc6534f89ce36ebf526765e131", + "created_at": 1742958482000, + "created_by": 2476444212131, + "is_private": false, + "links": { + "enabled": false, + "systems": [] + }, + "no_geo": false, + "no_ip": false, + "status": "enabled", + "team_id": 2477033058131, + "tracing": { + "enabled": true, + "endpoint": "https://www.tracing.com/${trace_id}", + "open_type": "popup" + }, + "type": "browser", + "updated_at": 1772096392711, + "updated_by": 3122470302131 + } + ], + "total": 7 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44528,7 +50631,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleNameMessageListResponse" + "$ref": "#/components/schemas/RumApplicationListResponse" } }, "type": "object" @@ -44552,38 +50655,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Move alert rules to folder", + "summary": "List applications", "tags": [ - "Monitors/Alert rules" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Rules whose names already exist in the destination folder are skipped. Inspect each result's `message` to identify conflicts.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-move", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Use `is_my_team` to filter applications belonging to the current user's teams.\n- Default page size is 20, maximum is 100.\n- `orderby` accepts `created_at` or `updated_at`.", + "href": "/en/api-reference/rum/applications/rum-application-read-list", "metadata": { - "sidebarTitle": "Move alert rules to folder" + "sidebarTitle": "List applications" } } } }, - "/monit/rule/update/fields": { + "/rum/application/remote-config/get": { "post": { - "description": "Update specific fields across multiple alert rules at once. Only the fields listed in `fields` are applied.", - "operationId": "monit-rule-write-fields-update", + "description": "Retrieve the live remote configuration of a RUM application and the version it is stored under.", + "operationId": "rum-application-remote-config-read-get", "requestBody": { "content": { "application/json": { "example": { - "enabled": false, - "fields": [ - "enabled" - ], - "ids": [ - 50001, - 50002 - ] + "application_id": "WoyQQ3BohkdtPivubEvE8o" }, "schema": { - "$ref": "#/components/schemas/RuleFieldsUpdateRequest" + "$ref": "#/components/schemas/GetRemoteConfigRequest" } } }, @@ -44594,16 +50690,38 @@ "content": { "application/json": { "example": { - "data": [ - { - "message": "", - "name": "CPU High" + "data": { + "config": { + "activation": "next_session", + "custom": { + "feature_flags": { + "checkout_v2": true + } + }, + "default": { + "defaultPrivacyLevel": "mask-user-input", + "sessionReplaySampleRate": 20, + "sessionSampleRate": 100, + "traceSampleRate": 100 + }, + "enabled": true, + "refresh_on_foreground": false, + "rules": [ + { + "match": { + "env": "production" + }, + "set": { + "defaultPrivacyLevel": "mask", + "sessionReplaySampleRate": 0, + "sessionSampleRate": 5 + } + } + ] }, - { - "message": "", - "name": "Disk High" - } - ], + "updated_at": 1773398630657, + "version": 7 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -44614,7 +50732,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RuleNameMessageListResponse" + "$ref": "#/components/schemas/GetRemoteConfigResponse" } }, "type": "object" @@ -44638,123 +50756,143 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Batch update rule fields", + "summary": "Get remote config detail", "tags": [ - "Monitors/Alert rules" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- Include the field names you want to update in the `fields` array, e.g. `[\"enabled\", \"channel_ids\"]`.\n- Only the specified fields are updated; others are left unchanged.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-fields-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Version `0` means the application has never been configured; SDKs then run entirely on their init values.\n- A change reaches a client when its next session starts unless activation is set to `immediate`.", + "href": "/en/api-reference/rum/applications/rum-application-remote-config-read-get", "metadata": { - "sidebarTitle": "Batch update rule fields" + "sidebarTitle": "Get remote config detail" } } } }, - "/monit/rule/v2/info": { + "/rum/application/remote-config/history/list": { "post": { - "operationId": "monit-rule-read-info-v2", - "summary": "Get alert rule detail (V2)", - "description": "Return the full V2 configuration of an alert rule by ID, including lifecycle v2 recovery and ending modes.", - "tags": [ - "Monitors/Alert rules" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Alerting Rules Read** (`monit`) |\n\n## Usage\n\n- `id` is required and must not be `0`; otherwise the call returns `InvalidParameter`.\n- A missing rule returns `InvalidParameter` (`alert rule not found`).", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-read-info-v2", - "metadata": { - "sidebarTitle": "Get alert rule detail (V2)" - } + "description": "List published remote configuration versions of a RUM application.", + "operationId": "rum-application-remote-config-read-history-list", + "requestBody": { + "content": { + "application/json": { + "example": { + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "asc": false, + "limit": 20, + "orderby": "updated_at", + "p": 0 + }, + "schema": { + "$ref": "#/components/schemas/ListRemoteConfigHistoryRequest" + } + } + }, + "required": true }, "responses": { "200": { - "description": "Success", "content": { "application/json": { + "example": { + "data": { + "has_next_page": false, + "items": [ + { + "config": { + "activation": "next_session", + "custom": { + "feature_flags": { + "checkout_v2": true + } + }, + "default": { + "defaultPrivacyLevel": "mask-user-input", + "sessionReplaySampleRate": 20, + "sessionSampleRate": 100, + "traceSampleRate": 100 + }, + "enabled": true, + "refresh_on_foreground": false, + "rules": [ + { + "match": { + "env": "production" + }, + "set": { + "defaultPrivacyLevel": "mask", + "sessionReplaySampleRate": 0, + "sessionSampleRate": 5 + } + } + ] + }, + "content_hash": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08", + "reason": "Tighten replay sampling for the Q4 launch", + "updated_at": 1773398630657, + "updated_by": 4441703362131, + "updated_by_name": "Alice Zhang", + "version": 8 + }, + { + "config": { + "activation": "next_session", + "custom": { + "feature_flags": { + "checkout_v2": true + } + }, + "default": { + "defaultPrivacyLevel": "mask-user-input", + "sessionReplaySampleRate": 20, + "sessionSampleRate": 100, + "traceSampleRate": 100 + }, + "enabled": true, + "refresh_on_foreground": false, + "rules": [ + { + "match": { + "env": "production" + }, + "set": { + "defaultPrivacyLevel": "mask", + "sessionReplaySampleRate": 0, + "sessionSampleRate": 5 + } + } + ] + }, + "content_hash": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08", + "reason": "", + "updated_at": 1772398630657, + "updated_by": 4441703362131, + "updated_by_name": "Alice Zhang", + "version": 7 + } + ], + "total": 3 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { "allOf": [ { "$ref": "#/components/schemas/SuccessEnvelope" }, { - "type": "object", "properties": { "data": { - "$ref": "#/components/schemas/AlertRuleV2" + "$ref": "#/components/schemas/ListRemoteConfigHistoryResponse" } - } + }, + "type": "object" } ] - }, - "example": { - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", - "data": { - "id": 50001, - "account_id": 888, - "folder_id": 100, - "name": "CPU High", - "labels": {}, - "ds_type": "prometheus", - "ds_list": [ - "prometheus*" - ], - "ds_ids": [], - "enabled": true, - "debug_log_enabled": false, - "rule_configs": { - "queries": [ - { - "name": "A", - "expr": "100 - avg(cpu_usage_idle)" - } - ], - "check_threshold": { - "enabled": true, - "alerting_check_times": 3, - "alerting_window_size": 5, - "recovery_check_times": 2, - "critical": "$A > 90", - "warning": "$A > 80", - "recovery_mode": "condition_clear" - } - }, - "cron_pattern": "0 * * * * *", - "timezone": "Asia/Shanghai", - "delay_seconds": 0, - "enabled_times": [ - { - "days": [ - 1, - 2, - 3, - 4, - 5, - 6, - 0 - ], - "stime": "00:00", - "etime": "23:59" - } - ], - "annotations": {}, - "description_type": "text", - "description": "", - "channel_ids": [ - 20001 - ], - "repeat_interval": 3600, - "repeat_total": 3, - "investigation_targets": [], - "creator_id": 66, - "creator_name": "zhangsan", - "updater_id": 66, - "updater_name": "zhangsan", - "created_at": 1712000000, - "updated_at": 1712000000 - } } } - } + }, + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -44769,125 +50907,66 @@ "$ref": "#/components/responses/ServerError" } }, + "summary": "List remote config history", + "tags": [ + "RUM/Applications" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Newest first by default (`orderby=updated_at`, `asc=false`).\n- `content_hash` and `equivalent_to` identify versions whose content is identical, so the console can say \"this is an earlier version's content\" instead of showing a false difference.", + "href": "/en/api-reference/rum/applications/rum-application-remote-config-read-history-list", + "metadata": { + "sidebarTitle": "List remote config history" + } + } + } + }, + "/rum/application/remote-config/history/revert": { + "post": { + "description": "Republish an earlier remote configuration version's content as a new version.", + "operationId": "rum-application-remote-config-write-history-revert", "requestBody": { - "required": true, "content": { "application/json": { - "schema": { - "$ref": "#/components/schemas/RuleIDRequest" - }, "example": { - "id": 50001 + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "reason": "Rolled back after the Q4 launch incident", + "version": 7 + }, + "schema": { + "$ref": "#/components/schemas/RevertRemoteConfigRequest" } } - } - } - } - }, - "/monit/rule/v2/create": { - "post": { - "operationId": "monit-rule-write-create-v2", - "summary": "Create alert rule (V2)", - "description": "Create a new V2 alert rule. Returns the created rule with its assigned ID.", - "tags": [ - "Monitors/Alert rules" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- `name`, `ds_type`, `enabled`, `cron_pattern`, and `rule_configs.queries` are required; either `ds_list` (supports wildcards) or `ds_ids` must be non-empty.\n- `enabled` must be passed explicitly (including `false`); omitting it returns `InvalidParameter`.\n- `id`, `account_id`, `creator_*`, `updater_*`, `created_at`, and `updated_at` are assigned by the server; client-supplied values are ignored.\n- `name` must be unique within `folder_id`; a duplicate returns `InvalidParameter`.\n- `channel_ids` can be empty; alerts will then route through the global integration.\n- The request body tolerates additional unknown fields (forward compatibility); they are ignored.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-create-v2", - "metadata": { - "sidebarTitle": "Create alert rule (V2)" - } + }, + "required": true }, "responses": { "200": { - "description": "Success", "content": { "application/json": { + "example": { + "data": { + "version": 9 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { "allOf": [ { "$ref": "#/components/schemas/SuccessEnvelope" }, { - "type": "object", "properties": { "data": { - "$ref": "#/components/schemas/AlertRuleV2" + "$ref": "#/components/schemas/RevertRemoteConfigResponse" } - } + }, + "type": "object" } ] - }, - "example": { - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", - "data": { - "id": 50001, - "account_id": 888, - "folder_id": 100, - "name": "CPU High", - "labels": {}, - "ds_type": "prometheus", - "ds_list": [ - "prometheus*" - ], - "ds_ids": [], - "enabled": true, - "debug_log_enabled": false, - "rule_configs": { - "queries": [ - { - "name": "A", - "expr": "100 - avg(cpu_usage_idle)" - } - ], - "check_threshold": { - "enabled": true, - "alerting_check_times": 3, - "alerting_window_size": 5, - "recovery_check_times": 2, - "critical": "$A > 90", - "warning": "$A > 80", - "recovery_mode": "condition_clear" - } - }, - "cron_pattern": "0 * * * * *", - "timezone": "Asia/Shanghai", - "delay_seconds": 0, - "enabled_times": [ - { - "days": [ - 1, - 2, - 3, - 4, - 5, - 6, - 0 - ], - "stime": "00:00", - "etime": "23:59" - } - ], - "annotations": {}, - "description_type": "text", - "description": "", - "channel_ids": [ - 20001 - ], - "repeat_interval": 3600, - "repeat_total": 3, - "investigation_targets": [], - "creator_id": 66, - "creator_name": "zhangsan", - "updater_id": 66, - "updater_name": "zhangsan", - "created_at": 1712000000, - "updated_at": 1712000000 - } } } - } + }, + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -44902,152 +50981,72 @@ "$ref": "#/components/responses/ServerError" } }, + "summary": "Revert remote config", + "tags": [ + "RUM/Applications" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- History is never rewritten: the revert publishes the earlier version's content under a NEW version number.\n- An empty `reason` is filled in by the console as `rolled back to vN`.", + "href": "/en/api-reference/rum/applications/rum-application-remote-config-write-history-revert", + "metadata": { + "sidebarTitle": "Revert remote config" + } + } + } + }, + "/rum/application/remote-config/preview": { + "post": { + "description": "Evaluate a draft remote configuration against a client context without publishing it.", + "operationId": "rum-application-remote-config-read-preview", "requestBody": { - "required": true, "content": { "application/json": { - "schema": { - "$ref": "#/components/schemas/AlertRuleV2" - }, "example": { - "folder_id": 100, - "name": "CPU High", - "ds_type": "prometheus", - "ds_list": [ - "prometheus*" - ], - "enabled": true, - "cron_pattern": "0 * * * * *", - "channel_ids": [ - 20001 - ], - "rule_configs": { - "queries": [ - { - "name": "A", - "expr": "100 - avg(cpu_usage_idle)" - } - ], - "check_threshold": { - "enabled": true, - "alerting_check_times": 3, - "alerting_window_size": 5, - "recovery_check_times": 2, - "critical": "$A > 90", - "warning": "$A > 80", - "recovery_mode": "condition_clear" - } - } + "app_version": "2.14.3", + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "env": "production", + "sdk": "web@2.4.1" + }, + "schema": { + "$ref": "#/components/schemas/PreviewRemoteConfigRequest" } } - } - } - } - }, - "/monit/rule/v2/update": { - "post": { - "operationId": "monit-rule-write-update-v2", - "summary": "Update alert rule (V2)", - "description": "Replace an alert rule's V2 configuration in full by ID. Returns the updated rule.", - "tags": [ - "Monitors/Alert rules" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Alerting Rules Manage** (`monit`) |\n\n## Usage\n\n- `id` is required and the rule must already exist; otherwise the call returns `InvalidParameter`.\n- This is a full-field replacement: except for the cases below, fields you omit are stored as zero values. Fetch the full configuration via `/monit/rule/v2/info` before modifying it.\n- `enabled` must be passed explicitly (including `false`); omitting it returns `InvalidParameter`. Setting it to `false` clears the rule's active alerts.\n- `investigation_targets` is the exception: omit it to keep the current value, pass `[]` to clear, or pass a value to replace it entirely.\n- `folder_id` cannot be changed through this operation; use `/monit/rule/move` to move the rule to another folder.\n- `account_id`, `creator_*`, `updater_*`, `created_at`, and `updated_at` are maintained by the server; client-supplied values are ignored.\n- `name` must be unique within `folder_id`; a duplicate returns `InvalidParameter`.\n- The request body tolerates additional unknown fields (forward compatibility); they are ignored.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/monitors/alert-rules/monit-rule-write-update-v2", - "metadata": { - "sidebarTitle": "Update alert rule (V2)" - } + }, + "required": true }, "responses": { "200": { - "description": "Success", "content": { "application/json": { + "example": { + "data": { + "hit_rule_index": 0, + "values": { + "defaultPrivacyLevel": "mask", + "sessionReplaySampleRate": 0, + "sessionSampleRate": 5 + } + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { "allOf": [ { "$ref": "#/components/schemas/SuccessEnvelope" }, { - "type": "object", "properties": { "data": { - "$ref": "#/components/schemas/AlertRuleV2" + "$ref": "#/components/schemas/PreviewRemoteConfigResponse" } - } + }, + "type": "object" } ] - }, - "example": { - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4", - "data": { - "id": 50001, - "account_id": 888, - "folder_id": 100, - "name": "CPU High", - "labels": {}, - "ds_type": "prometheus", - "ds_list": [ - "prometheus*" - ], - "ds_ids": [], - "enabled": true, - "debug_log_enabled": false, - "rule_configs": { - "queries": [ - { - "name": "A", - "expr": "100 - avg(cpu_usage_idle)" - } - ], - "check_threshold": { - "enabled": true, - "alerting_check_times": 3, - "alerting_window_size": 5, - "recovery_check_times": 2, - "critical": "$A > 95", - "warning": "$A > 80", - "recovery_mode": "condition_clear" - } - }, - "cron_pattern": "0 * * * * *", - "timezone": "Asia/Shanghai", - "delay_seconds": 0, - "enabled_times": [ - { - "days": [ - 1, - 2, - 3, - 4, - 5, - 6, - 0 - ], - "stime": "00:00", - "etime": "23:59" - } - ], - "annotations": {}, - "description_type": "text", - "description": "", - "channel_ids": [ - 20001 - ], - "repeat_interval": 3600, - "repeat_total": 3, - "investigation_targets": [], - "creator_id": 66, - "creator_name": "zhangsan", - "updater_id": 66, - "updater_name": "zhangsan", - "created_at": 1712000000, - "updated_at": 1712003600 - } } } - } + }, + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -45062,59 +51061,60 @@ "$ref": "#/components/responses/ServerError" } }, - "requestBody": { - "required": true, - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AlertRuleV2" - }, - "example": { - "folder_id": 100, - "name": "CPU High", - "ds_type": "prometheus", - "ds_list": [ - "prometheus*" - ], - "enabled": true, - "cron_pattern": "0 * * * * *", - "channel_ids": [ - 20001 - ], - "rule_configs": { - "queries": [ - { - "name": "A", - "expr": "100 - avg(cpu_usage_idle)" - } - ], - "check_threshold": { - "enabled": true, - "alerting_check_times": 3, - "alerting_window_size": 5, - "recovery_check_times": 2, - "critical": "$A > 95", - "warning": "$A > 80", - "recovery_mode": "condition_clear" - } - }, - "id": 50001 - } - } + "summary": "Preview remote config", + "tags": [ + "RUM/Applications" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Runs the same matcher as the engine, so the result matches what production clients receive.\n- Omit `config` to preview the currently live configuration.", + "href": "/en/api-reference/rum/applications/rum-application-remote-config-read-preview", + "metadata": { + "sidebarTitle": "Preview remote config" } } } }, - "/oncall/license/list": { + "/rum/application/remote-config/update": { "post": { - "description": "List people with active fixed or temporary On-call licenses in the current account.", - "operationId": "oncall-license-read-license-list", + "description": "Publish a complete new remote configuration version for a RUM application.", + "operationId": "rum-application-remote-config-write-update", "requestBody": { "content": { "application/json": { - "example": {}, + "example": { + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "config": { + "activation": "next_session", + "custom": { + "feature_flags": { + "checkout_v2": true + } + }, + "default": { + "defaultPrivacyLevel": "mask-user-input", + "sessionReplaySampleRate": 20, + "sessionSampleRate": 100, + "traceSampleRate": 100 + }, + "enabled": true, + "refresh_on_foreground": false, + "rules": [ + { + "match": { + "env": "production" + }, + "set": { + "defaultPrivacyLevel": "mask", + "sessionReplaySampleRate": 0, + "sessionSampleRate": 5 + } + } + ] + }, + "reason": "Tighten replay sampling for the Q4 launch" + }, "schema": { - "$ref": "#/components/schemas/EmptyRequest" + "$ref": "#/components/schemas/UpdateRemoteConfigRequest" } } }, @@ -45126,27 +51126,9 @@ "application/json": { "example": { "data": { - "items": [ - { - "created_at": 1719792000, - "person_id": 80011, - "person_name": "Yuki Zhang", - "type": "fixed", - "updated_at": 1719878400, - "updated_by": 80001 - }, - { - "created_at": 0, - "person_id": 80012, - "person_name": "Alex Chen", - "type": "temporary", - "updated_at": 0, - "updated_by": 0 - } - ], - "total": 2 + "version": 8 }, - "request_id": "01J0D5Y31GY2TWAHRP3Q8K4M6N" + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ @@ -45156,7 +51138,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/LicenseListResponse" + "$ref": "#/components/schemas/UpdateRemoteConfigResponse" } }, "type": "object" @@ -45180,34 +51162,55 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List On-call licenses", + "summary": "Update remote config", "tags": [ - "On-call/Licenses" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `items` contains only people with an active fixed or temporary On-call license.\n- For temporary licenses, `updated_by`, `created_at`, and `updated_at` are `0`.", - "href": "/en/api-reference/on-call/licenses/oncall-license-read-license-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- The client sends the complete object, not a patch: rule order is the priority, so a partial update has no unambiguous interpretation.\n- Each call allocates a new version and records a history row in the same transaction as the write.\n- Call `POST /rum/application/remote-config/preview` first to check what clients would receive.", + "href": "/en/api-reference/rum/applications/rum-application-remote-config-write-update", "metadata": { - "sidebarTitle": "List On-call licenses" + "sidebarTitle": "Update remote config" } } } }, - "/person/infos": { + "/rum/application/update": { "post": { - "description": "Return profile information for a batch of person IDs (members or accounts).", - "operationId": "personInfos", + "description": "Update an existing RUM application. All fields except `application_id` are optional — only provided fields are updated.", + "operationId": "rum-application-write-update", "requestBody": { "content": { "application/json": { "example": { - "person_ids": [ - 2476444212131, - 3790925372131 - ] + "alerting": { + "channel_ids": [ + 2490121812131 + ], + "enabled": true + }, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "application_name": "My Web App v2", + "links": { + "enabled": true, + "systems": [ + { + "enabled": true, + "event_types": [ + "crash", + "error" + ], + "icon_color": "#0F766E", + "icon_text": "S3", + "id": "s3-crash-logs", + "name": "S3 Crash Logs", + "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" + } + ] + } }, "schema": { - "$ref": "#/components/schemas/PersonInfosRequest" + "$ref": "#/components/schemas/RumApplicationUpdateRequest" } } }, @@ -45218,33 +51221,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 2451002751131, - "as": "member", - "avatar": "/image/avatar1.png", - "email": "alice@example.com", - "email_verified": true, - "locale": "zh-CN", - "person_id": 2476444212131, - "person_name": "Alice", - "phone_verified": false, - "status": "enabled", - "time_zone": "Asia/Shanghai" - }, - { - "account_id": 2451002751131, - "as": "member", - "email": "bob@example.com", - "email_verified": true, - "person_id": 3790925372131, - "person_name": "Bob", - "phone_verified": false, - "status": "enabled" - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45255,7 +51232,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PersonInfosResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -45279,31 +51256,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Batch get persons", + "summary": "Update application", "tags": [ - "Platform/Members" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/platform/members/person-infos", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- `links.systems[].url` must start with `http` or `https`; `${var}` tokens are resolved from RUM event context.\n- `links.systems[].event_types` accepts: `crash`, `error`, `view`, `action`, `resource`, `session`, `all`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/applications/rum-application-write-update", "metadata": { - "sidebarTitle": "Batch get persons" + "sidebarTitle": "Update application" } } } }, - "/role/delete": { + "/rum/application/webhook/test": { "post": { - "description": "Delete a custom role. While members still hold the role, the call fails with `ReferenceExist` unless `is_force` is true.", - "operationId": "role-write-delete", + "description": "Send a sample RUM alert event to verify an application's webhook URL.", + "operationId": "rum-application-webhook-test", "requestBody": { "content": { "application/json": { "example": { - "role_id": 150 + "application_id": "rum-app-prod", + "webhook_url": "https://hooks.example.com/rum-alerts" }, "schema": { - "$ref": "#/components/schemas/RoleDeleteRequest" + "$ref": "#/components/schemas/RumWebhookTestRequest" } } }, @@ -45314,7 +51292,11 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "message": "ok", + "ok": true, + "status_code": 200 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45325,7 +51307,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PlatformEmptyObject" + "$ref": "#/components/schemas/RumWebhookTestResponse" } }, "type": "object" @@ -45352,31 +51334,40 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete a role", + "summary": "Test application webhook", "tags": [ - "Platform/Roles & permissions" + "RUM/Applications" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Built-in roles are synthetic and are never deleted; the call is a no-op for them.\n- While any member still holds the role, the default (`is_force=false`) call fails with error code `ReferenceExist` and the holders listed in `data.refs`. Set `is_force=true` to revoke the role from all holders and delete it in one call.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/platform/roles-permissions/role-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- The endpoint validates the URL before sending the sample event.\n- A failed delivery still returns HTTP 200 with `ok=false` and the delivery error in `message`.", + "href": "/en/api-reference/rum/applications/rum-application-webhook-test", "metadata": { - "sidebarTitle": "Delete a role" + "sidebarTitle": "Test application webhook" } } } }, - "/role/disable": { + "/rum/data/query": { "post": { - "description": "Disable a custom role to prevent it from granting permissions.", - "operationId": "role-write-disable", + "description": "Run one or more SQL-style RUM data queries over a bounded time range.", + "operationId": "rum-read-data-query", "requestBody": { "content": { "application/json": { "example": { - "role_id": 150 + "end_time": 1712707200000, + "queries": [ + { + "format": "table", + "id": "errors_by_type", + "sql": "SELECT error.type, count(*) AS errors FROM error GROUP BY error.type ORDER BY errors DESC LIMIT 10", + "time_zone": "Asia/Shanghai" + } + ], + "start_time": 1712620800000 }, "schema": { - "$ref": "#/components/schemas/RoleIDRequest" + "$ref": "#/components/schemas/RumDataQueryRequest" } } }, @@ -45387,7 +51378,34 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "errors_by_type": { + "data": { + "fields": [ + { + "name": "error.type", + "nullable": false, + "type": "String" + }, + { + "name": "errors", + "nullable": false, + "type": "UInt64" + } + ], + "values": [ + [ + "TypeError", + 1523 + ], + [ + "ReferenceError", + 342 + ] + ] + } + } + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45398,7 +51416,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PlatformEmptyObject" + "$ref": "#/components/schemas/RumDataQueryResponse" } }, "type": "object" @@ -45415,9 +51433,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -45425,31 +51440,61 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable a role", + "summary": "Query RUM data", "tags": [ - "Platform/Roles & permissions" + "RUM/Data query" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Members who held this role lose its permissions immediately.\n- Built-in roles always remain enabled; enabling or disabling them is a silent no-op.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/platform/roles-permissions/role-write-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Send 1 to 10 queries in one request; each query `id` becomes a key in the response object.\n- `start_time` and `end_time` are required Unix epoch milliseconds. The maximum time range is 31 days.\n- Use `format: table` for tabular results, or `format: time_series` for bucketed time-series results.\n- For `time_series`, `interval` defaults to 3600 seconds and `max_points` defaults to 1226 when omitted.\n- `search_after_ctx` is returned by paginated table queries and can be sent back to continue scanning.", + "href": "/en/api-reference/rum/data-query/rum-read-data-query", "metadata": { - "sidebarTitle": "Disable a role" + "sidebarTitle": "Query RUM data" } } } }, - "/role/enable": { + "/rum/error-ingestion/rules/create": { "post": { - "description": "Re-enable a previously disabled custom role.", - "operationId": "role-write-enable", + "description": "Create a new error ingestion rule that filters which errors are stored.", + "operationId": "rum-error-ingestion-rules-create", "requestBody": { "content": { "application/json": { "example": { - "role_id": 150 + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "description": "Only ingest TypeError/ReferenceError from production, excluding Safari.", + "filters": [ + [ + { + "key": "error.env", + "oper": "IN", + "vals": [ + "production" + ] + }, + { + "key": "error.error_type", + "oper": "IN", + "vals": [ + "TypeError", + "ReferenceError" + ] + } + ], + [ + { + "key": "error.browser_name", + "oper": "NOTIN", + "vals": [ + "Safari" + ] + } + ] + ], + "rule_name": "Production console errors" }, "schema": { - "$ref": "#/components/schemas/RoleIDRequest" + "$ref": "#/components/schemas/RumErrorIngestionCreateRequest" } } }, @@ -45460,7 +51505,10 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "rule_id": "9spXEVoMeZWujjz25yrgTe", + "rule_name": "Production console errors" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45471,7 +51519,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PlatformEmptyObject" + "$ref": "#/components/schemas/RumErrorIngestionCreateResponse" } }, "type": "object" @@ -45488,9 +51536,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -45498,31 +51543,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable a role", + "summary": "Create an error ingestion rule", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Built-in roles always remain enabled; enabling or disabling them is a silent no-op.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/platform/roles-permissions/role-write-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Create, update, enable, disable, and delete all snapshot the application's full current rule set into history first, so `history/list` reflects every mutation.\n- Every condition key in `filters` must be one of the supported `error.*` fields or a `context.*` path; unsupported keys are rejected with `InvalidParameter`.\n- New rules are created with status `enabled`; call `disable` afterward if the rule should start inactive.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-create", "metadata": { - "sidebarTitle": "Enable a role" + "sidebarTitle": "Create an error ingestion rule" } } } }, - "/role/info": { + "/rum/error-ingestion/rules/delete": { "post": { - "description": "Return the detail of a single role by its ID.", - "operationId": "role-read-info", + "description": "Delete an error ingestion rule from a RUM application.", + "operationId": "rum-error-ingestion-rules-delete", "requestBody": { "content": { "application/json": { "example": { - "role_id": 2 + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "rule_id": "9spXEVoMeZWujjz25yrgTe" }, "schema": { - "$ref": "#/components/schemas/RoleInfoRequest" + "$ref": "#/components/schemas/RumErrorIngestionRuleIDRequest" } } }, @@ -45533,20 +51579,7 @@ "content": { "application/json": { "example": { - "data": { - "created_at": 1700000000, - "description": "Account admin with all permissions.", - "editable": false, - "permission_ids": [ - 101, - 102, - 201 - ], - "role_id": 2, - "role_name": "Account Admin", - "status": "enabled", - "updated_at": 1700000000 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45557,7 +51590,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RoleItem" + "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" } }, "type": "object" @@ -45581,32 +51614,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get role detail", + "summary": "Delete an error ingestion rule", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/platform/roles-permissions/role-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The rule disappears from `list` immediately, but the enabled-rule set used for filtering is cached for up to 5 seconds, so errors ingested shortly after deletion can still be matched against it.\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-delete", "metadata": { - "sidebarTitle": "Get role detail" + "sidebarTitle": "Delete an error ingestion rule" } } } }, - "/role/list": { + "/rum/error-ingestion/rules/disable": { "post": { - "description": "Return all custom and built-in roles for the current account.", - "operationId": "role-read-list", + "description": "Disable an error ingestion rule without deleting it.", + "operationId": "rum-error-ingestion-rules-disable", "requestBody": { "content": { "application/json": { "example": { - "asc": false, - "orderby": "created_at" + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "rule_id": "9spXEVoMeZWujjz25yrgTe" }, "schema": { - "$ref": "#/components/schemas/RoleListRequest" + "$ref": "#/components/schemas/RumErrorIngestionRuleIDRequest" } } }, @@ -45617,21 +51650,7 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "created_at": 1700000000, - "description": "", - "editable": false, - "permission_ids": [], - "role_id": 2, - "role_name": "Account Admin", - "status": "enabled", - "updated_at": 1700000000 - } - ], - "total": 3 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45642,7 +51661,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RoleListResponse" + "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" } }, "type": "object" @@ -45666,35 +51685,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List roles", + "summary": "Disable an error ingestion rule", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Built-in roles (`editable: false`) cannot be modified or deleted.", - "href": "/en/api-reference/platform/roles-permissions/role-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- A disabled rule is kept and still returned by `list`, but is skipped when matching incoming errors.\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-disable", "metadata": { - "sidebarTitle": "List roles" + "sidebarTitle": "Disable an error ingestion rule" } } } }, - "/role/member/grant": { + "/rum/error-ingestion/rules/enable": { "post": { - "description": "Assign a role to one or more members, giving them its permissions.", - "operationId": "role-write-grant-role", + "description": "Re-enable a previously disabled error ingestion rule.", + "operationId": "rum-error-ingestion-rules-enable", "requestBody": { "content": { "application/json": { "example": { - "member_ids": [ - 80011, - 80012 - ], - "role_id": 150 + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "rule_id": "9spXEVoMeZWujjz25yrgTe" }, "schema": { - "$ref": "#/components/schemas/RoleGrantRequest" + "$ref": "#/components/schemas/RumErrorIngestionRuleIDRequest" } } }, @@ -45716,7 +51732,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PlatformEmptyObject" + "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" } }, "type": "object" @@ -45733,9 +51749,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -45743,34 +51756,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Grant role to members", + "summary": "Enable an error ingestion rule", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Members who already have the role are silently skipped.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/platform/roles-permissions/role-write-grant-role", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-enable", "metadata": { - "sidebarTitle": "Grant role to members" + "sidebarTitle": "Enable an error ingestion rule" } } } }, - "/role/member/revoke": { + "/rum/error-ingestion/rules/history/list": { "post": { - "description": "Remove a role from one or more members, revoking the permissions it granted.", - "operationId": "role-write-revoke-role", + "description": "Return paginated snapshots of an application's error ingestion rule history.", + "operationId": "rum-error-ingestion-rules-history-list", "requestBody": { "content": { "application/json": { "example": { - "member_ids": [ - 80011 - ], - "role_id": 150 + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "asc": false, + "limit": 20, + "orderby": "updated_at", + "p": 0 }, "schema": { - "$ref": "#/components/schemas/RoleGrantRequest" + "$ref": "#/components/schemas/RumErrorIngestionHistoryListRequest" } } }, @@ -45781,7 +51795,69 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "has_next_page": false, + "items": [ + { + "rules": [ + { + "account_id": 20001, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "created_at": 1786000000000, + "created_by": 1001, + "deleted_at": 0, + "description": "Only ingest TypeError/ReferenceError from production, excluding Safari.", + "filters": [ + [ + { + "key": "error.env", + "oper": "IN", + "vals": [ + "production" + ] + }, + { + "key": "error.error_type", + "oper": "IN", + "vals": [ + "TypeError", + "ReferenceError" + ] + } + ], + [ + { + "key": "error.browser_name", + "oper": "NOTIN", + "vals": [ + "Safari" + ] + } + ] + ], + "id": 1044, + "rule_id": "9spXEVoMeZWujjz25yrgTe", + "rule_name": "Production console errors", + "status": "enabled", + "updated_at": 1786000000000, + "updated_by": 1001 + } + ], + "updated_at": 1786003600000, + "updated_by": 1001, + "updated_by_name": "Alice Chen", + "version": 2 + }, + { + "rules": [], + "updated_at": 1786000000000, + "updated_by": 1001, + "updated_by_name": "Alice Chen", + "version": 1 + } + ], + "total": 2 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45792,7 +51868,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PlatformEmptyObject" + "$ref": "#/components/schemas/RumErrorIngestionHistoryListResponse" } }, "type": "object" @@ -45809,9 +51885,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -45819,33 +51892,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Revoke role from members", + "summary": "List error ingestion rule history", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Members who don't have the role are silently skipped.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/platform/roles-permissions/role-write-revoke-role", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- One history item is a full snapshot of every rule for the application at that point in time, not a diff of a single rule.\n- `p` is a zero-based page number, not a byte offset — the server computes `offset = p * limit` internally.\n- `orderby` accepts `updated_at` or `version`; any other value silently falls back to `updated_at`.\n- `limit` defaults to 20 and is capped at 100 server-side; values above 100 are silently clamped, values of 0 or below fall back to the default.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-history-list", "metadata": { - "sidebarTitle": "Revoke role from members" + "sidebarTitle": "List error ingestion rule history" } } } }, - "/role/permission/factor/list": { + "/rum/error-ingestion/rules/history/revert": { "post": { - "description": "Return all permission factors (API, button, menu, URL, visit) granted to the calling member, optionally filtered by type. Requires a member-scoped credential — calls authenticated as the account principal (e.g. an account-level app key) are rejected with a 400, because the account principal implicitly holds every permission.", - "operationId": "role-read-list-permission-factor", + "description": "Restore an application's entire rule set to a prior history version.", + "operationId": "rum-error-ingestion-rules-history-revert", "requestBody": { "content": { "application/json": { "example": { - "factor_types": [ - "api" - ] + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "version": 2 }, "schema": { - "$ref": "#/components/schemas/PermissionFactorListRequest" + "$ref": "#/components/schemas/RumErrorIngestionRevertRequest" } } }, @@ -45856,13 +51928,7 @@ "content": { "application/json": { "example": { - "data": [ - { - "factor_name": "template:read:info", - "factor_type": "api", - "source": "system" - } - ], + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -45873,7 +51939,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PermissionFactorListResponse" + "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" } }, "type": "object" @@ -45897,34 +51963,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List permission factors", + "summary": "Revert error ingestion rules to a history version", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — but the credential must belong to a member; account-principal credentials (e.g. an account-level app key) are rejected with a 400 |\n\n## Usage\n\n- Permission factors are the fine-grained controls that make up each permission.\n- `factor_types` accepts: `api`, `button`, `visit`, `menu`, `url`.", - "href": "/en/api-reference/platform/roles-permissions/role-read-list-permission-factor", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Revert replaces the entire rule set for the application — rules created after the target version are removed, not merged.\n- The current state is snapshotted into history before the revert runs, so a revert can itself be undone by reverting again.\n- Returns `InvalidParameter` (not `ResourceNotFound`) when `version` doesn't exist for the application.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-history-revert", "metadata": { - "sidebarTitle": "List permission factors" + "sidebarTitle": "Revert error ingestion rules to a history version" } } } }, - "/role/permission/list": { + "/rum/error-ingestion/rules/list": { "post": { - "description": "Return all available permissions, optionally filtered to those granted to specific roles.", - "operationId": "role-read-list-permission", + "description": "Return every error ingestion rule configured for a RUM application.", + "operationId": "rum-error-ingestion-rules-list", "requestBody": { "content": { "application/json": { "example": { - "role_ids": [ - 150 - ], - "with_all": true + "application_id": "WoyQQ3BohkdtPivubEvE8o" }, "schema": { - "$ref": "#/components/schemas/RolePermissionListRequest" + "$ref": "#/components/schemas/RumErrorIngestionListRequest" } } }, @@ -45938,15 +52001,40 @@ "data": { "items": [ { - "class": "On-call", - "description": "View notification templates", - "id": 501, - "is_granted": true, - "permission_name": "Templates Read", - "permission_type": "read", - "scope": "on-call", - "source": "system", - "status": "enabled" + "created_at": 1786000000000, + "description": "Only ingest TypeError/ReferenceError from production, excluding Safari.", + "filters": [ + [ + { + "key": "error.env", + "oper": "IN", + "vals": [ + "production" + ] + }, + { + "key": "error.error_type", + "oper": "IN", + "vals": [ + "TypeError", + "ReferenceError" + ] + } + ], + [ + { + "key": "error.browser_name", + "oper": "NOTIN", + "vals": [ + "Safari" + ] + } + ] + ], + "rule_id": "9spXEVoMeZWujjz25yrgTe", + "rule_name": "Production console errors", + "status": "enabled", + "updated_at": 1786003600000 } ] }, @@ -45960,7 +52048,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RolePermissionListResponse" + "$ref": "#/components/schemas/RumErrorIngestionListResponse" } }, "type": "object" @@ -45984,36 +52072,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List permissions", + "summary": "List error ingestion rules", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Pass `role_ids` to filter permissions to those granted to those roles.\n- Pass `with_all: true` to include all permissions regardless of role filter, with `is_granted` set to indicate which are granted to the specified roles.", - "href": "/en/api-reference/platform/roles-permissions/role-read-list-permission", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Deleted rules are excluded; only rules with status `enabled` or `disabled` are returned.\n- Rules are ordered newest-created first.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-list", "metadata": { - "sidebarTitle": "List permissions" + "sidebarTitle": "List error ingestion rules" } } } }, - "/role/upsert": { + "/rum/error-ingestion/rules/update": { "post": { - "description": "Create a new custom role or update an existing one. Pass `role_id` to update.", - "operationId": "role-write-upsert", + "description": "Update the name, description, or filters of an error ingestion rule.", + "operationId": "rum-error-ingestion-rules-update", "requestBody": { "content": { "application/json": { "example": { - "description": "Manage on-call rotations and incidents.", - "permission_ids": [ - 501, - 502 - ], - "role_name": "On-call Manager" + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "description": "Now also excludes staging traffic.", + "rule_id": "9spXEVoMeZWujjz25yrgTe" }, "schema": { - "$ref": "#/components/schemas/RoleUpsertRequest" + "$ref": "#/components/schemas/RumErrorIngestionUpdateRequest" } } }, @@ -46024,10 +52109,7 @@ "content": { "application/json": { "example": { - "data": { - "role_id": 150, - "role_name": "On-call Manager" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -46038,7 +52120,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RoleUpsertResponse" + "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" } }, "type": "object" @@ -46055,9 +52137,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -46065,31 +52144,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create or update a role", + "summary": "Update an error ingestion rule", "tags": [ - "Platform/Roles & permissions" + "RUM/Error ingestion rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Roles Manage** (`organization`) |\n\n## Usage\n\n- Omit `role_id` (or set to 0) to create; pass an existing ID to update.\n- `role_name` must be 1–39 characters and unique within the account.\n- `permission_ids` sets the full permission set for the role, replacing any previous assignment.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/platform/roles-permissions/role-write-upsert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Only fields present in the request are changed; omitted fields keep their current value.\n- Calling update with no fields set is a no-op that still returns success.\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-update", "metadata": { - "sidebarTitle": "Create or update a role" + "sidebarTitle": "Update an error ingestion rule" } } } }, - "/route/info": { + "/rum/facet/count": { "post": { - "description": "Retrieve the routing rule configuration for a specific integration. Returns null when the integration has no routing rule configured.", - "operationId": "routeInfo", + "description": "Return the top N values for a facet field within a time range, sorted by occurrence count descending.", + "operationId": "rum-read-facet-count", "requestBody": { "content": { "application/json": { "example": { - "integration_id": 6113996590131 + "end_time": 1712707200000, + "facet_key": "error.type", + "limit": 10, + "scope": "error", + "start_time": 1712620800000 }, "schema": { - "$ref": "#/components/schemas/RouteInfoRequest" + "$ref": "#/components/schemas/RumFacetCountRequest" } } }, @@ -46101,51 +52184,20 @@ "application/json": { "example": { "data": { - "cases": [ + "items": [ { - "channel_ids": [ - 2533748993131 - ], - "fallthrough": false, - "if": [ - { - "key": "labels.check", - "oper": "IN", - "vals": [ - "cpu.idle<20%" - ] - } - ], - "routing_mode": "standard" + "count": 1523, + "facet_value": "TypeError" }, { - "channel_ids": null, - "fallthrough": false, - "if": [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Warning" - ] - } - ], - "name_mapping_label": "labels.service", - "routing_mode": "name_mapping" + "count": 342, + "facet_value": "ReferenceError" + }, + { + "count": 89, + "facet_value": "SyntaxError" } - ], - "created_at": 1774606136, - "creator_id": 3790925372131, - "default": { - "channel_ids": [ - 3521074710131 - ] - }, - "integration_id": 6113996590131, - "status": "enabled", - "updated_at": 1774606136, - "updated_by": 3790925372131, - "version": 6 + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -46157,7 +52209,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RouteItem" + "$ref": "#/components/schemas/RumFacetCountResponse" } }, "type": "object" @@ -46181,34 +52233,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get routing rule detail", + "summary": "Count facet value distribution", "tags": [ - "On-call/Channels" + "RUM/Facets" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/route-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **100 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Use `POST /rum/field/list` with `is_facet: true` to discover available `facet_key` values for each scope.\n- The `scope` must be one of: `session`, `view`, `action`, `error`, `resource`, `long_task`, `vital`, `issue`, `sourcemap`.\n- Pass `dql` to further filter events before counting. DQL syntax follows the RUM query language.\n- Pass `sql` with a WHERE-clause only (no SELECT) for SQL-style filtering.\n- Default limit is 100; maximum is 100.\n- Time range is required (`start_time` / `end_time` in Unix epoch **milliseconds**). Maximum span is 31 days.", + "href": "/en/api-reference/rum/facets/rum-read-facet-count", "metadata": { - "sidebarTitle": "Get routing rule detail" + "sidebarTitle": "Count facet value distribution" } } } }, - "/route/list": { + "/rum/field/list": { "post": { - "description": "Return routing rules for the specified integrations. Integrations without a configured rule are omitted from the response.", - "operationId": "routeList", + "description": "Return RUM field definitions, optionally filtered by scope and facet status.", + "operationId": "rum-read-field-list", "requestBody": { "content": { "application/json": { "example": { - "integration_ids": [ - 6113996590131, - 6113996590132 + "is_facet": false, + "scopes": [ + "error" ] }, "schema": { - "$ref": "#/components/schemas/ListRoutesRequest" + "$ref": "#/components/schemas/RumFieldListRequest" } } }, @@ -46222,36 +52274,23 @@ "data": { "items": [ { - "cases": [ - { - "channel_ids": [ - 2533748993131 - ], - "fallthrough": false, - "if": [ - { - "key": "labels.check", - "oper": "IN", - "vals": [ - "cpu.idle<20%" - ] - } - ], - "routing_mode": "standard" - } + "account_id": 0, + "description": "The type of the error.", + "edit_able": false, + "enum_values": [], + "field_key": "error.type", + "field_name": "Error type", + "group": "Error", + "is_facet": true, + "queryable": true, + "scopes": [ + "error" ], - "created_at": 1774606136, - "creator_id": 3790925372131, - "default": { - "channel_ids": [ - 3521074710131 - ] - }, - "integration_id": 6113996590131, - "status": "enabled", - "updated_at": 1774606136, - "updated_by": 3790925372131, - "version": 6 + "show_type": "list", + "status": "active", + "unit_family": "", + "unit_name": "", + "value_type": "string" } ] }, @@ -46265,7 +52304,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListRoutesResponse" + "$ref": "#/components/schemas/RumFieldListResponse" } }, "type": "object" @@ -46289,54 +52328,50 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List routing rules", + "summary": "List RUM fields", "tags": [ - "On-call/Channels" + "RUM/Facets" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) or **Integrations Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/route-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- This is the current field-model route for discovering RUM fields.\n- Use returned `field_key` values in RUM data queries and facet-count requests.\n- Set `is_facet: true` to return only fields that support value distribution queries.", + "href": "/en/api-reference/rum/facets/rum-read-field-list", "metadata": { - "sidebarTitle": "List routing rules" + "sidebarTitle": "List RUM fields" } } } }, - "/route/upsert": { + "/rum/issue/export": { "post": { - "description": "Create or update routing rules for an integration to direct alerts to specific channels. At least one of `cases` or `default` must be provided.", - "operationId": "routeUpsert", + "description": "Export the filtered RUM error tracking issues as a CSV file. The response is a `text/csv` stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope; non-console callers can read the `X-Export-Total` and `X-Export-Truncated` response headers.", + "operationId": "rum-issue-read-export", "requestBody": { "content": { "application/json": { "example": { - "cases": [ - { - "channel_ids": [ - 3521074710131 - ], - "fallthrough": false, - "if": [ - { - "key": "severity", - "oper": "IN", - "vals": [ - "Critical" - ] - } - ], - "routing_mode": "standard" - } + "application_ids": [ + "eWbr4xk3ZRnLabRa6unqwD" ], - "default": { - "channel_ids": [ - 3521074710131 - ] - }, - "integration_id": 6113996590131 + "console_origin": "https://console.flashcat.cloud", + "end_time": 1775961914595, + "export_fields": [ + "issue_id", + "error_type", + "error_message", + "status", + "error_count", + "session_count", + "last_seen_at" + ], + "orderby": "updated_at", + "start_time": 1772611200000, + "statuses": [ + "for_review" + ], + "time_zone": "Asia/Shanghai" }, "schema": { - "$ref": "#/components/schemas/UpsertRouteRequest" + "$ref": "#/components/schemas/RumIssueExportRequest" } } }, @@ -46345,123 +52380,30 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "text/csv": { + "example": "Issue ID,Error type,Error message,Status,Error count,Affected sessions,Last seen (Asia/Shanghai)\nNHEacQHi2DhXqobr9qPQz9,Error,Script error.,for_review,752,381,2026-04-12 10:43:59\nH8kZSmxiE7EgdyD4fCyyNa,Error,\"API ERROR: We encountered an internal error | POST /api/access/logout\",for_review,3,1,2026-04-03 12:41:24", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/EmptyResponse" - } - }, - "type": "object" - } - ] + "description": "CSV file content. The header row matches the exported columns in order; values are sanitized against spreadsheet formula injection.", + "type": "string" } } }, - "description": "Success" - }, - "400": { - "$ref": "#/components/responses/BadRequest" - }, - "401": { - "$ref": "#/components/responses/Unauthorized" - }, - "429": { - "$ref": "#/components/responses/TooManyRequests" - }, - "500": { - "$ref": "#/components/responses/ServerError" - } - }, - "summary": "Upsert routing rule", - "tags": [ - "On-call/Channels" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/channels/route-upsert", - "metadata": { - "sidebarTitle": "Upsert routing rule" - } - } - } - }, - "/rum/application/create": { - "post": { - "description": "Create a new RUM application. Returns the generated `application_id` and `client_token`.", - "operationId": "rum-application-write-create", - "requestBody": { - "content": { - "application/json": { - "example": { - "application_name": "My Web App", - "is_private": false, - "links": { - "enabled": true, - "systems": [ - { - "enabled": true, - "event_types": [ - "crash", - "error" - ], - "icon_color": "#0F766E", - "icon_text": "S3", - "id": "s3-crash-logs", - "name": "S3 Crash Logs", - "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" - } - ] - }, - "team_id": 2477033058131, - "type": "browser" + "description": "Success. CSV attachment, not a JSON envelope.", + "headers": { + "X-Export-Total": { + "description": "Total number of issues matching the filters, before the row cap.", + "schema": { + "format": "int64", + "type": "integer" + } }, - "schema": { - "$ref": "#/components/schemas/RumApplicationCreateRequest" - } - } - }, - "required": true - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "application_id": "qLpu24Dz4CAzWsESPbJYWA", - "application_name": "My Web App", - "client_token": "e090078724855a4ca168c3884880dfbc131" - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "X-Export-Truncated": { + "description": "`true` when more issues matched than the 100-row cap and the file was truncated.", "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/RumApplicationCreateResponse" - } - }, - "type": "object" - } - ] + "type": "boolean" } } - }, - "description": "Success" + } }, "400": { "$ref": "#/components/responses/BadRequest" @@ -46476,31 +52418,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create application", + "summary": "Export issues as CSV", "tags": [ - "RUM/Applications" + "RUM/Issues" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- `type` must be one of: `browser`, `ios`, `android`, `react-native`, `flutter`, `kotlin-multiplatform`, `roku`, `unity`, `miniprogram`, `harmony`, `electron`.\n- `links.systems[].url` must start with `http` or `https`; `${var}` tokens are resolved from RUM event context.\n- `links.systems[].event_types` accepts: `crash`, `error`, `view`, `action`, `resource`, `session`, `all`.\n- `client_token` is auto-generated and used to initialize the RUM SDK.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/applications/rum-application-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **200 requests/day**; **100 requests/minute**; **10 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The response is a `text/csv` stream delivered with `Content-Disposition: attachment` — it is not wrapped in the standard envelope. The filename is `rum-issues-.csv`, stamped in the requested `time_zone`. Read `X-Export-Total` and `X-Export-Truncated` response headers instead of a body field.\n- The export reads the first 100 matching rows (`ExportMaxRows`); `X-Export-Truncated` is `true` when more issues match. `p` and `limit` are ignored.\n- The request filters are exactly those of `POST /rum/issue/list` — an export is \"what I am looking at, as a file\".\n- `export_fields` names the CSV columns in the order they appear. Unknown keys are rejected with a parameter error; an empty array uses the default column set.\n- `time_zone` must be a valid IANA zone name (e.g. `Asia/Shanghai`, `UTC`); timestamps are rendered in that zone and time columns carry the zone in their header. Invalid names are rejected.\n- `console_origin` is used to build the `issue_url` column; the service cannot infer it (SaaS, on-premises and dev releases answer on different origins).\n- Every call is recorded in the account's audit log with the caller's member ID, request payload, and resulting error (if any). Do not put secrets in request fields.", + "href": "/en/api-reference/rum/issues/rum-issue-read-export", "metadata": { - "sidebarTitle": "Create application" + "sidebarTitle": "Export issues as CSV" } } } }, - "/rum/application/delete": { + "/rum/issue/info": { "post": { - "description": "Delete a RUM application by `application_id`.", - "operationId": "rum-application-write-delete", + "description": "Retrieve full details of a single issue by `issue_id`.", + "operationId": "rum-issue-read-info", "requestBody": { "content": { "application/json": { "example": { - "application_id": "qLpu24Dz4CAzWsESPbJYWA" + "issue_id": "NHEacQHi2DhXqobr9qPQz9" }, "schema": { - "$ref": "#/components/schemas/RumApplicationIDRequest" + "$ref": "#/components/schemas/RumIssueIDRequest" } } }, @@ -46511,7 +52453,44 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "age": 5078684, + "application_id": "eWbr4xk3ZRnLabRa6unqwD", + "application_name": "Flashduty DEV", + "created_at": 1770883154944, + "error": { + "message": "Script error.", + "type": "Error" + }, + "error_count": 752, + "first_seen": { + "timestamp": 1770883154944, + "version": "1.0.0" + }, + "is_crash": false, + "issue_id": "NHEacQHi2DhXqobr9qPQz9", + "last_seen": { + "timestamp": 1775961839090, + "version": "1.0.0" + }, + "resolved_at": 0, + "resolved_by": 0, + "service": "fd-console", + "session_count": 381, + "severity": "Info", + "status": "for_review", + "suspected_cause": { + "person_id": 0, + "reason": "The error message 'Script error.' typically indicates an unhandled exception in JavaScript.", + "source": "auto", + "value": "code.exception" + }, + "team_id": 2477033058131, + "updated_at": 1775961914595, + "versions": [ + "1.0.0" + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -46522,7 +52501,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/RumIssueItem" } }, "type": "object" @@ -46546,31 +52525,41 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete application", + "summary": "Get issue detail", "tags": [ - "RUM/Applications" + "RUM/Issues" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/applications/rum-application-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `team_id` is the owning application's **current** team; `POST /rum/issue/list` and `POST /rum/issue/export` report the team recorded when the issue was first seen, which differs once the application moves to another team.", + "href": "/en/api-reference/rum/issues/rum-issue-read-info", "metadata": { - "sidebarTitle": "Delete application" + "sidebarTitle": "Get issue detail" } } } }, - "/rum/application/info": { + "/rum/issue/list": { "post": { - "description": "Retrieve full details of a single RUM application by `application_id`.", - "operationId": "rum-application-read-info", + "description": "Return a paginated list of RUM error tracking issues matching the given filters.", + "operationId": "rum-issue-read-list", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o" + "application_ids": [ + "eWbr4xk3ZRnLabRa6unqwD" + ], + "end_time": 1775961914595, + "limit": 20, + "orderby": "updated_at", + "p": 1, + "start_time": 1772611200000, + "statuses": [ + "for_review" + ] }, "schema": { - "$ref": "#/components/schemas/RumApplicationIDRequest" + "$ref": "#/components/schemas/RumIssueListRequest" } } }, @@ -46582,49 +52571,86 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "alerting": { - "channel_ids": [ - 2490121812131 - ], - "enabled": true, - "integration_id": 4759595678131 - }, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "application_name": "flashcat-rum", - "client_token": "a3cea433a8685a398cdfd68f54a45e06131", - "created_at": 1746673831462, - "created_by": 4441703362131, - "is_private": true, - "links": { - "enabled": true, - "systems": [ - { - "enabled": true, - "event_types": [ - "crash", - "error" - ], - "icon_color": "#0F766E", - "icon_text": "S3", - "id": "s3-crash-logs", - "name": "S3 Crash Logs", - "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" - } - ] - }, - "no_geo": false, - "no_ip": true, - "status": "enabled", - "team_id": 2477033058131, - "tracing": { - "enabled": false, - "endpoint": "", - "open_type": "" - }, - "type": "browser", - "updated_at": 1773398630657, - "updated_by": 3790925372131 + "has_next_page": true, + "items": [ + { + "age": 5078684, + "application_id": "eWbr4xk3ZRnLabRa6unqwD", + "application_name": "Flashduty DEV", + "created_at": 1770883154944, + "error": { + "message": "Script error.", + "type": "Error" + }, + "error_count": 752, + "first_seen": { + "timestamp": 1770883154944, + "version": "1.0.0" + }, + "is_crash": false, + "issue_id": "NHEacQHi2DhXqobr9qPQz9", + "last_seen": { + "timestamp": 1775961839090, + "version": "1.0.0" + }, + "resolved_at": 0, + "resolved_by": 0, + "service": "fd-console", + "session_count": 381, + "severity": "Info", + "status": "for_review", + "suspected_cause": { + "person_id": 0, + "reason": "The error message 'Script error.' typically indicates an unhandled exception in JavaScript.", + "source": "auto", + "value": "code.exception" + }, + "team_id": 2477033058131, + "updated_at": 1775961914595, + "versions": [ + "1.0.0" + ] + }, + { + "age": 48, + "application_id": "eWbr4xk3ZRnLabRa6unqwD", + "application_name": "Flashduty DEV", + "created_at": 1775189479566, + "error": { + "message": "API ERROR: We encountered an internal error | POST /api/access/logout", + "type": "Error" + }, + "error_count": 3, + "first_seen": { + "timestamp": 1775189479566, + "version": "1.0.0" + }, + "is_crash": false, + "issue_id": "H8kZSmxiE7EgdyD4fCyyNa", + "last_seen": { + "timestamp": 1775189527762, + "version": "1.0.0" + }, + "resolved_at": 0, + "resolved_by": 0, + "service": "fd-console", + "session_count": 1, + "severity": "Info", + "status": "for_review", + "suspected_cause": { + "person_id": 0, + "reason": "The error indicates an internal server error during a POST request to /api/access/logout.", + "source": "auto", + "value": "api.failed_request" + }, + "team_id": 2477033058131, + "updated_at": 1775191284163, + "versions": [ + "1.0.0" + ] + } + ], + "total": 111 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -46636,7 +52662,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumApplicationItem" + "$ref": "#/components/schemas/RumIssueListResponse" } }, "type": "object" @@ -46660,34 +52686,52 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get application detail", + "summary": "List issues", "tags": [ - "RUM/Applications" + "RUM/Issues" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/rum/applications/rum-application-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `start_time` and `end_time` are millisecond timestamps. Maximum range: 183 days.\n- `statuses` filters by issue status. Valid values: `for_review`, `reviewed`, `ignored`, `resolved`.\n- `orderby` accepts: `created_at`, `updated_at`, `session_count`, `error_count`, `severity`.\n- Use `dql` or `sql` for advanced filtering. Cannot provide both.", + "href": "/en/api-reference/rum/issues/rum-issue-read-list", "metadata": { - "sidebarTitle": "Get application detail" + "sidebarTitle": "List issues" } } } }, - "/rum/application/infos": { + "/rum/issue/preset-severity/rules/create": { "post": { - "description": "Retrieve details for multiple RUM applications by their IDs in one request.", - "operationId": "rum-application-read-infos", + "description": "Create a new preset severity rule for a RUM application.", + "operationId": "rum-issue-preset-severity-rules-create", "requestBody": { "content": { "application/json": { "example": { - "application_ids": [ - "eWbr4xk3ZRnLabRa6unqwD", - "WoyQQ3BohkdtPivubEvE8o" - ] + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "description": "Escalate production crashes to Critical severity", + "filters": [ + [ + { + "key": "error.env", + "oper": "IN", + "vals": [ + "production" + ] + }, + { + "key": "error.is_crash", + "oper": "IN", + "vals": [ + "true" + ] + } + ] + ], + "rule_name": "Critical crash spikes", + "severity": "Critical" }, "schema": { - "$ref": "#/components/schemas/RumApplicationInfosRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleCreateRequest" } } }, @@ -46699,86 +52743,9 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "alerting": { - "channel_ids": [ - 5962711836131, - 5967875767131 - ], - "enabled": true, - "integration_id": 4759595678131 - }, - "application_id": "eWbr4xk3ZRnLabRa6unqwD", - "application_name": "Flashduty DEV", - "client_token": "ce8d1be90fc6534f89ce36ebf526765e131", - "created_at": 1742958482000, - "created_by": 2476444212131, - "is_private": false, - "links": { - "enabled": false, - "systems": [] - }, - "no_geo": false, - "no_ip": false, - "status": "enabled", - "team_id": 2477033058131, - "tracing": { - "enabled": true, - "endpoint": "https://www.tracing.com/${trace_id}", - "open_type": "popup" - }, - "type": "browser", - "updated_at": 1772096392711, - "updated_by": 3122470302131 - }, - { - "account_id": 2451002751131, - "alerting": { - "channel_ids": [ - 2490121812131 - ], - "enabled": true, - "integration_id": 4759595678131 - }, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "application_name": "flashcat-rum", - "client_token": "a3cea433a8685a398cdfd68f54a45e06131", - "created_at": 1746673831462, - "created_by": 4441703362131, - "is_private": true, - "links": { - "enabled": true, - "systems": [ - { - "enabled": true, - "event_types": [ - "crash", - "error" - ], - "icon_color": "#0F766E", - "icon_text": "S3", - "id": "s3-crash-logs", - "name": "S3 Crash Logs", - "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" - } - ] - }, - "no_geo": false, - "no_ip": true, - "status": "enabled", - "team_id": 2477033058131, - "tracing": { - "enabled": false, - "endpoint": "", - "open_type": "" - }, - "type": "browser", - "updated_at": 1773398630657, - "updated_by": 3790925372131 - } - ] + "priority": 2, + "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", + "rule_name": "Critical crash spikes" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -46790,7 +52757,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumApplicationInfosResponse" + "$ref": "#/components/schemas/RumPresetSeverityRuleCreateResponse" } }, "type": "object" @@ -46814,34 +52781,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Batch get applications", + "summary": "Create preset severity rule", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Maximum 200 IDs per request.", - "href": "/en/api-reference/rum/applications/rum-application-read-infos", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `filters.*.key` accepts only a fixed set of Error-level attributes; any other key returns `InvalidParameter`.\n- Pass at least one condition group: an empty `filters` array is accepted but produces a rule that can never match.\n- The new rule is created enabled and appended with the lowest evaluation precedence (`priority` = current max + 1); use the `reorder` operation to move it earlier.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-create", "metadata": { - "sidebarTitle": "Batch get applications" + "sidebarTitle": "Create preset severity rule" } } } }, - "/rum/application/list": { + "/rum/issue/preset-severity/rules/delete": { "post": { - "description": "Return a paginated list of RUM applications accessible to the current user.", - "operationId": "rum-application-read-list", + "description": "Delete a preset severity rule.", + "operationId": "rum-issue-preset-severity-rules-delete", "requestBody": { "content": { "application/json": { "example": { - "is_my_team": false, - "limit": 20, - "p": 1, - "query": "" + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay" }, "schema": { - "$ref": "#/components/schemas/RumApplicationListRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleIDRequest" } } }, @@ -46852,90 +52817,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": true, - "items": [ - { - "account_id": 2451002751131, - "alerting": { - "channel_ids": [ - 2490121812131 - ], - "enabled": true, - "integration_id": 4759595678131 - }, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "application_name": "flashcat-rum", - "client_token": "a3cea433a8685a398cdfd68f54a45e06131", - "created_at": 1746673831462, - "created_by": 4441703362131, - "is_private": true, - "links": { - "enabled": true, - "systems": [ - { - "enabled": true, - "event_types": [ - "crash", - "error" - ], - "icon_color": "#0F766E", - "icon_text": "S3", - "id": "s3-crash-logs", - "name": "S3 Crash Logs", - "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" - } - ] - }, - "no_geo": false, - "no_ip": true, - "status": "enabled", - "team_id": 2477033058131, - "tracing": { - "enabled": false, - "endpoint": "", - "open_type": "" - }, - "type": "browser", - "updated_at": 1773398630657, - "updated_by": 3790925372131 - }, - { - "account_id": 2451002751131, - "alerting": { - "channel_ids": [ - 5962711836131, - 5967875767131 - ], - "enabled": true, - "integration_id": 4759595678131 - }, - "application_id": "eWbr4xk3ZRnLabRa6unqwD", - "application_name": "Flashduty DEV", - "client_token": "ce8d1be90fc6534f89ce36ebf526765e131", - "created_at": 1742958482000, - "created_by": 2476444212131, - "is_private": false, - "links": { - "enabled": false, - "systems": [] - }, - "no_geo": false, - "no_ip": false, - "status": "enabled", - "team_id": 2477033058131, - "tracing": { - "enabled": true, - "endpoint": "https://www.tracing.com/${trace_id}", - "open_type": "popup" - }, - "type": "browser", - "updated_at": 1772096392711, - "updated_by": 3122470302131 - } - ], - "total": 7 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -46946,7 +52828,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumApplicationListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -46970,73 +52852,43 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List applications", + "summary": "Delete preset severity rule", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Use `is_my_team` to filter applications belonging to the current user's teams.\n- Default page size is 20, maximum is 100.\n- `orderby` accepts `created_at` or `updated_at`.", - "href": "/en/api-reference/rum/applications/rum-application-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- Deletion is a soft delete: the rule stops being listed immediately, but enabled rules are cached for up to 5 seconds, so it can still be evaluated against errors ingested shortly afterwards. Its pre-delete state remains visible via the history endpoints.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-delete", "metadata": { - "sidebarTitle": "List applications" + "sidebarTitle": "Delete preset severity rule" } } } }, - "/rum/application/remote-config/get": { + "/rum/issue/preset-severity/rules/disable": { "post": { - "description": "Retrieve the live remote configuration of a RUM application and the version it is stored under.", - "operationId": "rum-application-remote-config-read-get", - "requestBody": { - "content": { - "application/json": { - "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o" - }, - "schema": { - "$ref": "#/components/schemas/GetRemoteConfigRequest" - } - } - }, - "required": true - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "config": { - "activation": "next_session", - "custom": { - "feature_flags": { - "checkout_v2": true - } - }, - "default": { - "defaultPrivacyLevel": "mask-user-input", - "sessionReplaySampleRate": 20, - "sessionSampleRate": 100, - "traceSampleRate": 100 - }, - "enabled": true, - "refresh_on_foreground": false, - "rules": [ - { - "match": { - "env": "production" - }, - "set": { - "defaultPrivacyLevel": "mask", - "sessionReplaySampleRate": 0, - "sessionSampleRate": 5 - } - } - ] - }, - "updated_at": 1773398630657, - "version": 7 - }, + "description": "Disable a preset severity rule.", + "operationId": "rum-issue-preset-severity-rules-disable", + "requestBody": { + "content": { + "application/json": { + "example": { + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "rule_id": "TAHUYnQmXKzgMS4TFVUKvz" + }, + "schema": { + "$ref": "#/components/schemas/RumPresetSeverityRuleIDRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -47047,7 +52899,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/GetRemoteConfigResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -47071,35 +52923,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get remote config detail", + "summary": "Disable preset severity rule", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Version `0` means the application has never been configured; SDKs then run entirely on their init values.\n- A change reaches a client when its next session starts unless activation is set to `immediate`.", - "href": "/en/api-reference/rum/applications/rum-application-remote-config-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- A disabled rule is skipped during evaluation but keeps its `priority` slot; the cache can take up to 5 seconds to reflect the change.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-disable", "metadata": { - "sidebarTitle": "Get remote config detail" + "sidebarTitle": "Disable preset severity rule" } } } }, - "/rum/application/remote-config/history/list": { + "/rum/issue/preset-severity/rules/enable": { "post": { - "description": "List published remote configuration versions of a RUM application.", - "operationId": "rum-application-remote-config-read-history-list", + "description": "Enable a preset severity rule.", + "operationId": "rum-issue-preset-severity-rules-enable", "requestBody": { "content": { "application/json": { "example": { "application_id": "WoyQQ3BohkdtPivubEvE8o", - "asc": false, - "limit": 20, - "orderby": "updated_at", - "p": 0 + "rule_id": "TAHUYnQmXKzgMS4TFVUKvz" }, "schema": { - "$ref": "#/components/schemas/ListRemoteConfigHistoryRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleIDRequest" } } }, @@ -47110,84 +52959,7 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": false, - "items": [ - { - "config": { - "activation": "next_session", - "custom": { - "feature_flags": { - "checkout_v2": true - } - }, - "default": { - "defaultPrivacyLevel": "mask-user-input", - "sessionReplaySampleRate": 20, - "sessionSampleRate": 100, - "traceSampleRate": 100 - }, - "enabled": true, - "refresh_on_foreground": false, - "rules": [ - { - "match": { - "env": "production" - }, - "set": { - "defaultPrivacyLevel": "mask", - "sessionReplaySampleRate": 0, - "sessionSampleRate": 5 - } - } - ] - }, - "content_hash": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08", - "reason": "Tighten replay sampling for the Q4 launch", - "updated_at": 1773398630657, - "updated_by": 4441703362131, - "updated_by_name": "Alice Zhang", - "version": 8 - }, - { - "config": { - "activation": "next_session", - "custom": { - "feature_flags": { - "checkout_v2": true - } - }, - "default": { - "defaultPrivacyLevel": "mask-user-input", - "sessionReplaySampleRate": 20, - "sessionSampleRate": 100, - "traceSampleRate": 100 - }, - "enabled": true, - "refresh_on_foreground": false, - "rules": [ - { - "match": { - "env": "production" - }, - "set": { - "defaultPrivacyLevel": "mask", - "sessionReplaySampleRate": 0, - "sessionSampleRate": 5 - } - } - ] - }, - "content_hash": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08", - "reason": "", - "updated_at": 1772398630657, - "updated_by": 4441703362131, - "updated_by_name": "Alice Zhang", - "version": 7 - } - ], - "total": 3 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -47198,7 +52970,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ListRemoteConfigHistoryResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -47222,33 +52994,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List remote config history", + "summary": "Enable preset severity rule", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Newest first by default (`orderby=updated_at`, `asc=false`).\n- `content_hash` and `equivalent_to` identify versions whose content is identical, so the console can say \"this is an earlier version's content\" instead of showing a false difference.", - "href": "/en/api-reference/rum/applications/rum-application-remote-config-read-history-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- Enabled rules are cached for up to 5 seconds, so the effect on newly ingested errors can lag by a few seconds.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-enable", "metadata": { - "sidebarTitle": "List remote config history" + "sidebarTitle": "Enable preset severity rule" } } } }, - "/rum/application/remote-config/history/revert": { + "/rum/issue/preset-severity/rules/history/list": { "post": { - "description": "Republish an earlier remote configuration version's content as a new version.", - "operationId": "rum-application-remote-config-write-history-revert", + "description": "Return the change history of preset severity rules for a RUM application.", + "operationId": "rum-issue-preset-severity-rules-history-list", "requestBody": { "content": { "application/json": { "example": { "application_id": "WoyQQ3BohkdtPivubEvE8o", - "reason": "Rolled back after the Q4 launch incident", - "version": 7 + "limit": 20, + "p": 0 }, "schema": { - "$ref": "#/components/schemas/RevertRemoteConfigRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleHistoryListRequest" } } }, @@ -47260,7 +53032,121 @@ "application/json": { "example": { "data": { - "version": 9 + "has_next_page": false, + "items": [ + { + "rules": [ + { + "account_id": 3790925372131, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "created_at": 1785744052160, + "created_by": 3790925372131, + "deleted_at": 0, + "description": "Downgrade known extension errors to Info", + "filters": [ + [ + { + "key": "error.error_message", + "oper": "IN", + "vals": [ + "/^ResizeObserver loop.*|.*chrome-extension:\\/\\/.*/" + ] + } + ] + ], + "id": 4820, + "priority": 1, + "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", + "rule_name": "Known noisy browser extension errors", + "severity": "Info", + "status": "enabled", + "updated_at": 1785744052160, + "updated_by": 3790925372131 + }, + { + "account_id": 3790925372131, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "created_at": 1785830452160, + "created_by": 3790925372131, + "deleted_at": 0, + "description": "Escalate production crashes to Critical severity", + "filters": [ + [ + { + "key": "error.env", + "oper": "IN", + "vals": [ + "production" + ] + }, + { + "key": "error.is_crash", + "oper": "IN", + "vals": [ + "true" + ] + } + ] + ], + "id": 4821, + "priority": 2, + "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", + "rule_name": "Critical crash spikes", + "severity": "Critical", + "status": "enabled", + "updated_at": 1785830452160, + "updated_by": 3790925372131 + } + ], + "updated_at": 1785916852160, + "updated_by": 2476444212131, + "updated_by_name": "Alice Chen", + "version": 3 + }, + { + "rules": [ + { + "account_id": 3790925372131, + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "created_at": 1785744052160, + "created_by": 3790925372131, + "deleted_at": 0, + "description": "Downgrade known extension errors to Info", + "filters": [ + [ + { + "key": "error.error_message", + "oper": "IN", + "vals": [ + "/^ResizeObserver loop.*|.*chrome-extension:\\/\\/.*/" + ] + } + ] + ], + "id": 4820, + "priority": 1, + "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", + "rule_name": "Known noisy browser extension errors", + "severity": "Info", + "status": "enabled", + "updated_at": 1785744052160, + "updated_by": 3790925372131 + } + ], + "updated_at": 1785830452160, + "updated_by": 3790925372131, + "updated_by_name": "Bob Zhang", + "version": 2 + }, + { + "rules": [], + "updated_at": 1785744052160, + "updated_by": 3790925372131, + "updated_by_name": "Bob Zhang", + "version": 1 + } + ], + "total": 3 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -47272,7 +53158,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RevertRemoteConfigResponse" + "$ref": "#/components/schemas/RumPresetSeverityRuleHistoryListResponse" } }, "type": "object" @@ -47296,34 +53182,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Revert remote config", + "summary": "List preset severity rule history", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- History is never rewritten: the revert publishes the earlier version's content under a NEW version number.\n- An empty `reason` is filled in by the console as `rolled back to vN`.", - "href": "/en/api-reference/rum/applications/rum-application-remote-config-write-history-revert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Each entry is an application-level snapshot of every rule as it existed immediately *before* the mutation that produced it — not a diff. A fresh snapshot is written before every create/update/enable/disable/delete/reorder/revert call that actually changes something — an `update` carrying none of the mutable fields returns success without writing one — so `version=1` is typically an empty rule set captured just before the first rule was ever created.\n- `rules` items carry the full internal row (including `account_id`, `created_by`, `id`, `deleted_at`), which is a wider shape than the one returned by `rules/list`.\n- `limit` defaults to 20 and is silently capped at 100 rather than rejected.\n- `orderby` accepts only `updated_at` or `version`; any other value (including omitted) falls back to `updated_at` rather than erroring.\n- Results sort descending by default; pass `asc=true` for ascending order.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-history-list", "metadata": { - "sidebarTitle": "Revert remote config" + "sidebarTitle": "List preset severity rule history" } } } }, - "/rum/application/remote-config/preview": { + "/rum/issue/preset-severity/rules/history/revert": { "post": { - "description": "Evaluate a draft remote configuration against a client context without publishing it.", - "operationId": "rum-application-remote-config-read-preview", + "description": "Roll back preset severity rules to the state captured in a specific history snapshot.", + "operationId": "rum-issue-preset-severity-rules-history-revert", "requestBody": { "content": { "application/json": { "example": { - "app_version": "2.14.3", "application_id": "WoyQQ3BohkdtPivubEvE8o", - "env": "production", - "sdk": "web@2.4.1" + "version": 2 }, "schema": { - "$ref": "#/components/schemas/PreviewRemoteConfigRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleHistoryRevertRequest" } } }, @@ -47334,14 +53218,7 @@ "content": { "application/json": { "example": { - "data": { - "hit_rule_index": 0, - "values": { - "defaultPrivacyLevel": "mask", - "sessionReplaySampleRate": 0, - "sessionSampleRate": 5 - } - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -47352,7 +53229,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PreviewRemoteConfigResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -47376,60 +53253,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Preview remote config", + "summary": "Revert preset severity rules to a history snapshot", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Runs the same matcher as the engine, so the result matches what production clients receive.\n- Omit `config` to preview the currently live configuration.", - "href": "/en/api-reference/rum/applications/rum-application-remote-config-read-preview", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Replaces the entire current rule set with the snapshot's rows: `rule_id`, `priority`, `filters`, `severity`, `status`, and `created_by` are preserved from the snapshot, but `created_at`/`updated_at` are reset to the revert time and `updated_by` is set to the reverting user.\n- Returns `InvalidParameter` (not `ResourceNotFound`) when `version` does not correspond to an existing history snapshot for the application.\n- The revert itself is captured as a new history snapshot before it is applied, so a revert can itself be reverted.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-history-revert", "metadata": { - "sidebarTitle": "Preview remote config" + "sidebarTitle": "Revert preset severity rules to a history snapshot" } } } }, - "/rum/application/remote-config/update": { + "/rum/issue/preset-severity/rules/list": { "post": { - "description": "Publish a complete new remote configuration version for a RUM application.", - "operationId": "rum-application-remote-config-write-update", + "description": "Return all preset severity rules configured for a RUM application.", + "operationId": "rum-issue-preset-severity-rules-list", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "config": { - "activation": "next_session", - "custom": { - "feature_flags": { - "checkout_v2": true - } - }, - "default": { - "defaultPrivacyLevel": "mask-user-input", - "sessionReplaySampleRate": 20, - "sessionSampleRate": 100, - "traceSampleRate": 100 - }, - "enabled": true, - "refresh_on_foreground": false, - "rules": [ - { - "match": { - "env": "production" - }, - "set": { - "defaultPrivacyLevel": "mask", - "sessionReplaySampleRate": 0, - "sessionSampleRate": 5 - } - } - ] - }, - "reason": "Tighten replay sampling for the Q4 launch" + "application_id": "WoyQQ3BohkdtPivubEvE8o" }, "schema": { - "$ref": "#/components/schemas/UpdateRemoteConfigRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleListRequest" } } }, @@ -47441,7 +53289,57 @@ "application/json": { "example": { "data": { - "version": 8 + "items": [ + { + "created_at": 1785744052160, + "description": "Downgrade known extension errors to Info", + "filters": [ + [ + { + "key": "error.error_message", + "oper": "IN", + "vals": [ + "/^ResizeObserver loop.*|.*chrome-extension:\\/\\/.*/" + ] + } + ] + ], + "priority": 1, + "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", + "rule_name": "Known noisy browser extension errors", + "severity": "Info", + "status": "disabled", + "updated_at": 1785916852160 + }, + { + "created_at": 1785830452160, + "description": "Escalate production crashes to Critical severity", + "filters": [ + [ + { + "key": "error.env", + "oper": "IN", + "vals": [ + "production" + ] + }, + { + "key": "error.is_crash", + "oper": "IN", + "vals": [ + "true" + ] + } + ] + ], + "priority": 2, + "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", + "rule_name": "Critical crash spikes", + "severity": "Critical", + "status": "enabled", + "updated_at": 1785830452160 + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -47453,7 +53351,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/UpdateRemoteConfigResponse" + "$ref": "#/components/schemas/RumPresetSeverityRuleListResponse" } }, "type": "object" @@ -47477,55 +53375,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update remote config", + "summary": "List preset severity rules", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- The client sends the complete object, not a patch: rule order is the priority, so a partial update has no unambiguous interpretation.\n- Each call allocates a new version and records a history row in the same transaction as the write.\n- Call `POST /rum/application/remote-config/preview` first to check what clients would receive.", - "href": "/en/api-reference/rum/applications/rum-application-remote-config-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Rules are returned ordered by `priority` ascending, then `created_at` ascending — the same order they are evaluated in.\n- Only enabled rules are evaluated against incoming errors; the first enabled rule (in priority order) whose filters match an error wins and assigns its `severity`. Errors matching no enabled rule keep their default severity.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-list", "metadata": { - "sidebarTitle": "Update remote config" + "sidebarTitle": "List preset severity rules" } } } }, - "/rum/application/update": { + "/rum/issue/preset-severity/rules/reorder": { "post": { - "description": "Update an existing RUM application. All fields except `application_id` are optional — only provided fields are updated.", - "operationId": "rum-application-write-update", + "description": "Move one preset severity rule to another rule's position in evaluation order.", + "operationId": "rum-issue-preset-severity-rules-reorder", "requestBody": { "content": { "application/json": { "example": { - "alerting": { - "channel_ids": [ - 2490121812131 - ], - "enabled": true - }, "application_id": "WoyQQ3BohkdtPivubEvE8o", - "application_name": "My Web App v2", - "links": { - "enabled": true, - "systems": [ - { - "enabled": true, - "event_types": [ - "crash", - "error" - ], - "icon_color": "#0F766E", - "icon_text": "S3", - "id": "s3-crash-logs", - "name": "S3 Crash Logs", - "url": "https://s3.example.com/logs?app=${application_id}&trace=${trace_id}" - } - ] - } + "drag_rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", + "target_rule_id": "TAHUYnQmXKzgMS4TFVUKvz" }, "schema": { - "$ref": "#/components/schemas/RumApplicationUpdateRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleReorderRequest" } } }, @@ -47571,32 +53447,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update application", + "summary": "Reorder preset severity rule", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- `links.systems[].url` must start with `http` or `https`; `${var}` tokens are resolved from RUM event context.\n- `links.systems[].event_types` accepts: `crash`, `error`, `view`, `action`, `resource`, `session`, `all`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/applications/rum-application-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- This moves exactly one rule, not a full reordering: `drag_rule_id`'s `priority` is set to `target_rule_id`'s current `priority`, and every rule between the two original positions — the target rule itself included — shifts by one to close the gap.\n- Lower `priority` numbers are evaluated first; moving toward a lower-numbered target moves the rule earlier in evaluation order, and toward a higher-numbered target moves it later.\n- Returns `ResourceNotFound` if either `drag_rule_id` or `target_rule_id` does not exist in the application.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-reorder", "metadata": { - "sidebarTitle": "Update application" + "sidebarTitle": "Reorder preset severity rule" } } } }, - "/rum/application/webhook/test": { + "/rum/issue/preset-severity/rules/update": { "post": { - "description": "Send a sample RUM alert event to verify an application's webhook URL.", - "operationId": "rum-application-webhook-test", + "description": "Update the name, description, filters, or severity of a preset severity rule.", + "operationId": "rum-issue-preset-severity-rules-update", "requestBody": { "content": { "application/json": { "example": { - "application_id": "rum-app-prod", - "webhook_url": "https://hooks.example.com/rum-alerts" + "application_id": "WoyQQ3BohkdtPivubEvE8o", + "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", + "rule_name": "Critical crash spikes (updated)", + "severity": "Critical" }, "schema": { - "$ref": "#/components/schemas/RumWebhookTestRequest" + "$ref": "#/components/schemas/RumPresetSeverityRuleUpdateRequest" } } }, @@ -47607,11 +53485,7 @@ "content": { "application/json": { "example": { - "data": { - "message": "ok", - "ok": true, - "status_code": 200 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -47622,7 +53496,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumWebhookTestResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -47639,9 +53513,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -47649,40 +53520,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Test application webhook", + "summary": "Update preset severity rule", "tags": [ - "RUM/Applications" + "RUM/Issue preset severity rules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Applications Manage** (`rum`) |\n\n## Usage\n\n- The endpoint validates the URL before sending the sample event.\n- A failed delivery still returns HTTP 200 with `ok=false` and the delivery error in `message`.", - "href": "/en/api-reference/rum/applications/rum-application-webhook-test", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Only fields present in the request are changed; omitted fields keep their current value.\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- If `filters` is provided it replaces the entire filter structure and is revalidated against the same allowed key set as `create`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-update", "metadata": { - "sidebarTitle": "Test application webhook" + "sidebarTitle": "Update preset severity rule" } } } }, - "/rum/data/query": { + "/rum/issue/update": { "post": { - "description": "Run one or more SQL-style RUM data queries over a bounded time range.", - "operationId": "rum-read-data-query", + "description": "Update the status or suspected cause of an issue.", + "operationId": "rum-issue-write-update", "requestBody": { "content": { "application/json": { "example": { - "end_time": 1712707200000, - "queries": [ - { - "format": "table", - "id": "errors_by_type", - "sql": "SELECT error.type, count(*) AS errors FROM error GROUP BY error.type ORDER BY errors DESC LIMIT 10", - "time_zone": "Asia/Shanghai" - } - ], - "start_time": 1712620800000 + "issue_id": "NHEacQHi2DhXqobr9qPQz9", + "status": "resolved" }, "schema": { - "$ref": "#/components/schemas/RumDataQueryRequest" + "$ref": "#/components/schemas/RumIssueUpdateRequest" } } }, @@ -47693,34 +53556,7 @@ "content": { "application/json": { "example": { - "data": { - "errors_by_type": { - "data": { - "fields": [ - { - "name": "error.type", - "nullable": false, - "type": "String" - }, - { - "name": "errors", - "nullable": false, - "type": "UInt64" - } - ], - "values": [ - [ - "TypeError", - 1523 - ], - [ - "ReferenceError", - 342 - ] - ] - } - } - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -47731,7 +53567,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumDataQueryResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -47755,61 +53591,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Query RUM data", + "summary": "Update issue", "tags": [ - "RUM/Data query" + "RUM/Issues" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Send 1 to 10 queries in one request; each query `id` becomes a key in the response object.\n- `start_time` and `end_time` are required Unix epoch milliseconds. The maximum time range is 31 days.\n- Use `format: table` for tabular results, or `format: time_series` for bucketed time-series results.\n- For `time_series`, `interval` defaults to 3600 seconds and `max_points` defaults to 1226 when omitted.\n- `search_after_ctx` is returned by paginated table queries and can be sent back to continue scanning.", - "href": "/en/api-reference/rum/data-query/rum-read-data-query", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `status` valid values: `for_review`, `reviewed`, `ignored`, `resolved`.\n- `suspected_cause` valid values: `api.failed_request`, `network.error`, `code.exception`, `code.invalid_object_access`, `code.invalid_argument`, `unknown`.\n- Setting `status` to `resolved` also stamps `resolved_at` and `resolved_by` on the issue; moving a resolved issue back to another status clears them.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/rum/issues/rum-issue-write-update", "metadata": { - "sidebarTitle": "Query RUM data" + "sidebarTitle": "Update issue" } } } }, - "/rum/error-ingestion/rules/create": { + "/rum/resource/info": { "post": { - "description": "Create a new error ingestion rule that filters which errors are stored.", - "operationId": "rum-error-ingestion-rules-create", + "description": "Return the account's RUM resource record and its current session usage.", + "operationId": "rum-resource-read-info", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "description": "Only ingest TypeError/ReferenceError from production, excluding Safari.", - "filters": [ - [ - { - "key": "error.env", - "oper": "IN", - "vals": [ - "production" - ] - }, - { - "key": "error.error_type", - "oper": "IN", - "vals": [ - "TypeError", - "ReferenceError" - ] - } - ], - [ - { - "key": "error.browser_name", - "oper": "NOTIN", - "vals": [ - "Safari" - ] - } - ] - ], - "rule_name": "Production console errors" + "no_cache": false }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionCreateRequest" + "$ref": "#/components/schemas/RumResourceInfoRequest" } } }, @@ -47821,8 +53627,31 @@ "application/json": { "example": { "data": { - "rule_id": "9spXEVoMeZWujjz25yrgTe", - "rule_name": "Production console errors" + "account_id": 2451002751131, + "action.days": 30, + "created_at": 1750000000, + "error.days": 30, + "long_task.days": 15, + "offering_id": 11, + "order_id": "fd_order_20250615_8f3a1c2b", + "product": "rum", + "resource.days": 15, + "resource_id": "rum_2451002751131", + "resource_name": "rum_2451002751131", + "session.days": 30, + "session_investigate.free_cnt": 0, + "session_investigate.used_cnt": 5230, + "session_limit_reached": false, + "session_measure.free_cnt": 0, + "session_measure.used_cnt": 128400, + "session_replay.free_cnt": 0, + "session_replay.used_cnt": 812, + "status": "enabled", + "updated_at": 1752000000, + "version": "professional", + "view.days": 30, + "window_end_time": 1752592000, + "window_start_time": 1750000000 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -47834,7 +53663,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionCreateResponse" + "$ref": "#/components/schemas/RumResourceItem" } }, "type": "object" @@ -47858,32 +53687,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create an error ingestion rule", + "summary": "Get RUM resource info", "tags": [ - "RUM/Error ingestion rules" + "RUM/Resources" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Create, update, enable, disable, and delete all snapshot the application's full current rule set into history first, so `history/list` reflects every mutation.\n- Every condition key in `filters` must be one of the supported `error.*` fields or a `context.*` path; unsupported keys are rejected with `InvalidParameter`.\n- New rules are created with status `enabled`; call `disable` afterward if the rule should start inactive.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` when the account has no RUM resource provisioned yet, or when the resource's status is `deleted`/`destroyed`.\n- `no_cache=true` bypasses the short-lived cache of the resource record itself (plan version, quotas, status). The `used_cnt` figures come from a separate hourly cache that this flag does not affect, so they can lag behind live usage either way.\n- The used-count fields reflect the current 30-day billing window (`window_start_time` to `window_end_time`), not lifetime totals.\n- `expired_at` is only populated on on-premises deployments, from the license expiry date; it is omitted entirely for SaaS accounts.\n- For `version=free` accounts, `session_limit_reached` is `true` once usage exceeds the combined free quota across all applications (per-app free quota × application count); it stays `false` while the account has no applications yet.", + "href": "/en/api-reference/rum/resources/rum-resource-read-info", "metadata": { - "sidebarTitle": "Create an error ingestion rule" + "sidebarTitle": "Get RUM resource info" } } } }, - "/rum/error-ingestion/rules/delete": { + "/rum/session-replay/metadata": { "post": { - "description": "Delete an error ingestion rule from a RUM application.", - "operationId": "rum-error-ingestion-rules-delete", + "description": "Return the application, device, session bounds, and views recorded for a replayable session.", + "operationId": "rum-session-replay-read-metadata", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "9spXEVoMeZWujjz25yrgTe" + "session_id": "0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81" }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionRuleIDRequest" + "$ref": "#/components/schemas/RumSessionReplayMetaRequest" } } }, @@ -47894,7 +53722,37 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "application": { + "id": "WoyQQ3BohkdtPivubEvE8o" + }, + "device": { + "type": "desktop" + }, + "foreground_periods": [], + "session": { + "end": 1752480600000, + "is_active": false, + "server_time_delta": 0, + "source": "browser", + "start": 1752480000000 + }, + "views": [ + { + "container_source": "", + "container_view_id": "", + "end": 1752480600000, + "is_active": false, + "loading_type": "initial_load", + "name": "/dashboard", + "server_time_delta": 0, + "source": "browser", + "start": 1752480000000, + "url": "https://app.example.com/dashboard", + "view_id": "6f2b6b1a-8f7e-4e3a-9c2b-1a2b3c4d5e6f" + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -47905,7 +53763,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" + "$ref": "#/components/schemas/RumSessionReplayMetaItem" } }, "type": "object" @@ -47929,32 +53787,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete an error ingestion rule", + "summary": "Get session replay metadata", "tags": [ - "RUM/Error ingestion rules" + "RUM/Session replay" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The rule disappears from `list` immediately, but the enabled-rule set used for filtering is cached for up to 5 seconds, so errors ingested shortly after deletion can still be matched against it.\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `InvalidParameter` if the session does not exist, or if it has no replay data recorded (`session_has_replay` is false).\n- Returns `InvalidParameter` if no views are found within the session's time window.\n- Pass `ts` to disambiguate when a `session_id` has been reused across different time windows.", + "href": "/en/api-reference/rum/session-replay/rum-session-replay-read-metadata", "metadata": { - "sidebarTitle": "Delete an error ingestion rule" + "sidebarTitle": "Get session replay metadata" } } } }, - "/rum/error-ingestion/rules/disable": { + "/rum/session-replay/segments": { "post": { - "description": "Disable an error ingestion rule without deleting it.", - "operationId": "rum-error-ingestion-rules-disable", + "description": "Page through the recorded replay segments of a session, as presigned URLs or a raw stream.", + "operationId": "rum-session-replay-read-segments", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "9spXEVoMeZWujjz25yrgTe" + "limit": 20, + "session_id": "0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81", + "url_mode": true }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionRuleIDRequest" + "$ref": "#/components/schemas/RumSessionReplaySegmentsRequest" } } }, @@ -47965,8 +53824,14 @@ "content": { "application/json": { "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + "data": { + "items": [ + "https://rum-replay.flashcat.cloud/short-term/2451002751131/0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81/segments/1752480001234?X-Amz-Signature=example", + "https://rum-replay.flashcat.cloud/short-term/2451002751131/0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81/segments/1752480032456?X-Amz-Signature=example" + ], + "search_after_ctx": "c2hvcnQtdGVybS8yNDUxMDAyNzUxMTMxLzBhNGEyZTY0LThhNGYtNGI5YS05YzFlLTNhMmY5ZTZkN2M4MS9zZWdtZW50cy8xNzUyNDgwMDMyNDU2" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R5" }, "schema": { "allOf": [ @@ -47976,16 +53841,30 @@ { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" + "$ref": "#/components/schemas/RumSessionReplaySegmentsResult" } }, "type": "object" } ] } + }, + "application/x-ndjson": { + "schema": { + "description": "Newline-delimited JSON (NDJSON). Each line is one decompressed replay segment record (rrweb-format events), streamed directly and not wrapped in the standard envelope.", + "type": "string" + } } }, - "description": "Success" + "description": "Success. Shape depends on `url_mode` — see Usage.", + "headers": { + "X-Search-After-Ctx": { + "description": "Base64-encoded pagination cursor for the next call. Only set in streaming mode (`url_mode: false`).", + "schema": { + "type": "string" + } + } + } }, "400": { "$ref": "#/components/responses/BadRequest" @@ -48000,32 +53879,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable an error ingestion rule", + "summary": "List session replay segments", "tags": [ - "RUM/Error ingestion rules" + "RUM/Session replay" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- A disabled rule is kept and still returned by `list`, but is skipped when matching incoming errors.\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- When `url_mode` is `false` (default), the response streams `application/x-ndjson` — one decompressed replay segment JSON object per line — and is **not** wrapped in the standard envelope. The pagination cursor for the next call is returned in the `X-Search-After-Ctx` response header instead of a body field.\n- When `url_mode` is `true`, the response is a normal JSON envelope containing presigned download URLs (valid 1 hour) instead of the raw segment bytes.\n- Pass `ts` to seek to the most recent full-snapshot segment at or before that time, instead of paging from the start of the session.\n- `limit` accepts 1-99; values of 100 or more are rejected.", + "href": "/en/api-reference/rum/session-replay/rum-session-replay-read-segments", "metadata": { - "sidebarTitle": "Disable an error ingestion rule" + "sidebarTitle": "List session replay segments" } } } }, - "/rum/error-ingestion/rules/enable": { + "/safari/a2a-agent/create": { "post": { - "description": "Re-enable a previously disabled error ingestion rule.", - "operationId": "rum-error-ingestion-rules-enable", + "description": "Register a new A2A remote agent from its agent-card URL.", + "operationId": "remote-agent-write-create", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "9spXEVoMeZWujjz25yrgTe" + "agent_name": "deploy-bot", + "auth_type": "bearer", + "card_url": "https://agents.example.com/deploy-bot/card", + "environments": [ + "env_8s7Hn2kLpQ3xYbVc4Wd2m" + ], + "instructions": "Inspect deployment pipelines and propose rollbacks when a canary fails health checks.", + "streaming": true, + "team_id": 0 }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionRuleIDRequest" + "$ref": "#/components/schemas/A2AAgentCreateRequest" } } }, @@ -48036,18 +53922,20 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" + "$ref": "#/components/schemas/A2AAgentCreateResponse" } }, "type": "object" @@ -48064,6 +53952,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -48071,35 +53962,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable an error ingestion rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Create A2A agent", "tags": [ - "RUM/Error ingestion rules" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- `instructions` is required; a deprecated `description` field is still accepted for legacy clients and, if both are sent, must exactly match `instructions`.\n- `card_url` must be an absolute `http`/`https` URL with a non-empty host (reachability is enforced by the execution environment, not here); `auth_type` accepts only `none`, `api_key`, or `bearer`.\n- `environments` restricts where the agent can run: a list of `cloud` and/or BYOC runner environment IDs; omitted or empty means all environments, and each runner must be visible to the caller.\n- Creating into a team (`team_id > 0`) requires the caller to actually belong to that team; only the account owner/admin may create at account scope (`team_id=0`).\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-create", "metadata": { - "sidebarTitle": "Enable an error ingestion rule" + "sidebarTitle": "Create A2A agent" } } } }, - "/rum/error-ingestion/rules/history/list": { + "/safari/a2a-agent/delete": { "post": { - "description": "Return paginated snapshots of an application's error ingestion rule history.", - "operationId": "rum-error-ingestion-rules-history-list", + "description": "Soft-delete an A2A agent by ID.", + "operationId": "remote-agent-write-delete", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "asc": false, - "limit": 20, - "orderby": "updated_at", - "p": 0 + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionHistoryListRequest" + "$ref": "#/components/schemas/A2AAgentIDRequest" } } }, @@ -48110,80 +54002,19 @@ "content": { "application/json": { "example": { - "data": { - "has_next_page": false, - "items": [ - { - "rules": [ - { - "account_id": 20001, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "created_at": 1786000000000, - "created_by": 1001, - "deleted_at": 0, - "description": "Only ingest TypeError/ReferenceError from production, excluding Safari.", - "filters": [ - [ - { - "key": "error.env", - "oper": "IN", - "vals": [ - "production" - ] - }, - { - "key": "error.error_type", - "oper": "IN", - "vals": [ - "TypeError", - "ReferenceError" - ] - } - ], - [ - { - "key": "error.browser_name", - "oper": "NOTIN", - "vals": [ - "Safari" - ] - } - ] - ], - "id": 1044, - "rule_id": "9spXEVoMeZWujjz25yrgTe", - "rule_name": "Production console errors", - "status": "enabled", - "updated_at": 1786000000000, - "updated_by": 1001 - } - ], - "updated_at": 1786003600000, - "updated_by": 1001, - "updated_by_name": "Alice Chen", - "version": 2 - }, - { - "rules": [], - "updated_at": 1786000000000, - "updated_by": 1001, - "updated_by_name": "Alice Chen", - "version": 1 - } - ], - "total": 2 - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionHistoryListResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -48200,6 +54031,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -48207,32 +54041,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List error ingestion rule history", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Delete A2A agent", "tags": [ - "RUM/Error ingestion rules" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- One history item is a full snapshot of every rule for the application at that point in time, not a diff of a single rule.\n- `p` is a zero-based page number, not a byte offset — the server computes `offset = p * limit` internally.\n- `orderby` accepts `updated_at` or `version`; any other value silently falls back to `updated_at`.\n- `limit` defaults to 20 and is capped at 100 server-side; values above 100 are silently clamped, values of 0 or below fall back to the default.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-history-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Delete is a soft delete; the agent stops appearing in list/get and can no longer be dispatched once removed.\n- Requires edit permission (`access.CanEdit`) on the agent's team.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-delete", "metadata": { - "sidebarTitle": "List error ingestion rule history" + "sidebarTitle": "Delete A2A agent" } } } }, - "/rum/error-ingestion/rules/history/revert": { + "/safari/a2a-agent/disable": { "post": { - "description": "Restore an application's entire rule set to a prior history version.", - "operationId": "rum-error-ingestion-rules-history-revert", + "description": "Disable an enabled A2A agent.", + "operationId": "remote-agent-write-disable", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "version": 2 + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionRevertRequest" + "$ref": "#/components/schemas/A2AAgentIDRequest" } } }, @@ -48243,18 +54081,19 @@ "content": { "application/json": { "example": { - "data": {}, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -48271,6 +54110,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -48278,31 +54120,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Revert error ingestion rules to a history version", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Disable A2A agent", "tags": [ - "RUM/Error ingestion rules" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Revert replaces the entire rule set for the application — rules created after the target version are removed, not merged.\n- The current state is snapshotted into history before the revert runs, so a revert can itself be undone by reverting again.\n- Returns `InvalidParameter` (not `ResourceNotFound`) when `version` doesn't exist for the application.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-history-revert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Requires edit permission (`access.CanEdit`) on the agent's team.\n- Returns `InvalidParameter` if the agent is already disabled.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-disable", "metadata": { - "sidebarTitle": "Revert error ingestion rules to a history version" + "sidebarTitle": "Disable A2A agent" } } } }, - "/rum/error-ingestion/rules/list": { + "/safari/a2a-agent/enable": { "post": { - "description": "Return every error ingestion rule configured for a RUM application.", - "operationId": "rum-error-ingestion-rules-list", + "description": "Enable a disabled A2A agent.", + "operationId": "remote-agent-write-enable", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o" + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionListRequest" + "$ref": "#/components/schemas/A2AAgentIDRequest" } } }, @@ -48313,57 +54160,19 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "created_at": 1786000000000, - "description": "Only ingest TypeError/ReferenceError from production, excluding Safari.", - "filters": [ - [ - { - "key": "error.env", - "oper": "IN", - "vals": [ - "production" - ] - }, - { - "key": "error.error_type", - "oper": "IN", - "vals": [ - "TypeError", - "ReferenceError" - ] - } - ], - [ - { - "key": "error.browser_name", - "oper": "NOTIN", - "vals": [ - "Safari" - ] - } - ] - ], - "rule_id": "9spXEVoMeZWujjz25yrgTe", - "rule_name": "Production console errors", - "status": "enabled", - "updated_at": 1786003600000 - } - ] - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionListResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -48380,6 +54189,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -48387,33 +54199,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List error ingestion rules", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Enable A2A agent", "tags": [ - "RUM/Error ingestion rules" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Deleted rules are excluded; only rules with status `enabled` or `disabled` are returned.\n- Rules are ordered newest-created first.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Requires edit permission (`access.CanEdit`) on the agent's team, not just visibility into it.\n- Returns `InvalidParameter` if the agent is already enabled.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-enable", "metadata": { - "sidebarTitle": "List error ingestion rules" + "sidebarTitle": "Enable A2A agent" } } } }, - "/rum/error-ingestion/rules/update": { + "/safari/a2a-agent/get": { "post": { - "description": "Update the name, description, or filters of an error ingestion rule.", - "operationId": "rum-error-ingestion-rules-update", + "description": "Get one A2A agent by ID.", + "operationId": "remote-agent-read-get", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "description": "Now also excludes staging traffic.", - "rule_id": "9spXEVoMeZWujjz25yrgTe" + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" }, "schema": { - "$ref": "#/components/schemas/RumErrorIngestionUpdateRequest" + "$ref": "#/components/schemas/A2AAgentIDRequest" } } }, @@ -48424,18 +54239,43 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "account_id": 10023, + "agent_card_name": "Deploy Bot", + "agent_card_skills": [ + "rollback", + "diff" + ], + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D", + "agent_name": "deploy-bot", + "auth_mode": "shared", + "auth_type": "bearer", + "can_edit": true, + "card_resolve_timeout": 0, + "card_url": "https://agents.example.com/deploy-bot/card", + "created_at": 1716960000000, + "created_by": 80011, + "environments": [ + "env_8s7Hn2kLpQ3xYbVc4Wd2m" + ], + "instructions": "Inspect deployment pipelines and propose rollbacks when a canary fails health checks.", + "status": "enabled", + "streaming": true, + "task_timeout": 0, + "team_id": 0, + "updated_at": 1717046400000 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumErrorIngestionEmptyResponse" + "$ref": "#/components/schemas/A2AAgentItem" } }, "type": "object" @@ -48459,35 +54299,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update an error ingestion rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Get A2A agent detail", "tags": [ - "RUM/Error ingestion rules" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Only fields present in the request are changed; omitted fields keep their current value.\n- Calling update with no fields set is a no-op that still returns success.\n- Returns `ResourceNotFound` if `rule_id` doesn't exist under `application_id`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/error-ingestion-rules/rum-error-ingestion-rules-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `card_resolve_timeout` and `task_timeout` are always `0` today — the API does not yet expose a way to set them.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-read-get", "metadata": { - "sidebarTitle": "Update an error ingestion rule" + "sidebarTitle": "Get A2A agent detail" } } } }, - "/rum/facet/count": { + "/safari/a2a-agent/list": { "post": { - "description": "Return the top N values for a facet field within a time range, sorted by occurrence count descending.", - "operationId": "rum-read-facet-count", + "description": "List A2A agents visible to the caller across account and team scopes, with pagination.", + "operationId": "remote-agent-read-list", "requestBody": { "content": { "application/json": { "example": { - "end_time": 1712707200000, - "facet_key": "error.type", - "limit": 10, - "scope": "error", - "start_time": 1712620800000 + "include_account": true, + "limit": 20, + "offset": 0 }, "schema": { - "$ref": "#/components/schemas/RumFacetCountRequest" + "$ref": "#/components/schemas/A2AAgentListRequest" } } }, @@ -48501,30 +54344,45 @@ "data": { "items": [ { - "count": 1523, - "facet_value": "TypeError" - }, - { - "count": 342, - "facet_value": "ReferenceError" - }, - { - "count": 89, - "facet_value": "SyntaxError" + "account_id": 10023, + "agent_card_name": "Deploy Bot", + "agent_card_skills": [ + "rollback", + "diff" + ], + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D", + "agent_name": "deploy-bot", + "auth_mode": "shared", + "auth_type": "bearer", + "can_edit": true, + "card_resolve_timeout": 0, + "card_url": "https://agents.example.com/deploy-bot/card", + "created_at": 1716960000000, + "created_by": 80011, + "environments": [ + "env_8s7Hn2kLpQ3xYbVc4Wd2m" + ], + "instructions": "Inspect deployment pipelines and propose rollbacks when a canary fails health checks.", + "status": "enabled", + "streaming": true, + "task_timeout": 0, + "team_id": 0, + "updated_at": 1717046400000 } - ] + ], + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumFacetCountResponse" + "$ref": "#/components/schemas/A2AAgentListResponse" } }, "type": "object" @@ -48548,34 +54406,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Count facet value distribution", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "List A2A agents", "tags": [ - "RUM/Facets" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **100 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Use `POST /rum/field/list` with `is_facet: true` to discover available `facet_key` values for each scope.\n- The `scope` must be one of: `session`, `view`, `action`, `error`, `resource`, `long_task`, `vital`, `issue`, `sourcemap`.\n- Pass `dql` to further filter events before counting. DQL syntax follows the RUM query language.\n- Pass `sql` with a WHERE-clause only (no SELECT) for SQL-style filtering.\n- Default limit is 100; maximum is 100.\n- Time range is required (`start_time` / `end_time` in Unix epoch **milliseconds**). Maximum span is 31 days.", - "href": "/en/api-reference/rum/facets/rum-read-facet-count", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Pagination uses `offset`/`limit` (not `p`/`limit`).\n- `scope=account` restricts to account-scoped agents; `scope=team` restricts to the caller's visible teams; the default `all` combines both, subject to `include_account`.\n- `query` performs a case-insensitive substring search across agent name, instructions, card URL, agent ID, and the resolved card name.\n- `card_resolve_timeout` and `task_timeout` are always `0` today — the API does not yet expose a way to set them.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-read-list", "metadata": { - "sidebarTitle": "Count facet value distribution" + "sidebarTitle": "List A2A agents" } } } }, - "/rum/field/list": { + "/safari/a2a-agent/update": { "post": { - "description": "Return RUM field definitions, optionally filtered by scope and facet status.", - "operationId": "rum-read-field-list", + "description": "Apply a partial update to an A2A agent. Omit a field to leave it unchanged.", + "operationId": "remote-agent-write-update", "requestBody": { "content": { "application/json": { "example": { - "is_facet": false, - "scopes": [ - "error" - ] + "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D", + "instructions": "Inspect deployment pipelines and propose rollbacks." }, "schema": { - "$ref": "#/components/schemas/RumFieldListRequest" + "$ref": "#/components/schemas/A2AAgentUpdateRequest" } } }, @@ -48586,40 +54447,19 @@ "content": { "application/json": { "example": { - "data": { - "items": [ - { - "account_id": 0, - "description": "The type of the error.", - "edit_able": false, - "enum_values": [], - "field_key": "error.type", - "field_name": "Error type", - "group": "Error", - "is_facet": true, - "queryable": true, - "scopes": [ - "error" - ], - "show_type": "list", - "status": "active", - "unit_family": "", - "unit_name": "", - "value_type": "string" - } - ] - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumFieldListResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -48636,6 +54476,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -48643,50 +54486,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List RUM fields", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Update A2A agent", "tags": [ - "RUM/Facets" + "AI SRE/A2A agents" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- This is the current field-model route for discovering RUM fields.\n- Use returned `field_key` values in RUM data queries and facet-count requests.\n- Set `is_facet: true` to return only fields that support value distribution queries.", - "href": "/en/api-reference/rum/facets/rum-read-field-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Requires edit permission (`access.CanEdit`) on the agent's *current* team before any field may change.\n- Reassigning `team_id` requires rights on the destination team; if the team changes without also sending a new environment binding, the existing runner binding must remain selectable by the caller or the update is rejected.\n- Changing `auth_mode` always rewrites `secret_schema` together with it; omitting `oauth_metadata` alongside a new `auth_mode` clears it to empty.\n- Sending back a masked or empty value for a sensitive `auth_config` key (`api_key`, `token`, `client_secret`) keeps the stored secret instead of overwriting it.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-update", "metadata": { - "sidebarTitle": "List RUM fields" + "sidebarTitle": "Update A2A agent" } } } }, - "/rum/issue/export": { + "/safari/artifact/gallery/delete": { "post": { - "description": "Export the filtered RUM error tracking issues as a CSV file. The response is a `text/csv` stream delivered with `Content-Disposition: attachment` — it is not a JSON envelope; non-console callers can read the `X-Export-Total` and `X-Export-Truncated` response headers.", - "operationId": "rum-issue-read-export", + "description": "Detach an artifact from the gallery; the source file stays with its session.", + "operationId": "artifact-write-delete", "requestBody": { "content": { "application/json": { "example": { - "application_ids": [ - "eWbr4xk3ZRnLabRa6unqwD" - ], - "console_origin": "https://console.flashcat.cloud", - "end_time": 1775961914595, - "export_fields": [ - "issue_id", - "error_type", - "error_message", - "status", - "error_count", - "session_count", - "last_seen_at" - ], - "orderby": "updated_at", - "start_time": 1772611200000, - "statuses": [ - "for_review" - ], - "time_zone": "Asia/Shanghai" + "artifact_id": "art_CWQzDU2PXSRJvKDhQbuMKu" }, "schema": { - "$ref": "#/components/schemas/RumIssueExportRequest" + "$ref": "#/components/schemas/ArtifactIdRequest" } } }, @@ -48695,30 +54524,30 @@ "responses": { "200": { "content": { - "text/csv": { - "example": "Issue ID,Error type,Error message,Status,Error count,Affected sessions,Last seen (Asia/Shanghai)\nNHEacQHi2DhXqobr9qPQz9,Error,Script error.,for_review,752,381,2026-04-12 10:43:59\nH8kZSmxiE7EgdyD4fCyyNa,Error,\"API ERROR: We encountered an internal error | POST /api/access/logout\",for_review,3,1,2026-04-03 12:41:24", + "application/json": { + "example": { + "data": null, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { - "description": "CSV file content. The header row matches the exported columns in order; values are sanitized against spreadsheet formula injection.", - "type": "string" + "allOf": [ + { + "$ref": "#/components/schemas/ResponseEnvelope" + }, + { + "properties": { + "data": { + "description": "Always null on success.", + "type": "null" + } + }, + "type": "object" + } + ] } } }, - "description": "Success. CSV attachment, not a JSON envelope.", - "headers": { - "X-Export-Total": { - "description": "Total number of issues matching the filters, before the row cap.", - "schema": { - "format": "int64", - "type": "integer" - } - }, - "X-Export-Truncated": { - "description": "`true` when more issues matched than the 100-row cap and the file was truncated.", - "schema": { - "type": "boolean" - } - } - } + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -48733,31 +54562,39 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Export issues as CSV", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Remove artifact from gallery", "tags": [ - "RUM/Issues" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **200 requests/day**; **100 requests/minute**; **10 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The response is a `text/csv` stream delivered with `Content-Disposition: attachment` — it is not wrapped in the standard envelope. The filename is `rum-issues-.csv`, stamped in the requested `time_zone`. Read `X-Export-Total` and `X-Export-Truncated` response headers instead of a body field.\n- The export reads the first 100 matching rows (`ExportMaxRows`); `X-Export-Truncated` is `true` when more issues match. `p` and `limit` are ignored.\n- The request filters are exactly those of `POST /rum/issue/list` — an export is \"what I am looking at, as a file\".\n- `export_fields` names the CSV columns in the order they appear. Unknown keys are rejected with a parameter error; an empty array uses the default column set.\n- `time_zone` must be a valid IANA zone name (e.g. `Asia/Shanghai`, `UTC`); timestamps are rendered in that zone and time columns carry the zone in their header. Invalid names are rejected.\n- `console_origin` is used to build the `issue_url` column; the service cannot infer it (SaaS, on-premises and dev releases answer on different origins).\n- Every call is recorded in the account's audit log with the caller's member ID, request payload, and resulting error (if any). Do not put secrets in request fields.", - "href": "/en/api-reference/rum/issues/rum-issue-read-export", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- This is a detach, not a byte delete: the underlying presented file stays with the source session and can be published again.\n- If public sharing was enabled, the public objects are destroyed in the same operation and the link stops resolving.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-write-delete", "metadata": { - "sidebarTitle": "Export issues as CSV" + "sidebarTitle": "Remove artifact from gallery" } } } }, - "/rum/issue/info": { + "/safari/artifact/gallery/file-state": { "post": { - "description": "Retrieve full details of a single issue by `issue_id`.", - "operationId": "rum-issue-read-info", + "description": "Check which presented files already have a live published artifact.", + "operationId": "artifact-read-get-file-state", "requestBody": { "content": { "application/json": { "example": { - "issue_id": "NHEacQHi2DhXqobr9qPQz9" + "file_ids": [ + "pf_SdhEA5fbZJGnHzwrNJMMSB", + "pf_9kLm2nQpRsTuVwXyZaBcDe" + ] }, "schema": { - "$ref": "#/components/schemas/RumIssueIDRequest" + "$ref": "#/components/schemas/ArtifactFileStateRequest" } } }, @@ -48769,41 +54606,13 @@ "application/json": { "example": { "data": { - "age": 5078684, - "application_id": "eWbr4xk3ZRnLabRa6unqwD", - "application_name": "Flashduty DEV", - "created_at": 1770883154944, - "error": { - "message": "Script error.", - "type": "Error" - }, - "error_count": 752, - "first_seen": { - "timestamp": 1770883154944, - "version": "1.0.0" - }, - "is_crash": false, - "issue_id": "NHEacQHi2DhXqobr9qPQz9", - "last_seen": { - "timestamp": 1775961839090, - "version": "1.0.0" - }, - "resolved_at": 0, - "resolved_by": 0, - "service": "fd-console", - "session_count": 381, - "severity": "Info", - "status": "for_review", - "suspected_cause": { - "person_id": 0, - "reason": "The error message 'Script error.' typically indicates an unhandled exception in JavaScript.", - "source": "auto", - "value": "code.exception" - }, - "team_id": 2477033058131, - "updated_at": 1775961914595, - "versions": [ - "1.0.0" + "items": [ + { + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "gallery_path": "/ai-sre/artifacts/art_VnfrWic8UbB9q3EfYR4Gmg", + "title": "SK 海力士 2026 Q2 财报深度分析" + } ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" @@ -48811,12 +54620,12 @@ "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumIssueItem" + "$ref": "#/components/schemas/ArtifactFileStateResponse" } }, "type": "object" @@ -48840,41 +54649,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get issue detail", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Get file publish state", "tags": [ - "RUM/Issues" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/rum/issues/rum-issue-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- At most 50 `file_ids` per call; duplicates and empty strings are ignored.\n- Files with no live published artifact are simply absent from `items` — match results by the echoed `file_id`.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-read-get-file-state", "metadata": { - "sidebarTitle": "Get issue detail" + "sidebarTitle": "Get file publish state" } } } }, - "/rum/issue/list": { + "/safari/artifact/gallery/get": { "post": { - "description": "Return a paginated list of RUM error tracking issues matching the given filters.", - "operationId": "rum-issue-read-list", + "description": "Get a single published artifact by ID.", + "operationId": "artifact-read-get", "requestBody": { "content": { "application/json": { "example": { - "application_ids": [ - "eWbr4xk3ZRnLabRa6unqwD" - ], - "end_time": 1775961914595, - "limit": 20, - "orderby": "updated_at", - "p": 1, - "start_time": 1772611200000, - "statuses": [ - "for_review" - ] + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" }, "schema": { - "$ref": "#/components/schemas/RumIssueListRequest" + "$ref": "#/components/schemas/ArtifactIdRequest" } } }, @@ -48886,98 +54690,39 @@ "application/json": { "example": { "data": { - "has_next_page": true, - "items": [ - { - "age": 5078684, - "application_id": "eWbr4xk3ZRnLabRa6unqwD", - "application_name": "Flashduty DEV", - "created_at": 1770883154944, - "error": { - "message": "Script error.", - "type": "Error" - }, - "error_count": 752, - "first_seen": { - "timestamp": 1770883154944, - "version": "1.0.0" - }, - "is_crash": false, - "issue_id": "NHEacQHi2DhXqobr9qPQz9", - "last_seen": { - "timestamp": 1775961839090, - "version": "1.0.0" - }, - "resolved_at": 0, - "resolved_by": 0, - "service": "fd-console", - "session_count": 381, - "severity": "Info", - "status": "for_review", - "suspected_cause": { - "person_id": 0, - "reason": "The error message 'Script error.' typically indicates an unhandled exception in JavaScript.", - "source": "auto", - "value": "code.exception" - }, - "team_id": 2477033058131, - "updated_at": 1775961914595, - "versions": [ - "1.0.0" - ] - }, - { - "age": 48, - "application_id": "eWbr4xk3ZRnLabRa6unqwD", - "application_name": "Flashduty DEV", - "created_at": 1775189479566, - "error": { - "message": "API ERROR: We encountered an internal error | POST /api/access/logout", - "type": "Error" - }, - "error_count": 3, - "first_seen": { - "timestamp": 1775189479566, - "version": "1.0.0" - }, - "is_crash": false, - "issue_id": "H8kZSmxiE7EgdyD4fCyyNa", - "last_seen": { - "timestamp": 1775189527762, - "version": "1.0.0" - }, - "resolved_at": 0, - "resolved_by": 0, - "service": "fd-console", - "session_count": 1, - "severity": "Info", - "status": "for_review", - "suspected_cause": { - "person_id": 0, - "reason": "The error indicates an internal server error during a POST request to /api/access/logout.", - "source": "auto", - "value": "api.failed_request" - }, - "team_id": 2477033058131, - "updated_at": 1775191284163, - "versions": [ - "1.0.0" - ] - } - ], - "total": 111 + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "can_edit": true, + "content_type": "text/html", + "created_at": 1785293373899, + "creator_name": "yushuangyu", + "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "is_mine": true, + "name": "sk-hynix-q2-2026-report.html", + "person_id": 2476444212131, + "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", + "session_id": "sess_VCbVPZrq9YoyBu8sNCmqUy", + "session_title": "分析海力士财报并发布报告", + "share_enabled": true, + "share_file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "shared_at": 1785747928665, + "shared_by": 3790925372131, + "size": 18996, + "team_id": 2477033058131, + "team_name": "研发团队", + "title": "SK 海力士 2026 Q2 财报深度分析", + "updated_at": 1785747910219 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumIssueListResponse" + "$ref": "#/components/schemas/PublishedArtifactItem" } }, "type": "object" @@ -49001,52 +54746,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List issues", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Get artifact detail", "tags": [ - "RUM/Issues" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `start_time` and `end_time` are millisecond timestamps. Maximum range: 183 days.\n- `statuses` filters by issue status. Valid values: `for_review`, `reviewed`, `ignored`, `resolved`.\n- `orderby` accepts: `created_at`, `updated_at`, `session_count`, `error_count`, `severity`.\n- Use `dql` or `sql` for advanced filtering. Cannot provide both.", - "href": "/en/api-reference/rum/issues/rum-issue-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Visibility is account-wide: any valid `app_key` can read any artifact in the account. `is_mine` and `can_edit` are computed relative to the key owner.\n- When `share_enabled` is true and `file_id` differs from `share_file_id`, the public snapshot is stale — refresh it with `/safari/artifact/gallery/share/sync`.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-read-get", "metadata": { - "sidebarTitle": "List issues" + "sidebarTitle": "Get artifact detail" } } } }, - "/rum/issue/preset-severity/rules/create": { + "/safari/artifact/gallery/list": { "post": { - "description": "Create a new preset severity rule for a RUM application.", - "operationId": "rum-issue-preset-severity-rules-create", + "description": "List published artifacts visible to the caller, with pagination and title search.", + "operationId": "artifact-read-list", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "description": "Escalate production crashes to Critical severity", - "filters": [ - [ - { - "key": "error.env", - "oper": "IN", - "vals": [ - "production" - ] - }, - { - "key": "error.is_crash", - "oper": "IN", - "vals": [ - "true" - ] - } - ] - ], - "rule_name": "Critical crash spikes", - "severity": "Critical" + "limit": 20, + "page": 1, + "scope": "all" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleCreateRequest" + "$ref": "#/components/schemas/ArtifactListRequest" } } }, @@ -49058,21 +54789,62 @@ "application/json": { "example": { "data": { - "priority": 2, - "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", - "rule_name": "Critical crash spikes" + "items": [ + { + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "can_edit": true, + "content_type": "text/html", + "created_at": 1785293373899, + "creator_name": "yushuangyu", + "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "is_mine": true, + "name": "sk-hynix-q2-2026-report.html", + "person_id": 2476444212131, + "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", + "session_id": "sess_VCbVPZrq9YoyBu8sNCmqUy", + "session_title": "分析海力士财报并发布报告", + "share_enabled": true, + "share_file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "shared_at": 1785747928665, + "shared_by": 3790925372131, + "size": 18996, + "team_id": 2477033058131, + "team_name": "研发团队", + "title": "SK 海力士 2026 Q2 财报深度分析", + "updated_at": 1785747910219 + }, + { + "artifact_id": "art_CWQzDU2PXSRJvKDhQbuMKu", + "can_edit": true, + "content_type": "application/pdf", + "created_at": 1785229432881, + "creator_name": "牛伟利", + "file_id": "pf_Jnc4E5YBcWLGzunB4ntP9s", + "is_mine": false, + "name": "rum_recommendation.pdf", + "person_id": 3790925372131, + "session_id": "sess_QXUC9C2PYWP5EE7vETR3UD", + "session_title": "生成 RUM 文档多格式", + "size": 137107, + "team_id": 2477033058131, + "team_name": "研发团队", + "title": "rum_recommendation", + "updated_at": 1785741344822 + } + ], + "total": 17 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumPresetSeverityRuleCreateResponse" + "$ref": "#/components/schemas/ArtifactListResponse" } }, "type": "object" @@ -49096,32 +54868,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create preset severity rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "List artifacts", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `filters.*.key` accepts only a fixed set of Error-level attributes; any other key returns `InvalidParameter`.\n- Pass at least one condition group: an empty `filters` array is accepted but produces a rule that can never match.\n- The new rule is created enabled and appended with the lowest evaluation precedence (`priority` = current max + 1); use the `reorder` operation to move it earlier.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `scope` selects `all` (default — the caller's own personal artifacts plus every team the caller belongs to), `personal` (only the caller's own), or `team` (only team-owned artifacts of the caller's teams).\n- `team_ids` narrows further to specific teams, intersected with the caller's visibility — teams the caller does not belong to return nothing.\n- Default sort is `updated_at` descending; set `orderby` to `created_at` to change the field and `asc: true` to flip direction.\n- For an `app_key` call, visibility is evaluated against the key owner's identity — the list shows that member's personal artifacts and their teams' artifacts.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-read-list", "metadata": { - "sidebarTitle": "Create preset severity rule" + "sidebarTitle": "List artifacts" } } } }, - "/rum/issue/preset-severity/rules/delete": { + "/safari/artifact/gallery/publish-from-file": { "post": { - "description": "Delete a preset severity rule.", - "operationId": "rum-issue-preset-severity-rules-delete", + "description": "Publish a session-produced file to the artifact gallery.", + "operationId": "artifact-write-publish", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay" + "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "title": "SK 海力士 2026 Q2 财报深度分析" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleIDRequest" + "$ref": "#/components/schemas/ArtifactPublishFromFileRequest" } } }, @@ -49132,18 +54909,22 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "gallery_path": "/ai-sre/artifacts/art_VnfrWic8UbB9q3EfYR4Gmg", + "title": "SK 海力士 2026 Q2 财报深度分析" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ArtifactPublishResponse" } }, "type": "object" @@ -49167,32 +54948,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete preset severity rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Publish file as artifact", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- Deletion is a soft delete: the rule stops being listed immediately, but enabled rules are cached for up to 5 seconds, so it can still be evaluated against errors ingested shortly afterwards. Its pre-delete state remains visible via the history endpoints.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Allowed file types: HTML/Markdown, images, PDF, text/data/code files, and zip/tar archives, matched by extension. Files over 16 MiB are rejected.\n- Publishing is an upsert keyed by the source session and workspace path — republishing the same file replaces the artifact's bytes under a fresh `file_id`, which makes an existing public snapshot stale until synced.\n- The artifact inherits personal/team scope from the source session; move it afterwards with `/safari/artifact/gallery/update` if needed.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-write-publish", "metadata": { - "sidebarTitle": "Delete preset severity rule" + "sidebarTitle": "Publish file as artifact" } } } }, - "/rum/issue/preset-severity/rules/disable": { + "/safari/artifact/gallery/share/enable": { "post": { - "description": "Disable a preset severity rule.", - "operationId": "rum-issue-preset-severity-rules-disable", + "description": "Turn on anonymous public sharing for an artifact and return its public link.", + "operationId": "artifact-write-share-enable", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "TAHUYnQmXKzgMS4TFVUKvz" + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleIDRequest" + "$ref": "#/components/schemas/ArtifactIdRequest" } } }, @@ -49203,18 +54988,24 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", + "share_enabled": true, + "shared_at": 1785747928665, + "shared_by": 2476444212131 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/ArtifactShareState" } }, "type": "object" @@ -49238,32 +55029,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Disable preset severity rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Enable public sharing", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- A disabled rule is skipped during evaluation but keeps its `priority` slot; the cache can take up to 5 seconds to reflect the change.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The public link is anonymous — anyone with it can view the content, and the link may be forwarded. Content is copied to public CDN objects; the gallery API is not involved when the link is viewed.\n- Idempotent: enabling an already-shared artifact returns the existing link unchanged, and re-enabling after a revoke brings the same link back — the link is keyed by artifact ID.\n- Artifacts over 16 MiB cannot be shared; the call fails with `InvalidParameter`.\n- Sharing is a snapshot: later republishes do not update the public content until you call `/safari/artifact/gallery/share/sync`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-write-share-enable", "metadata": { - "sidebarTitle": "Disable preset severity rule" + "sidebarTitle": "Enable public sharing" } } } }, - "/rum/issue/preset-severity/rules/enable": { + "/safari/artifact/gallery/share/revoke": { "post": { - "description": "Enable a preset severity rule.", - "operationId": "rum-issue-preset-severity-rules-enable", + "description": "Turn off public sharing; the link stops resolving immediately.", + "operationId": "artifact-write-share-revoke", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "TAHUYnQmXKzgMS4TFVUKvz" + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleIDRequest" + "$ref": "#/components/schemas/ArtifactIdRequest" } } }, @@ -49274,18 +55069,19 @@ "content": { "application/json": { "example": { - "data": {}, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -49309,33 +55105,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enable preset severity rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Revoke public sharing", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- Enabled rules are cached for up to 5 seconds, so the effect on newly ingested errors can lag by a few seconds.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The public CDN objects are deleted, so the link stops resolving; this is a no-op when the artifact is not shared.\n- Re-enabling later returns the same `public_url` — the link is keyed by artifact ID, so revoke is not a way to rotate the link.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-write-share-revoke", "metadata": { - "sidebarTitle": "Enable preset severity rule" + "sidebarTitle": "Revoke public sharing" } } } }, - "/rum/issue/preset-severity/rules/history/list": { + "/safari/artifact/gallery/share/sync": { "post": { - "description": "Return the change history of preset severity rules for a RUM application.", - "operationId": "rum-issue-preset-severity-rules-history-list", + "description": "Refresh the public snapshot of a shared artifact with its latest content.", + "operationId": "artifact-write-share-sync", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "limit": 20, - "p": 0 + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleHistoryListRequest" + "$ref": "#/components/schemas/ArtifactIdRequest" } } }, @@ -49347,133 +55146,23 @@ "application/json": { "example": { "data": { - "has_next_page": false, - "items": [ - { - "rules": [ - { - "account_id": 3790925372131, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "created_at": 1785744052160, - "created_by": 3790925372131, - "deleted_at": 0, - "description": "Downgrade known extension errors to Info", - "filters": [ - [ - { - "key": "error.error_message", - "oper": "IN", - "vals": [ - "/^ResizeObserver loop.*|.*chrome-extension:\\/\\/.*/" - ] - } - ] - ], - "id": 4820, - "priority": 1, - "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", - "rule_name": "Known noisy browser extension errors", - "severity": "Info", - "status": "enabled", - "updated_at": 1785744052160, - "updated_by": 3790925372131 - }, - { - "account_id": 3790925372131, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "created_at": 1785830452160, - "created_by": 3790925372131, - "deleted_at": 0, - "description": "Escalate production crashes to Critical severity", - "filters": [ - [ - { - "key": "error.env", - "oper": "IN", - "vals": [ - "production" - ] - }, - { - "key": "error.is_crash", - "oper": "IN", - "vals": [ - "true" - ] - } - ] - ], - "id": 4821, - "priority": 2, - "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", - "rule_name": "Critical crash spikes", - "severity": "Critical", - "status": "enabled", - "updated_at": 1785830452160, - "updated_by": 3790925372131 - } - ], - "updated_at": 1785916852160, - "updated_by": 2476444212131, - "updated_by_name": "Alice Chen", - "version": 3 - }, - { - "rules": [ - { - "account_id": 3790925372131, - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "created_at": 1785744052160, - "created_by": 3790925372131, - "deleted_at": 0, - "description": "Downgrade known extension errors to Info", - "filters": [ - [ - { - "key": "error.error_message", - "oper": "IN", - "vals": [ - "/^ResizeObserver loop.*|.*chrome-extension:\\/\\/.*/" - ] - } - ] - ], - "id": 4820, - "priority": 1, - "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", - "rule_name": "Known noisy browser extension errors", - "severity": "Info", - "status": "enabled", - "updated_at": 1785744052160, - "updated_by": 3790925372131 - } - ], - "updated_at": 1785830452160, - "updated_by": 3790925372131, - "updated_by_name": "Bob Zhang", - "version": 2 - }, - { - "rules": [], - "updated_at": 1785744052160, - "updated_by": 3790925372131, - "updated_by_name": "Bob Zhang", - "version": 1 - } - ], - "total": 3 + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", + "share_enabled": true, + "shared_at": 1785829900000, + "shared_by": 2476444212131 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumPresetSeverityRuleHistoryListResponse" + "$ref": "#/components/schemas/ArtifactShareState" } }, "type": "object" @@ -49497,32 +55186,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List preset severity rule history", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Update shared snapshot", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Each entry is an application-level snapshot of every rule as it existed immediately *before* the mutation that produced it — not a diff. A fresh snapshot is written before every create/update/enable/disable/delete/reorder/revert call that actually changes something — an `update` carrying none of the mutable fields returns success without writing one — so `version=1` is typically an empty rule set captured just before the first rule was ever created.\n- `rules` items carry the full internal row (including `account_id`, `created_by`, `id`, `deleted_at`), which is a wider shape than the one returned by `rules/list`.\n- `limit` defaults to 20 and is silently capped at 100 rather than rejected.\n- `orderby` accepts only `updated_at` or `version`; any other value (including omitted) falls back to `updated_at` rather than erroring.\n- Results sort descending by default; pass `asc=true` for ascending order.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-history-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Fails with `InvalidParameter` when sharing is not enabled — enable it first.\n- The link never changes; only the snapshot bytes and `shared_at` are refreshed.\n- Use `share_file_id != file_id` on the artifact detail to detect a stale snapshot before syncing.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-write-share-sync", "metadata": { - "sidebarTitle": "List preset severity rule history" + "sidebarTitle": "Update shared snapshot" } } } }, - "/rum/issue/preset-severity/rules/history/revert": { + "/safari/artifact/gallery/update": { "post": { - "description": "Roll back preset severity rules to the state captured in a specific history snapshot.", - "operationId": "rum-issue-preset-severity-rules-history-revert", + "description": "Rename an artifact or transfer it between personal and team scope.", + "operationId": "artifact-write-update", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "version": 2 + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "title": "SK 海力士 2026 Q2 财报深度分析(终稿)" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleHistoryRevertRequest" + "$ref": "#/components/schemas/ArtifactUpdateRequest" } } }, @@ -49533,18 +55227,40 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "can_edit": true, + "content_type": "text/html", + "created_at": 1785293373899, + "creator_name": "yushuangyu", + "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "is_mine": true, + "name": "sk-hynix-q2-2026-report.html", + "person_id": 2476444212131, + "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", + "session_id": "sess_VCbVPZrq9YoyBu8sNCmqUy", + "session_title": "分析海力士财报并发布报告", + "share_enabled": true, + "share_file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", + "shared_at": 1785747928665, + "shared_by": 3790925372131, + "size": 18996, + "team_id": 2477033058131, + "team_name": "研发团队", + "title": "SK 海力士 2026 Q2 财报深度分析(终稿)", + "updated_at": 1785829000000 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/PublishedArtifactItem" } }, "type": "object" @@ -49568,31 +55284,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Revert preset severity rules to a history snapshot", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Update artifact", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Replaces the entire current rule set with the snapshot's rows: `rule_id`, `priority`, `filters`, `severity`, `status`, and `created_by` are preserved from the snapshot, but `created_at`/`updated_at` are reset to the revert time and `updated_by` is set to the reverting user.\n- Returns `InvalidParameter` (not `ResourceNotFound`) when `version` does not correspond to an existing history snapshot for the application.\n- The revert itself is captured as a new history snapshot before it is applied, so a revert can itself be reverted.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-history-revert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Only the provided fields change — omit `title` or `team_id` to leave them unchanged.\n- `team_id: 0` moves the artifact to personal scope (only the creator can manage it); a positive `team_id` requires the caller (for `app_key` calls, the key owner) to be a member of that team.\n- Returns the full artifact after the update.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-write-update", "metadata": { - "sidebarTitle": "Revert preset severity rules to a history snapshot" + "sidebarTitle": "Update artifact" } } } }, - "/rum/issue/preset-severity/rules/list": { + "/safari/artifact/sign": { "post": { - "description": "Return all preset severity rules configured for a RUM application.", - "operationId": "rum-issue-preset-severity-rules-list", + "description": "Create short-lived signed URLs to download or preview a presented file.", + "operationId": "artifact-read-sign", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o" + "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleListRequest" + "$ref": "#/components/schemas/ArtifactSignRequest" } } }, @@ -49604,69 +55325,24 @@ "application/json": { "example": { "data": { - "items": [ - { - "created_at": 1785744052160, - "description": "Downgrade known extension errors to Info", - "filters": [ - [ - { - "key": "error.error_message", - "oper": "IN", - "vals": [ - "/^ResizeObserver loop.*|.*chrome-extension:\\/\\/.*/" - ] - } - ] - ], - "priority": 1, - "rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", - "rule_name": "Known noisy browser extension errors", - "severity": "Info", - "status": "disabled", - "updated_at": 1785916852160 - }, - { - "created_at": 1785830452160, - "description": "Escalate production crashes to Critical severity", - "filters": [ - [ - { - "key": "error.env", - "oper": "IN", - "vals": [ - "production" - ] - }, - { - "key": "error.is_crash", - "oper": "IN", - "vals": [ - "true" - ] - } - ] - ], - "priority": 2, - "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", - "rule_name": "Critical crash spikes", - "severity": "Critical", - "status": "enabled", - "updated_at": 1785830452160 - } - ] + "content_type": "text/html", + "download_url": "/safari/artifact/stream?mode=download&t=cGZfU2RoRUE1ZmJaSkduSHp3ck5KTU1TQnxzZXNzX1ZDYlZQWnJxOVlveUJ1OHNOQ21xVXl8MjQ1MTAwMjc1MTEzMXwyNDc2NDQ0MjEyMTMxfDB8MHwxNzg4NTI5NjI2NTU0.hPQHab0MBNbnrHYwc6VwDJbGonIamfWUr0yeSmLHYAs", + "expires_in": 300, + "name": "sk-hynix-q2-2026-report.html", + "preview_url": "/safari/artifact/stream?mode=preview&t=cGZfU2RoRUE1ZmJaSkduSHp3ck5KTU1TQnxzZXNzX1ZDYlZQWnJxOVlveUJ1OHNOQ21xVXl8MjQ1MTAwMjc1MTEzMXwyNDc2NDQ0MjEyMTMxfDB8MHwxNzg4NTI5NjI2NTU0.hPQHab0MBNbnrHYwc6VwDJbGonIamfWUr0yeSmLHYAs", + "size": 18996 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumPresetSeverityRuleListResponse" + "$ref": "#/components/schemas/SignedURLs" } }, "type": "object" @@ -49690,64 +55366,67 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List preset severity rules", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Create signed file URLs", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Rules are returned ordered by `priority` ascending, then `created_at` ascending — the same order they are evaluated in.\n- Only enabled rules are evaluated against incoming errors; the first enabled rule (in priority order) whose filters match an error wins and assigns its `severity`. Errors matching no enabled rule keep their default severity.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Both URLs expire after `expires_in` seconds (300). Sign again to get fresh URLs.\n- Returned URLs are relative — prepend `https://api.flashcat.cloud` before use, then follow them with `GET /safari/artifact/stream`.\n- The signed token is bound to the calling account and the app_key owner's identity, so a leaked URL does not work for another account or member.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-read-sign", "metadata": { - "sidebarTitle": "List preset severity rules" + "sidebarTitle": "Create signed file URLs" } } } }, - "/rum/issue/preset-severity/rules/reorder": { - "post": { - "description": "Move one preset severity rule to another rule's position in evaluation order.", - "operationId": "rum-issue-preset-severity-rules-reorder", - "requestBody": { - "content": { - "application/json": { - "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "drag_rule_id": "n8mZQ2VbXk4wPRs6DfC9Ay", - "target_rule_id": "TAHUYnQmXKzgMS4TFVUKvz" - }, - "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleReorderRequest" - } + "/safari/artifact/stream": { + "get": { + "description": "Download or preview a file's bytes using a signed token.", + "operationId": "artifact-read-stream", + "parameters": [ + { + "description": "Signed token issued by `POST /safari/artifact/sign`. Bound to the calling account and person; valid for 5 minutes.", + "in": "query", + "name": "t", + "required": true, + "schema": { + "type": "string" } }, - "required": true - }, + { + "description": "`download` (default) serves the file as an attachment; `preview` serves it inline for browser display. Any other value falls back to `download`.", + "in": "query", + "name": "mode", + "required": false, + "schema": { + "default": "download", + "enum": [ + "download", + "preview" + ], + "type": "string" + } + } + ], "responses": { "200": { "content": { - "application/json": { - "example": { - "data": {}, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/octet-stream": { "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/SuccessEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/EmptyResponse" - } - }, - "type": "object" - } - ] + "format": "binary", + "type": "string" } } }, - "description": "Success" + "description": "File bytes, proxied, when the file is hosted on a self-hosted runner. Content-Disposition follows `mode`." + }, + "302": { + "description": "Redirect to a short-lived presigned object-storage URL when the file lives in S3-compatible storage. Follow the `Location` header; no body." }, "400": { "$ref": "#/components/responses/BadRequest" @@ -49762,34 +55441,51 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Reorder preset severity rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Download or preview a file", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Artifacts" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- This moves exactly one rule, not a full reordering: `drag_rule_id`'s `priority` is set to `target_rule_id`'s current `priority`, and every rule between the two original positions — the target rule itself included — shifts by one to close the gap.\n- Lower `priority` numbers are evaluated first; moving toward a lower-numbered target moves the rule earlier in evaluation order, and toward a higher-numbered target moves it later.\n- Returns `ResourceNotFound` if either `drag_rule_id` or `target_rule_id` does not exist in the application.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-reorder", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **10 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Success has two forms: a `302` redirect to a short-lived presigned object-storage URL (files stored in S3-compatible storage), or a `200` binary stream (files hosted on a self-hosted runner). Follow redirects.\n- Responses carry `Cache-Control: private, no-store` — they are never cached by the gateway.\n", + "href": "/en/api-reference/ai-sre/artifacts/artifact-read-stream", "metadata": { - "sidebarTitle": "Reorder preset severity rule" + "sidebarTitle": "Download or preview a file" } } } }, - "/rum/issue/preset-severity/rules/update": { + "/safari/automation/rule/create": { "post": { - "description": "Update the name, description, filters, or severity of a preset severity rule.", - "operationId": "rum-issue-preset-severity-rules-update", + "description": "Create an Automation rule with schedule, HTTP POST, and On-call incident triggers.", + "operationId": "automation-rule-write-create", "requestBody": { "content": { "application/json": { "example": { - "application_id": "WoyQQ3BohkdtPivubEvE8o", - "rule_id": "TAHUYnQmXKzgMS4TFVUKvz", - "rule_name": "Critical crash spikes (updated)", - "severity": "Critical" + "cron_expr": "0 9 * * 1", + "enabled": true, + "http_post_trigger_enabled": true, + "name": "Weekly on-call review", + "oncall_incident_channel_ids": [ + 456 + ], + "oncall_incident_severities": [ + "Critical", + "Warning" + ], + "oncall_incident_trigger_enabled": true, + "prompt": "Summarize last week's alert noise and escalation load.", + "schedule_trigger_enabled": true, + "team_id": 123, + "timezone": "Asia/Shanghai" }, "schema": { - "$ref": "#/components/schemas/RumPresetSeverityRuleUpdateRequest" + "$ref": "#/components/schemas/AutomationRuleCreateRequest" } } }, @@ -49800,18 +55496,50 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "account_id": 10023, + "can_edit": true, + "created_at": 1780367971228, + "cron_expr": "0 9 * * 1", + "enabled": true, + "environment_id": "", + "environment_kind": "", + "http_post_token": "sat_yQ9p8V7n6M5k4J3h2G1f0E9d8C7b6A5z4Y3x2W1v0U", + "http_post_trigger_enabled": true, + "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", + "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", + "name": "Weekly on-call review", + "oncall_incident_channel_ids": [ + 456 + ], + "oncall_incident_severities": [ + "Critical", + "Warning" + ], + "oncall_incident_trigger_enabled": true, + "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", + "owner_id": 80011, + "prompt": "Summarize last week's alert noise and escalation load.", + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "run_scope": "team", + "schedule_next_fire_at_ms": 1780630800000, + "schedule_trigger_enabled": true, + "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", + "team_id": 123, + "timezone": "Asia/Shanghai", + "updated_at": 1780367971228 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/AutomationRuleItem" } }, "type": "object" @@ -49828,6 +55556,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -49835,32 +55566,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update preset severity rule", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Create Automation rule", "tags": [ - "RUM/Issue preset severity rules" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Only fields present in the request are changed; omitted fields keep their current value.\n- Returns `ResourceNotFound` if `rule_id` does not exist in the application.\n- If `filters` is provided it replaces the entire filter structure and is revalidated against the same allowed key set as `create`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issue-preset-severity-rules/rum-issue-preset-severity-rules-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Valid `app_key`; management operations require the caller to manage the target rule |\n\n## Usage\n\n- A caller may create personal rules and rules for any team in the current account; `team_id` can be reassigned later via update (converting a team rule to personal is owner-only; moving into a team requires the caller to belong to it).\n- `cron_expr` is evaluated in `timezone` if provided, else the caller's member timezone, else the account timezone, else the server default (Asia/Shanghai).\n- `http_post_trigger_enabled=true` creates and enables an HTTP POST trigger; the response's `http_post_token` is a one-time value returned only on creation — save it immediately.\n- `oncall_incident_trigger_enabled=true` requires at least one `oncall_incident_channel_ids` entry and one `oncall_incident_severities` value; matching incidents run with `trigger_kind=oncall_incident`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/automations/automation-rule-write-create", "metadata": { - "sidebarTitle": "Update preset severity rule" + "sidebarTitle": "Create Automation rule" } } } }, - "/rum/issue/update": { + "/safari/automation/rule/delete": { "post": { - "description": "Update the status or suspected cause of an issue.", - "operationId": "rum-issue-write-update", + "description": "Delete an Automation rule.", + "operationId": "automation-rule-write-delete", "requestBody": { "content": { "application/json": { "example": { - "issue_id": "NHEacQHi2DhXqobr9qPQz9", - "status": "resolved" + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" }, "schema": { - "$ref": "#/components/schemas/RumIssueUpdateRequest" + "$ref": "#/components/schemas/AutomationRuleIDRequest" } } }, @@ -49871,18 +55606,19 @@ "content": { "application/json": { "example": { - "data": {}, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -49899,6 +55635,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -49906,31 +55645,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update issue", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Delete Automation rule", "tags": [ - "RUM/Issues" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `status` valid values: `for_review`, `reviewed`, `ignored`, `resolved`.\n- `suspected_cause` valid values: `api.failed_request`, `network.error`, `code.exception`, `code.invalid_object_access`, `code.invalid_argument`, `unknown`.\n- Setting `status` to `resolved` also stamps `resolved_at` and `resolved_by` on the issue; moving a resolved issue back to another status clears them.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/rum/issues/rum-issue-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Valid `app_key`; management operations require the caller to manage the target rule |\n\n## Usage\n\n- Deleting a rule also removes its schedule, HTTP POST, and On-call incident triggers; a deleted HTTP POST trigger's token stops working immediately.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/automations/automation-rule-write-delete", "metadata": { - "sidebarTitle": "Update issue" + "sidebarTitle": "Delete Automation rule" } } } }, - "/rum/resource/info": { + "/safari/automation/rule/get": { "post": { - "description": "Return the account's RUM resource record and its current session usage.", - "operationId": "rum-resource-read-info", + "description": "Get one Automation rule by ID.", + "operationId": "automation-rule-read-get", "requestBody": { "content": { "application/json": { "example": { - "no_cache": false + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" }, "schema": { - "$ref": "#/components/schemas/RumResourceInfoRequest" + "$ref": "#/components/schemas/AutomationRuleIDRequest" } } }, @@ -49942,43 +55686,48 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "action.days": 30, - "created_at": 1750000000, - "error.days": 30, - "long_task.days": 15, - "offering_id": 11, - "order_id": "fd_order_20250615_8f3a1c2b", - "product": "rum", - "resource.days": 15, - "resource_id": "rum_2451002751131", - "resource_name": "rum_2451002751131", - "session.days": 30, - "session_investigate.free_cnt": 0, - "session_investigate.used_cnt": 5230, - "session_limit_reached": false, - "session_measure.free_cnt": 0, - "session_measure.used_cnt": 128400, - "session_replay.free_cnt": 0, - "session_replay.used_cnt": 812, - "status": "enabled", - "updated_at": 1752000000, - "version": "professional", - "view.days": 30, - "window_end_time": 1752592000, - "window_start_time": 1750000000 + "account_id": 10023, + "can_edit": true, + "created_at": 1780367971228, + "cron_expr": "0 9 * * 1", + "enabled": true, + "environment_id": "", + "environment_kind": "", + "http_post_trigger_enabled": true, + "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", + "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", + "name": "Weekly on-call review", + "oncall_incident_channel_ids": [ + 456 + ], + "oncall_incident_severities": [ + "Critical", + "Warning" + ], + "oncall_incident_trigger_enabled": true, + "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", + "owner_id": 80011, + "prompt": "Summarize last week's alert noise and escalation load.", + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "run_scope": "team", + "schedule_next_fire_at_ms": 1780630800000, + "schedule_trigger_enabled": true, + "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", + "team_id": 123, + "timezone": "Asia/Shanghai", + "updated_at": 1780367971228 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumResourceItem" + "$ref": "#/components/schemas/AutomationRuleItem" } }, "type": "object" @@ -49995,6 +55744,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -50002,31 +55754,37 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get RUM resource info", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Get Automation rule", "tags": [ - "RUM/Resources" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` when the account has no RUM resource provisioned yet, or when the resource's status is `deleted`/`destroyed`.\n- `no_cache=true` bypasses the short-lived cache of the resource record itself (plan version, quotas, status). The `used_cnt` figures come from a separate hourly cache that this flag does not affect, so they can lag behind live usage either way.\n- The used-count fields reflect the current 30-day billing window (`window_start_time` to `window_end_time`), not lifetime totals.\n- `expired_at` is only populated on on-premises deployments, from the license expiry date; it is omitted entirely for SaaS accounts.\n- For `version=free` accounts, `session_limit_reached` is `true` once usage exceeds the combined free quota across all applications (per-app free quota × application count); it stays `false` while the account has no applications yet.", - "href": "/en/api-reference/rum/resources/rum-resource-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; caller must manage the target rule |\n\n## Usage\n\n- Manage rights mean the personal rule owner; for team rules, an account admin or a member of the rule's team.\n", + "href": "/en/api-reference/ai-sre/automations/automation-rule-read-get", "metadata": { - "sidebarTitle": "Get RUM resource info" + "sidebarTitle": "Get Automation rule" } } } }, - "/rum/session-replay/metadata": { + "/safari/automation/rule/list": { "post": { - "description": "Return the application, device, session bounds, and views recorded for a replayable session.", - "operationId": "rum-session-replay-read-metadata", + "description": "List Automation rules visible to the caller.", + "operationId": "automation-rule-read-list", "requestBody": { "content": { "application/json": { "example": { - "session_id": "0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81" + "limit": 20, + "scope": "all" }, "schema": { - "$ref": "#/components/schemas/RumSessionReplayMetaRequest" + "$ref": "#/components/schemas/AutomationRuleListRequest" } } }, @@ -50038,47 +55796,53 @@ "application/json": { "example": { "data": { - "application": { - "id": "WoyQQ3BohkdtPivubEvE8o" - }, - "device": { - "type": "desktop" - }, - "foreground_periods": [], - "session": { - "end": 1752480600000, - "is_active": false, - "server_time_delta": 0, - "source": "browser", - "start": 1752480000000 - }, - "views": [ + "rules": [ { - "container_source": "", - "container_view_id": "", - "end": 1752480600000, - "is_active": false, - "loading_type": "initial_load", - "name": "/dashboard", - "server_time_delta": 0, - "source": "browser", - "start": 1752480000000, - "url": "https://app.example.com/dashboard", - "view_id": "6f2b6b1a-8f7e-4e3a-9c2b-1a2b3c4d5e6f" + "account_id": 10023, + "can_edit": true, + "created_at": 1780367971228, + "cron_expr": "0 9 * * 1", + "enabled": true, + "environment_id": "", + "environment_kind": "", + "http_post_trigger_enabled": true, + "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", + "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", + "name": "Weekly on-call review", + "oncall_incident_channel_ids": [ + 456 + ], + "oncall_incident_severities": [ + "Critical", + "Warning" + ], + "oncall_incident_trigger_enabled": true, + "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", + "owner_id": 80011, + "prompt": "Summarize last week's alert noise and escalation load.", + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "run_scope": "team", + "schedule_next_fire_at_ms": 1780630800000, + "schedule_trigger_enabled": true, + "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", + "team_id": 123, + "timezone": "Asia/Shanghai", + "updated_at": 1780367971228 } - ] + ], + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumSessionReplayMetaItem" + "$ref": "#/components/schemas/AutomationRuleListResponse" } }, "type": "object" @@ -50095,6 +55859,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -50102,33 +55869,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get session replay metadata", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "List Automation rules", "tags": [ - "RUM/Session replay" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `InvalidParameter` if the session does not exist, or if it has no replay data recorded (`session_has_replay` is false).\n- Returns `InvalidParameter` if no views are found within the session's time window.\n- Pass `ts` to disambiguate when a `session_id` has been reused across different time windows.", - "href": "/en/api-reference/rum/session-replay/rum-session-replay-read-metadata", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; results are filtered to the caller's visible scope |\n\n## Usage\n\n- `all` returns your personal rules plus team rules you can access.\n- Account admins see all team rules in list results, but not other users' personal rules.\n- `team_ids` narrows the visible set and never expands access.\n", + "href": "/en/api-reference/ai-sre/automations/automation-rule-read-list", "metadata": { - "sidebarTitle": "Get session replay metadata" + "sidebarTitle": "List Automation rules" } } } }, - "/rum/session-replay/segments": { + "/safari/automation/rule/run": { "post": { - "description": "Page through the recorded replay segments of a session, as presigned URLs or a raw stream.", - "operationId": "rum-session-replay-read-segments", + "description": "Manually run an Automation rule immediately, outside its schedule.", + "operationId": "automation-rule-write-run", "requestBody": { "content": { "application/json": { "example": { - "limit": 20, - "session_id": "0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81", - "url_mode": true + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" }, "schema": { - "$ref": "#/components/schemas/RumSessionReplaySegmentsRequest" + "$ref": "#/components/schemas/AutomationRuleIDRequest" } } }, @@ -50140,46 +55910,47 @@ "application/json": { "example": { "data": { - "items": [ - "https://rum-replay.flashcat.cloud/short-term/2451002751131/0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81/segments/1752480001234?X-Amz-Signature=example", - "https://rum-replay.flashcat.cloud/short-term/2451002751131/0a4a2e64-8a4f-4b9a-9c1e-3a2f9e6d7c81/segments/1752480032456?X-Amz-Signature=example" - ], - "search_after_ctx": "c2hvcnQtdGVybS8yNDUxMDAyNzUxMTMxLzBhNGEyZTY0LThhNGYtNGI5YS05YzFlLTNhMmY5ZTZkN2M4MS9zZWdtZW50cy8xNzUyNDgwMDMyNDU2" + "preflight": { + "app_name": "ai-sre", + "checks": [ + "rule_loaded", + "actor_authorized", + "app_allowed", + "runtime_scope_resolved", + "rule_config_valid" + ], + "ok": true, + "owner_id": 80011, + "scope": "team", + "team_id": 123 + }, + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "run": { + "run_id": "trun_5oDvqiG64uur6sBNsTc4u", + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" + }, + "trigger_kind": "manual" }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R5" + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/SuccessEnvelope" + "$ref": "#/components/schemas/ResponseEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/RumSessionReplaySegmentsResult" + "$ref": "#/components/schemas/ManualRunRuleResult" } }, "type": "object" } ] } - }, - "application/x-ndjson": { - "schema": { - "description": "Newline-delimited JSON (NDJSON). Each line is one decompressed replay segment record (rrweb-format events), streamed directly and not wrapped in the standard envelope.", - "type": "string" - } } }, - "description": "Success. Shape depends on `url_mode` — see Usage.", - "headers": { - "X-Search-After-Ctx": { - "description": "Base64-encoded pagination cursor for the next call. Only set in streaming mode (`url_mode: false`).", - "schema": { - "type": "string" - } - } - } + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -50187,6 +55958,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -50194,39 +55968,47 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List session replay segments", + "security": [ + { + "AppKeyAuth": [] + } + ], + "summary": "Run Automation rule", "tags": [ - "RUM/Session replay" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- When `url_mode` is `false` (default), the response streams `application/x-ndjson` — one decompressed replay segment JSON object per line — and is **not** wrapped in the standard envelope. The pagination cursor for the next call is returned in the `X-Search-After-Ctx` response header instead of a body field.\n- When `url_mode` is `true`, the response is a normal JSON envelope containing presigned download URLs (valid 1 hour) instead of the raw segment bytes.\n- Pass `ts` to seek to the most recent full-snapshot segment at or before that time, instead of paging from the start of the session.\n- `limit` accepts 1-99; values of 100 or more are rejected.", - "href": "/en/api-reference/rum/session-replay/rum-session-replay-read-segments", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **5 requests/second** per account |\n| Permissions | Valid `app_key`; caller must manage the target rule |\n\n## Usage\n\n- Rate-limited to at most once per minute per rule; a second call within that window returns `429` with `code: \"RequestTooFrequently\"`.\n- Only enabled rules can run manually; a disabled or misconfigured rule fails preflight with a `400` error before any run is created.\n- The call returns once the underlying agent session starts, not once the run finishes; the run continues asynchronously — use List Automation runs to check completion status.\n- `trigger_kind` is always `manual` for runs started this way, distinguishing them from `schedule`, `http_post`, and `oncall_incident` runs in run history.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/automations/automation-rule-write-run", "metadata": { - "sidebarTitle": "List session replay segments" + "sidebarTitle": "Run Automation rule" } } } }, - "/safari/a2a-agent/create": { + "/safari/automation/rule/update": { "post": { - "description": "Register a new A2A remote agent from its agent-card URL.", - "operationId": "remote-agent-write-create", + "description": "Update mutable Automation rule fields, including HTTP POST and On-call incident trigger settings.", + "operationId": "automation-rule-write-update", "requestBody": { "content": { "application/json": { "example": { - "agent_name": "deploy-bot", - "auth_type": "bearer", - "card_url": "https://agents.example.com/deploy-bot/card", - "environments": [ - "env_8s7Hn2kLpQ3xYbVc4Wd2m" + "cron_expr": "15 9 * * 1", + "enabled": true, + "oncall_incident_channel_ids": [ + 456 ], - "instructions": "Inspect deployment pipelines and propose rollbacks when a canary fails health checks.", - "streaming": true, - "team_id": 0 + "oncall_incident_severities": [ + "Critical", + "Warning" + ], + "oncall_incident_trigger_enabled": true, + "rotate_http_post_trigger_token": true, + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" }, "schema": { - "$ref": "#/components/schemas/A2AAgentCreateRequest" + "$ref": "#/components/schemas/AutomationRuleUpdateRequest" } } }, @@ -50238,7 +56020,37 @@ "application/json": { "example": { "data": { - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" + "account_id": 10023, + "can_edit": true, + "created_at": 1780367971228, + "cron_expr": "0 9 * * 1", + "enabled": true, + "environment_id": "", + "environment_kind": "", + "http_post_token": "sat_yQ9p8V7n6M5k4J3h2G1f0E9d8C7b6A5z4Y3x2W1v0U", + "http_post_trigger_enabled": true, + "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", + "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", + "name": "Weekly on-call review", + "oncall_incident_channel_ids": [ + 456 + ], + "oncall_incident_severities": [ + "Critical", + "Warning" + ], + "oncall_incident_trigger_enabled": true, + "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", + "owner_id": 80011, + "prompt": "Summarize last week's alert noise and escalation load.", + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "run_scope": "team", + "schedule_next_fire_at_ms": 1780630800000, + "schedule_trigger_enabled": true, + "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", + "team_id": 123, + "timezone": "Asia/Shanghai", + "updated_at": 1780367971228 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -50250,7 +56062,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/A2AAgentCreateResponse" + "$ref": "#/components/schemas/AutomationRuleItem" } }, "type": "object" @@ -50282,31 +56094,33 @@ "AppKeyAuth": [] } ], - "summary": "Create A2A agent", + "summary": "Update Automation rule", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- `instructions` is required; a deprecated `description` field is still accepted for legacy clients and, if both are sent, must exactly match `instructions`.\n- `card_url` must be an absolute `http`/`https` URL with a non-empty host (reachability is enforced by the execution environment, not here); `auth_type` accepts only `none`, `api_key`, or `bearer`.\n- `environments` restricts where the agent can run: a list of `cloud` and/or BYOC runner environment IDs; omitted or empty means all environments, and each runner must be visible to the caller.\n- Creating into a team (`team_id > 0`) requires the caller to actually belong to that team; only the account owner/admin may create at account scope (`team_id=0`).\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Valid `app_key`; management operations require the caller to manage the target rule |\n\n## Usage\n\n- Omitted or `null` fields are left unchanged. `team_id` reassigns the rule's scope: `0` converts a team rule to personal (owner-only), `>0` moves it into a team the caller belongs to.\n- `cron_expr` and `timezone` can be updated independently — sending only one keeps the other at its current stored value.\n- `rotate_http_post_trigger_token=true` issues a fresh webhook token, returned only in this response.\n- To trigger from On-call incidents, send `oncall_incident_trigger_enabled`, `oncall_incident_channel_ids`, and `oncall_incident_severities`; matching events run with `trigger_kind=oncall_incident`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/automations/automation-rule-write-update", "metadata": { - "sidebarTitle": "Create A2A agent" + "sidebarTitle": "Update Automation rule" } } } }, - "/safari/a2a-agent/delete": { + "/safari/automation/run/list": { "post": { - "description": "Soft-delete an A2A agent by ID.", - "operationId": "remote-agent-write-delete", + "description": "List run history for a rule the caller can manage.", + "operationId": "automation-run-read-list", "requestBody": { "content": { "application/json": { "example": { - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" + "limit": 20, + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "trigger_kind": "schedule" }, "schema": { - "$ref": "#/components/schemas/A2AAgentIDRequest" + "$ref": "#/components/schemas/AutomationRunListRequest" } } }, @@ -50317,7 +56131,34 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "runs": [ + { + "account_id": 10023, + "attempts": 1, + "completed_at": 1780630923456, + "created_at": 1780630800000, + "duration_ms": 123456, + "error_code": "", + "error_message": "", + "kind": "automation_rule", + "occurrence_key": "atrig_6aKp3wT9mQ2xVc8bR1nY7z:1780630800000", + "result_json": { + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" + }, + "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", + "run_id": "trun_5oDvqiG64uur6sBNsTc4u", + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", + "session_name": "Weekly on-call review", + "started_at": 1780630800000, + "stats_json": {}, + "status": "succeeded", + "trigger_kind": "schedule", + "updated_at": 1780630923456 + } + ], + "total": 1 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -50328,8 +56169,7 @@ { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/AutomationRunListResponse" } }, "type": "object" @@ -50361,31 +56201,31 @@ "AppKeyAuth": [] } ], - "summary": "Delete A2A agent", + "summary": "List Automation runs", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Delete is a soft delete; the agent stops appearing in list/get and can no longer be dispatched once removed.\n- Requires edit permission (`access.CanEdit`) on the agent's team.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; caller must manage the target rule |\n\n## Usage\n\n- Run history is visible only when the caller can manage the rule: the personal rule owner; for team rules, an account admin or a member of the rule's team.\n", + "href": "/en/api-reference/ai-sre/automations/automation-run-read-list", "metadata": { - "sidebarTitle": "Delete A2A agent" + "sidebarTitle": "List Automation runs" } } } }, - "/safari/a2a-agent/disable": { + "/safari/automation/template/list": { "post": { - "description": "Disable an enabled A2A agent.", - "operationId": "remote-agent-write-disable", + "description": "List preset Automation templates for the requested locale.", + "operationId": "automation-template-read-list", "requestBody": { "content": { "application/json": { "example": { - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" + "locale": "en-US" }, "schema": { - "$ref": "#/components/schemas/A2AAgentIDRequest" + "$ref": "#/components/schemas/AutomationTemplateListRequest" } } }, @@ -50396,7 +56236,17 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "templates": [ + { + "description": "Analyze incidents, alerts, response activity, notification load, and related changes from the past week.", + "enabled": false, + "icon": "chart-no-axes-combined", + "name": "Weekly Insights", + "prompt": "Generate a weekly insights report. Analyze incidents, alerts, response activity, notification load, and related changes from the past week. Focus on what happened this week, which signals deserve attention, and which improvement actions are most valuable. Do not modify any Flashduty business state.\n" + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -50407,8 +56257,7 @@ { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/AutomationTemplateListResponse" } }, "type": "object" @@ -50440,31 +56289,31 @@ "AppKeyAuth": [] } ], - "summary": "Disable A2A agent", + "summary": "List Automation templates", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Automations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Requires edit permission (`access.CanEdit`) on the agent's team.\n- Returns `InvalidParameter` if the agent is already disabled.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; results are filtered to the caller's visible scope |\n", + "href": "/en/api-reference/ai-sre/automations/automation-template-read-list", "metadata": { - "sidebarTitle": "Disable A2A agent" + "sidebarTitle": "List Automation templates" } } } }, - "/safari/a2a-agent/enable": { + "/safari/knowledge/file/delete": { "post": { - "description": "Enable a disabled A2A agent.", - "operationId": "remote-agent-write-enable", + "description": "Delete a knowledge file by its relative path.", + "operationId": "knowledge-file-write-delete", "requestBody": { "content": { "application/json": { "example": { - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" + "rel_path": "tmp/openapi-delete-example.md" }, "schema": { - "$ref": "#/components/schemas/A2AAgentIDRequest" + "$ref": "#/components/schemas/KnowledgeFileDeleteRequest" } } }, @@ -50475,7 +56324,7 @@ "content": { "application/json": { "example": { - "data": null, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -50486,8 +56335,7 @@ { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/KnowledgeFileDeleteResponse" } }, "type": "object" @@ -50519,31 +56367,31 @@ "AppKeyAuth": [] } ], - "summary": "Enable A2A agent", + "summary": "Delete knowledge file", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Requires edit permission (`access.CanEdit`) on the agent's team, not just visibility into it.\n- Returns `InvalidParameter` if the agent is already enabled.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- Deleting is idempotent — removing a file that does not exist succeeds.\n- When other knowledge files still reference the target, the delete fails with `ReferenceExist` listing the referrers; set `force` to proceed (the referrers are returned as warnings).\n- Omitting `pack_id` targets the account-scope knowledge; editing the account knowledge requires account owner/admin, editing team knowledge requires team membership.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-write-delete", "metadata": { - "sidebarTitle": "Enable A2A agent" + "sidebarTitle": "Delete knowledge file" } } } }, - "/safari/a2a-agent/get": { + "/safari/knowledge/file/get": { "post": { - "description": "Get one A2A agent by ID.", - "operationId": "remote-agent-read-get", + "description": "Return a knowledge file's metadata and its base64-encoded content.", + "operationId": "knowledge-file-read-get", "requestBody": { "content": { "application/json": { "example": { - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D" + "rel_path": "tmp/openapi-example.md" }, "schema": { - "$ref": "#/components/schemas/A2AAgentIDRequest" + "$ref": "#/components/schemas/KnowledgeFileGetRequest" } } }, @@ -50555,30 +56403,17 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "agent_card_name": "Deploy Bot", - "agent_card_skills": [ - "rollback", - "diff" - ], - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D", - "agent_name": "deploy-bot", - "auth_mode": "shared", - "auth_type": "bearer", - "can_edit": true, - "card_resolve_timeout": 0, - "card_url": "https://agents.example.com/deploy-bot/card", - "created_at": 1716960000000, - "created_by": 80011, - "environments": [ - "env_8s7Hn2kLpQ3xYbVc4Wd2m" - ], - "instructions": "Inspect deployment pipelines and propose rollbacks when a canary fails health checks.", - "status": "enabled", - "streaming": true, - "task_timeout": 0, - "team_id": 0, - "updated_at": 1717046400000 + "content_b64": "IyBPcGVuQVBJIGV4YW1wbGUKVGVtcCBmaWxlIGZvciBBUEkgZG9jcyBleGFtcGxlLgo=", + "file": { + "checksum": "a0775f9b3f392cd0560b21ad2f579ae4a5d6b1282b9eb145688ba2de717a816d", + "content_type": "text/markdown", + "file_id": "kfl_gctXKRG45aFQGgxSFr59WY", + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "rel_path": "tmp/openapi-example.md", + "size_bytes": 50, + "updated_at_ms": 1786458764961, + "updated_by": 2476444212131 + } }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -50590,7 +56425,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/A2AAgentItem" + "$ref": "#/components/schemas/KnowledgeFileGetResponse" } }, "type": "object" @@ -50619,33 +56454,31 @@ "AppKeyAuth": [] } ], - "summary": "Get A2A agent detail", + "summary": "Get knowledge file", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `card_resolve_timeout` and `task_timeout` are always `0` today — the API does not yet expose a way to set them.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Content is returned in `content_b64` (base64); knowledge files are guaranteed UTF-8 text.\n- Omitting `pack_id` targets the account-scope knowledge; reading team-scope knowledge requires team membership.\n- A missing file returns `ResourceNotFound` (HTTP 400).\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-read-get", "metadata": { - "sidebarTitle": "Get A2A agent detail" + "sidebarTitle": "Get knowledge file" } } } }, - "/safari/a2a-agent/list": { + "/safari/knowledge/file/list": { "post": { - "description": "List A2A agents visible to the caller across account and team scopes, with pagination.", - "operationId": "remote-agent-read-list", + "description": "List knowledge files with metadata such as size and checksum.", + "operationId": "knowledge-file-read-list", "requestBody": { "content": { "application/json": { "example": { - "include_account": true, - "limit": 20, - "offset": 0 + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc" }, "schema": { - "$ref": "#/components/schemas/A2AAgentListRequest" + "$ref": "#/components/schemas/KnowledgeFileListRequest" } } }, @@ -50657,35 +56490,29 @@ "application/json": { "example": { "data": { - "items": [ + "files": [ { - "account_id": 10023, - "agent_card_name": "Deploy Bot", - "agent_card_skills": [ - "rollback", - "diff" - ], - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D", - "agent_name": "deploy-bot", - "auth_mode": "shared", - "auth_type": "bearer", - "can_edit": true, - "card_resolve_timeout": 0, - "card_url": "https://agents.example.com/deploy-bot/card", - "created_at": 1716960000000, - "created_by": 80011, - "environments": [ - "env_8s7Hn2kLpQ3xYbVc4Wd2m" - ], - "instructions": "Inspect deployment pipelines and propose rollbacks when a canary fails health checks.", - "status": "enabled", - "streaming": true, - "task_timeout": 0, - "team_id": 0, - "updated_at": 1717046400000 + "checksum": "fccc276c0d7fbae2e9508285cdde0f8475169634e89e466dac2e59f176c9be2f", + "content_type": "text/markdown", + "file_id": "kfl_QvT4g3c8zAHxTthuT6hGne", + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "rel_path": "aliyun.md", + "size_bytes": 1436, + "updated_at_ms": 1783311304757, + "updated_by": 3790925372131 + }, + { + "checksum": "450eabf178b41e46ea2f43d395a80bf8b956ddb9c9cea34f44ffc69a53e7a36b", + "content_type": "text/markdown", + "file_id": "kfl_BMsQZCZSqhW4TFskYNb4H5", + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "rel_path": "DUTY.md", + "size_bytes": 1301, + "updated_at_ms": 1784800003394, + "updated_by": 2476444212131 } ], - "total": 1 + "total": 17 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -50697,7 +56524,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/A2AAgentListResponse" + "$ref": "#/components/schemas/KnowledgeFileListResponse" } }, "type": "object" @@ -50726,32 +56553,33 @@ "AppKeyAuth": [] } ], - "summary": "List A2A agents", + "summary": "List knowledge files", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Pagination uses `offset`/`limit` (not `p`/`limit`).\n- `scope=account` restricts to account-scoped agents; `scope=team` restricts to the caller's visible teams; the default `all` combines both, subject to `include_account`.\n- `query` performs a case-insensitive substring search across agent name, instructions, card URL, agent ID, and the resolved card name.\n- `card_resolve_timeout` and `task_timeout` are always `0` today — the API does not yet expose a way to set them.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Omitting `pack_id` targets the caller's account-scope knowledge (created lazily if absent).\n- Reading team-scope knowledge requires membership of that team.\n- `p`/`limit` are accepted but the current implementation always returns the full file list.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-read-list", "metadata": { - "sidebarTitle": "List A2A agents" + "sidebarTitle": "List knowledge files" } } } }, - "/safari/a2a-agent/update": { + "/safari/knowledge/file/put": { "post": { - "description": "Apply a partial update to an A2A agent. Omit a field to leave it unchanged.", - "operationId": "remote-agent-write-update", + "description": "Create or overwrite a knowledge file with base64-encoded content.", + "operationId": "knowledge-file-write-put", "requestBody": { "content": { "application/json": { "example": { - "agent_id": "a2a_6mWqZ2pK9nLcR3tY8uVb4D", - "instructions": "Inspect deployment pipelines and propose rollbacks." + "content_b64": "IyBPcGVuQVBJIGV4YW1wbGUKVGVtcCBmaWxlIGZvciBBUEkgZG9jcyBleGFtcGxlLgo=", + "content_type": "text/markdown", + "rel_path": "tmp/openapi-example.md" }, "schema": { - "$ref": "#/components/schemas/A2AAgentUpdateRequest" + "$ref": "#/components/schemas/KnowledgeFilePutRequest" } } }, @@ -50762,7 +56590,18 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "file": { + "checksum": "a0775f9b3f392cd0560b21ad2f579ae4a5d6b1282b9eb145688ba2de717a816d", + "content_type": "text/markdown", + "file_id": "kfl_gctXKRG45aFQGgxSFr59WY", + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "rel_path": "tmp/openapi-example.md", + "size_bytes": 50, + "updated_at_ms": 1786458764961, + "updated_by": 2476444212131 + } + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -50773,8 +56612,7 @@ { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/KnowledgeFilePutResponse" } }, "type": "object" @@ -50806,31 +56644,29 @@ "AppKeyAuth": [] } ], - "summary": "Update A2A agent", + "summary": "Upload knowledge file", "tags": [ - "AI SRE/A2A agents" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Agent Manage** (`ai-sre`) |\n\n## Usage\n\n- Requires edit permission (`access.CanEdit`) on the agent's *current* team before any field may change.\n- Reassigning `team_id` requires rights on the destination team; if the team changes without also sending a new environment binding, the existing runner binding must remain selectable by the caller or the update is rejected.\n- Changing `auth_mode` always rewrites `secret_schema` together with it; omitting `oauth_metadata` alongside a new `auth_mode` clears it to empty.\n- Sending back a masked or empty value for a sensitive `auth_config` key (`api_key`, `token`, `client_secret`) keeps the stored secret instead of overwriting it.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/a2a-agents/remote-agent-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- The file body is sent as base64 text in the JSON field `content_b64` — this is not a multipart upload.\n- Writing an existing `rel_path` overwrites it; `content_type` is inferred from the extension when omitted (`.md` → `text/markdown`).\n- Content must decode to valid UTF-8 text; binary payloads are rejected with `InvalidParameter`.\n- Editing the account-scope knowledge requires account owner/admin; editing team knowledge requires team membership.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-write-put", "metadata": { - "sidebarTitle": "Update A2A agent" + "sidebarTitle": "Upload knowledge file" } } } }, - "/safari/artifact/gallery/delete": { + "/safari/knowledge/get": { "post": { - "description": "Detach an artifact from the gallery; the source file stays with its session.", - "operationId": "artifact-write-delete", + "description": "Return the metadata and file list of the account-scope knowledge.", + "operationId": "knowledge-pack-read-get", "requestBody": { "content": { "application/json": { - "example": { - "artifact_id": "art_CWQzDU2PXSRJvKDhQbuMKu" - }, + "example": {}, "schema": { - "$ref": "#/components/schemas/ArtifactIdRequest" + "$ref": "#/components/schemas/KnowledgeGetRequest" } } }, @@ -50841,7 +56677,44 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "files": [ + { + "checksum": "fccc276c0d7fbae2e9508285cdde0f8475169634e89e466dac2e59f176c9be2f", + "content_type": "text/markdown", + "file_id": "kfl_QvT4g3c8zAHxTthuT6hGne", + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "rel_path": "aliyun.md", + "size_bytes": 1436, + "updated_at_ms": 1783311304757, + "updated_by": 3790925372131 + }, + { + "checksum": "450eabf178b41e46ea2f43d395a80bf8b956ddb9c9cea34f44ffc69a53e7a36b", + "content_type": "text/markdown", + "file_id": "kfl_BMsQZCZSqhW4TFskYNb4H5", + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "rel_path": "DUTY.md", + "size_bytes": 1301, + "updated_at_ms": 1784800003394, + "updated_by": 2476444212131 + } + ], + "pack": { + "account_id": 2451002751131, + "can_edit": true, + "created_at_ms": 1778768680053, + "created_by": 2476444212131, + "duty_version": 130, + "file_count": 17, + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "scope": "account", + "scope_id": 2451002751131, + "total_bytes": 41010, + "updated_at_ms": 1786456567177, + "version": 134 + } + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -50852,8 +56725,7 @@ { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/KnowledgeGetResponse" } }, "type": "object" @@ -50882,34 +56754,31 @@ "AppKeyAuth": [] } ], - "summary": "Remove artifact from gallery", + "summary": "Get account knowledge", "tags": [ - "AI SRE/Artifacts" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- This is a detach, not a byte delete: the underlying presented file stays with the source session and can be published again.\n- If public sharing was enabled, the public objects are destroyed in the same operation and the link stops resolving.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Always targets the caller's account-scope knowledge — there is no `pack_id` parameter; use `POST /safari/knowledge/pack/list` to discover team knowledge.\n- The account knowledge is created lazily on first access, so a valid account never gets not-found here.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-read-get", "metadata": { - "sidebarTitle": "Remove artifact from gallery" + "sidebarTitle": "Get account knowledge" } } } }, - "/safari/artifact/gallery/file-state": { + "/safari/knowledge/pack/delete": { "post": { - "description": "Check which presented files already have a live published artifact.", - "operationId": "artifact-read-get-file-state", + "description": "Delete knowledge and all of its files.", + "operationId": "knowledge-pack-write-delete", "requestBody": { "content": { "application/json": { "example": { - "file_ids": [ - "pf_SdhEA5fbZJGnHzwrNJMMSB", - "pf_9kLm2nQpRsTuVwXyZaBcDe" - ] + "pack_id": "kpk_YqHXPTEUHQFGepUfRS7vsh" }, "schema": { - "$ref": "#/components/schemas/ArtifactFileStateRequest" + "$ref": "#/components/schemas/KnowledgePackDeleteRequest" } } }, @@ -50921,14 +56790,7 @@ "application/json": { "example": { "data": { - "items": [ - { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", - "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "gallery_path": "/ai-sre/artifacts/art_VnfrWic8UbB9q3EfYR4Gmg", - "title": "SK 海力士 2026 Q2 财报深度分析" - } - ] + "ok": true }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -50940,7 +56802,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ArtifactFileStateResponse" + "$ref": "#/components/schemas/KnowledgePackDeleteResponse" } }, "type": "object" @@ -50957,6 +56819,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -50969,31 +56834,32 @@ "AppKeyAuth": [] } ], - "summary": "Get file publish state", + "summary": "Delete knowledge", "tags": [ - "AI SRE/Artifacts" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- At most 50 `file_ids` per call; duplicates and empty strings are ignored.\n- Files with no live published artifact are simply absent from `items` — match results by the echoed `file_id`.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-read-get-file-state", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- Deleting knowledge removes every file it contains; the operation cannot be undone.\n- Deleting the account-scope knowledge is allowed; it is re-created empty on next access.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-write-delete", "metadata": { - "sidebarTitle": "Get file publish state" + "sidebarTitle": "Delete knowledge" } } } }, - "/safari/artifact/gallery/get": { + "/safari/knowledge/pack/ensure": { "post": { - "description": "Get a single published artifact by ID.", - "operationId": "artifact-read-get", + "description": "Idempotently create the knowledge at the given scope, or return the existing one.", + "operationId": "knowledge-pack-write-ensure", "requestBody": { "content": { "application/json": { "example": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" + "scope": "team", + "scope_id": 2477033058131 }, "schema": { - "$ref": "#/components/schemas/ArtifactIdRequest" + "$ref": "#/components/schemas/KnowledgePackEnsureRequest" } } }, @@ -51005,27 +56871,18 @@ "application/json": { "example": { "data": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "account_id": 2451002751131, "can_edit": true, - "content_type": "text/html", - "created_at": 1785293373899, - "creator_name": "yushuangyu", - "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "is_mine": true, - "name": "sk-hynix-q2-2026-report.html", - "person_id": 2476444212131, - "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", - "session_id": "sess_VCbVPZrq9YoyBu8sNCmqUy", - "session_title": "分析海力士财报并发布报告", - "share_enabled": true, - "share_file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "shared_at": 1785747928665, - "shared_by": 3790925372131, - "size": 18996, - "team_id": 2477033058131, - "team_name": "研发团队", - "title": "SK 海力士 2026 Q2 财报深度分析", - "updated_at": 1785747910219 + "created_at_ms": 1778768680053, + "created_by": 2476444212131, + "duty_version": 130, + "file_count": 17, + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "scope": "account", + "scope_id": 2451002751131, + "total_bytes": 41010, + "updated_at_ms": 1786458765182, + "version": 138 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -51037,7 +56894,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PublishedArtifactItem" + "$ref": "#/components/schemas/KnowledgePackItem" } }, "type": "object" @@ -51054,6 +56911,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51066,33 +56926,34 @@ "AppKeyAuth": [] } ], - "summary": "Get artifact detail", + "summary": "Ensure knowledge", "tags": [ - "AI SRE/Artifacts" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Visibility is account-wide: any valid `app_key` can read any artifact in the account. `is_mine` and `can_edit` are computed relative to the key owner.\n- When `share_enabled` is true and `file_id` differs from `share_file_id`, the public snapshot is stale — refresh it with `/safari/artifact/gallery/share/sync`.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- Idempotent: if knowledge already exists at (`scope`, `scope_id`), it is returned unchanged.\n- For `account` scope, `scope_id` is ignored (the account ID is used) and a default `DUTY.md` is seeded on first creation.\n- Creating the account-scope knowledge requires account owner/admin; creating into a team requires membership of that team.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-write-ensure", "metadata": { - "sidebarTitle": "Get artifact detail" + "sidebarTitle": "Ensure knowledge" } } } }, - "/safari/artifact/gallery/list": { + "/safari/knowledge/pack/list": { "post": { - "description": "List published artifacts visible to the caller, with pagination and title search.", - "operationId": "artifact-read-list", + "description": "List the knowledge visible to the caller across account and team scopes.", + "operationId": "knowledge-pack-read-list", "requestBody": { "content": { "application/json": { "example": { + "include_account": true, "limit": 20, - "page": 1, + "p": 1, "scope": "all" }, "schema": { - "$ref": "#/components/schemas/ArtifactListRequest" + "$ref": "#/components/schemas/KnowledgePackListRequest" } } }, @@ -51104,50 +56965,38 @@ "application/json": { "example": { "data": { - "items": [ + "packs": [ { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", + "account_id": 2451002751131, "can_edit": true, - "content_type": "text/html", - "created_at": 1785293373899, - "creator_name": "yushuangyu", - "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "is_mine": true, - "name": "sk-hynix-q2-2026-report.html", - "person_id": 2476444212131, - "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", - "session_id": "sess_VCbVPZrq9YoyBu8sNCmqUy", - "session_title": "分析海力士财报并发布报告", - "share_enabled": true, - "share_file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "shared_at": 1785747928665, - "shared_by": 3790925372131, - "size": 18996, - "team_id": 2477033058131, - "team_name": "研发团队", - "title": "SK 海力士 2026 Q2 财报深度分析", - "updated_at": 1785747910219 + "created_at_ms": 1778768680053, + "created_by": 2476444212131, + "duty_version": 130, + "file_count": 17, + "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", + "scope": "account", + "scope_id": 2451002751131, + "total_bytes": 41010, + "updated_at_ms": 1786456567177, + "version": 134 }, { - "artifact_id": "art_CWQzDU2PXSRJvKDhQbuMKu", + "account_id": 2451002751131, "can_edit": true, - "content_type": "application/pdf", - "created_at": 1785229432881, - "creator_name": "牛伟利", - "file_id": "pf_Jnc4E5YBcWLGzunB4ntP9s", - "is_mine": false, - "name": "rum_recommendation.pdf", - "person_id": 3790925372131, - "session_id": "sess_QXUC9C2PYWP5EE7vETR3UD", - "session_title": "生成 RUM 文档多格式", - "size": 137107, - "team_id": 2477033058131, + "created_at_ms": 1782201586089, + "created_by": 2476444212131, + "duty_version": 15, + "file_count": 4, + "pack_id": "kpk_5qRL34nKtoWM4nQVT2kHzy", + "scope": "team", + "scope_id": 2477033058131, "team_name": "研发团队", - "title": "rum_recommendation", - "updated_at": 1785741344822 + "total_bytes": 11159, + "updated_at_ms": 1785462092702, + "version": 15 } ], - "total": 17 + "total": 3 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -51159,7 +57008,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ArtifactListResponse" + "$ref": "#/components/schemas/KnowledgePackListResponse" } }, "type": "object" @@ -51188,32 +57037,33 @@ "AppKeyAuth": [] } ], - "summary": "List artifacts", + "summary": "List knowledge", "tags": [ - "AI SRE/Artifacts" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `scope` selects `all` (default — the caller's own personal artifacts plus every team the caller belongs to), `personal` (only the caller's own), or `team` (only team-owned artifacts of the caller's teams).\n- `team_ids` narrows further to specific teams, intersected with the caller's visibility — teams the caller does not belong to return nothing.\n- Default sort is `updated_at` descending; set `orderby` to `created_at` to change the field and `asc: true` to flip direction.\n- For an `app_key` call, visibility is evaluated against the key owner's identity — the list shows that member's personal artifacts and their teams' artifacts.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Visibility matches the console: admins see the account knowledge plus every team's knowledge; non-admins see the account knowledge plus their own teams' knowledge, and requested `team_ids` are silently intersected with their teams.\n- `scope` selects `all` (default), `account`-only, or `team`-only, overriding `include_account`.\n- `query` applies a case-insensitive substring filter over knowledge ID, scope, and team name; `p`/`limit` paginate the filtered result.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-read-list", "metadata": { - "sidebarTitle": "List artifacts" + "sidebarTitle": "List knowledge" } } } }, - "/safari/artifact/gallery/publish-from-file": { + "/safari/knowledge/pack/update": { "post": { - "description": "Publish a session-produced file to the artifact gallery.", - "operationId": "artifact-write-publish", + "description": "Move knowledge to a different account or team scope.", + "operationId": "knowledge-pack-write-update", "requestBody": { "content": { "application/json": { "example": { - "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "title": "SK 海力士 2026 Q2 财报深度分析" + "pack_id": "kpk_5qRL34nKtoWM4nQVT2kHzy", + "scope": "team", + "scope_id": 2477033058131 }, "schema": { - "$ref": "#/components/schemas/ArtifactPublishFromFileRequest" + "$ref": "#/components/schemas/KnowledgePackUpdateRequest" } } }, @@ -51225,9 +57075,19 @@ "application/json": { "example": { "data": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", - "gallery_path": "/ai-sre/artifacts/art_VnfrWic8UbB9q3EfYR4Gmg", - "title": "SK 海力士 2026 Q2 财报深度分析" + "account_id": 2451002751131, + "can_edit": true, + "created_at_ms": 1782201586089, + "created_by": 2476444212131, + "duty_version": 15, + "file_count": 4, + "pack_id": "kpk_5qRL34nKtoWM4nQVT2kHzy", + "scope": "team", + "scope_id": 2477033058131, + "team_name": "研发团队", + "total_bytes": 11159, + "updated_at_ms": 1785462092702, + "version": 15 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -51239,7 +57099,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ArtifactPublishResponse" + "$ref": "#/components/schemas/KnowledgePackItem" } }, "type": "object" @@ -51256,6 +57116,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51268,31 +57131,35 @@ "AppKeyAuth": [] } ], - "summary": "Publish file as artifact", + "summary": "Update knowledge", "tags": [ - "AI SRE/Artifacts" + "AI SRE/Knowledge" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Allowed file types: HTML/Markdown, images, PDF, text/data/code files, and zip/tar archives, matched by extension. Files over 16 MiB are rejected.\n- Publishing is an upsert keyed by the source session and workspace path — republishing the same file replaces the artifact's bytes under a fresh `file_id`, which makes an existing public snapshot stale until synced.\n- The artifact inherits personal/team scope from the source session; move it afterwards with `/safari/artifact/gallery/update` if needed.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-write-publish", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- `scope` is the only mutable field; omitting it is a no-op that returns the current knowledge.\n- For `team` scope, `scope_id` is required; for `account` scope it is set to the account ID automatically.\n- The move fails with `ReferenceExist` when the destination scope already has knowledge — knowledge is never merged.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-write-update", "metadata": { - "sidebarTitle": "Publish file as artifact" + "sidebarTitle": "Update knowledge" } } } }, - "/safari/artifact/gallery/share/enable": { + "/safari/mcp/server/create": { "post": { - "description": "Turn on anonymous public sharing for an artifact and return its public link.", - "operationId": "artifact-write-share-enable", + "description": "Register a new MCP server (connector) on the account.", + "operationId": "mcp-write-server-create", "requestBody": { "content": { "application/json": { "example": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" + "description": "Query Prometheus metrics and alerts.", + "server_name": "prometheus", + "status": "enabled", + "transport": "streamable-http", + "url": "https://mcp.example.com/prometheus" }, "schema": { - "$ref": "#/components/schemas/ArtifactIdRequest" + "$ref": "#/components/schemas/MCPServerCreateRequest" } } }, @@ -51304,11 +57171,22 @@ "application/json": { "example": { "data": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", - "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", - "share_enabled": true, - "shared_at": 1785747928665, - "shared_by": 2476444212131 + "account_id": 10023, + "auth_mode": "shared", + "call_timeout": 60, + "can_edit": true, + "connect_timeout": 10, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Query Prometheus metrics and alerts.", + "environments": [], + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", + "server_name": "prometheus", + "status": "enabled", + "team_id": 0, + "transport": "streamable-http", + "updated_at": 1717046400000, + "url": "https://mcp.example.com/prometheus" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -51320,7 +57198,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ArtifactShareState" + "$ref": "#/components/schemas/MCPServerItem" } }, "type": "object" @@ -51337,6 +57215,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51349,31 +57230,31 @@ "AppKeyAuth": [] } ], - "summary": "Enable public sharing", + "summary": "Create MCP server", "tags": [ - "AI SRE/Artifacts" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The public link is anonymous — anyone with it can view the content, and the link may be forwarded. Content is copied to public CDN objects; the gallery API is not involved when the link is viewed.\n- Idempotent: enabling an already-shared artifact returns the existing link unchanged, and re-enabling after a revoke brings the same link back — the link is keyed by artifact ID.\n- Artifacts over 16 MiB cannot be shared; the call fails with `InvalidParameter`.\n- Sharing is a snapshot: later republishes do not update the public content until you call `/safari/artifact/gallery/share/sync`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-write-share-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- `command`/`args`/`env` apply to `stdio`; `url`/`headers` apply to `sse`/`streamable-http`.\n- Server name must start with a letter and contain only letters, digits, `-`, or `_`, and is unique within its scope (account-wide or one team), case-insensitive; violations return InvalidParameter.\n- `environments` restricts where the server can run: a list of `cloud` and/or BYOC runner environment IDs; omitted or empty means all environments.\n- `per_user_secret` auth mode requires `secret_schema` to be valid JSON with a non-empty `header_name`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-create", "metadata": { - "sidebarTitle": "Enable public sharing" + "sidebarTitle": "Create MCP server" } } } }, - "/safari/artifact/gallery/share/revoke": { + "/safari/mcp/server/delete": { "post": { - "description": "Turn off public sharing; the link stops resolving immediately.", - "operationId": "artifact-write-share-revoke", + "description": "Delete an MCP server by ID.", + "operationId": "mcp-write-server-delete", "requestBody": { "content": { "application/json": { "example": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" }, "schema": { - "$ref": "#/components/schemas/ArtifactIdRequest" + "$ref": "#/components/schemas/MCPServerDeleteRequest" } } }, @@ -51413,6 +57294,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51425,31 +57309,31 @@ "AppKeyAuth": [] } ], - "summary": "Revoke public sharing", + "summary": "Delete MCP server", "tags": [ - "AI SRE/Artifacts" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The public CDN objects are deleted, so the link stops resolving; this is a no-op when the artifact is not shared.\n- Re-enabling later returns the same `public_url` — the link is keyed by artifact ID, so revoke is not a way to rotate the link.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-write-share-revoke", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-delete", "metadata": { - "sidebarTitle": "Revoke public sharing" + "sidebarTitle": "Delete MCP server" } } } }, - "/safari/artifact/gallery/share/sync": { + "/safari/mcp/server/disable": { "post": { - "description": "Refresh the public snapshot of a shared artifact with its latest content.", - "operationId": "artifact-write-share-sync", + "description": "Disable an enabled MCP server.", + "operationId": "mcp-write-server-disable", "requestBody": { "content": { "application/json": { "example": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg" + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" }, "schema": { - "$ref": "#/components/schemas/ArtifactIdRequest" + "$ref": "#/components/schemas/MCPServerStatusRequest" } } }, @@ -51460,13 +57344,7 @@ "content": { "application/json": { "example": { - "data": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", - "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", - "share_enabled": true, - "shared_at": 1785829900000, - "shared_by": 2476444212131 - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -51477,7 +57355,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ArtifactShareState" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -51494,6 +57373,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51506,32 +57388,31 @@ "AppKeyAuth": [] } ], - "summary": "Update shared snapshot", + "summary": "Disable MCP server", "tags": [ - "AI SRE/Artifacts" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Fails with `InvalidParameter` when sharing is not enabled — enable it first.\n- The link never changes; only the snapshot bytes and `shared_at` are refreshed.\n- Use `share_file_id != file_id` on the artifact detail to detect a stale snapshot before syncing.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-write-share-sync", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Disabling an already-disabled server returns InvalidParameter instead of a silent no-op.\n- Requires edit permission on the server's current team: account-scope servers are owner/admin only; team-scope servers require the caller to belong to that team (or be owner/admin).\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-disable", "metadata": { - "sidebarTitle": "Update shared snapshot" + "sidebarTitle": "Disable MCP server" } } } }, - "/safari/artifact/gallery/update": { + "/safari/mcp/server/enable": { "post": { - "description": "Rename an artifact or transfer it between personal and team scope.", - "operationId": "artifact-write-update", + "description": "Enable a disabled MCP server.", + "operationId": "mcp-write-server-enable", "requestBody": { "content": { "application/json": { "example": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", - "title": "SK 海力士 2026 Q2 财报深度分析(终稿)" + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" }, "schema": { - "$ref": "#/components/schemas/ArtifactUpdateRequest" + "$ref": "#/components/schemas/MCPServerStatusRequest" } } }, @@ -51542,29 +57423,7 @@ "content": { "application/json": { "example": { - "data": { - "artifact_id": "art_VnfrWic8UbB9q3EfYR4Gmg", - "can_edit": true, - "content_type": "text/html", - "created_at": 1785293373899, - "creator_name": "yushuangyu", - "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "is_mine": true, - "name": "sk-hynix-q2-2026-report.html", - "person_id": 2476444212131, - "public_url": "https://console.flashcat.cloud/share/artifact/art_VnfrWic8UbB9q3EfYR4Gmg", - "session_id": "sess_VCbVPZrq9YoyBu8sNCmqUy", - "session_title": "分析海力士财报并发布报告", - "share_enabled": true, - "share_file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB", - "shared_at": 1785747928665, - "shared_by": 3790925372131, - "size": 18996, - "team_id": 2477033058131, - "team_name": "研发团队", - "title": "SK 海力士 2026 Q2 财报深度分析(终稿)", - "updated_at": 1785829000000 - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -51575,7 +57434,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/PublishedArtifactItem" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -51592,6 +57452,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51604,31 +57467,31 @@ "AppKeyAuth": [] } ], - "summary": "Update artifact", + "summary": "Enable MCP server", "tags": [ - "AI SRE/Artifacts" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Only the provided fields change — omit `title` or `team_id` to leave them unchanged.\n- `team_id: 0` moves the artifact to personal scope (only the creator can manage it); a positive `team_id` requires the caller (for `app_key` calls, the key owner) to be a member of that team.\n- Returns the full artifact after the update.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Enabling an already-enabled server returns InvalidParameter instead of a silent no-op.\n- Requires edit permission on the server's current team: account-scope servers are owner/admin only; team-scope servers require the caller to belong to that team (or be owner/admin).\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-enable", "metadata": { - "sidebarTitle": "Update artifact" + "sidebarTitle": "Enable MCP server" } } } }, - "/safari/artifact/sign": { + "/safari/mcp/server/get": { "post": { - "description": "Create short-lived signed URLs to download or preview a presented file.", - "operationId": "artifact-read-sign", + "description": "Get one MCP server as a pure database read — no live probe is performed.", + "operationId": "mcp-read-server-get", "requestBody": { "content": { "application/json": { "example": { - "file_id": "pf_SdhEA5fbZJGnHzwrNJMMSB" + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" }, "schema": { - "$ref": "#/components/schemas/ArtifactSignRequest" + "$ref": "#/components/schemas/MCPServerGetRequest" } } }, @@ -51640,12 +57503,22 @@ "application/json": { "example": { "data": { - "content_type": "text/html", - "download_url": "/safari/artifact/stream?mode=download&t=cGZfU2RoRUE1ZmJaSkduSHp3ck5KTU1TQnxzZXNzX1ZDYlZQWnJxOVlveUJ1OHNOQ21xVXl8MjQ1MTAwMjc1MTEzMXwyNDc2NDQ0MjEyMTMxfDB8MHwxNzg4NTI5NjI2NTU0.hPQHab0MBNbnrHYwc6VwDJbGonIamfWUr0yeSmLHYAs", - "expires_in": 300, - "name": "sk-hynix-q2-2026-report.html", - "preview_url": "/safari/artifact/stream?mode=preview&t=cGZfU2RoRUE1ZmJaSkduSHp3ck5KTU1TQnxzZXNzX1ZDYlZQWnJxOVlveUJ1OHNOQ21xVXl8MjQ1MTAwMjc1MTEzMXwyNDc2NDQ0MjEyMTMxfDB8MHwxNzg4NTI5NjI2NTU0.hPQHab0MBNbnrHYwc6VwDJbGonIamfWUr0yeSmLHYAs", - "size": 18996 + "account_id": 10023, + "auth_mode": "shared", + "call_timeout": 60, + "can_edit": true, + "connect_timeout": 10, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Query Prometheus metrics and alerts.", + "environments": [], + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", + "server_name": "prometheus", + "status": "enabled", + "team_id": 0, + "transport": "streamable-http", + "updated_at": 1717046400000, + "url": "https://mcp.example.com/prometheus" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -51657,7 +57530,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/SignedURLs" + "$ref": "#/components/schemas/MCPServerItem" } }, "type": "object" @@ -51686,121 +57559,33 @@ "AppKeyAuth": [] } ], - "summary": "Create signed file URLs", - "tags": [ - "AI SRE/Artifacts" - ], - "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Both URLs expire after `expires_in` seconds (300). Sign again to get fresh URLs.\n- Returned URLs are relative — prepend `https://api.flashcat.cloud` before use, then follow them with `GET /safari/artifact/stream`.\n- The signed token is bound to the calling account and the app_key owner's identity, so a leaked URL does not work for another account or member.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-read-sign", - "metadata": { - "sidebarTitle": "Create signed file URLs" - } - } - } - }, - "/safari/artifact/stream": { - "get": { - "description": "Download or preview a file's bytes using a signed token.", - "operationId": "artifact-read-stream", - "parameters": [ - { - "description": "Signed token issued by `POST /safari/artifact/sign`. Bound to the calling account and person; valid for 5 minutes.", - "in": "query", - "name": "t", - "required": true, - "schema": { - "type": "string" - } - }, - { - "description": "`download` (default) serves the file as an attachment; `preview` serves it inline for browser display. Any other value falls back to `download`.", - "in": "query", - "name": "mode", - "required": false, - "schema": { - "default": "download", - "enum": [ - "download", - "preview" - ], - "type": "string" - } - } - ], - "responses": { - "200": { - "content": { - "application/octet-stream": { - "schema": { - "format": "binary", - "type": "string" - } - } - }, - "description": "File bytes, proxied, when the file is hosted on a self-hosted runner. Content-Disposition follows `mode`." - }, - "302": { - "description": "Redirect to a short-lived presigned object-storage URL when the file lives in S3-compatible storage. Follow the `Location` header; no body." - }, - "400": { - "$ref": "#/components/responses/BadRequest" - }, - "401": { - "$ref": "#/components/responses/Unauthorized" - }, - "429": { - "$ref": "#/components/responses/TooManyRequests" - }, - "500": { - "$ref": "#/components/responses/ServerError" - } - }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Download or preview a file", + "summary": "Get MCP server detail", "tags": [ - "AI SRE/Artifacts" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **10 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Success has two forms: a `302` redirect to a short-lived presigned object-storage URL (files stored in S3-compatible storage), or a `200` binary stream (files hosted on a self-hosted runner). Follow redirects.\n- Responses carry `Cache-Control: private, no-store` — they are never cached by the gateway.\n", - "href": "/en/api-reference/ai-sre/artifacts/artifact-read-stream", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- A pure database read — it never probes the live server; the stored configuration (with secrets masked) and the cached `ai_description` are returned as-is.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-read-server-get", "metadata": { - "sidebarTitle": "Download or preview a file" + "sidebarTitle": "Get MCP server detail" } } } }, - "/safari/automation/rule/create": { + "/safari/mcp/server/list": { "post": { - "description": "Create an Automation rule with schedule, HTTP POST, and On-call incident triggers.", - "operationId": "automation-rule-write-create", + "description": "List MCP servers visible to the caller across account and team scopes, with pagination.", + "operationId": "mcp-read-server-list", "requestBody": { "content": { "application/json": { "example": { - "cron_expr": "0 9 * * 1", - "enabled": true, - "http_post_trigger_enabled": true, - "name": "Weekly on-call review", - "oncall_incident_channel_ids": [ - 456 - ], - "oncall_incident_severities": [ - "Critical", - "Warning" - ], - "oncall_incident_trigger_enabled": true, - "prompt": "Summarize last week's alert noise and escalation load.", - "schedule_trigger_enabled": true, - "team_id": 123, - "timezone": "Asia/Shanghai" + "include_account": true, + "limit": 20, + "p": 1 }, "schema": { - "$ref": "#/components/schemas/AutomationRuleCreateRequest" + "$ref": "#/components/schemas/MCPServerListRequest" } } }, @@ -51812,37 +57597,27 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "can_edit": true, - "created_at": 1780367971228, - "cron_expr": "0 9 * * 1", - "enabled": true, - "environment_id": "", - "environment_kind": "", - "http_post_token": "sat_yQ9p8V7n6M5k4J3h2G1f0E9d8C7b6A5z4Y3x2W1v0U", - "http_post_trigger_enabled": true, - "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", - "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", - "name": "Weekly on-call review", - "oncall_incident_channel_ids": [ - 456 - ], - "oncall_incident_severities": [ - "Critical", - "Warning" + "servers": [ + { + "account_id": 10023, + "auth_mode": "shared", + "call_timeout": 60, + "can_edit": true, + "connect_timeout": 10, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Query Prometheus metrics and alerts.", + "environments": [], + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", + "server_name": "prometheus", + "status": "enabled", + "team_id": 0, + "transport": "streamable-http", + "updated_at": 1717046400000, + "url": "https://mcp.example.com/prometheus" + } ], - "oncall_incident_trigger_enabled": true, - "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", - "owner_id": 80011, - "prompt": "Summarize last week's alert noise and escalation load.", - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "run_scope": "team", - "schedule_next_fire_at_ms": 1780630800000, - "schedule_trigger_enabled": true, - "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", - "team_id": 123, - "timezone": "Asia/Shanghai", - "updated_at": 1780367971228 + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -51854,7 +57629,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AutomationRuleItem" + "$ref": "#/components/schemas/MCPServerListResponse" } }, "type": "object" @@ -51871,9 +57646,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -51886,31 +57658,32 @@ "AppKeyAuth": [] } ], - "summary": "Create Automation rule", + "summary": "List MCP servers", "tags": [ - "AI SRE/Automations" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Valid `app_key`; management operations require the caller to manage the target rule |\n\n## Usage\n\n- A caller may create personal rules and rules for any team in the current account; `team_id` can be reassigned later via update (converting a team rule to personal is owner-only; moving into a team requires the caller to belong to it).\n- `cron_expr` is evaluated in `timezone` if provided, else the caller's member timezone, else the account timezone, else the server default (Asia/Shanghai).\n- `http_post_trigger_enabled=true` creates and enables an HTTP POST trigger; the response's `http_post_token` is a one-time value returned only on creation — save it immediately.\n- `oncall_incident_trigger_enabled=true` requires at least one `oncall_incident_channel_ids` entry and one `oncall_incident_severities` value; matching incidents run with `trigger_kind=oncall_incident`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/automations/automation-rule-write-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The response never includes a live tool list; tools are probed asynchronously on create/update and cached for runtime use.\n- `query` performs a case-insensitive substring search across name, description, AI-generated description, server ID, transport, URL, command, and source template name.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-read-server-list", "metadata": { - "sidebarTitle": "Create Automation rule" + "sidebarTitle": "List MCP servers" } } } }, - "/safari/automation/rule/delete": { + "/safari/mcp/server/update": { "post": { - "description": "Delete an Automation rule.", - "operationId": "automation-rule-write-delete", + "description": "Update an MCP server's configuration. Omit a field to leave it unchanged.", + "operationId": "mcp-write-server-update", "requestBody": { "content": { "application/json": { "example": { - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" + "description": "Query Prometheus metrics, alerts, and rules.", + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" }, "schema": { - "$ref": "#/components/schemas/AutomationRuleIDRequest" + "$ref": "#/components/schemas/MCPServerUpdateRequest" } } }, @@ -51921,7 +57694,24 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "account_id": 10023, + "auth_mode": "shared", + "call_timeout": 60, + "can_edit": true, + "connect_timeout": 10, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Query Prometheus metrics, alerts, and rules.", + "environments": [], + "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", + "server_name": "prometheus", + "status": "enabled", + "team_id": 0, + "transport": "streamable-http", + "updated_at": 1717046400000, + "url": "https://mcp.example.com/prometheus" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -51932,8 +57722,7 @@ { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/MCPServerItem" } }, "type": "object" @@ -51965,31 +57754,31 @@ "AppKeyAuth": [] } ], - "summary": "Delete Automation rule", + "summary": "Update MCP server", "tags": [ - "AI SRE/Automations" + "AI SRE/MCP servers" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Valid `app_key`; management operations require the caller to manage the target rule |\n\n## Usage\n\n- Deleting a rule also removes its schedule, HTTP POST, and On-call incident triggers; a deleted HTTP POST trigger's token stops working immediately.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/automations/automation-rule-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Masked secret values in `env`/`headers` are preserved — sending the masked value back does not overwrite the stored secret.\n- `environments` is a tri-state partial-update field: omit (null) to leave it unchanged; send a list to set it — an empty list clears the restriction back to all environments.\n- Changing `team_id` requires reassignment permission on the destination team; if `environments` is left unchanged, the current environments must still be selectable by the caller under the new team or the update is rejected.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-update", "metadata": { - "sidebarTitle": "Delete Automation rule" + "sidebarTitle": "Update MCP server" } } } }, - "/safari/automation/rule/get": { + "/safari/session/delete": { "post": { - "description": "Get one Automation rule by ID.", - "operationId": "automation-rule-read-get", + "description": "Delete a session by ID.", + "operationId": "session-write-delete", "requestBody": { "content": { "application/json": { "example": { - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" }, "schema": { - "$ref": "#/components/schemas/AutomationRuleIDRequest" + "$ref": "#/components/schemas/SessionDeleteRequest" } } }, @@ -52000,38 +57789,7 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 10023, - "can_edit": true, - "created_at": 1780367971228, - "cron_expr": "0 9 * * 1", - "enabled": true, - "environment_id": "", - "environment_kind": "", - "http_post_trigger_enabled": true, - "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", - "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", - "name": "Weekly on-call review", - "oncall_incident_channel_ids": [ - 456 - ], - "oncall_incident_severities": [ - "Critical", - "Warning" - ], - "oncall_incident_trigger_enabled": true, - "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", - "owner_id": 80011, - "prompt": "Summarize last week's alert noise and escalation load.", - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "run_scope": "team", - "schedule_next_fire_at_ms": 1780630800000, - "schedule_trigger_enabled": true, - "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", - "team_id": 123, - "timezone": "Asia/Shanghai", - "updated_at": 1780367971228 - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -52042,7 +57800,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AutomationRuleItem" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -52074,32 +57833,32 @@ "AppKeyAuth": [] } ], - "summary": "Get Automation rule", + "summary": "Delete session", "tags": [ - "AI SRE/Automations" + "AI SRE/Sessions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; caller must manage the target rule |\n\n## Usage\n\n- Manage rights mean the personal rule owner; for team rules, an account admin or a member of the rule's team.\n", - "href": "/en/api-reference/ai-sre/automations/automation-rule-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Personal sessions can be deleted only by their creator; team sessions can be deleted by the creator, an account admin, or a member of the owning team.\n- This is a soft delete: it also cascades to delete child subagent sessions and any presented files; the underlying S3/MinIO blobs are removed best-effort after the transaction commits, so an orphaned blob is possible on partial failure.\n", + "href": "/en/api-reference/ai-sre/sessions/session-write-delete", "metadata": { - "sidebarTitle": "Get Automation rule" + "sidebarTitle": "Delete session" } } } }, - "/safari/automation/rule/list": { + "/safari/session/export": { "post": { - "description": "List Automation rules visible to the caller.", - "operationId": "automation-rule-read-list", + "description": "Stream a session's full event transcript as newline-delimited JSON.", + "operationId": "session-read-export", "requestBody": { "content": { "application/json": { "example": { - "limit": 20, - "scope": "all" + "include_subagents": false, + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" }, "schema": { - "$ref": "#/components/schemas/AutomationRuleListRequest" + "$ref": "#/components/schemas/SessionExportRequest" } } }, @@ -52108,65 +57867,14 @@ "responses": { "200": { "content": { - "application/json": { - "example": { - "data": { - "rules": [ - { - "account_id": 10023, - "can_edit": true, - "created_at": 1780367971228, - "cron_expr": "0 9 * * 1", - "enabled": true, - "environment_id": "", - "environment_kind": "", - "http_post_trigger_enabled": true, - "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", - "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", - "name": "Weekly on-call review", - "oncall_incident_channel_ids": [ - 456 - ], - "oncall_incident_severities": [ - "Critical", - "Warning" - ], - "oncall_incident_trigger_enabled": true, - "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", - "owner_id": 80011, - "prompt": "Summarize last week's alert noise and escalation load.", - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "run_scope": "team", - "schedule_next_fire_at_ms": 1780630800000, - "schedule_trigger_enabled": true, - "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", - "team_id": 123, - "timezone": "Asia/Shanghai", - "updated_at": 1780367971228 - } - ], - "total": 1 - }, - "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" - }, + "application/x-ndjson": { "schema": { - "allOf": [ - { - "$ref": "#/components/schemas/ResponseEnvelope" - }, - { - "properties": { - "data": { - "$ref": "#/components/schemas/AutomationRuleListResponse" - } - }, - "type": "object" - } - ] + "description": "Newline-delimited JSON stream. Parse line-by-line; do not buffer the whole body.", + "type": "string" } } }, - "description": "Success" + "description": "Streaming NDJSON (application/x-ndjson). One JSON object per line, terminated by a newline. The first line is always a `session_meta` envelope; subsequent lines are session events." }, "400": { "$ref": "#/components/responses/BadRequest" @@ -52189,31 +57897,32 @@ "AppKeyAuth": [] } ], - "summary": "List Automation rules", + "summary": "Export session transcript", "tags": [ - "AI SRE/Automations" + "AI SRE/Sessions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; results are filtered to the caller's visible scope |\n\n## Usage\n\n- `all` returns your personal rules plus team rules you can access.\n- Account admins see all team rules in list results, but not other users' personal rules.\n- `team_ids` narrows the visible set and never expands access.\n", - "href": "/en/api-reference/ai-sre/automations/automation-rule-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/day**; **200 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Personal sessions are exportable only by their creator; team sessions can be exported by same-account callers with the `session_id`.\n- The response is `application/x-ndjson` — parse line-by-line and write to a file; do not buffer the whole body in memory.\n- The first line is always a `session_meta` envelope; `include_subagents=true` inlines each child session's stream after its dispatch line.\n- Requests are capped at a 60-second execution timeout; very large sessions may not finish exporting within that window.\n- If the stream fails partway through, the response ends with a JSON error line instead of a proper error envelope (headers are already sent) — check for this trailing line to detect truncation.\n", + "href": "/en/api-reference/ai-sre/sessions/session-read-export", "metadata": { - "sidebarTitle": "List Automation rules" + "sidebarTitle": "Export session transcript" } } } }, - "/safari/automation/rule/run": { + "/safari/session/get": { "post": { - "description": "Manually run an Automation rule immediately, outside its schedule.", - "operationId": "automation-rule-write-run", + "description": "Fetch one session plus a backward-paged window of its most recent events.", + "operationId": "session-read-info", "requestBody": { "content": { "application/json": { "example": { - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" + "num_recent_events": 50, + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" }, "schema": { - "$ref": "#/components/schemas/AutomationRuleIDRequest" + "$ref": "#/components/schemas/SessionGetRequest" } } }, @@ -52225,26 +57934,75 @@ "application/json": { "example": { "data": { - "preflight": { + "events": [ + { + "author": "user", + "created_at": 1780367971241, + "event_id": "evt_3aZQ9p", + "partial": false, + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", + "status": "normal", + "turn_complete": false + }, + { + "author": "ai-sre", + "content": { + "parts": [ + { + "text": "..." + } + ], + "role": "model" + }, + "created_at": 1780367992649, + "event_id": "evt_7bWk2r", + "partial": false, + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", + "status": "normal", + "turn_complete": true + } + ], + "has_more_older": false, + "session": { + "access_source": "manager", "app_name": "ai-sre", - "checks": [ - "rule_loaded", - "actor_authorized", - "app_allowed", - "runtime_scope_resolved", - "rule_config_valid" - ], - "ok": true, - "owner_id": 80011, - "scope": "team", - "team_id": 123 - }, - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "run": { - "run_id": "trun_5oDvqiG64uur6sBNsTc4u", - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" + "archived_at": 0, + "can_continue": true, + "can_fork": true, + "can_manage": true, + "can_view": true, + "context_window": 0, + "created_at": 1780367971228, + "current_context_tokens": 14948, + "current_turn_active_ms": 0, + "current_turn_started_at": 0, + "current_turn_tokens": 0, + "current_turn_wait_ms": 0, + "entry_kind": "web", + "has_unread": true, + "incognito": false, + "is_mine": false, + "is_running": false, + "last_event_at": 1780367992649, + "person_id": "3790925372131", + "pinned_at": 0, + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", + "session_name": "Investigate cloud-assistant first heartbeat", + "share_enabled": true, + "share_version": 3, + "shared_at": 1780367971000, + "shared_by": 3790925372131, + "status": "enabled", + "team_id": 0, + "token_usage": { + "cached_tokens": 11520, + "input_tokens": 14948, + "output_tokens": 888, + "reasoning_tokens": 351 + }, + "updated_at": 1780367993457 }, - "trigger_kind": "manual" + "suggest_init": false }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -52256,7 +58014,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ManualRunRuleResult" + "$ref": "#/components/schemas/SessionGetResponse" } }, "type": "object" @@ -52288,42 +58046,34 @@ "AppKeyAuth": [] } ], - "summary": "Run Automation rule", + "summary": "Get session detail", "tags": [ - "AI SRE/Automations" + "AI SRE/Sessions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/minute**; **5 requests/second** per account |\n| Permissions | Valid `app_key`; caller must manage the target rule |\n\n## Usage\n\n- Rate-limited to at most once per minute per rule; a second call within that window returns `429` with `code: \"RequestTooFrequently\"`.\n- Only enabled rules can run manually; a disabled or misconfigured rule fails preflight with a `400` error before any run is created.\n- The call returns once the underlying agent session starts, not once the run finishes; the run continues asynchronously — use List Automation runs to check completion status.\n- `trigger_kind` is always `manual` for runs started this way, distinguishing them from `schedule`, `http_post`, and `oncall_incident` runs in run history.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/automations/automation-rule-write-run", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Personal sessions are readable only by their creator; team sessions can be read by same-account callers with the `session_id`.\n- Page older history with `search_after_ctx` from the previous response.\n- `limit` (or legacy `num_recent_events`) caps the event page; default 100, max 1000.\n- A malformed `search_after_ctx` returns 400 immediately, before any DB work.\n- `current_turn_*` fields are populated only while the session `is_running`; `suggest_init` is the same account-wide onboarding flag as `session/list`.\n", + "href": "/en/api-reference/ai-sre/sessions/session-read-info", "metadata": { - "sidebarTitle": "Run Automation rule" + "sidebarTitle": "Get session detail" } } } }, - "/safari/automation/rule/update": { + "/safari/session/list": { "post": { - "description": "Update mutable Automation rule fields, including HTTP POST and On-call incident trigger settings.", - "operationId": "automation-rule-write-update", + "description": "List agent sessions visible to the caller, filtered by app, surface, archive status, and team.", + "operationId": "session-read-list", "requestBody": { "content": { "application/json": { "example": { - "cron_expr": "15 9 * * 1", - "enabled": true, - "oncall_incident_channel_ids": [ - 456 - ], - "oncall_incident_severities": [ - "Critical", - "Warning" - ], - "oncall_incident_trigger_enabled": true, - "rotate_http_post_trigger_token": true, - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b" + "app_name": "ai-sre", + "limit": 2, + "orderby": "updated_at", + "scope": "all" }, "schema": { - "$ref": "#/components/schemas/AutomationRuleUpdateRequest" + "$ref": "#/components/schemas/SessionListRequest" } } }, @@ -52335,37 +58085,49 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "can_edit": true, - "created_at": 1780367971228, - "cron_expr": "0 9 * * 1", - "enabled": true, - "environment_id": "", - "environment_kind": "", - "http_post_token": "sat_yQ9p8V7n6M5k4J3h2G1f0E9d8C7b6A5z4Y3x2W1v0U", - "http_post_trigger_enabled": true, - "http_post_trigger_id": "atrig_2bLq4xT8mP1sWd9cN3rF6y", - "http_post_trigger_url": "/safari/automation/triggers/atrig_2bLq4xT8mP1sWd9cN3rF6y/fire", - "name": "Weekly on-call review", - "oncall_incident_channel_ids": [ - 456 - ], - "oncall_incident_severities": [ - "Critical", - "Warning" + "sessions": [ + { + "access_source": "manager", + "app_name": "ai-sre", + "archived_at": 0, + "can_continue": true, + "can_fork": true, + "can_manage": true, + "can_view": true, + "context_window": 0, + "created_at": 1780367971228, + "current_context_tokens": 14948, + "current_turn_active_ms": 0, + "current_turn_started_at": 0, + "current_turn_tokens": 0, + "current_turn_wait_ms": 0, + "entry_kind": "web", + "has_unread": true, + "incognito": false, + "is_mine": false, + "is_running": false, + "last_event_at": 1780367992649, + "person_id": "3790925372131", + "pinned_at": 0, + "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", + "session_name": "Investigate cloud-assistant first heartbeat", + "share_enabled": true, + "share_version": 3, + "shared_at": 1780367971000, + "shared_by": 3790925372131, + "status": "enabled", + "team_id": 0, + "token_usage": { + "cached_tokens": 11520, + "input_tokens": 14948, + "output_tokens": 888, + "reasoning_tokens": 351 + }, + "updated_at": 1780367993457 + } ], - "oncall_incident_trigger_enabled": true, - "oncall_incident_trigger_id": "atrig_9cVb2mN7qKs4dEa8T1rY5p", - "owner_id": 80011, - "prompt": "Summarize last week's alert noise and escalation load.", - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "run_scope": "team", - "schedule_next_fire_at_ms": 1780630800000, - "schedule_trigger_enabled": true, - "schedule_trigger_id": "atrig_6aKp3wT9mQ2xVc8bR1nY7z", - "team_id": 123, - "timezone": "Asia/Shanghai", - "updated_at": 1780367971228 + "suggest_init": false, + "total": 988 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -52377,7 +58139,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AutomationRuleItem" + "$ref": "#/components/schemas/SessionListResponse" } }, "type": "object" @@ -52409,33 +58171,31 @@ "AppKeyAuth": [] } ], - "summary": "Update Automation rule", + "summary": "List sessions", "tags": [ - "AI SRE/Automations" + "AI SRE/Sessions" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | Valid `app_key`; management operations require the caller to manage the target rule |\n\n## Usage\n\n- Omitted or `null` fields are left unchanged. `team_id` reassigns the rule's scope: `0` converts a team rule to personal (owner-only), `>0` moves it into a team the caller belongs to.\n- `cron_expr` and `timezone` can be updated independently — sending only one keeps the other at its current stored value.\n- `rotate_http_post_trigger_token=true` issues a fresh webhook token, returned only in this response.\n- To trigger from On-call incidents, send `oncall_incident_trigger_enabled`, `oncall_incident_channel_ids`, and `oncall_incident_severities`; matching events run with `trigger_kind=oncall_incident`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/automations/automation-rule-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Pagination uses `p`/`limit` (max 100); `scope` defaults to `all`.\n- `all` returns your personal sessions plus team sessions you can access; account admins see all team sessions, but not other users' personal sessions.\n- `team_ids` narrows the visible set and never expands access.\n- `is_running` reflects the live run-set; `has_unread` is computed per calling user; the `current_turn_*` fields are always zero here — only `session/get` computes them while a session is running.\n- `suggest_init` is an account-wide onboarding flag (true only when the account has no knowledge in any scope) — it doesn't depend on the list filters.\n", + "href": "/en/api-reference/ai-sre/sessions/session-read-list", "metadata": { - "sidebarTitle": "Update Automation rule" + "sidebarTitle": "List sessions" } } } }, - "/safari/automation/run/list": { + "/safari/skill/delete": { "post": { - "description": "List run history for a rule the caller can manage.", - "operationId": "automation-run-read-list", + "description": "Delete a skill by ID.", + "operationId": "skill-write-delete", "requestBody": { "content": { "application/json": { "example": { - "limit": 20, - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "trigger_kind": "schedule" + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" }, "schema": { - "$ref": "#/components/schemas/AutomationRunListRequest" + "$ref": "#/components/schemas/SkillDeleteRequest" } } }, @@ -52446,34 +58206,7 @@ "content": { "application/json": { "example": { - "data": { - "runs": [ - { - "account_id": 10023, - "attempts": 1, - "completed_at": 1780630923456, - "created_at": 1780630800000, - "duration_ms": 123456, - "error_code": "", - "error_message": "", - "kind": "automation_rule", - "occurrence_key": "atrig_6aKp3wT9mQ2xVc8bR1nY7z:1780630800000", - "result_json": { - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" - }, - "rule_id": "arule_7NnLzY2Qp8xS4kUaV3mR6b", - "run_id": "trun_5oDvqiG64uur6sBNsTc4u", - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", - "session_name": "Weekly on-call review", - "started_at": 1780630800000, - "stats_json": {}, - "status": "succeeded", - "trigger_kind": "schedule", - "updated_at": 1780630923456 - } - ], - "total": 1 - }, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -52484,7 +58217,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AutomationRunListResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -52516,52 +58250,42 @@ "AppKeyAuth": [] } ], - "summary": "List Automation runs", + "summary": "Delete skill", "tags": [ - "AI SRE/Automations" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; caller must manage the target rule |\n\n## Usage\n\n- Run history is visible only when the caller can manage the rule: the personal rule owner; for team rules, an account admin or a member of the rule's team.\n", - "href": "/en/api-reference/ai-sre/automations/automation-run-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Soft delete only: sets `status` to `deleted` and renames the row to free its name for reuse; the skill's zip archive is not removed from object storage.\n- Deleting an already-deleted or nonexistent `skill_id` returns `ResourceNotFound`, since the lookup excludes deleted rows before the delete itself runs.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/skills/skill-write-delete", "metadata": { - "sidebarTitle": "List Automation runs" + "sidebarTitle": "Delete skill" } } } }, - "/safari/automation/template/list": { + "/safari/skill/disable": { "post": { - "description": "List preset Automation templates for the requested locale.", - "operationId": "automation-template-read-list", + "description": "Disable an enabled skill so the agent stops loading it.", + "operationId": "skill-write-disable", "requestBody": { "content": { "application/json": { "example": { - "locale": "en-US" + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" }, "schema": { - "$ref": "#/components/schemas/AutomationTemplateListRequest" + "$ref": "#/components/schemas/SkillStatusRequest" } } }, - "required": true - }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "templates": [ - { - "description": "Analyze incidents, alerts, response activity, notification load, and related changes from the past week.", - "enabled": false, - "icon": "chart-no-axes-combined", - "name": "Weekly Insights", - "prompt": "Generate a weekly insights report. Analyze incidents, alerts, response activity, notification load, and related changes from the past week. Focus on what happened this week, which signals deserve attention, and which improvement actions are most valuable. Do not modify any Flashduty business state.\n" - } - ] - }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -52572,7 +58296,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/AutomationTemplateListResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -52604,31 +58329,31 @@ "AppKeyAuth": [] } ], - "summary": "List Automation templates", + "summary": "Disable skill", "tags": [ - "AI SRE/Automations" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | Valid `app_key`; results are filtered to the caller's visible scope |\n", - "href": "/en/api-reference/ai-sre/automations/automation-template-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Only an `enabled` skill can be disabled; an already-disabled skill returns `InvalidParameter`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/skills/skill-write-disable", "metadata": { - "sidebarTitle": "List Automation templates" + "sidebarTitle": "Disable skill" } } } }, - "/safari/knowledge/file/delete": { + "/safari/skill/enable": { "post": { - "description": "Delete a file from a knowledge pack by its relative path.", - "operationId": "knowledge-file-write-delete", + "description": "Enable a disabled skill so the agent can load it.", + "operationId": "skill-read-enable", "requestBody": { "content": { "application/json": { "example": { - "rel_path": "tmp/openapi-delete-example.md" + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" }, "schema": { - "$ref": "#/components/schemas/KnowledgeFileDeleteRequest" + "$ref": "#/components/schemas/SkillStatusRequest" } } }, @@ -52639,7 +58364,7 @@ "content": { "application/json": { "example": { - "data": {}, + "data": null, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -52650,7 +58375,8 @@ { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgeFileDeleteResponse" + "description": "Always null on success.", + "type": "null" } }, "type": "object" @@ -52682,31 +58408,31 @@ "AppKeyAuth": [] } ], - "summary": "Delete knowledge file", + "summary": "Enable skill", "tags": [ - "AI SRE/Knowledge" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- Deleting is idempotent — removing a file that does not exist succeeds.\n- When other pack files still reference the target, the delete fails with `ReferenceExist` listing the referrers; set `force` to proceed (the referrers are returned as warnings).\n- Omitting `pack_id` targets the account-scope pack; editing the account pack requires account owner/admin, editing a team pack requires team membership.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Only a `disabled` skill can be enabled; an already-enabled skill returns `InvalidParameter`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/skills/skill-read-enable", "metadata": { - "sidebarTitle": "Delete knowledge file" + "sidebarTitle": "Enable skill" } } } }, - "/safari/knowledge/file/get": { + "/safari/skill/get": { "post": { - "description": "Return a knowledge file's metadata and its base64-encoded content.", - "operationId": "knowledge-file-read-get", + "description": "Get one skill including its full SKILL.md content.", + "operationId": "skill-read-get", "requestBody": { "content": { "application/json": { "example": { - "rel_path": "tmp/openapi-example.md" + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" }, "schema": { - "$ref": "#/components/schemas/KnowledgeFileGetRequest" + "$ref": "#/components/schemas/SkillGetRequest" } } }, @@ -52718,17 +58444,30 @@ "application/json": { "example": { "data": { - "content_b64": "IyBPcGVuQVBJIGV4YW1wbGUKVGVtcCBmaWxlIGZvciBBUEkgZG9jcyBleGFtcGxlLgo=", - "file": { - "checksum": "a0775f9b3f392cd0560b21ad2f579ae4a5d6b1282b9eb145688ba2de717a816d", - "content_type": "text/markdown", - "file_id": "kfl_gctXKRG45aFQGgxSFr59WY", - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "rel_path": "tmp/openapi-example.md", - "size_bytes": 50, - "updated_at_ms": 1786458764961, - "updated_by": 2476444212131 - } + "account_id": 10023, + "author": "sre-team", + "can_edit": true, + "content": "---\nname: k8s-triage\ndescription: ...\n---\n# Triage steps", + "created_at": 1716960000000, + "created_by": 80011, + "description": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", + "description_en": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", + "is_modified": false, + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", + "skill_name": "k8s-triage", + "status": "enabled", + "tags": [ + "kubernetes", + "triage" + ], + "team_id": 0, + "tools": [ + "bash", + "mcp:prometheus/query" + ], + "update_available": false, + "updated_at": 1717046400000, + "version": "1.2.0" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -52740,7 +58479,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgeFileGetResponse" + "$ref": "#/components/schemas/SkillItem" } }, "type": "object" @@ -52769,31 +58508,33 @@ "AppKeyAuth": [] } ], - "summary": "Get knowledge file", + "summary": "Get skill detail", "tags": [ - "AI SRE/Knowledge" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Content is returned in `content_b64` (base64); pack files are guaranteed UTF-8 text.\n- Omitting `pack_id` targets the account-scope pack; reading a team-scope pack requires team membership.\n- A missing file returns `ResourceNotFound` (HTTP 400).\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if the skill does not exist or has already been deleted.\n- `can_edit` reflects team membership, but read access itself is open to any caller regardless of team.\n", + "href": "/en/api-reference/ai-sre/skills/skill-read-get", "metadata": { - "sidebarTitle": "Get knowledge file" + "sidebarTitle": "Get skill detail" } } } }, - "/safari/knowledge/file/list": { + "/safari/skill/list": { "post": { - "description": "List the files in a knowledge pack with metadata such as size and checksum.", - "operationId": "knowledge-file-read-list", + "description": "List AI SRE skills visible to the caller across account and team scopes, with pagination.", + "operationId": "skill-read-list", "requestBody": { "content": { "application/json": { "example": { - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc" + "include_account": true, + "limit": 20, + "p": 1 }, "schema": { - "$ref": "#/components/schemas/KnowledgeFileListRequest" + "$ref": "#/components/schemas/SkillListRequest" } } }, @@ -52805,29 +58546,33 @@ "application/json": { "example": { "data": { - "files": [ - { - "checksum": "fccc276c0d7fbae2e9508285cdde0f8475169634e89e466dac2e59f176c9be2f", - "content_type": "text/markdown", - "file_id": "kfl_QvT4g3c8zAHxTthuT6hGne", - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "rel_path": "aliyun.md", - "size_bytes": 1436, - "updated_at_ms": 1783311304757, - "updated_by": 3790925372131 - }, + "skills": [ { - "checksum": "450eabf178b41e46ea2f43d395a80bf8b956ddb9c9cea34f44ffc69a53e7a36b", - "content_type": "text/markdown", - "file_id": "kfl_BMsQZCZSqhW4TFskYNb4H5", - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "rel_path": "DUTY.md", - "size_bytes": 1301, - "updated_at_ms": 1784800003394, - "updated_by": 2476444212131 + "account_id": 10023, + "author": "sre-team", + "can_edit": true, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", + "is_modified": false, + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", + "skill_name": "k8s-triage", + "status": "enabled", + "tags": [ + "kubernetes", + "triage" + ], + "team_id": 0, + "tools": [ + "bash", + "mcp:prometheus/query" + ], + "update_available": false, + "updated_at": 1717046400000, + "version": "1.2.0" } ], - "total": 17 + "total": 1 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -52839,7 +58584,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgeFileListResponse" + "$ref": "#/components/schemas/SkillListResponse" } }, "type": "object" @@ -52868,33 +58613,32 @@ "AppKeyAuth": [] } ], - "summary": "List knowledge files", + "summary": "List skills", "tags": [ - "AI SRE/Knowledge" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Omitting `pack_id` targets the caller's account-scope pack (created lazily if absent).\n- Reading a team-scope pack requires membership of that team.\n- `p`/`limit` are accepted but the current implementation always returns the full file list.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The `content` field is omitted in list rows; fetch a single skill to read its body.\n- `scope` selects `all` (default), `account`-only, or `team`-only, overriding `include_account`; non-admins requesting specific `team_ids` are silently filtered down to the teams they belong to.\n- `update_available` compares against the marketplace catalog once per call; if the catalog fails to load, the badge is simply suppressed rather than the request failing.\n", + "href": "/en/api-reference/ai-sre/skills/skill-read-list", "metadata": { - "sidebarTitle": "List knowledge files" + "sidebarTitle": "List skills" } } } }, - "/safari/knowledge/file/put": { + "/safari/skill/update": { "post": { - "description": "Create or overwrite a file in a knowledge pack with base64-encoded content.", - "operationId": "knowledge-file-write-put", + "description": "Update a skill's descriptions or reassign its team scope.", + "operationId": "skill-write-update", "requestBody": { "content": { "application/json": { "example": { - "content_b64": "IyBPcGVuQVBJIGV4YW1wbGUKVGVtcCBmaWxlIGZvciBBUEkgZG9jcyBleGFtcGxlLgo=", - "content_type": "text/markdown", - "rel_path": "tmp/openapi-example.md" + "description": "Updated triage runbook.", + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" }, "schema": { - "$ref": "#/components/schemas/KnowledgeFilePutRequest" + "$ref": "#/components/schemas/SkillUpdateRequest" } } }, @@ -52906,16 +58650,28 @@ "application/json": { "example": { "data": { - "file": { - "checksum": "a0775f9b3f392cd0560b21ad2f579ae4a5d6b1282b9eb145688ba2de717a816d", - "content_type": "text/markdown", - "file_id": "kfl_gctXKRG45aFQGgxSFr59WY", - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "rel_path": "tmp/openapi-example.md", - "size_bytes": 50, - "updated_at_ms": 1786458764961, - "updated_by": 2476444212131 - } + "account_id": 10023, + "author": "sre-team", + "can_edit": true, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Updated triage runbook.", + "is_modified": false, + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", + "skill_name": "k8s-triage", + "status": "enabled", + "tags": [ + "kubernetes", + "triage" + ], + "team_id": 0, + "tools": [ + "bash", + "mcp:prometheus/query" + ], + "update_available": false, + "updated_at": 1717046400000, + "version": "1.2.0" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -52927,7 +58683,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgeFilePutResponse" + "$ref": "#/components/schemas/SkillItem" } }, "type": "object" @@ -52959,29 +58715,32 @@ "AppKeyAuth": [] } ], - "summary": "Upload knowledge file", + "summary": "Update skill", "tags": [ - "AI SRE/Knowledge" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- The file body is sent as base64 text in the JSON field `content_b64` — this is not a multipart upload.\n- Writing an existing `rel_path` overwrites it; `content_type` is inferred from the extension when omitted (`.md` → `text/markdown`).\n- Content must decode to valid UTF-8 text; binary payloads are rejected with `InvalidParameter`.\n- Editing the account-scope pack requires account owner/admin; editing a team pack requires team membership.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-file-write-put", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Only `description`, `description_en`, and `team_id` are editable; the skill body is changed by re-uploading.\n- `description` only updates when non-empty — there is no way to clear it via this field; `description_en` is nilable, so send an empty string to explicitly clear it.\n- Reassigning `team_id` to a different team runs a second authorization check beyond edit access, verifying the caller may target the destination team.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/skills/skill-write-update", "metadata": { - "sidebarTitle": "Upload knowledge file" + "sidebarTitle": "Update skill" } } } }, - "/safari/knowledge/get": { + "/safari/skill/upload": { "post": { - "description": "Return the account-scope knowledge pack metadata and its file list.", - "operationId": "knowledge-pack-read-get", + "description": "Upload a skill archive (.skill/.zip/.tar.gz/.tgz) to create or replace a skill.", + "operationId": "skill-write-upload", "requestBody": { "content": { - "application/json": { - "example": {}, + "multipart/form-data": { + "example": { + "replace": false, + "team_id": 0 + }, "schema": { - "$ref": "#/components/schemas/KnowledgeGetRequest" + "$ref": "#/components/schemas/SkillUploadRequest" } } }, @@ -52993,42 +58752,28 @@ "application/json": { "example": { "data": { - "files": [ - { - "checksum": "fccc276c0d7fbae2e9508285cdde0f8475169634e89e466dac2e59f176c9be2f", - "content_type": "text/markdown", - "file_id": "kfl_QvT4g3c8zAHxTthuT6hGne", - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "rel_path": "aliyun.md", - "size_bytes": 1436, - "updated_at_ms": 1783311304757, - "updated_by": 3790925372131 - }, - { - "checksum": "450eabf178b41e46ea2f43d395a80bf8b956ddb9c9cea34f44ffc69a53e7a36b", - "content_type": "text/markdown", - "file_id": "kfl_BMsQZCZSqhW4TFskYNb4H5", - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "rel_path": "DUTY.md", - "size_bytes": 1301, - "updated_at_ms": 1784800003394, - "updated_by": 2476444212131 - } + "account_id": 10023, + "author": "sre-team", + "can_edit": true, + "created_at": 1716960000000, + "created_by": 80011, + "description": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", + "is_modified": false, + "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", + "skill_name": "k8s-triage", + "status": "enabled", + "tags": [ + "kubernetes", + "triage" ], - "pack": { - "account_id": 2451002751131, - "can_edit": true, - "created_at_ms": 1778768680053, - "created_by": 2476444212131, - "duty_version": 130, - "file_count": 17, - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "scope": "account", - "scope_id": 2451002751131, - "total_bytes": 41010, - "updated_at_ms": 1786456567177, - "version": 134 - } + "team_id": 0, + "tools": [ + "bash", + "mcp:prometheus/query" + ], + "update_available": false, + "updated_at": 1717046400000, + "version": "1.2.0" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -53040,7 +58785,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgeGetResponse" + "$ref": "#/components/schemas/SkillItem" } }, "type": "object" @@ -53057,6 +58802,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53069,31 +58817,31 @@ "AppKeyAuth": [] } ], - "summary": "Get account knowledge pack", + "summary": "Upload skill", "tags": [ - "AI SRE/Knowledge" + "AI SRE/Skills" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Always targets the caller's account-scope pack — there is no `pack_id` parameter; use `POST /safari/knowledge/pack/list` to discover team packs.\n- The account pack is created lazily on first access, so a valid account never gets not-found here.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **30 requests/minute**; **3 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Send as `multipart/form-data` with a `file` part; accepted archive types are `.skill`, `.zip`, `.tar.gz`, `.tgz`, capped at 100MB (oversized files are rejected before the body is read).\n- `skill_id` + `replace=true` targets and overwrites that specific skill, skipping the team-authorship check since the caller already owns the row.\n- `replace=true` without `skill_id` upserts by matching skill name; omitting `replace` always creates a new skill — both paths require the caller to be allowed to author into the target `team_id`.\n- The response always stamps `can_edit: true`.\n- Every call is recorded in the account audit log.\n", + "href": "/en/api-reference/ai-sre/skills/skill-write-upload", "metadata": { - "sidebarTitle": "Get account knowledge pack" + "sidebarTitle": "Upload skill" } } } }, - "/safari/knowledge/pack/delete": { + "/schedule/by-person": { "post": { - "description": "Delete a knowledge pack and all of its files.", - "operationId": "knowledge-pack-write-delete", + "description": "Get a member's current and next on-call shifts and every enabled schedule they participate in.", + "operationId": "scheduleByPerson", "requestBody": { "content": { "application/json": { "example": { - "pack_id": "kpk_YqHXPTEUHQFGepUfRS7vsh" + "person_id": 2476444212131 }, "schema": { - "$ref": "#/components/schemas/KnowledgePackDeleteRequest" + "$ref": "#/components/schemas/ScheduleByPersonRequest" } } }, @@ -53105,19 +58853,36 @@ "application/json": { "example": { "data": { - "ok": true + "current": { + "end_at": 1773532799, + "schedule_id": 2539108069860, + "schedule_name": "Open Source Q&A", + "start_at": 1773446400 + }, + "next": { + "end_at": 1773619199, + "schedule_id": 2539108069860, + "schedule_name": "Open Source Q&A", + "start_at": 1773532800 + }, + "schedules": [ + { + "schedule_id": 2539108069860, + "schedule_name": "Open Source Q&A" + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgePackDeleteResponse" + "$ref": "#/components/schemas/ScheduleByPersonResponse" } }, "type": "object" @@ -53134,9 +58899,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53144,37 +58906,102 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Delete knowledge pack", + "summary": "Get member on-call status", "tags": [ - "AI SRE/Knowledge" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- Deleting a pack removes every file it contains; the operation cannot be undone.\n- Deleting the account-scope pack is allowed; it is re-created empty on next access.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |\n\n## Usage\n\n- `current` carries the shift in progress with its true start time; `next` is the upcoming shift, absent when nothing is scheduled within the lookup window.\n- Disabled schedules are not listed.", + "href": "/en/api-reference/on-call/schedules/schedule-by-person", "metadata": { - "sidebarTitle": "Delete knowledge pack" + "sidebarTitle": "Get member on-call status" } } } }, - "/safari/knowledge/pack/ensure": { + "/schedule/create": { "post": { - "description": "Idempotently create the knowledge pack at the given scope, or return the existing one.", - "operationId": "knowledge-pack-write-ensure", + "description": "Create a new on-call schedule (escalation rule schedule).", + "operationId": "scheduleCreate", "requestBody": { "content": { "application/json": { "example": { - "scope": "team", - "scope_id": 2477033058131 + "description": "Primary on-call rotation for the production team", + "layers": [ + { + "day_mask": { + "repeat": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "enable_time": 1712000000, + "expire_time": 0, + "fair_rotation": false, + "groups": [ + { + "end": 0, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2451002751131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 0 + }, + { + "end": 0, + "group_name": "B", + "members": [ + { + "person_ids": [ + 2476123212131 + ], + "role_id": 0 + } + ], + "name": "B", + "start": 0 + } + ], + "handoff_time": 0, + "hidden": 0, + "layer_name": "Layer 1", + "mask_continuous_enabled": false, + "mode": 0, + "name": "Layer 1", + "restrict_end": 0, + "restrict_mode": 0, + "restrict_periods": [], + "restrict_start": 0, + "rotation_duration": 86400, + "rotation_unit": "day", + "rotation_value": 1, + "weight": 0 + } + ], + "notify": { + "advance_in_time": 300, + "by": { + "follow_preference": true, + "personal_channels": null + }, + "fixed_time": null, + "webhooks": null + }, + "schedule_name": "Production On-Call", + "team_id": 4291079133131 }, "schema": { - "$ref": "#/components/schemas/KnowledgePackEnsureRequest" + "$ref": "#/components/schemas/ScheduleUpsertRequest" } } }, @@ -53186,30 +59013,19 @@ "application/json": { "example": { "data": { - "account_id": 2451002751131, - "can_edit": true, - "created_at_ms": 1778768680053, - "created_by": 2476444212131, - "duty_version": 130, - "file_count": 17, - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "scope": "account", - "scope_id": 2451002751131, - "total_bytes": 41010, - "updated_at_ms": 1786458765182, - "version": 138 + "schedule_id": 6294534917601 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgePackItem" + "$ref": "#/components/schemas/ScheduleIDResponse" } }, "type": "object" @@ -53226,9 +59042,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53236,39 +59049,33 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Ensure knowledge pack", + "summary": "Create schedule", "tags": [ - "AI SRE/Knowledge" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- Idempotent: if a pack already exists at (`scope`, `scope_id`), it is returned unchanged.\n- For `account` scope, `scope_id` is ignored (the account ID is used) and a default `DUTY.md` is seeded on first creation.\n- Creating the account-scope pack requires account owner/admin; creating into a team requires membership of that team.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-write-ensure", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-create", "metadata": { - "sidebarTitle": "Ensure knowledge pack" + "sidebarTitle": "Create schedule" } } } }, - "/safari/knowledge/pack/list": { + "/schedule/delete": { "post": { - "description": "List knowledge packs visible to the caller across account and team scopes.", - "operationId": "knowledge-pack-read-list", + "description": "Delete one or more on-call schedules by ID.", + "operationId": "scheduleDelete", "requestBody": { "content": { "application/json": { "example": { - "include_account": true, - "limit": 20, - "p": 1, - "scope": "all" + "schedule_ids": [ + 2001 + ] }, "schema": { - "$ref": "#/components/schemas/KnowledgePackListRequest" + "$ref": "#/components/schemas/ScheduleIDsBodyRequest" } } }, @@ -53279,51 +59086,18 @@ "content": { "application/json": { "example": { - "data": { - "packs": [ - { - "account_id": 2451002751131, - "can_edit": true, - "created_at_ms": 1778768680053, - "created_by": 2476444212131, - "duty_version": 130, - "file_count": 17, - "pack_id": "kpk_kE49k3FhecfJBwutbshEEc", - "scope": "account", - "scope_id": 2451002751131, - "total_bytes": 41010, - "updated_at_ms": 1786456567177, - "version": 134 - }, - { - "account_id": 2451002751131, - "can_edit": true, - "created_at_ms": 1782201586089, - "created_by": 2476444212131, - "duty_version": 15, - "file_count": 4, - "pack_id": "kpk_5qRL34nKtoWM4nQVT2kHzy", - "scope": "team", - "scope_id": 2477033058131, - "team_name": "研发团队", - "total_bytes": 11159, - "updated_at_ms": 1785462092702, - "version": 15 - } - ], - "total": 3 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgePackListResponse" + "$ref": "#/components/schemas/ScheduleEmptyObject" } }, "type": "object" @@ -53347,38 +59121,33 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "List knowledge packs", + "summary": "Delete schedules", "tags": [ - "AI SRE/Knowledge" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Visibility matches the console: admins see the account pack plus every team pack; non-admins see the account pack plus their own teams, and requested `team_ids` are silently intersected with their teams.\n- `scope` selects `all` (default), `account`-only, or `team`-only, overriding `include_account`.\n- `query` applies a case-insensitive substring filter over pack ID, scope, and team name; `p`/`limit` paginate the filtered result.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-delete", "metadata": { - "sidebarTitle": "List knowledge packs" + "sidebarTitle": "Delete schedules" } } } }, - "/safari/knowledge/pack/update": { + "/schedule/info": { "post": { - "description": "Move a knowledge pack to a different account or team scope.", - "operationId": "knowledge-pack-write-update", + "description": "Return details of an on-call schedule including the computed schedule layers for the requested time window (max 45 days).", + "operationId": "scheduleInfo", "requestBody": { "content": { "application/json": { "example": { - "pack_id": "kpk_5qRL34nKtoWM4nQVT2kHzy", - "scope": "team", - "scope_id": 2477033058131 + "end": 1712086400, + "schedule_id": 2001, + "start": 1712000000 }, "schema": { - "$ref": "#/components/schemas/KnowledgePackUpdateRequest" + "$ref": "#/components/schemas/ScheduleInfoRequest" } } }, @@ -53391,30 +59160,267 @@ "example": { "data": { "account_id": 2451002751131, - "can_edit": true, - "created_at_ms": 1782201586089, - "created_by": 2476444212131, - "duty_version": 15, - "file_count": 4, - "pack_id": "kpk_5qRL34nKtoWM4nQVT2kHzy", - "scope": "team", - "scope_id": 2477033058131, - "team_name": "研发团队", - "total_bytes": 11159, - "updated_at_ms": 1785462092702, - "version": 15 + "create_at": 1766110836, + "create_by": 2476123212131, + "cur_oncall": { + "end": 1776009600, + "group": { + "end": 1776009600, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2451002751131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1775972040 + }, + "index": 0, + "start": 1775972040, + "update_at": 0, + "weight": 0 + }, + "description": "abc", + "disabled": 0, + "final_schedule": { + "layer_name": "", + "mode": 0, + "name": "", + "schedules": [ + { + "end": 1776096000, + "group": { + "end": 1776096000, + "group_name": "A", + "members": [ + { + "person_ids": [ + 3122470302131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1776009600 + }, + "index": 0, + "start": 1776009600 + } + ] + }, + "group_id": 4291079133131, + "id": 5789640530410, + "layer_schedules": [ + { + "layer_name": "Layer 1", + "mode": 0, + "name": "Layer 1", + "schedules": [ + { + "end": 1776096000, + "group": { + "end": 1776096000, + "group_name": "A", + "members": [ + { + "person_ids": [ + 3122470302131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1776009600 + }, + "index": 0, + "start": 1776009600 + } + ] + } + ], + "layers": [ + { + "account_id": 2451002751131, + "create_at": 1775205795, + "create_by": 2476123212131, + "day_mask": { + "repeat": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "enable_time": 1767542400, + "expire_time": 0, + "fair_rotation": false, + "groups": [ + { + "end": 0, + "group_name": "A", + "members": [ + { + "person_ids": [ + 3122470302131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 0 + }, + { + "end": 0, + "group_name": "B", + "members": [ + { + "person_ids": [ + 2659460982131 + ], + "role_id": 0 + } + ], + "name": "B", + "start": 0 + } + ], + "handoff_time": 0, + "hidden": 0, + "layer_end": null, + "layer_name": "Layer 1", + "layer_start": 1767542400, + "mask_continuous_enabled": false, + "mode": 0, + "name": "Layer 1", + "restrict_end": 0, + "restrict_mode": 0, + "restrict_periods": [], + "restrict_start": 0, + "rotation_duration": 86400, + "rotation_unit": "day", + "rotation_value": 1, + "schedule_id": 5789640530410, + "update_at": 1775205795, + "update_by": 2476123212131, + "weight": 0 + } + ], + "name": "test-000001", + "next_oncall": { + "end": 1776096000, + "group": { + "end": 1776096000, + "group_name": "A", + "members": [ + { + "person_ids": [ + 3122470302131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1776009600 + }, + "index": 0, + "start": 1776009600, + "update_at": 0, + "weight": 0 + }, + "notify": { + "advance_in_time": 300, + "by": { + "follow_preference": false, + "personal_channels": [ + "email" + ] + }, + "fixed_time": null, + "webhooks": [ + { + "settings": { + "alias": "", + "chat_ids": [ + "oc_60a6dc4c6e4e5cbc4934ef08aa7ff76d" + ], + "data_source_id": 5427276014131, + "sign_secret": "", + "token": "", + "verify_token": "" + }, + "type": "feishu_app" + } + ] + }, + "schedule_id": 5789640530410, + "schedule_layers": [ + { + "layer_name": "Layer 1", + "mode": 0, + "name": "Layer 1", + "schedules": [ + { + "end": 1776096000, + "group": { + "end": 1776096000, + "group_name": "A", + "members": [ + { + "person_ids": [ + 3122470302131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1776009600 + }, + "index": 0, + "start": 1776009600 + }, + { + "end": 1776182400, + "group": { + "end": 1776182400, + "group_name": "B", + "members": [ + { + "person_ids": [ + 2659460982131 + ], + "role_id": 0 + } + ], + "name": "B", + "start": 1776096000 + }, + "index": 0, + "start": 1776096000 + } + ] + } + ], + "schedule_name": "test-000001", + "status": 0, + "team_id": 4291079133131, + "update_at": 1775205795, + "update_by": 2476123212131 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/KnowledgePackItem" + "$ref": "#/components/schemas/ScheduleItem" } }, "type": "object" @@ -53431,9 +59437,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53441,40 +59444,35 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Update knowledge pack", + "summary": "Get schedule info", "tags": [ - "AI SRE/Knowledge" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Knowledge Manage** (`ai-sre`) |\n\n## Usage\n\n- `scope` is the only mutable field; omitting it is a no-op that returns the current pack.\n- For `team` scope, `scope_id` is required; for `account` scope it is set to the account ID automatically.\n- The move fails with `ReferenceExist` when the destination scope already has a pack — packs are never merged.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/knowledge/knowledge-pack-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-info", "metadata": { - "sidebarTitle": "Update knowledge pack" + "sidebarTitle": "Get schedule info" } } } }, - "/safari/mcp/server/create": { + "/schedule/infos": { "post": { - "description": "Register a new MCP server (connector) on the account.", - "operationId": "mcp-write-server-create", + "description": "Return details of multiple on-call schedules by their IDs.", + "operationId": "scheduleInfos", "requestBody": { "content": { "application/json": { "example": { - "description": "Query Prometheus metrics and alerts.", - "server_name": "prometheus", - "status": "enabled", - "transport": "streamable-http", - "url": "https://mcp.example.com/prometheus" + "schedule_ids": [ + 2001, + 2002, + 2003 + ] }, "schema": { - "$ref": "#/components/schemas/MCPServerCreateRequest" + "$ref": "#/components/schemas/ScheduleIDsRequest" } } }, @@ -53486,34 +59484,72 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "auth_mode": "shared", - "call_timeout": 60, - "can_edit": true, - "connect_timeout": 10, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Query Prometheus metrics and alerts.", - "environments": [], - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", - "server_name": "prometheus", - "status": "enabled", - "team_id": 0, - "transport": "streamable-http", - "updated_at": 1717046400000, - "url": "https://mcp.example.com/prometheus" + "items": [ + { + "account_id": 2451002751131, + "create_at": 1766110836, + "create_by": 2476123212131, + "cur_oncall": null, + "description": "abc", + "disabled": 0, + "final_schedule": { + "layer_name": "", + "mode": 0, + "name": "", + "schedules": null + }, + "group_id": 4291079133131, + "id": 5789640530410, + "layer_schedules": null, + "layers": null, + "name": "test-000001", + "next_oncall": null, + "notify": { + "advance_in_time": 300, + "by": { + "follow_preference": false, + "personal_channels": [ + "email" + ] + }, + "fixed_time": null, + "webhooks": [ + { + "settings": { + "alias": "", + "chat_ids": [ + "oc_60a6dc4c6e4e5cbc4934ef08aa7ff76d" + ], + "data_source_id": 5427276014131, + "sign_secret": "", + "token": "", + "verify_token": "" + }, + "type": "feishu_app" + } + ] + }, + "schedule_id": 5789640530410, + "schedule_layers": null, + "schedule_name": "test-000001", + "status": 0, + "team_id": 4291079133131, + "update_at": 1775205795, + "update_by": 2476123212131 + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/MCPServerItem" + "$ref": "#/components/schemas/ScheduleSelfResponse" } }, "type": "object" @@ -53530,9 +59566,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53540,36 +59573,34 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Create MCP server", + "summary": "Batch get schedules", "tags": [ - "AI SRE/MCP servers" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- `command`/`args`/`env` apply to `stdio`; `url`/`headers` apply to `sse`/`streamable-http`.\n- Server name must start with a letter and contain only letters, digits, `-`, or `_`, and is unique within its scope (account-wide or one team), case-insensitive; violations return InvalidParameter.\n- `environments` restricts where the server can run: a list of `cloud` and/or BYOC runner environment IDs; omitted or empty means all environments.\n- `per_user_secret` auth mode requires `secret_schema` to be valid JSON with a non-empty `header_name`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-infos", "metadata": { - "sidebarTitle": "Create MCP server" + "sidebarTitle": "Batch get schedules" } } } }, - "/safari/mcp/server/delete": { + "/schedule/list": { "post": { - "description": "Delete an MCP server by ID.", - "operationId": "mcp-write-server-delete", + "description": "Return a paginated list of on-call schedules. When both start and end are provided (max 45 days apart), computed layer schedules are included.", + "operationId": "scheduleList", "requestBody": { "content": { "application/json": { "example": { - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" + "is_my_team": true, + "limit": 20, + "p": 1, + "query": "production" }, "schema": { - "$ref": "#/components/schemas/MCPServerDeleteRequest" + "$ref": "#/components/schemas/ScheduleListRequest" } } }, @@ -53580,19 +59611,110 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "items": [ + { + "account_id": 2451002751131, + "create_at": 1766110836, + "create_by": 2476123212131, + "cur_oncall": null, + "description": "abc", + "disabled": 0, + "final_schedule": { + "layer_name": "", + "mode": 0, + "name": "", + "schedules": null + }, + "group_id": 4291079133131, + "id": 5789640530410, + "layer_schedules": null, + "layers": null, + "name": "test-000001", + "next_oncall": null, + "notify": { + "advance_in_time": 300, + "by": { + "follow_preference": false, + "personal_channels": [ + "email" + ] + }, + "fixed_time": null, + "webhooks": [ + { + "settings": { + "alias": "", + "chat_ids": [ + "oc_60a6dc4c6e4e5cbc4934ef08aa7ff76d" + ], + "data_source_id": 5427276014131, + "sign_secret": "", + "token": "", + "verify_token": "" + }, + "type": "feishu_app" + } + ] + }, + "schedule_id": 5789640530410, + "schedule_layers": null, + "schedule_name": "test-000001", + "status": 0, + "team_id": 4291079133131, + "update_at": 1775205795, + "update_by": 2476123212131 + }, + { + "account_id": 2451002751131, + "create_at": 1759132037, + "create_by": 2476123212131, + "cur_oncall": null, + "description": "", + "disabled": 0, + "final_schedule": { + "layer_name": "", + "mode": 0, + "name": "", + "schedules": null + }, + "group_id": 2477033058131, + "id": 5432326025106, + "layer_schedules": null, + "layers": null, + "name": "test-2509300001", + "next_oncall": null, + "notify": { + "advance_in_time": 300, + "by": { + "follow_preference": true, + "personal_channels": null + }, + "fixed_time": null, + "webhooks": null + }, + "schedule_id": 5432326025106, + "schedule_layers": null, + "schedule_name": "test-2509300001", + "status": 0, + "team_id": 2477033058131, + "update_at": 1775207501, + "update_by": 2476123212131 + } + ], + "total": 41 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/ScheduleListResponse" } }, "type": "object" @@ -53609,9 +59731,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53619,36 +59738,79 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Delete MCP server", + "summary": "List schedules", "tags": [ - "AI SRE/MCP servers" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/schedules/schedule-list", "metadata": { - "sidebarTitle": "Delete MCP server" + "sidebarTitle": "List schedules" } } } }, - "/safari/mcp/server/disable": { + "/schedule/preview": { "post": { - "description": "Disable an enabled MCP server.", - "operationId": "mcp-write-server-disable", + "description": "Preview the coverage generated by a schedule configuration without persisting it. The request accepts the same body as create/update plus a required start/end window (max 45 days).", + "operationId": "schedulePreview", "requestBody": { "content": { "application/json": { "example": { - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" + "end": 1712086400, + "layers": [ + { + "day_mask": { + "repeat": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "enable_time": 1712000000, + "expire_time": 0, + "fair_rotation": false, + "groups": [ + { + "end": 0, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2451002751131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 0 + } + ], + "handoff_time": 0, + "hidden": 0, + "layer_name": "Layer 1", + "mask_continuous_enabled": false, + "mode": 0, + "name": "Layer 1", + "restrict_end": 0, + "restrict_mode": 0, + "restrict_periods": [], + "restrict_start": 0, + "rotation_duration": 86400, + "rotation_unit": "day", + "rotation_value": 1, + "weight": 0 + } + ], + "schedule_name": "Preview Schedule", + "start": 1712000000 }, "schema": { - "$ref": "#/components/schemas/MCPServerStatusRequest" + "$ref": "#/components/schemas/ScheduleUpsertRequest" } } }, @@ -53659,19 +59821,180 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "account_id": 0, + "create_at": 0, + "create_by": 0, + "cur_oncall": null, + "description": null, + "disabled": null, + "end": 1776240000, + "final_schedule": { + "layer_name": "", + "mode": 0, + "name": "", + "schedules": [ + { + "end": 1776096000, + "group": { + "end": 1776096000, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2451002751131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1776009600 + }, + "index": 0, + "start": 1776009600 + } + ] + }, + "group_id": null, + "id": null, + "layer_schedules": null, + "layers": [ + { + "account_id": 0, + "create_at": 0, + "create_by": 0, + "day_mask": { + "repeat": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "enable_time": 1775980800, + "expire_time": 0, + "fair_rotation": false, + "groups": [ + { + "end": 0, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2451002751131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 0 + }, + { + "end": 0, + "group_name": "B", + "members": [ + { + "person_ids": [ + 2476123212131 + ], + "role_id": 0 + } + ], + "name": "B", + "start": 0 + } + ], + "handoff_time": 0, + "hidden": 0, + "layer_end": null, + "layer_name": "Layer 1", + "layer_start": 1775980800, + "mask_continuous_enabled": false, + "mode": 0, + "name": "Layer 1", + "restrict_end": 0, + "restrict_mode": 0, + "restrict_periods": [], + "restrict_start": 0, + "rotation_duration": 86400, + "rotation_unit": "day", + "rotation_value": 1, + "schedule_id": 0, + "update_at": 0, + "update_by": 0, + "weight": 0 + } + ], + "name": null, + "next_oncall": null, + "notify": null, + "schedule_id": 0, + "schedule_layers": [ + { + "layer_name": "Layer 1", + "mode": 0, + "name": "Layer 1", + "schedules": [ + { + "end": 1776096000, + "group": { + "end": 1776096000, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2451002751131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 1776009600 + }, + "index": 0, + "start": 1776009600 + }, + { + "end": 1776182400, + "group": { + "end": 1776182400, + "group_name": "B", + "members": [ + { + "person_ids": [ + 2476123212131 + ], + "role_id": 0 + } + ], + "name": "B", + "start": 1776096000 + }, + "index": 0, + "start": 1776096000 + } + ] + } + ], + "schedule_name": null, + "start": 1775980800, + "status": null, + "team_id": null, + "update_at": 0, + "update_by": 0 + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/ScheduleItem" } }, "type": "object" @@ -53688,9 +60011,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53698,36 +60018,32 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Disable MCP server", + "summary": "Preview schedule", "tags": [ - "AI SRE/MCP servers" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Disabling an already-disabled server returns InvalidParameter instead of a silent no-op.\n- Requires edit permission on the server's current team: account-scope servers are owner/admin only; team-scope servers require the caller to belong to that team (or be owner/admin).\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **60 requests/minute**; **10 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-preview", "metadata": { - "sidebarTitle": "Disable MCP server" + "sidebarTitle": "Preview schedule" } } } }, - "/safari/mcp/server/enable": { + "/schedule/self": { "post": { - "description": "Enable a disabled MCP server.", - "operationId": "mcp-write-server-enable", + "description": "Return on-call schedules where the current user is assigned.", + "operationId": "scheduleSelf", "requestBody": { "content": { "application/json": { "example": { - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" + "end": 1712086400, + "start": 1712000000 }, "schema": { - "$ref": "#/components/schemas/MCPServerStatusRequest" + "$ref": "#/components/schemas/ScheduleSelfRequest" } } }, @@ -53738,19 +60054,120 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "items": [ + { + "account_id": 2451002751131, + "create_at": 1702623874, + "create_by": 2451002751131, + "cur_oncall": null, + "description": "", + "disabled": 0, + "final_schedule": { + "layer_name": "", + "mode": 0, + "name": "", + "schedules": null + }, + "group_id": 2477033058131, + "id": 2539108069860, + "layer_schedules": null, + "layers": [ + { + "account_id": 2451002751131, + "create_at": 1702623874, + "create_by": 2451002751131, + "day_mask": { + "repeat": [ + 1, + 2, + 3, + 4, + 5 + ] + }, + "enable_time": 1702623874, + "expire_time": 0, + "fair_rotation": false, + "groups": [ + { + "end": 0, + "group_name": "A", + "members": [ + { + "person_ids": [ + 2476444212131 + ], + "role_id": 0 + } + ], + "name": "A", + "start": 0 + }, + { + "end": 0, + "group_name": "B", + "members": [ + { + "person_ids": [ + 2469167612131 + ], + "role_id": 0 + } + ], + "name": "B", + "start": 0 + } + ], + "handoff_time": 0, + "hidden": 0, + "layer_end": null, + "layer_name": "Rule 1", + "layer_start": 1702623874, + "mask_continuous_enabled": false, + "mode": 0, + "name": "Rule 1", + "restrict_end": 0, + "restrict_mode": 0, + "restrict_periods": [], + "restrict_start": 0, + "rotation_duration": 86400, + "rotation_unit": "day", + "rotation_value": 1, + "schedule_id": 2539108069860, + "update_at": 1710468081, + "update_by": 2476444212131, + "weight": 0 + } + ], + "name": "Open Source Q&A", + "next_oncall": null, + "notify": { + "by": null, + "fixed_time": null, + "webhooks": null + }, + "schedule_id": 2539108069860, + "schedule_layers": null, + "schedule_name": "Open Source Q&A", + "status": 0, + "team_id": 2477033058131, + "update_at": 1710468081, + "update_by": 2476444212131 + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/ScheduleSelfResponse" } }, "type": "object" @@ -53767,9 +60184,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -53777,36 +60191,34 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Enable MCP server", + "summary": "List my schedules", "tags": [ - "AI SRE/MCP servers" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Enabling an already-enabled server returns InvalidParameter instead of a silent no-op.\n- Requires edit permission on the server's current team: account-scope servers are owner/admin only; team-scope servers require the caller to belong to that team (or be owner/admin).\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-self", "metadata": { - "sidebarTitle": "Enable MCP server" + "sidebarTitle": "List my schedules" } } } }, - "/safari/mcp/server/get": { + "/schedule/update": { "post": { - "description": "Get one MCP server as a pure database read — no live probe is performed.", - "operationId": "mcp-read-server-get", + "description": "Update an existing on-call schedule. Provide schedule_id to identify the schedule.", + "operationId": "scheduleUpdate", "requestBody": { "content": { "application/json": { "example": { - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" + "description": "Updated primary on-call rotation", + "schedule_id": 2001, + "schedule_name": "Production On-Call (Updated)", + "team_id": 4291079133131 }, "schema": { - "$ref": "#/components/schemas/MCPServerGetRequest" + "$ref": "#/components/schemas/ScheduleUpsertRequest" } } }, @@ -53817,35 +60229,18 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 10023, - "auth_mode": "shared", - "call_timeout": 60, - "can_edit": true, - "connect_timeout": 10, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Query Prometheus metrics and alerts.", - "environments": [], - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", - "server_name": "prometheus", - "status": "enabled", - "team_id": 0, - "transport": "streamable-http", - "updated_at": 1717046400000, - "url": "https://mcp.example.com/prometheus" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/MCPServerItem" + "$ref": "#/components/schemas/ScheduleEmptyObject" } }, "type": "object" @@ -53869,82 +60264,76 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Get MCP server detail", + "summary": "Update schedule", "tags": [ - "AI SRE/MCP servers" + "On-call/Schedules" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- A pure database read — it never probes the live server; the stored configuration (with secrets masked) and the cached `ai_description` are returned as-is.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-read-server-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/schedules/schedule-update", "metadata": { - "sidebarTitle": "Get MCP server detail" + "sidebarTitle": "Update schedule" } } } }, - "/safari/mcp/server/list": { + "/sourcemap/list": { "post": { - "description": "List MCP servers visible to the caller across account and team scopes, with pagination.", - "operationId": "mcp-read-server-list", + "description": "Return a paginated list of uploaded sourcemap files filtered by platform type, service, and version.", + "operationId": "sourcemap-read-list", "requestBody": { "content": { "application/json": { "example": { - "include_account": true, + "end_time": 1712700000000, "limit": 20, - "p": 1 + "p": 1, + "services": [ + "my-web-app" + ], + "start_time": 1712000000000, + "type": "browser" }, "schema": { - "$ref": "#/components/schemas/MCPServerListRequest" + "$ref": "#/components/schemas/SourcemapListRequest" } } }, "required": true }, - "responses": { - "200": { - "content": { - "application/json": { - "example": { - "data": { - "servers": [ - { - "account_id": 10023, - "auth_mode": "shared", - "call_timeout": 60, - "can_edit": true, - "connect_timeout": 10, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Query Prometheus metrics and alerts.", - "environments": [], - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", - "server_name": "prometheus", - "status": "enabled", - "team_id": 0, - "transport": "streamable-http", - "updated_at": 1717046400000, - "url": "https://mcp.example.com/prometheus" + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "items": [ + { + "created_at": 1712700000, + "git_commit_sha": "abc1234def5678", + "git_repository_url": "https://github.com/example/my-web-app", + "key": "browser/my-web-app/1.0.0/main.js.map", + "metadata": {}, + "service": "my-web-app", + "size": 204800, + "type": "browser", + "updated_at": 1712700000, + "version": "1.0.0" } ], - "total": 1 + "total": 3 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/MCPServerListResponse" + "$ref": "#/components/schemas/SourcemapListResponse" } }, "type": "object" @@ -53968,37 +60357,35 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "List MCP servers", + "summary": "List sourcemaps", "tags": [ - "AI SRE/MCP servers" + "RUM/Sourcemaps" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The response never includes a live tool list; tools are probed asynchronously on create/update and cached for runtime use.\n- `query` performs a case-insensitive substring search across name, description, AI-generated description, server ID, transport, URL, command, and source template name.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-read-server-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `start_time` and `end_time` are required — both use Unix epoch **milliseconds**. Maximum window is 365 days.\n- The `type` field selects the platform: `browser` (JavaScript), `android`, or `ios`. Defaults to `browser` when omitted.\n- Default page size is 20; maximum is 100. Default sort is `created_at` descending.\n- For Android, `build_id` matches the Gradle plugin build identifier. For iOS, `uuid` matches the dSYM bundle UUID.", + "href": "/en/api-reference/rum/sourcemaps/sourcemap-read-list", "metadata": { - "sidebarTitle": "List MCP servers" + "sidebarTitle": "List sourcemaps" } } } }, - "/safari/mcp/server/update": { + "/sourcemap/stack/enrich": { "post": { - "description": "Update an MCP server's configuration. Omit a field to leave it unchanged.", - "operationId": "mcp-write-server-update", + "description": "Symbolicate or deobfuscate a browser, Android, iOS, Mini Program, or HarmonyOS stack trace.", + "operationId": "sourcemap-read-stack-enrich", "requestBody": { "content": { "application/json": { "example": { - "description": "Query Prometheus metrics, alerts, and rules.", - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1" + "near": 3, + "service": "my-web-app", + "stack": "TypeError: Cannot read properties of undefined\n at render (https://cdn.example.com/app.min.js:1:2345)", + "type": "browser", + "version": "1.0.0" }, "schema": { - "$ref": "#/components/schemas/MCPServerUpdateRequest" + "$ref": "#/components/schemas/SourcemapStackEnrichRequest" } } }, @@ -54010,34 +60397,43 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "auth_mode": "shared", - "call_timeout": 60, - "can_edit": true, - "connect_timeout": 10, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Query Prometheus metrics, alerts, and rules.", - "environments": [], - "server_id": "mcp_4kP9wQ2nLceRtY7uVb3xA1", - "server_name": "prometheus", - "status": "enabled", - "team_id": 0, - "transport": "streamable-http", - "updated_at": 1717046400000, - "url": "https://mcp.example.com/prometheus" + "frames": [ + { + "code_snippets": [ + { + "code": "const cart = props.cart;", + "line": 41 + }, + { + "code": "return cart.items.map(renderItem);", + "line": 42 + } + ], + "column": 17, + "converted": true, + "file": "src/pages/checkout.tsx", + "function": "renderCheckout", + "line": 42, + "original_frame": { + "column": 2345, + "file": "https://cdn.example.com/app.min.js", + "function": "render", + "line": 1 + } + } + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/MCPServerItem" + "$ref": "#/components/schemas/SourcemapStackEnrichResponse" } }, "type": "object" @@ -54054,9 +60450,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54064,59 +60457,103 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Update MCP server", + "summary": "Enrich a stack trace", "tags": [ - "AI SRE/MCP servers" + "RUM/Sourcemaps" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **MCP Manage** (`ai-sre`) |\n\n## Usage\n\n- Masked secret values in `env`/`headers` are preserved — sending the masked value back does not overwrite the stored secret.\n- `environments` is a tri-state partial-update field: omit (null) to leave it unchanged; send a list to set it — an empty list clears the restriction back to all environments.\n- Changing `team_id` requires reassignment permission on the destination team; if `environments` is left unchanged, the current environments must still be selectable by the caller under the new team or the update is rejected.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/mcp-servers/mcp-write-server-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `type` defaults to `browser` when omitted for backward compatibility.\n- Set `near` from 1 to 20 to include source-code snippets around converted frames.\n- For Android NDK native crashes, provide `arch` and `source_type: ndk` so the backend routes to native symbolication.\n- For iOS crash stacks, pass `binary_images` so addresses can be relocated against the uploaded dSYM files.\n- `no_cache` is intended for debugging and bypasses cached enrich results.", + "href": "/en/api-reference/rum/sourcemaps/sourcemap-read-stack-enrich", "metadata": { - "sidebarTitle": "Update MCP server" + "sidebarTitle": "Enrich a stack trace" } } } }, - "/safari/session/delete": { - "post": { - "description": "Delete a session by ID.", - "operationId": "session-write-delete", - "requestBody": { - "content": { - "application/json": { - "example": { - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" - }, - "schema": { - "$ref": "#/components/schemas/SessionDeleteRequest" - } + "/status-page/change/active/list": { + "get": { + "description": "List in-progress (non-terminal) events of a given type for a status page.", + "operationId": "statusPageChangeActiveList", + "parameters": [ + { + "description": "Status page ID.", + "in": "query", + "name": "page_id", + "required": true, + "schema": { + "format": "int64", + "type": "integer" } }, - "required": true - }, + { + "description": "Event type filter. Required. Returns only in-progress (non-terminal) events — `investigating`/`identified`/`monitoring` for `incident`, `scheduled`/`ongoing` for `maintenance`.", + "in": "query", + "name": "type", + "required": true, + "schema": { + "enum": [ + "incident", + "maintenance" + ], + "type": "string" + } + } + ], "responses": { "200": { "content": { "application/json": { "example": { - "data": null, + "data": { + "items": [ + { + "affected_components": [ + { + "available_since_seconds": 1765349358, + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "name": "Web Console", + "order_id": 1, + "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2", + "status": "degraded" + } + ], + "change_id": 5821693893131, + "description": "We are currently investigating an issue affecting some services.", + "notify_subscribers": true, + "page_id": 5750613685214, + "start_at_seconds": 1766736878, + "status": "investigating", + "title": "Web Console Degraded Performance", + "type": "incident", + "updates": [ + { + "at_seconds": 1766736876, + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "component_name": "Web Console", + "status": "degraded" + } + ], + "description": "We are currently investigating an issue affecting some services.", + "status": "investigating", + "update_id": "01KDCVJQ88SZPHWPTDV2Z2AZW8" + } + ] + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/StatusPageChangeListResponse" } }, "type": "object" @@ -54133,9 +60570,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54143,37 +60577,49 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Delete session", + "summary": "List active status page events", "tags": [ - "AI SRE/Sessions" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Personal sessions can be deleted only by their creator; team sessions can be deleted by the creator, an account admin, or a member of the owning team.\n- This is a soft delete: it also cascades to delete child subagent sessions and any presented files; the underlying S3/MinIO blobs are removed best-effort after the transaction commits, so an orphaned blob is possible on partial failure.\n", - "href": "/en/api-reference/ai-sre/sessions/session-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-active-list", "metadata": { - "sidebarTitle": "Delete session" + "sidebarTitle": "List active status page events" } } } }, - "/safari/session/export": { + "/status-page/change/create": { "post": { - "description": "Stream a session's full event transcript as newline-delimited JSON.", - "operationId": "session-read-export", + "description": "Create a new incident or maintenance event on a status page.", + "operationId": "statusPageChangeCreate", "requestBody": { "content": { "application/json": { "example": { - "include_subagents": false, - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" + "description": "We are investigating degraded performance affecting the web console.", + "notify_subscribers": true, + "page_id": 5750613685214, + "start_at_seconds": 1712000000, + "status": "investigating", + "title": "Web Console Degraded Performance", + "type": "incident", + "updates": [ + { + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "status": "degraded" + } + ], + "description": "We are currently investigating an issue affecting some users.", + "status": "investigating" + } + ] }, "schema": { - "$ref": "#/components/schemas/SessionExportRequest" + "$ref": "#/components/schemas/CreateStatusPageChangeRequest" } } }, @@ -54182,14 +60628,32 @@ "responses": { "200": { "content": { - "application/x-ndjson": { + "application/json": { + "example": { + "data": { + "change_id": 6294539747131, + "change_name": "API Test Incident" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, "schema": { - "description": "Newline-delimited JSON stream. Parse line-by-line; do not buffer the whole body.", - "type": "string" + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/StatusPageChangeCreateResponse" + } + }, + "type": "object" + } + ] } } }, - "description": "Streaming NDJSON (application/x-ndjson). One JSON object per line, terminated by a newline. The first line is always a `session_meta` envelope; subsequent lines are session events." + "description": "Success" }, "400": { "$ref": "#/components/responses/BadRequest" @@ -54197,9 +60661,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54207,37 +60668,32 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Export session transcript", + "summary": "Create status page event", "tags": [ - "AI SRE/Sessions" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/day**; **200 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Personal sessions are exportable only by their creator; team sessions can be exported by same-account callers with the `session_id`.\n- The response is `application/x-ndjson` — parse line-by-line and write to a file; do not buffer the whole body in memory.\n- The first line is always a `session_meta` envelope; `include_subagents=true` inlines each child session's stream after its dispatch line.\n- Requests are capped at a 60-second execution timeout; very large sessions may not finish exporting within that window.\n- If the stream fails partway through, the response ends with a JSON error line instead of a proper error envelope (headers are already sent) — check for this trailing line to detect truncation.\n", - "href": "/en/api-reference/ai-sre/sessions/session-read-export", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-create", "metadata": { - "sidebarTitle": "Export session transcript" + "sidebarTitle": "Create status page event" } } } }, - "/safari/session/get": { + "/status-page/change/delete": { "post": { - "description": "Fetch one session plus a backward-paged window of its most recent events.", - "operationId": "session-read-info", + "description": "Delete a status page event.", + "operationId": "statusPageChangeDelete", "requestBody": { "content": { "application/json": { "example": { - "num_recent_events": 50, - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u" + "change_id": 5821693893131, + "page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/SessionGetRequest" + "$ref": "#/components/schemas/DeleteStatusPageChangeRequest" } } }, @@ -54248,88 +60704,18 @@ "content": { "application/json": { "example": { - "data": { - "events": [ - { - "author": "user", - "created_at": 1780367971241, - "event_id": "evt_3aZQ9p", - "partial": false, - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", - "status": "normal", - "turn_complete": false - }, - { - "author": "ai-sre", - "content": { - "parts": [ - { - "text": "..." - } - ], - "role": "model" - }, - "created_at": 1780367992649, - "event_id": "evt_7bWk2r", - "partial": false, - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", - "status": "normal", - "turn_complete": true - } - ], - "has_more_older": false, - "session": { - "access_source": "manager", - "app_name": "ai-sre", - "archived_at": 0, - "can_continue": true, - "can_fork": true, - "can_manage": true, - "can_view": true, - "context_window": 0, - "created_at": 1780367971228, - "current_context_tokens": 14948, - "current_turn_active_ms": 0, - "current_turn_started_at": 0, - "current_turn_tokens": 0, - "current_turn_wait_ms": 0, - "entry_kind": "web", - "has_unread": true, - "incognito": false, - "is_mine": false, - "is_running": false, - "last_event_at": 1780367992649, - "person_id": "3790925372131", - "pinned_at": 0, - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", - "session_name": "Investigate cloud-assistant first heartbeat", - "share_enabled": true, - "share_version": 3, - "shared_at": 1780367971000, - "shared_by": 3790925372131, - "status": "enabled", - "team_id": 0, - "token_usage": { - "cached_tokens": 11520, - "input_tokens": 14948, - "output_tokens": 888, - "reasoning_tokens": 351 - }, - "updated_at": 1780367993457 - }, - "suggest_init": false - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/SessionGetResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -54346,9 +60732,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54356,105 +60739,110 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Get session detail", + "summary": "Delete status page event", "tags": [ - "AI SRE/Sessions" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Personal sessions are readable only by their creator; team sessions can be read by same-account callers with the `session_id`.\n- Page older history with `search_after_ctx` from the previous response.\n- `limit` (or legacy `num_recent_events`) caps the event page; default 100, max 1000.\n- A malformed `search_after_ctx` returns 400 immediately, before any DB work.\n- `current_turn_*` fields are populated only while the session `is_running`; `suggest_init` is the same account-wide onboarding flag as `session/list`.\n", - "href": "/en/api-reference/ai-sre/sessions/session-read-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-delete", "metadata": { - "sidebarTitle": "Get session detail" + "sidebarTitle": "Delete status page event" } } } }, - "/safari/session/list": { - "post": { - "description": "List agent sessions visible to the caller, filtered by app, surface, archive status, and team.", - "operationId": "session-read-list", - "requestBody": { - "content": { - "application/json": { - "example": { - "app_name": "ai-sre", - "limit": 2, - "orderby": "updated_at", - "scope": "all" - }, - "schema": { - "$ref": "#/components/schemas/SessionListRequest" - } + "/status-page/change/info": { + "get": { + "description": "Retrieve details of a specific status page event (incident or maintenance).", + "operationId": "statusPageChangeInfo", + "parameters": [ + { + "description": "Status page ID.", + "in": "query", + "name": "page_id", + "required": true, + "schema": { + "format": "int64", + "type": "integer" } }, - "required": true - }, + { + "description": "Event (change) ID.", + "in": "query", + "name": "change_id", + "required": true, + "schema": { + "format": "int64", + "type": "integer" + } + } + ], "responses": { "200": { "content": { "application/json": { "example": { "data": { - "sessions": [ + "affected_components": [ { - "access_source": "manager", - "app_name": "ai-sre", - "archived_at": 0, - "can_continue": true, - "can_fork": true, - "can_manage": true, - "can_view": true, - "context_window": 0, - "created_at": 1780367971228, - "current_context_tokens": 14948, - "current_turn_active_ms": 0, - "current_turn_started_at": 0, - "current_turn_tokens": 0, - "current_turn_wait_ms": 0, - "entry_kind": "web", - "has_unread": true, - "incognito": false, - "is_mine": false, - "is_running": false, - "last_event_at": 1780367992649, - "person_id": "3790925372131", - "pinned_at": 0, - "session_id": "sess_f8oDvqiG64uur6sBNsTc4u", - "session_name": "Investigate cloud-assistant first heartbeat", - "share_enabled": true, - "share_version": 3, - "shared_at": 1780367971000, - "shared_by": 3790925372131, - "status": "enabled", - "team_id": 0, - "token_usage": { - "cached_tokens": 11520, - "input_tokens": 14948, - "output_tokens": 888, - "reasoning_tokens": 351 - }, - "updated_at": 1780367993457 + "available_since_seconds": 1765349358, + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "name": "Web Console", + "order_id": 1, + "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2", + "status": "operational" + } + ], + "change_id": 5821693893131, + "close_at_seconds": 1775529742, + "description": "The issue has been resolved, and all services are operating normally.\n\nThank you for your patience.", + "notify_subscribers": true, + "page_id": 5750613685214, + "start_at_seconds": 1766736878, + "status": "resolved", + "title": "Web Console Degraded Performance", + "type": "incident", + "updates": [ + { + "at_seconds": 1766736876, + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "component_name": "Web Console", + "status": "degraded" + } + ], + "description": "We are currently investigating an issue affecting some services.", + "status": "investigating", + "update_id": "01KDCVJQ88SZPHWPTDV2Z2AZW8" + }, + { + "at_seconds": 1775529742, + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "component_name": "Web Console", + "status": "operational" + } + ], + "description": "The issue has been resolved, and all services are operating normally.", + "status": "resolved", + "update_id": "01KNJX3KW873ZZSRZC14SGFYS3" } - ], - "suggest_init": false, - "total": 988 + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/SessionListResponse" + "$ref": "#/components/schemas/StatusPageChangeItem" } }, "type": "object" @@ -54471,9 +60859,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54481,59 +60866,155 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "List sessions", + "summary": "Get status page event detail", "tags": [ - "AI SRE/Sessions" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Pagination uses `p`/`limit` (max 100); `scope` defaults to `all`.\n- `all` returns your personal sessions plus team sessions you can access; account admins see all team sessions, but not other users' personal sessions.\n- `team_ids` narrows the visible set and never expands access.\n- `is_running` reflects the live run-set; `has_unread` is computed per calling user; the `current_turn_*` fields are always zero here — only `session/get` computes them while a session is running.\n- `suggest_init` is an account-wide onboarding flag (true only when the account has zero knowledge packs anywhere) — it doesn't depend on the list filters.\n", - "href": "/en/api-reference/ai-sre/sessions/session-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-info", "metadata": { - "sidebarTitle": "List sessions" + "sidebarTitle": "Get status page event detail" } } } }, - "/safari/skill/delete": { - "post": { - "description": "Delete a skill by ID.", - "operationId": "skill-write-delete", - "requestBody": { - "content": { - "application/json": { - "example": { - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" - }, - "schema": { - "$ref": "#/components/schemas/SkillDeleteRequest" - } + "/status-page/change/list": { + "get": { + "description": "List status page events for console management. Unlike the public display endpoints, the response includes hidden components.", + "operationId": "statusPageChangeList", + "parameters": [ + { + "description": "Status page ID.", + "in": "query", + "name": "page_id", + "required": true, + "schema": { + "format": "int64", + "type": "integer" } }, - "required": true - }, + { + "description": "Lower bound of the event activity window: only events still open at, or closed at or after, this Unix timestamp (seconds) are returned.", + "in": "query", + "name": "start_at_seconds", + "required": false, + "schema": { + "format": "int64", + "type": "integer" + } + }, + { + "description": "Upper bound of the event activity window: only events started at or before this Unix timestamp (seconds) are returned.", + "in": "query", + "name": "end_at_seconds", + "required": false, + "schema": { + "format": "int64", + "type": "integer" + } + }, + { + "description": "Event type filter. Required.", + "in": "query", + "name": "type", + "required": true, + "schema": { + "enum": [ + "incident", + "maintenance" + ], + "type": "string" + } + }, + { + "description": "Event status filter. Required. Must be a status valid for the given `type` (`investigating`/`identified`/`monitoring`/`resolved` for `incident`; `scheduled`/`ongoing`/`completed` for `maintenance`).", + "in": "query", + "name": "status", + "required": true, + "schema": { + "enum": [ + "investigating", + "identified", + "monitoring", + "resolved", + "scheduled", + "ongoing", + "completed" + ], + "type": "string" + } + } + ], "responses": { "200": { "content": { "application/json": { "example": { - "data": null, + "data": { + "items": [ + { + "affected_components": [ + { + "available_since_seconds": 1765349358, + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "name": "Web Console", + "order_id": 1, + "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2", + "status": "operational" + } + ], + "change_id": 5821693893131, + "close_at_seconds": 1775529742, + "description": "The issue has been resolved, and all services are operating normally.", + "notify_subscribers": true, + "page_id": 5750613685214, + "start_at_seconds": 1766736878, + "status": "resolved", + "title": "Web Console Degraded Performance", + "type": "incident", + "updates": [ + { + "at_seconds": 1766736876, + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "component_name": "Web Console", + "status": "degraded" + } + ], + "description": "We are currently investigating an issue affecting some services.", + "status": "investigating", + "update_id": "01KDCVJQ88SZPHWPTDV2Z2AZW8" + }, + { + "at_seconds": 1775529742, + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "component_name": "Web Console", + "status": "operational" + } + ], + "description": "The issue has been resolved, and all services are operating normally.", + "status": "resolved", + "update_id": "01KNJX3KW873ZZSRZC14SGFYS3" + } + ] + } + ] + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/StatusPageChangeListResponse" } }, "type": "object" @@ -54550,9 +61031,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54560,36 +61038,41 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Delete skill", + "summary": "List status page events", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Soft delete only: sets `status` to `deleted` and renames the row to free its name for reuse; the skill's zip archive is not removed from object storage.\n- Deleting an already-deleted or nonexistent `skill_id` returns `ResourceNotFound`, since the lookup excludes deleted rows before the delete itself runs.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/skills/skill-write-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-list", "metadata": { - "sidebarTitle": "Delete skill" + "sidebarTitle": "List status page events" } } } }, - "/safari/skill/disable": { + "/status-page/change/timeline/create": { "post": { - "description": "Disable an enabled skill so the agent stops loading it.", - "operationId": "skill-write-disable", + "description": "Add a timeline update to a status page event.", + "operationId": "statusPageChangeTimelineCreate", "requestBody": { "content": { "application/json": { "example": { - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" + "at_seconds": 1712003600, + "change_id": 5821693893131, + "component_changes": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "status": "partial_outage" + } + ], + "description": "We have identified the root cause and are working on a fix.", + "page_id": 5750613685214, + "status": "identified" }, "schema": { - "$ref": "#/components/schemas/SkillStatusRequest" + "$ref": "#/components/schemas/CreateStatusPageChangeTimelineRequest" } } }, @@ -54600,19 +61083,20 @@ "content": { "application/json": { "example": { - "data": null, + "data": { + "update_id": "01KP0311872NVYFRRQ82FWXAP4" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/StatusPageChangeTimelineCreateResponse" } }, "type": "object" @@ -54629,9 +61113,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54639,36 +61120,33 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Disable skill", + "summary": "Create event timeline entry", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Only an `enabled` skill can be disabled; an already-disabled skill returns `InvalidParameter`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/skills/skill-write-disable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-timeline-create", "metadata": { - "sidebarTitle": "Disable skill" + "sidebarTitle": "Create event timeline entry" } } } }, - "/safari/skill/enable": { + "/status-page/change/timeline/delete": { "post": { - "description": "Enable a disabled skill so the agent can load it.", - "operationId": "skill-read-enable", + "description": "Delete a timeline entry from a status page event.", + "operationId": "statusPageChangeTimelineDelete", "requestBody": { "content": { "application/json": { "example": { - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" + "change_id": 5821693893131, + "page_id": 5750613685214, + "update_id": "01KP0311872NVYFRRQ82FWXAP4" }, "schema": { - "$ref": "#/components/schemas/SkillStatusRequest" + "$ref": "#/components/schemas/DeleteStatusPageChangeTimelineRequest" } } }, @@ -54679,19 +61157,18 @@ "content": { "application/json": { "example": { - "data": null, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "description": "Always null on success.", - "type": "null" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -54708,9 +61185,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -54718,36 +61192,35 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Enable skill", + "summary": "Delete event timeline entry", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Only a `disabled` skill can be enabled; an already-enabled skill returns `InvalidParameter`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/skills/skill-read-enable", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-timeline-delete", "metadata": { - "sidebarTitle": "Enable skill" + "sidebarTitle": "Delete event timeline entry" } } } }, - "/safari/skill/get": { + "/status-page/change/timeline/update": { "post": { - "description": "Get one skill including its full SKILL.md content.", - "operationId": "skill-read-get", + "description": "Update a timeline entry for a status page event.", + "operationId": "statusPageChangeTimelineUpdate", "requestBody": { "content": { "application/json": { "example": { - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" + "at_seconds": 1712003600, + "change_id": 5821693893131, + "description": "Corrected description: root cause identified in database layer.", + "page_id": 5750613685214, + "update_id": "01KP0311872NVYFRRQ82FWXAP4" }, "schema": { - "$ref": "#/components/schemas/SkillGetRequest" + "$ref": "#/components/schemas/UpdateStatusPageChangeTimelineRequest" } } }, @@ -54758,43 +61231,18 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 10023, - "author": "sre-team", - "can_edit": true, - "content": "---\nname: k8s-triage\ndescription: ...\n---\n# Triage steps", - "created_at": 1716960000000, - "created_by": 80011, - "description": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", - "description_en": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", - "is_modified": false, - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", - "skill_name": "k8s-triage", - "status": "enabled", - "tags": [ - "kubernetes", - "triage" - ], - "team_id": 0, - "tools": [ - "bash", - "mcp:prometheus/query" - ], - "update_available": false, - "updated_at": 1717046400000, - "version": "1.2.0" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/SkillItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -54818,38 +61266,33 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Get skill detail", + "summary": "Update event timeline entry", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Returns `ResourceNotFound` if the skill does not exist or has already been deleted.\n- `can_edit` reflects team membership, but read access itself is open to any caller regardless of team.\n", - "href": "/en/api-reference/ai-sre/skills/skill-read-get", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-timeline-update", "metadata": { - "sidebarTitle": "Get skill detail" + "sidebarTitle": "Update event timeline entry" } } } }, - "/safari/skill/list": { + "/status-page/change/update": { "post": { - "description": "List AI SRE skills visible to the caller across account and team scopes, with pagination.", - "operationId": "skill-read-list", + "description": "Update an existing status page event.", + "operationId": "statusPageChangeUpdate", "requestBody": { "content": { "application/json": { "example": { - "include_account": true, - "limit": 20, - "p": 1 + "change_id": 5821693893131, + "page_id": 5750613685214, + "title": "Web Console Degraded Performance (Updated)" }, "schema": { - "$ref": "#/components/schemas/SkillListRequest" + "$ref": "#/components/schemas/UpdateStatusPageChangeRequest" } } }, @@ -54860,46 +61303,18 @@ "content": { "application/json": { "example": { - "data": { - "skills": [ - { - "account_id": 10023, - "author": "sre-team", - "can_edit": true, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", - "is_modified": false, - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", - "skill_name": "k8s-triage", - "status": "enabled", - "tags": [ - "kubernetes", - "triage" - ], - "team_id": 0, - "tools": [ - "bash", - "mcp:prometheus/query" - ], - "update_available": false, - "updated_at": 1717046400000, - "version": "1.2.0" - } - ], - "total": 1 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/SkillListResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -54923,37 +61338,34 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "List skills", + "summary": "Update status page event", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The `content` field is omitted in list rows; fetch a single skill to read its body.\n- `scope` selects `all` (default), `account`-only, or `team`-only, overriding `include_account`; non-admins requesting specific `team_ids` are silently filtered down to the teams they belong to.\n- `update_available` compares against the marketplace catalog once per call; if the catalog fails to load, the badge is simply suppressed rather than the request failing.\n", - "href": "/en/api-reference/ai-sre/skills/skill-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-change-update", "metadata": { - "sidebarTitle": "List skills" + "sidebarTitle": "Update status page event" } } } }, - "/safari/skill/update": { + "/status-page/component/delete": { "post": { - "description": "Update a skill's descriptions or reassign its team scope.", - "operationId": "skill-write-update", + "description": "Delete a service component from a status page.", + "operationId": "statusPageComponentDelete", "requestBody": { "content": { "application/json": { "example": { - "description": "Updated triage runbook.", - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m" + "component_ids": [ + "01KP032KMN9YFBMPWANJMFZFG1" + ], + "page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/SkillUpdateRequest" + "$ref": "#/components/schemas/DeleteStatusPageComponentRequest" } } }, @@ -54964,41 +61376,18 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 10023, - "author": "sre-team", - "can_edit": true, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Updated triage runbook.", - "is_modified": false, - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", - "skill_name": "k8s-triage", - "status": "enabled", - "tags": [ - "kubernetes", - "triage" - ], - "team_id": 0, - "tools": [ - "bash", - "mcp:prometheus/query" - ], - "update_available": false, - "updated_at": 1717046400000, - "version": "1.2.0" - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/SkillItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -55015,9 +61404,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -55025,37 +61411,39 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Update skill", + "summary": "Delete status page component", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Only `description`, `description_en`, and `team_id` are editable; the skill body is changed by re-uploading.\n- `description` only updates when non-empty — there is no way to clear it via this field; `description_en` is nilable, so send an empty string to explicitly clear it.\n- Reassigning `team_id` to a different team runs a second authorization check beyond edit access, verifying the caller may target the destination team.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/skills/skill-write-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-component-delete", "metadata": { - "sidebarTitle": "Update skill" + "sidebarTitle": "Delete status page component" } } } }, - "/safari/skill/upload": { + "/status-page/component/upsert": { "post": { - "description": "Upload a skill archive (.skill/.zip/.tar.gz/.tgz) to create or replace a skill.", - "operationId": "skill-write-upload", + "description": "Create or update a service component on a status page.", + "operationId": "statusPageComponentUpsert", "requestBody": { "content": { - "multipart/form-data": { + "application/json": { "example": { - "replace": false, - "team_id": 0 + "components": [ + { + "description": "Main web interface", + "name": "Web Console", + "order_id": 1, + "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2" + } + ], + "page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/SkillUploadRequest" + "$ref": "#/components/schemas/UpsertStatusPageComponentRequest" } } }, @@ -55067,40 +61455,21 @@ "application/json": { "example": { "data": { - "account_id": 10023, - "author": "sre-team", - "can_edit": true, - "created_at": 1716960000000, - "created_by": 80011, - "description": "Diagnose unhealthy Kubernetes workloads from cluster events and pod logs.", - "is_modified": false, - "skill_id": "skill_8s7Hn2kLpQ3xYbVc4Wd2m", - "skill_name": "k8s-triage", - "status": "enabled", - "tags": [ - "kubernetes", - "triage" - ], - "team_id": 0, - "tools": [ - "bash", - "mcp:prometheus/query" - ], - "update_available": false, - "updated_at": 1717046400000, - "version": "1.2.0" + "component_ids": [ + "01KP032KMN9YFBMPWANJMFZFG1" + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { "allOf": [ { - "$ref": "#/components/schemas/ResponseEnvelope" + "$ref": "#/components/schemas/SuccessEnvelope" }, { "properties": { "data": { - "$ref": "#/components/schemas/SkillItem" + "$ref": "#/components/schemas/UpsertStatusPageComponentResponse" } }, "type": "object" @@ -55117,9 +61486,6 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, - "403": { - "$ref": "#/components/responses/Forbidden" - }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -55127,36 +61493,35 @@ "$ref": "#/components/responses/ServerError" } }, - "security": [ - { - "AppKeyAuth": [] - } - ], - "summary": "Upload skill", + "summary": "Upsert status page component", "tags": [ - "AI SRE/Skills" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **30 requests/minute**; **3 requests/second** per account |\n| Permissions | **Skill Manage** (`ai-sre`) |\n\n## Usage\n\n- Send as `multipart/form-data` with a `file` part; accepted archive types are `.skill`, `.zip`, `.tar.gz`, `.tgz`, capped at 100MB (oversized files are rejected before the body is read).\n- `skill_id` + `replace=true` targets and overwrites that specific skill, skipping the team-authorship check since the caller already owns the row.\n- `replace=true` without `skill_id` upserts by matching skill name; omitting `replace` always creates a new skill — both paths require the caller to be allowed to author into the target `team_id`.\n- The response always stamps `can_edit: true`.\n- Every call is recorded in the account audit log.\n", - "href": "/en/api-reference/ai-sre/skills/skill-write-upload", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-component-upsert", "metadata": { - "sidebarTitle": "Upload skill" + "sidebarTitle": "Upsert status page component" } } } }, - "/schedule/by-person": { + "/status-page/create": { "post": { - "description": "Get a member's current and next on-call shifts and every enabled schedule they participate in.", - "operationId": "scheduleByPerson", + "description": "Create a new status page.", + "operationId": "statusPageCreate", "requestBody": { "content": { "application/json": { "example": { - "person_id": 2476444212131 + "contact_info": "mailto:support@example.com", + "name": "My Status Page", + "page_header": "Welcome to our status page", + "type": "public", + "url_name": "my-status-page" }, "schema": { - "$ref": "#/components/schemas/ScheduleByPersonRequest" + "$ref": "#/components/schemas/CreateStatusPageRequest" } } }, @@ -55168,24 +61533,9 @@ "application/json": { "example": { "data": { - "current": { - "end_at": 1773532799, - "schedule_id": 2539108069860, - "schedule_name": "Open Source Q&A", - "start_at": 1773446400 - }, - "next": { - "end_at": 1773619199, - "schedule_id": 2539108069860, - "schedule_name": "Open Source Q&A", - "start_at": 1773532800 - }, - "schedules": [ - { - "schedule_id": 2539108069860, - "schedule_name": "Open Source Q&A" - } - ] + "page_id": 6294565612043, + "page_name": "My Status Page", + "page_url_name": "my-status-page" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -55197,7 +61547,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleByPersonResponse" + "$ref": "#/components/schemas/CreateStatusPageResponse" } }, "type": "object" @@ -55221,102 +61571,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get member on-call status", + "summary": "Create status page", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |\n\n## Usage\n\n- `current` carries the shift in progress with its true start time; `next` is the upcoming shift, absent when nothing is scheduled within the lookup window.\n- Disabled schedules are not listed.", - "href": "/en/api-reference/on-call/schedules/schedule-by-person", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-create", "metadata": { - "sidebarTitle": "Get member on-call status" + "sidebarTitle": "Create status page" } } } }, - "/schedule/create": { + "/status-page/delete": { "post": { - "description": "Create a new on-call schedule (escalation rule schedule).", - "operationId": "scheduleCreate", + "description": "Delete a status page.", + "operationId": "statusPageDelete", "requestBody": { "content": { "application/json": { "example": { - "description": "Primary on-call rotation for the production team", - "layers": [ - { - "day_mask": { - "repeat": [ - 1, - 2, - 3, - 4, - 5 - ] - }, - "enable_time": 1712000000, - "expire_time": 0, - "fair_rotation": false, - "groups": [ - { - "end": 0, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2451002751131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 0 - }, - { - "end": 0, - "group_name": "B", - "members": [ - { - "person_ids": [ - 2476123212131 - ], - "role_id": 0 - } - ], - "name": "B", - "start": 0 - } - ], - "handoff_time": 0, - "hidden": 0, - "layer_name": "Layer 1", - "mask_continuous_enabled": false, - "mode": 0, - "name": "Layer 1", - "restrict_end": 0, - "restrict_mode": 0, - "restrict_periods": [], - "restrict_start": 0, - "rotation_duration": 86400, - "rotation_unit": "day", - "rotation_value": 1, - "weight": 0 - } - ], - "notify": { - "advance_in_time": 300, - "by": { - "follow_preference": true, - "personal_channels": null - }, - "fixed_time": null, - "webhooks": null - }, - "schedule_name": "Production On-Call", - "team_id": 4291079133131 + "page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/ScheduleUpsertRequest" + "$ref": "#/components/schemas/DeleteStatusPageRequest" } } }, @@ -55327,9 +61606,7 @@ "content": { "application/json": { "example": { - "data": { - "schedule_id": 6294534917601 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -55340,7 +61617,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleIDResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -55364,33 +61641,44 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create schedule", + "summary": "Delete status page", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-delete", "metadata": { - "sidebarTitle": "Create schedule" + "sidebarTitle": "Delete status page" } } } }, - "/schedule/delete": { + "/status-page/draft/create": { "post": { - "description": "Delete one or more on-call schedules by ID.", - "operationId": "scheduleDelete", + "description": "Store a status page event draft so a human can review and publish it from the console.", + "operationId": "statusPageDraftCreate", "requestBody": { "content": { "application/json": { "example": { - "schedule_ids": [ - 2001 - ] + "draft": { + "affected_components": [ + { + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "status": "degraded" + } + ], + "message": "We are investigating degraded performance affecting the web console.", + "name": "Web Console Degraded Performance", + "page_id": 5750613685214, + "type": "incident", + "v": 1 + }, + "source": "ai_sre:sess_01KC3H2A9ZQ8W7E6R5T4Y3U2I1" }, "schema": { - "$ref": "#/components/schemas/ScheduleIDsBodyRequest" + "$ref": "#/components/schemas/CreateStatusPageDraftRequest" } } }, @@ -55401,7 +61689,10 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "created_at": 1788000000, + "draft_id": "draft_3xK9mQ2vN7pR4wT8yH1sJ5" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -55412,7 +61703,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleEmptyObject" + "$ref": "#/components/schemas/StatusPageDraftCreateResponse" } }, "type": "object" @@ -55436,294 +61727,187 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete schedules", + "summary": "Create status page draft", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The `draft` payload is stored verbatim (up to 64 KB); the console publish form reads it back to prefill the event.\n- A draft lives for 30 days and is consumed exactly once when the event is published.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/status-pages/status-page-draft-create", "metadata": { - "sidebarTitle": "Delete schedules" + "sidebarTitle": "Create status page draft" } } } }, - "/schedule/info": { - "post": { - "description": "Return details of an on-call schedule including the computed schedule layers for the requested time window (max 45 days).", - "operationId": "scheduleInfo", - "requestBody": { - "content": { - "application/json": { - "example": { - "end": 1712086400, - "schedule_id": 2001, - "start": 1712000000 - }, - "schema": { - "$ref": "#/components/schemas/ScheduleInfoRequest" - } + "/status-page/info": { + "get": { + "description": "Retrieve detailed configuration for a specific status page.", + "operationId": "statusPageInfo", + "parameters": [ + { + "description": "Status page ID.", + "in": "query", + "name": "page_id", + "required": true, + "schema": { + "format": "int64", + "type": "integer" } - }, - "required": true - }, + } + ], "responses": { "200": { "content": { "application/json": { "example": { "data": { - "account_id": 2451002751131, - "create_at": 1766110836, - "create_by": 2476123212131, - "cur_oncall": { - "end": 1776009600, - "group": { - "end": 1776009600, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2451002751131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1775972040 - }, - "index": 0, - "start": 1775972040, - "update_at": 0, - "weight": 0 - }, - "description": "abc", - "disabled": 0, - "final_schedule": { - "layer_name": "", - "mode": 0, - "name": "", - "schedules": [ - { - "end": 1776096000, - "group": { - "end": 1776096000, - "group_name": "A", - "members": [ - { - "person_ids": [ - 3122470302131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1776009600 - }, - "index": 0, - "start": 1776009600 - } - ] - }, - "group_id": 4291079133131, - "id": 5789640530410, - "layer_schedules": [ + "components": [ { - "layer_name": "Layer 1", - "mode": 0, - "name": "Layer 1", - "schedules": [ - { - "end": 1776096000, - "group": { - "end": 1776096000, - "group_name": "A", - "members": [ - { - "person_ids": [ - 3122470302131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1776009600 - }, - "index": 0, - "start": 1776009600 - } - ] + "available_since_seconds": 1765349358, + "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", + "name": "Web Console", + "order_id": 1, + "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2" } ], - "layers": [ + "contact_info": "mailto:support@example.com", + "custom_domain": "status.example.com", + "custom_links": [ { - "account_id": 2451002751131, - "create_at": 1775205795, - "create_by": 2476123212131, - "day_mask": { - "repeat": [ - 1, - 2, - 3, - 4, - 5 - ] - }, - "enable_time": 1767542400, - "expire_time": 0, - "fair_rotation": false, - "groups": [ - { - "end": 0, - "group_name": "A", - "members": [ - { - "person_ids": [ - 3122470302131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 0 - }, - { - "end": 0, - "group_name": "B", - "members": [ - { - "person_ids": [ - 2659460982131 - ], - "role_id": 0 - } - ], - "name": "B", - "start": 0 - } - ], - "handoff_time": 0, - "hidden": 0, - "layer_end": null, - "layer_name": "Layer 1", - "layer_start": 1767542400, - "mask_continuous_enabled": false, - "mode": 0, - "name": "Layer 1", - "restrict_end": 0, - "restrict_mode": 0, - "restrict_periods": [], - "restrict_start": 0, - "rotation_duration": 86400, - "rotation_unit": "day", - "rotation_value": 1, - "schedule_id": 5789640530410, - "update_at": 1775205795, - "update_by": 2476123212131, - "weight": 0 + "key": "Documentation", + "value": "https://docs.example.com" } ], - "name": "test-000001", - "next_oncall": { - "end": 1776096000, - "group": { - "end": 1776096000, - "group_name": "A", - "members": [ - { - "person_ids": [ - 3122470302131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1776009600 - }, - "index": 0, - "start": 1776009600, - "update_at": 0, - "weight": 0 + "date_view": "list", + "display_uptime_mode": "chart_and_percentage", + "favicon": "https://cdn.example.com/favicon.png", + "logo": "https://cdn.example.com/logo.png", + "managed_domain_feature_enabled": true, + "name": "Flashduty Status Page", + "page_footer": "2025 Example Corp", + "page_header": "Welcome to our status page", + "page_id": 5750613685214, + "sections": [ + { + "description": "Our core services", + "hide_all": false, + "hide_uptime": false, + "name": "Core Services", + "order_id": 1, + "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2" + } + ], + "subscription": { + "email": true, + "im": false }, - "notify": { - "advance_in_time": 300, - "by": { - "follow_preference": false, - "personal_channels": [ - "email" - ] - }, - "fixed_time": null, - "webhooks": [ - { - "settings": { - "alias": "", - "chat_ids": [ - "oc_60a6dc4c6e4e5cbc4934ef08aa7ff76d" - ], - "data_source_id": 5427276014131, - "sign_secret": "", - "token": "", - "verify_token": "" - }, - "type": "feishu_app" - } - ] + "template_preference": "message", + "type": "public", + "url_name": "flashduty-statuspage" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" }, - "schedule_id": 5789640530410, - "schedule_layers": [ + { + "properties": { + "data": { + "$ref": "#/components/schemas/StatusPageInfoResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Get status page detail", + "tags": [ + "On-call/Status pages" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/status-pages/status-page-info", + "metadata": { + "sidebarTitle": "Get status page detail" + } + } + } + }, + "/status-page/list": { + "get": { + "description": "List all status pages owned by the account, including their components and sections.", + "operationId": "status-page-read-page-list", + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "items": [ { - "layer_name": "Layer 1", - "mode": 0, - "name": "Layer 1", - "schedules": [ + "components": [ { - "end": 1776096000, - "group": { - "end": 1776096000, - "group_name": "A", - "members": [ - { - "person_ids": [ - 3122470302131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1776009600 - }, - "index": 0, - "start": 1776009600 - }, + "available_since_seconds": 1716962400, + "component_id": "cmp_001", + "description": "Core API service", + "hide_all": false, + "hide_uptime": false, + "name": "API", + "order_id": 1, + "section_id": "sec_001" + } + ], + "contact_info": "mailto:support@acme.com", + "custom_domain": "status.acme.com", + "custom_links": [ { - "end": 1776182400, - "group": { - "end": 1776182400, - "group_name": "B", - "members": [ - { - "person_ids": [ - 2659460982131 - ], - "role_id": 0 - } - ], - "name": "B", - "start": 1776096000 - }, - "index": 0, - "start": 1776096000 + "name": "Home", + "url": "https://acme.com" } - ] + ], + "date_view": "calendar", + "display_uptime_mode": "chart_and_percentage", + "logo_url": "https://acme.com", + "name": "Acme Status", + "page_header": "Acme System Status", + "page_id": 7001, + "sections": [ + { + "hide_all": false, + "hide_uptime": false, + "name": "Core Services", + "order_id": 1, + "section_id": "sec_001" + } + ], + "subscription": { + "email": true, + "im": false + }, + "type": "public", + "url_name": "acme" } - ], - "schedule_name": "test-000001", - "status": 0, - "team_id": 4291079133131, - "update_at": 1775205795, - "update_by": 2476123212131 + ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -55735,7 +61919,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleItem" + "$ref": "#/components/schemas/ListStatusPageResponse" } }, "type": "object" @@ -55759,35 +61943,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get schedule info", + "summary": "List status pages", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n", + "href": "/en/api-reference/on-call/status-pages/status-page-read-page-list", "metadata": { - "sidebarTitle": "Get schedule info" + "sidebarTitle": "List status pages" } } } }, - "/schedule/infos": { + "/status-page/migrate-email-subscribers": { "post": { - "description": "Return details of multiple on-call schedules by their IDs.", - "operationId": "scheduleInfos", + "description": "Start a migration job that imports email subscribers from an Atlassian Statuspage into an existing Flashduty status page.", + "operationId": "statusPageMigrateEmailSubscribers", "requestBody": { "content": { "application/json": { "example": { - "schedule_ids": [ - 2001, - 2002, - 2003 - ] + "api_key": "sk-stsp-xxxxxxxxxxxxxxxxxxxx", + "source_page_id": "abcdefghij", + "target_page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/ScheduleIDsRequest" + "$ref": "#/components/schemas/MigrateStatusPageEmailSubscribersRequest" } } }, @@ -55799,60 +61981,7 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "create_at": 1766110836, - "create_by": 2476123212131, - "cur_oncall": null, - "description": "abc", - "disabled": 0, - "final_schedule": { - "layer_name": "", - "mode": 0, - "name": "", - "schedules": null - }, - "group_id": 4291079133131, - "id": 5789640530410, - "layer_schedules": null, - "layers": null, - "name": "test-000001", - "next_oncall": null, - "notify": { - "advance_in_time": 300, - "by": { - "follow_preference": false, - "personal_channels": [ - "email" - ] - }, - "fixed_time": null, - "webhooks": [ - { - "settings": { - "alias": "", - "chat_ids": [ - "oc_60a6dc4c6e4e5cbc4934ef08aa7ff76d" - ], - "data_source_id": 5427276014131, - "sign_secret": "", - "token": "", - "verify_token": "" - }, - "type": "feishu_app" - } - ] - }, - "schedule_id": 5789640530410, - "schedule_layers": null, - "schedule_name": "test-000001", - "status": 0, - "team_id": 4291079133131, - "update_at": 1775205795, - "update_by": 2476123212131 - } - ] + "job_id": "01KP0311872NVYFRRQ82FW0002" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -55864,7 +61993,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleSelfResponse" + "$ref": "#/components/schemas/StatusPageMigrationStartResponse" } }, "type": "object" @@ -55888,34 +62017,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Batch get schedules", + "summary": "Migrate email subscribers", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-infos", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-migrate-email-subscribers", "metadata": { - "sidebarTitle": "Batch get schedules" + "sidebarTitle": "Migrate email subscribers" } } } }, - "/schedule/list": { + "/status-page/migrate-structure": { "post": { - "description": "Return a paginated list of on-call schedules. When both start and end are provided (max 45 days apart), computed layer schedules are included.", - "operationId": "scheduleList", + "description": "Start a migration job that imports the structure and historical events of an Atlassian Statuspage into a new Flashduty status page.", + "operationId": "statusPageMigrateStructure", "requestBody": { "content": { "application/json": { "example": { - "is_my_team": true, - "limit": 20, - "p": 1, - "query": "production" + "api_key": "sk-stsp-xxxxxxxxxxxxxxxxxxxx", + "source_page_id": "abcdefghij" }, "schema": { - "$ref": "#/components/schemas/ScheduleListRequest" + "$ref": "#/components/schemas/MigrateStatusPageStructureRequest" } } }, @@ -55927,97 +62054,7 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "create_at": 1766110836, - "create_by": 2476123212131, - "cur_oncall": null, - "description": "abc", - "disabled": 0, - "final_schedule": { - "layer_name": "", - "mode": 0, - "name": "", - "schedules": null - }, - "group_id": 4291079133131, - "id": 5789640530410, - "layer_schedules": null, - "layers": null, - "name": "test-000001", - "next_oncall": null, - "notify": { - "advance_in_time": 300, - "by": { - "follow_preference": false, - "personal_channels": [ - "email" - ] - }, - "fixed_time": null, - "webhooks": [ - { - "settings": { - "alias": "", - "chat_ids": [ - "oc_60a6dc4c6e4e5cbc4934ef08aa7ff76d" - ], - "data_source_id": 5427276014131, - "sign_secret": "", - "token": "", - "verify_token": "" - }, - "type": "feishu_app" - } - ] - }, - "schedule_id": 5789640530410, - "schedule_layers": null, - "schedule_name": "test-000001", - "status": 0, - "team_id": 4291079133131, - "update_at": 1775205795, - "update_by": 2476123212131 - }, - { - "account_id": 2451002751131, - "create_at": 1759132037, - "create_by": 2476123212131, - "cur_oncall": null, - "description": "", - "disabled": 0, - "final_schedule": { - "layer_name": "", - "mode": 0, - "name": "", - "schedules": null - }, - "group_id": 2477033058131, - "id": 5432326025106, - "layer_schedules": null, - "layers": null, - "name": "test-2509300001", - "next_oncall": null, - "notify": { - "advance_in_time": 300, - "by": { - "follow_preference": true, - "personal_channels": null - }, - "fixed_time": null, - "webhooks": null - }, - "schedule_id": 5432326025106, - "schedule_layers": null, - "schedule_name": "test-2509300001", - "status": 0, - "team_id": 2477033058131, - "update_at": 1775207501, - "update_by": 2476123212131 - } - ], - "total": 41 + "job_id": "01KP0311872NVYFRRQ82FW0001" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -56029,7 +62066,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleListResponse" + "$ref": "#/components/schemas/StatusPageMigrationStartResponse" } }, "type": "object" @@ -56053,79 +62090,192 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List schedules", + "summary": "Migrate status page structure", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/schedules/schedule-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-migrate-structure", "metadata": { - "sidebarTitle": "List schedules" + "sidebarTitle": "Migrate status page structure" } } } }, - "/schedule/preview": { + "/status-page/migration/cancel": { "post": { - "description": "Preview the coverage generated by a schedule configuration without persisting it. The request accepts the same body as create/update plus a required start/end window (max 45 days).", - "operationId": "schedulePreview", + "description": "Cancel an in-progress status page migration job. Only jobs currently in the `running` state can be cancelled.", + "operationId": "statusPageMigrationCancel", "requestBody": { "content": { "application/json": { "example": { - "end": 1712086400, - "layers": [ - { - "day_mask": { - "repeat": [ - 1, - 2, - 3, - 4, - 5 - ] + "job_id": "01KP0311872NVYFRRQ82FW0001" + }, + "schema": { + "$ref": "#/components/schemas/CancelStatusPageMigrationRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": {}, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" }, - "enable_time": 1712000000, - "expire_time": 0, - "fair_rotation": false, - "groups": [ - { - "end": 0, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2451002751131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 0 - } - ], - "handoff_time": 0, - "hidden": 0, - "layer_name": "Layer 1", - "mask_continuous_enabled": false, - "mode": 0, - "name": "Layer 1", - "restrict_end": 0, - "restrict_mode": 0, - "restrict_periods": [], - "restrict_start": 0, - "rotation_duration": 86400, - "rotation_unit": "day", - "rotation_value": 1, - "weight": 0 - } - ], - "schedule_name": "Preview Schedule", - "start": 1712000000 + { + "properties": { + "data": { + "$ref": "#/components/schemas/EmptyResponse" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Cancel status page migration", + "tags": [ + "On-call/Status pages" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-migration-cancel", + "metadata": { + "sidebarTitle": "Cancel status page migration" + } + } + } + }, + "/status-page/migration/status": { + "get": { + "description": "Get the current status and progress of a status page migration job.", + "operationId": "statusPageMigrationStatus", + "parameters": [ + { + "description": "Migration job ID returned by `migrate-structure` or `migrate-email-subscribers`.", + "in": "query", + "name": "job_id", + "required": true, + "schema": { + "type": "string" + } + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "account_id": 2451002751131, + "created_at": 1766736878, + "job_id": "01KP0311872NVYFRRQ82FW0001", + "phase": "history", + "progress": { + "completed_steps": 5, + "components_imported": 8, + "incidents_imported": 12, + "maintenances_imported": 2, + "sections_imported": 3, + "subscribers_imported": 0, + "subscribers_skipped": 0, + "templates_imported": 0, + "total_steps": 5 + }, + "source_page_id": "abcdefghij", + "status": "completed", + "target_page_id": 5750613685214, + "updated_at": 1766740000 + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/StatusPageMigrationJob" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Get migration status", + "tags": [ + "On-call/Status pages" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/status-pages/status-page-migration-status", + "metadata": { + "sidebarTitle": "Get migration status" + } + } + } + }, + "/status-page/section/delete": { + "post": { + "description": "Delete a section from a status page.", + "operationId": "statusPageSectionDelete", + "requestBody": { + "content": { + "application/json": { + "example": { + "page_id": 5750613685214, + "section_ids": [ + "01KP032J1FV2H8DDGN0QSJ1CAR" + ] }, "schema": { - "$ref": "#/components/schemas/ScheduleUpsertRequest" + "$ref": "#/components/schemas/DeleteStatusPageSectionRequest" } } }, @@ -56136,169 +62286,7 @@ "content": { "application/json": { "example": { - "data": { - "account_id": 0, - "create_at": 0, - "create_by": 0, - "cur_oncall": null, - "description": null, - "disabled": null, - "end": 1776240000, - "final_schedule": { - "layer_name": "", - "mode": 0, - "name": "", - "schedules": [ - { - "end": 1776096000, - "group": { - "end": 1776096000, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2451002751131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1776009600 - }, - "index": 0, - "start": 1776009600 - } - ] - }, - "group_id": null, - "id": null, - "layer_schedules": null, - "layers": [ - { - "account_id": 0, - "create_at": 0, - "create_by": 0, - "day_mask": { - "repeat": [ - 1, - 2, - 3, - 4, - 5 - ] - }, - "enable_time": 1775980800, - "expire_time": 0, - "fair_rotation": false, - "groups": [ - { - "end": 0, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2451002751131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 0 - }, - { - "end": 0, - "group_name": "B", - "members": [ - { - "person_ids": [ - 2476123212131 - ], - "role_id": 0 - } - ], - "name": "B", - "start": 0 - } - ], - "handoff_time": 0, - "hidden": 0, - "layer_end": null, - "layer_name": "Layer 1", - "layer_start": 1775980800, - "mask_continuous_enabled": false, - "mode": 0, - "name": "Layer 1", - "restrict_end": 0, - "restrict_mode": 0, - "restrict_periods": [], - "restrict_start": 0, - "rotation_duration": 86400, - "rotation_unit": "day", - "rotation_value": 1, - "schedule_id": 0, - "update_at": 0, - "update_by": 0, - "weight": 0 - } - ], - "name": null, - "next_oncall": null, - "notify": null, - "schedule_id": 0, - "schedule_layers": [ - { - "layer_name": "Layer 1", - "mode": 0, - "name": "Layer 1", - "schedules": [ - { - "end": 1776096000, - "group": { - "end": 1776096000, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2451002751131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 1776009600 - }, - "index": 0, - "start": 1776009600 - }, - { - "end": 1776182400, - "group": { - "end": 1776182400, - "group_name": "B", - "members": [ - { - "person_ids": [ - 2476123212131 - ], - "role_id": 0 - } - ], - "name": "B", - "start": 1776096000 - }, - "index": 0, - "start": 1776096000 - } - ] - } - ], - "schedule_name": null, - "start": 1775980800, - "status": null, - "team_id": null, - "update_at": 0, - "update_by": 0 - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -56309,7 +62297,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleItem" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -56333,32 +62321,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Preview schedule", + "summary": "Delete status page section", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **60 requests/minute**; **10 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-preview", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-section-delete", "metadata": { - "sidebarTitle": "Preview schedule" + "sidebarTitle": "Delete status page section" } } } }, - "/schedule/self": { + "/status-page/section/upsert": { "post": { - "description": "Return on-call schedules where the current user is assigned.", - "operationId": "scheduleSelf", + "description": "Create or update a section on a status page.", + "operationId": "statusPageSectionUpsert", "requestBody": { "content": { "application/json": { "example": { - "end": 1712086400, - "start": 1712000000 + "page_id": 5750613685214, + "sections": [ + { + "description": "Our core services", + "name": "Core Services", + "order_id": 1 + } + ] }, "schema": { - "$ref": "#/components/schemas/ScheduleSelfRequest" + "$ref": "#/components/schemas/UpsertStatusPageSectionRequest" } } }, @@ -56370,106 +62364,8 @@ "application/json": { "example": { "data": { - "items": [ - { - "account_id": 2451002751131, - "create_at": 1702623874, - "create_by": 2451002751131, - "cur_oncall": null, - "description": "", - "disabled": 0, - "final_schedule": { - "layer_name": "", - "mode": 0, - "name": "", - "schedules": null - }, - "group_id": 2477033058131, - "id": 2539108069860, - "layer_schedules": null, - "layers": [ - { - "account_id": 2451002751131, - "create_at": 1702623874, - "create_by": 2451002751131, - "day_mask": { - "repeat": [ - 1, - 2, - 3, - 4, - 5 - ] - }, - "enable_time": 1702623874, - "expire_time": 0, - "fair_rotation": false, - "groups": [ - { - "end": 0, - "group_name": "A", - "members": [ - { - "person_ids": [ - 2476444212131 - ], - "role_id": 0 - } - ], - "name": "A", - "start": 0 - }, - { - "end": 0, - "group_name": "B", - "members": [ - { - "person_ids": [ - 2469167612131 - ], - "role_id": 0 - } - ], - "name": "B", - "start": 0 - } - ], - "handoff_time": 0, - "hidden": 0, - "layer_end": null, - "layer_name": "Rule 1", - "layer_start": 1702623874, - "mask_continuous_enabled": false, - "mode": 0, - "name": "Rule 1", - "restrict_end": 0, - "restrict_mode": 0, - "restrict_periods": [], - "restrict_start": 0, - "rotation_duration": 86400, - "rotation_unit": "day", - "rotation_value": 1, - "schedule_id": 2539108069860, - "update_at": 1710468081, - "update_by": 2476444212131, - "weight": 0 - } - ], - "name": "Open Source Q&A", - "next_oncall": null, - "notify": { - "by": null, - "fixed_time": null, - "webhooks": null - }, - "schedule_id": 2539108069860, - "schedule_layers": null, - "schedule_name": "Open Source Q&A", - "status": 0, - "team_id": 2477033058131, - "update_at": 1710468081, - "update_by": 2476444212131 - } + "section_ids": [ + "01KP032J1FV2H8DDGN0QSJ1CAR" ] }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" @@ -56482,7 +62378,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleSelfResponse" + "$ref": "#/components/schemas/UpsertStatusPageSectionResponse" } }, "type": "object" @@ -56506,34 +62402,102 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List my schedules", + "summary": "Upsert status page section", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Read** (`on-call`) or **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-self", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-section-upsert", "metadata": { - "sidebarTitle": "List my schedules" + "sidebarTitle": "Upsert status page section" } } } }, - "/schedule/update": { + "/status-page/subscriber/export": { "post": { - "description": "Update an existing on-call schedule. Provide schedule_id to identify the schedule.", - "operationId": "scheduleUpdate", + "description": "Export subscribers list for a status page as a CSV attachment. The response is a `text/csv` file with columns: Method, Recipient, Components, Subscribe All, Locale.", + "operationId": "statusPageSubscriberExport", "requestBody": { "content": { "application/json": { "example": { - "description": "Updated primary on-call rotation", - "schedule_id": 2001, - "schedule_name": "Production On-Call (Updated)", - "team_id": 4291079133131 + "page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/ScheduleUpsertRequest" + "$ref": "#/components/schemas/ExportStatusPageSubscribersRequest" + } + } + }, + "required": true + }, + "responses": { + "200": { + "content": { + "text/csv": { + "example": "Method,Recipient,Components,Subscribe All,Locale\nemail,alice@example.com,,Yes,zh-CN\nemail,bob@example.com,\"Core Services › API\",No,en-US", + "schema": { + "$ref": "#/components/schemas/StatusPageSubscriberExportResponse" + } + } + }, + "description": "Success. CSV attachment, not a JSON envelope." + }, + "400": { + "$ref": "#/components/responses/BadRequest" + }, + "401": { + "$ref": "#/components/responses/Unauthorized" + }, + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" + } + }, + "summary": "Export subscribers", + "tags": [ + "On-call/Status pages" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **100 requests/day**; **20 requests/minute**; **10 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-subscriber-export", + "metadata": { + "sidebarTitle": "Export subscribers" + } + } + } + }, + "/status-page/subscriber/import": { + "post": { + "description": "Bulk import subscribers for a status page. The account must be allowlisted for subscriber import; otherwise the call is rejected with an access-denied error.", + "operationId": "statusPageSubscriberImport", + "requestBody": { + "content": { + "application/json": { + "example": { + "method": "email", + "page_id": 5750613685214, + "subscribers": [ + { + "all": true, + "locale": "en-US", + "recipient": "alice@example.com" + }, + { + "all": false, + "component_ids": [ + "01KC3GAZ6ZJE40H55GM31RPWZE" + ], + "locale": "zh-CN", + "recipient": "bob@example.com" + } + ] + }, + "schema": { + "$ref": "#/components/schemas/ImportStatusPageSubscribersRequest" } } }, @@ -56555,7 +62519,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/ScheduleEmptyObject" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -56579,64 +62543,93 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update schedule", + "summary": "Import subscribers", "tags": [ - "On-call/Schedules" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Schedules Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/schedules/schedule-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **20 requests/minute**; **2 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-subscriber-import", "metadata": { - "sidebarTitle": "Update schedule" + "sidebarTitle": "Import subscribers" } } } }, - "/sourcemap/list": { - "post": { - "description": "Return a paginated list of uploaded sourcemap files filtered by platform type, service, and version.", - "operationId": "sourcemap-read-list", - "requestBody": { - "content": { - "application/json": { - "example": { - "end_time": 1712700000000, - "limit": 20, - "p": 1, - "services": [ - "my-web-app" - ], - "start_time": 1712000000000, - "type": "browser" - }, - "schema": { - "$ref": "#/components/schemas/SourcemapListRequest" - } + "/status-page/subscriber/list": { + "get": { + "description": "List subscribers who have signed up for status page notifications.", + "operationId": "statusPageSubscriberList", + "parameters": [ + { + "description": "Status page ID.", + "in": "query", + "name": "page_id", + "required": true, + "schema": { + "format": "int64", + "type": "integer" } }, - "required": true - }, + { + "description": "Comma-separated component IDs to filter subscribers by.", + "in": "query", + "name": "component_ids", + "required": false, + "schema": { + "type": "string" + } + }, + { + "description": "Page number (1-based).", + "in": "query", + "name": "p", + "required": false, + "schema": { + "default": 1, + "format": "int64", + "minimum": 1, + "type": "integer" + } + }, + { + "description": "Page size (1-100).", + "in": "query", + "name": "limit", + "required": false, + "schema": { + "default": 10, + "format": "int64", + "maximum": 100, + "minimum": 1, + "type": "integer" + } + } + ], "responses": { "200": { "content": { "application/json": { "example": { "data": { + "has_next_page": false, "items": [ { - "created_at": 1712700000, - "git_commit_sha": "abc1234def5678", - "git_repository_url": "https://github.com/example/my-web-app", - "key": "browser/my-web-app/1.0.0/main.js.map", - "metadata": {}, - "service": "my-web-app", - "size": 204800, - "type": "browser", - "updated_at": 1712700000, - "version": "1.0.0" + "all": true, + "components": [], + "locale": "zh-CN", + "method": "email", + "recipient": "alice@example.com" + }, + { + "all": true, + "components": [], + "locale": "en-US", + "method": "email", + "recipient": "bob@example.com" } ], - "total": 3 + "total": 2 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -56648,7 +62641,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/SourcemapListResponse" + "$ref": "#/components/schemas/StatusPageSubscriberListResponse" } }, "type": "object" @@ -56672,35 +62665,33 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List sourcemaps", + "summary": "List status page subscribers", "tags": [ - "RUM/Sourcemaps" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `start_time` and `end_time` are required — both use Unix epoch **milliseconds**. Maximum window is 365 days.\n- The `type` field selects the platform: `browser` (JavaScript), `android`, or `ios`. Defaults to `browser` when omitted.\n- Default page size is 20; maximum is 100. Default sort is `created_at` descending.\n- For Android, `build_id` matches the Gradle plugin build identifier. For iOS, `uuid` matches the dSYM bundle UUID.", - "href": "/en/api-reference/rum/sourcemaps/sourcemap-read-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", + "href": "/en/api-reference/on-call/status-pages/status-page-subscriber-list", "metadata": { - "sidebarTitle": "List sourcemaps" + "sidebarTitle": "List status page subscribers" } } } }, - "/sourcemap/stack/enrich": { + "/status-page/template/delete": { "post": { - "description": "Symbolicate or deobfuscate a browser, Android, iOS, Mini Program, or HarmonyOS stack trace.", - "operationId": "sourcemap-read-stack-enrich", + "description": "Delete an event template from a status page.", + "operationId": "statusPageTemplateDelete", "requestBody": { "content": { "application/json": { "example": { - "near": 3, - "service": "my-web-app", - "stack": "TypeError: Cannot read properties of undefined\n at render (https://cdn.example.com/app.min.js:1:2345)", - "type": "browser", - "version": "1.0.0" + "page_id": 5720156736380, + "template_id": "01KP0339G5XDEPM4R86T2B23EP", + "type": "pre_defined" }, "schema": { - "$ref": "#/components/schemas/SourcemapStackEnrichRequest" + "$ref": "#/components/schemas/DeleteStatusPageTemplateRequest" } } }, @@ -56711,33 +62702,7 @@ "content": { "application/json": { "example": { - "data": { - "frames": [ - { - "code_snippets": [ - { - "code": "const cart = props.cart;", - "line": 41 - }, - { - "code": "return cart.items.map(renderItem);", - "line": 42 - } - ], - "column": 17, - "converted": true, - "file": "src/pages/checkout.tsx", - "function": "renderCheckout", - "line": 42, - "original_frame": { - "column": 2345, - "file": "https://cdn.example.com/app.min.js", - "function": "render", - "line": 1 - } - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -56748,7 +62713,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/SourcemapStackEnrichResponse" + "$ref": "#/components/schemas/EmptyResponse" } }, "type": "object" @@ -56772,23 +62737,23 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Enrich a stack trace", + "summary": "Delete status page template", "tags": [ - "RUM/Sourcemaps" + "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `type` defaults to `browser` when omitted for backward compatibility.\n- Set `near` from 1 to 20 to include source-code snippets around converted frames.\n- For Android NDK native crashes, provide `arch` and `source_type: ndk` so the backend routes to native symbolication.\n- For iOS crash stacks, pass `binary_images` so addresses can be relocated against the uploaded dSYM files.\n- `no_cache` is intended for debugging and bypasses cached enrich results.", - "href": "/en/api-reference/rum/sourcemaps/sourcemap-read-stack-enrich", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-template-delete", "metadata": { - "sidebarTitle": "Enrich a stack trace" + "sidebarTitle": "Delete status page template" } } } }, - "/status-page/change/active/list": { + "/status-page/template/list": { "get": { - "description": "List in-progress (non-terminal) events of a given type for a status page.", - "operationId": "statusPageChangeActiveList", + "description": "List all event templates for a status page.", + "operationId": "statusPageTemplateList", "parameters": [ { "description": "Status page ID.", @@ -56801,14 +62766,14 @@ } }, { - "description": "Event type filter. Required. Returns only in-progress (non-terminal) events — `investigating`/`identified`/`monitoring` for `incident`, `scheduled`/`ongoing` for `maintenance`.", + "description": "Template category. `pre_defined` returns predefined event templates; `message` returns message notification templates.", "in": "query", "name": "type", "required": true, "schema": { "enum": [ - "incident", - "maintenance" + "pre_defined", + "message" ], "type": "string" } @@ -56822,39 +62787,11 @@ "data": { "items": [ { - "affected_components": [ - { - "available_since_seconds": 1765349358, - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "name": "Web Console", - "order_id": 1, - "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2", - "status": "degraded" - } - ], - "change_id": 5821693893131, - "description": "We are currently investigating an issue affecting some services.", - "notify_subscribers": true, - "page_id": 5750613685214, - "start_at_seconds": 1766736878, - "status": "investigating", - "title": "Web Console Degraded Performance", - "type": "incident", - "updates": [ - { - "at_seconds": 1766736876, - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "component_name": "Web Console", - "status": "degraded" - } - ], - "description": "We are currently investigating an issue affecting some services.", - "status": "investigating", - "update_id": "01KDCVJQ88SZPHWPTDV2Z2AZW8" - } - ] + "description": "We have identified the root cause.", + "status": "identified", + "template_id": "01KC8KP6PHVPSCAB0BTKZBN2HR", + "title": "Service Disruption", + "type": "incident" } ] }, @@ -56868,7 +62805,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageChangeListResponse" + "$ref": "#/components/schemas/ListStatusPageTemplatesResponse" } }, "type": "object" @@ -56892,49 +62829,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List active status page events", + "summary": "List status page templates", "tags": [ "On-call/Status pages" ], "x-mint": { "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-active-list", + "href": "/en/api-reference/on-call/status-pages/status-page-template-list", "metadata": { - "sidebarTitle": "List active status page events" + "sidebarTitle": "List status page templates" } } } }, - "/status-page/change/create": { + "/status-page/template/upsert": { "post": { - "description": "Create a new incident or maintenance event on a status page.", - "operationId": "statusPageChangeCreate", + "description": "Create or update an event template for a status page.", + "operationId": "statusPageTemplateUpsert", "requestBody": { "content": { "application/json": { "example": { - "description": "We are investigating degraded performance affecting the web console.", - "notify_subscribers": true, - "page_id": 5750613685214, - "start_at_seconds": 1712000000, - "status": "investigating", - "title": "Web Console Degraded Performance", - "type": "incident", - "updates": [ - { - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "status": "degraded" - } - ], - "description": "We are currently investigating an issue affecting some users.", - "status": "investigating" - } - ] + "page_id": 5720156736380, + "template": { + "description": "We are investigating a service disruption affecting some users.", + "status": "investigating", + "title": "Service Disruption", + "type": "incident" + }, + "type": "pre_defined" }, "schema": { - "$ref": "#/components/schemas/CreateStatusPageChangeRequest" + "$ref": "#/components/schemas/UpsertStatusPageTemplateRequest" } } }, @@ -56946,8 +62872,7 @@ "application/json": { "example": { "data": { - "change_id": 6294539747131, - "change_name": "API Test Incident" + "template_id": "01KP0339G5XDEPM4R86T2B23EP" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -56959,7 +62884,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageChangeCreateResponse" + "$ref": "#/components/schemas/UpsertStatusPageTemplateResponse" } }, "type": "object" @@ -56983,32 +62908,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create status page event", + "summary": "Upsert status page template", "tags": [ "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-template-upsert", "metadata": { - "sidebarTitle": "Create status page event" + "sidebarTitle": "Upsert status page template" } } } }, - "/status-page/change/delete": { + "/status-page/update": { "post": { - "description": "Delete a status page event.", - "operationId": "statusPageChangeDelete", + "description": "Update an existing status page configuration.", + "operationId": "statusPageUpdate", "requestBody": { "content": { "application/json": { "example": { - "change_id": 5821693893131, + "contact_info": "mailto:support@example.com", + "name": "Flashduty Status Page (Updated)", + "page_header": "Updated status page header", "page_id": 5750613685214 }, "schema": { - "$ref": "#/components/schemas/DeleteStatusPageChangeRequest" + "$ref": "#/components/schemas/UpdateStatusPageRequest" } } }, @@ -57054,99 +62981,42 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete status page event", + "summary": "Update status page", "tags": [ "On-call/Status pages" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", + "href": "/en/api-reference/on-call/status-pages/status-page-update", "metadata": { - "sidebarTitle": "Delete status page event" + "sidebarTitle": "Update status page" } } } }, - "/status-page/change/info": { - "get": { - "description": "Retrieve details of a specific status page event (incident or maintenance).", - "operationId": "statusPageChangeInfo", - "parameters": [ - { - "description": "Status page ID.", - "in": "query", - "name": "page_id", - "required": true, - "schema": { - "format": "int64", - "type": "integer" + "/team/delete": { + "post": { + "description": "Permanently delete a team by ID, name, or external reference ID.", + "operationId": "team-write-delete", + "requestBody": { + "content": { + "application/json": { + "example": { + "team_id": 1001 + }, + "schema": { + "$ref": "#/components/schemas/TeamDeleteRequest" + } } }, - { - "description": "Event (change) ID.", - "in": "query", - "name": "change_id", - "required": true, - "schema": { - "format": "int64", - "type": "integer" - } - } - ], + "required": true + }, "responses": { "200": { "content": { "application/json": { "example": { - "data": { - "affected_components": [ - { - "available_since_seconds": 1765349358, - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "name": "Web Console", - "order_id": 1, - "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2", - "status": "operational" - } - ], - "change_id": 5821693893131, - "close_at_seconds": 1775529742, - "description": "The issue has been resolved, and all services are operating normally.\n\nThank you for your patience.", - "notify_subscribers": true, - "page_id": 5750613685214, - "start_at_seconds": 1766736878, - "status": "resolved", - "title": "Web Console Degraded Performance", - "type": "incident", - "updates": [ - { - "at_seconds": 1766736876, - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "component_name": "Web Console", - "status": "degraded" - } - ], - "description": "We are currently investigating an issue affecting some services.", - "status": "investigating", - "update_id": "01KDCVJQ88SZPHWPTDV2Z2AZW8" - }, - { - "at_seconds": 1775529742, - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "component_name": "Web Console", - "status": "operational" - } - ], - "description": "The issue has been resolved, and all services are operating normally.", - "status": "resolved", - "update_id": "01KNJX3KW873ZZSRZC14SGFYS3" - } - ] - }, + "data": {}, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -57157,7 +63027,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageChangeItem" + "$ref": "#/components/schemas/PlatformEmptyObject" } }, "type": "object" @@ -57174,6 +63044,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -57181,141 +63054,147 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get status page event detail", + "summary": "Delete a team", "tags": [ - "On-call/Status pages" + "Platform/Teams" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Teams Manage** (`organization`) |\n\n## Usage\n\n- At least one of `team_id`, `team_name`, or `ref_id` must be provided.\n- Fails with `400 ReferenceExist` if the team is still referenced by schedules, escalation rules, or other resources.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/teams/team-write-delete", "metadata": { - "sidebarTitle": "Get status page event detail" + "sidebarTitle": "Delete a team" } } } }, - "/status-page/change/list": { - "get": { - "description": "List status page events for console management. Unlike the public display endpoints, the response includes hidden components.", - "operationId": "statusPageChangeList", - "parameters": [ - { - "description": "Status page ID.", - "in": "query", - "name": "page_id", - "required": true, - "schema": { - "format": "int64", - "type": "integer" + "/team/info": { + "post": { + "description": "Return a single team by ID, name, or external reference ID.", + "operationId": "team-read-info", + "requestBody": { + "content": { + "application/json": { + "example": { + "team_id": 1001 + }, + "schema": { + "$ref": "#/components/schemas/TeamInfoRequest" + } } }, - { - "description": "Lower bound of the event activity window: only events still open at, or closed at or after, this Unix timestamp (seconds) are returned.", - "in": "query", - "name": "start_at_seconds", - "required": false, - "schema": { - "format": "int64", - "type": "integer" - } + "required": true + }, + "responses": { + "200": { + "content": { + "application/json": { + "example": { + "data": { + "account_id": 10023, + "created_at": 1710000000, + "creator_id": 80011, + "creator_name": "alice", + "description": "Backend reliability engineering team", + "person_ids": [ + 80011, + 80012 + ], + "ref_id": "", + "status": "enabled", + "team_id": 1001, + "team_name": "Backend SRE", + "updated_at": 1712000000, + "updated_by": 80011, + "updated_by_name": "alice" + }, + "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" + }, + "schema": { + "allOf": [ + { + "$ref": "#/components/schemas/SuccessEnvelope" + }, + { + "properties": { + "data": { + "$ref": "#/components/schemas/TeamItem" + } + }, + "type": "object" + } + ] + } + } + }, + "description": "Success" }, - { - "description": "Upper bound of the event activity window: only events started at or before this Unix timestamp (seconds) are returned.", - "in": "query", - "name": "end_at_seconds", - "required": false, - "schema": { - "format": "int64", - "type": "integer" - } + "400": { + "$ref": "#/components/responses/BadRequest" }, - { - "description": "Event type filter. Required.", - "in": "query", - "name": "type", - "required": true, - "schema": { - "enum": [ - "incident", - "maintenance" - ], - "type": "string" - } + "401": { + "$ref": "#/components/responses/Unauthorized" }, - { - "description": "Event status filter. Required. Must be a status valid for the given `type` (`investigating`/`identified`/`monitoring`/`resolved` for `incident`; `scheduled`/`ongoing`/`completed` for `maintenance`).", - "in": "query", - "name": "status", - "required": true, - "schema": { - "enum": [ - "investigating", - "identified", - "monitoring", - "resolved", - "scheduled", - "ongoing", - "completed" - ], - "type": "string" - } + "429": { + "$ref": "#/components/responses/TooManyRequests" + }, + "500": { + "$ref": "#/components/responses/ServerError" } + }, + "summary": "Get team detail", + "tags": [ + "Platform/Teams" ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- At least one of `team_id`, `team_name`, or `ref_id` must be provided.", + "href": "/en/api-reference/platform/teams/team-read-info", + "metadata": { + "sidebarTitle": "Get team detail" + } + } + } + }, + "/team/infos": { + "post": { + "description": "Return basic info for multiple teams by their IDs in a single request.", + "operationId": "team-read-infos", + "requestBody": { + "content": { + "application/json": { + "example": { + "team_ids": [ + 1001, + 1002 + ] + }, + "schema": { + "$ref": "#/components/schemas/TeamInfosRequest" + } + } + }, + "required": true + }, "responses": { "200": { - "content": { - "application/json": { - "example": { - "data": { - "items": [ - { - "affected_components": [ - { - "available_since_seconds": 1765349358, - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "name": "Web Console", - "order_id": 1, - "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2", - "status": "operational" - } - ], - "change_id": 5821693893131, - "close_at_seconds": 1775529742, - "description": "The issue has been resolved, and all services are operating normally.", - "notify_subscribers": true, - "page_id": 5750613685214, - "start_at_seconds": 1766736878, - "status": "resolved", - "title": "Web Console Degraded Performance", - "type": "incident", - "updates": [ - { - "at_seconds": 1766736876, - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "component_name": "Web Console", - "status": "degraded" - } - ], - "description": "We are currently investigating an issue affecting some services.", - "status": "investigating", - "update_id": "01KDCVJQ88SZPHWPTDV2Z2AZW8" - }, - { - "at_seconds": 1775529742, - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "component_name": "Web Console", - "status": "operational" - } - ], - "description": "The issue has been resolved, and all services are operating normally.", - "status": "resolved", - "update_id": "01KNJX3KW873ZZSRZC14SGFYS3" - } - ] + "content": { + "application/json": { + "example": { + "data": { + "items": [ + { + "person_ids": [ + 80011, + 80012 + ], + "team_id": 1001, + "team_name": "Backend SRE" + }, + { + "person_ids": [ + 80013 + ], + "team_id": 1002, + "team_name": "Frontend" } ] }, @@ -57329,7 +63208,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageChangeListResponse" + "$ref": "#/components/schemas/TeamInfosResponse" } }, "type": "object" @@ -57353,41 +63232,34 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "List status page events", + "summary": "Batch get teams", "tags": [ - "On-call/Status pages" + "Platform/Teams" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-list", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Duplicate IDs are deduplicated; IDs that match no team are ignored.", + "href": "/en/api-reference/platform/teams/team-read-infos", "metadata": { - "sidebarTitle": "List status page events" + "sidebarTitle": "Batch get teams" } } } }, - "/status-page/change/timeline/create": { + "/team/list": { "post": { - "description": "Add a timeline update to a status page event.", - "operationId": "statusPageChangeTimelineCreate", + "description": "Return a paginated list of teams in the current account.", + "operationId": "team-read-list", "requestBody": { "content": { "application/json": { "example": { - "at_seconds": 1712003600, - "change_id": 5821693893131, - "component_changes": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "status": "partial_outage" - } - ], - "description": "We have identified the root cause and are working on a fix.", - "page_id": 5750613685214, - "status": "identified" + "asc": false, + "limit": 20, + "orderby": "created_at", + "p": 1 }, "schema": { - "$ref": "#/components/schemas/CreateStatusPageChangeTimelineRequest" + "$ref": "#/components/schemas/TeamListRequest" } } }, @@ -57399,7 +63271,28 @@ "application/json": { "example": { "data": { - "update_id": "01KP0311872NVYFRRQ82FWXAP4" + "items": [ + { + "account_id": 10023, + "created_at": 1710000000, + "creator_id": 80011, + "creator_name": "alice", + "description": "", + "person_ids": [ + 80011 + ], + "ref_id": "", + "status": "enabled", + "team_id": 1001, + "team_name": "Backend SRE", + "updated_at": 1712000000, + "updated_by": 0, + "updated_by_name": "" + } + ], + "limit": 20, + "p": 1, + "total": 5 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -57411,7 +63304,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageChangeTimelineCreateResponse" + "$ref": "#/components/schemas/TeamListResponse" } }, "type": "object" @@ -57435,33 +63328,36 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create event timeline entry", + "summary": "List teams", "tags": [ - "On-call/Status pages" + "Platform/Teams" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-timeline-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- Filter by `person_id` to return teams that a specific person belongs to.\n- Defaults: p=1, limit=20.", + "href": "/en/api-reference/platform/teams/team-read-list", "metadata": { - "sidebarTitle": "Create event timeline entry" + "sidebarTitle": "List teams" } } } }, - "/status-page/change/timeline/delete": { + "/team/upsert": { "post": { - "description": "Delete a timeline entry from a status page event.", - "operationId": "statusPageChangeTimelineDelete", + "description": "Create a new team or update an existing one. Pass `team_id` to update.", + "operationId": "team-write-upsert", "requestBody": { "content": { "application/json": { "example": { - "change_id": 5821693893131, - "page_id": 5750613685214, - "update_id": "01KP0311872NVYFRRQ82FWXAP4" + "description": "Backend reliability engineering team", + "person_ids": [ + 80011, + 80012 + ], + "team_name": "Backend SRE" }, "schema": { - "$ref": "#/components/schemas/DeleteStatusPageChangeTimelineRequest" + "$ref": "#/components/schemas/TeamUpsertRequest" } } }, @@ -57472,7 +63368,10 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "team_id": 1001, + "team_name": "Backend SRE" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -57483,7 +63382,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/TeamUpsertResponse" } }, "type": "object" @@ -57500,6 +63399,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -57507,35 +63409,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete event timeline entry", + "summary": "Create or update a team", "tags": [ - "On-call/Status pages" + "Platform/Teams" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-timeline-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Teams Manage** (`organization`) |\n\n## Usage\n\n- Omit `team_id` (or set to 0) to create a new team; pass an existing ID to update.\n- `team_name` must be 1–39 characters and unique within the account.\n- Pass `person_ids` to set team membership; this replaces the entire member list.\n- Pass `emails` or `phones` to add existing members by contact; contacts that match no member are ignored — nobody is invited.\n- `ref_id` is an external identifier for integration with third-party HR systems.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/platform/teams/team-write-upsert", "metadata": { - "sidebarTitle": "Delete event timeline entry" + "sidebarTitle": "Create or update a team" } } } }, - "/status-page/change/timeline/update": { + "/template/create": { "post": { - "description": "Update a timeline entry for a status page event.", - "operationId": "statusPageChangeTimelineUpdate", + "description": "Create a new notification template.", + "operationId": "template-write-create", "requestBody": { "content": { "application/json": { "example": { - "at_seconds": 1712003600, - "change_id": 5821693893131, - "description": "Corrected description: root cause identified in database layer.", - "page_id": 5750613685214, - "update_id": "01KP0311872NVYFRRQ82FWXAP4" + "description": "Default template for production incidents.", + "email": "Incident {{ .IncidentName }} on {{ .Severity }}", + "sms": "[Flashduty] {{ .IncidentName }} — {{ .Severity }}", + "team_id": 0, + "template_name": "Prod incident default" }, "schema": { - "$ref": "#/components/schemas/UpdateStatusPageChangeTimelineRequest" + "$ref": "#/components/schemas/TemplateCreateRequest" } } }, @@ -57546,7 +63448,10 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "template_id": "6605a1b2c3d4e5f6a7b8c9d0", + "template_name": "Prod incident default" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -57557,7 +63462,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/TemplateCreateResponse" } }, "type": "object" @@ -57581,33 +63486,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update event timeline entry", + "summary": "Create a template", "tags": [ - "On-call/Status pages" + "On-call/Notification templates" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-timeline-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Templates Manage** (`on-call`) |\n\n## Usage\n\n- `template_name` must be unique within the account; duplicates return `InvalidParameter`.\n- The server validates every non-empty channel template by rendering it against a mock incident — a syntactic error in any channel fails the whole request with `InvalidParameter`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/notification-templates/template-write-create", "metadata": { - "sidebarTitle": "Update event timeline entry" + "sidebarTitle": "Create a template" } } } }, - "/status-page/change/update": { + "/template/delete": { "post": { - "description": "Update an existing status page event.", - "operationId": "statusPageChangeUpdate", + "description": "Soft-delete a template by ID.", + "operationId": "template-write-delete", "requestBody": { "content": { "application/json": { "example": { - "change_id": 5821693893131, - "page_id": 5750613685214, - "title": "Web Console Degraded Performance (Updated)" + "template_id": "6605a1b2c3d4e5f6a7b8c9d0" }, "schema": { - "$ref": "#/components/schemas/UpdateStatusPageChangeRequest" + "$ref": "#/components/schemas/TemplateIDRequest" } } }, @@ -57629,7 +63532,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/EmptyObject" } }, "type": "object" @@ -57646,6 +63549,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -57653,34 +63559,31 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Update status page event", + "summary": "Delete a template", "tags": [ - "On-call/Status pages" + "On-call/Notification templates" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Events Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-change-update", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Templates Manage** (`on-call`) |\n\n## Usage\n\n- Fails with `400 ReferenceExist` if the template is still referenced by any channel, escalation rule, or notification subscription.\n- Deletion is soft — `deleted_at` is set. The record remains for audit, but the template stops appearing in listings.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/notification-templates/template-write-delete", "metadata": { - "sidebarTitle": "Update status page event" + "sidebarTitle": "Delete a template" } } } }, - "/status-page/component/delete": { + "/template/info": { "post": { - "description": "Delete a service component from a status page.", - "operationId": "statusPageComponentDelete", + "description": "Return a single notification template by ID.", + "operationId": "template-read-info", "requestBody": { "content": { "application/json": { "example": { - "component_ids": [ - "01KP032KMN9YFBMPWANJMFZFG1" - ], - "page_id": 5750613685214 + "template_id": "6605a1b2c3d4e5f6a7b8c9d0" }, "schema": { - "$ref": "#/components/schemas/DeleteStatusPageComponentRequest" + "$ref": "#/components/schemas/TemplateIDRequest" } } }, @@ -57691,7 +63594,32 @@ "content": { "application/json": { "example": { - "data": {}, + "data": { + "account_id": 10023, + "created_at": 1712700000, + "creator_id": 80011, + "description": "Default template for production incidents.", + "dingtalk": "", + "dingtalk_app": "", + "email": "Incident {{ .IncidentName }} on {{ .Severity }}", + "feishu": "", + "feishu_app": "", + "slack": "", + "slack_app": "", + "sms": "[Flashduty] {{ .IncidentName }} — {{ .Severity }}", + "status": "enabled", + "team_id": 0, + "teams_app": "", + "telegram": "", + "template_id": "6605a1b2c3d4e5f6a7b8c9d0", + "template_name": "Prod incident default", + "updated_at": 1712702400, + "updated_by": 80011, + "voice": "", + "wecom": "", + "wecom_app": "", + "zoom": "" + }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, "schema": { @@ -57702,7 +63630,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/TemplateItem" } }, "type": "object" @@ -57726,39 +63654,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete status page component", + "summary": "Get template detail", "tags": [ - "On-call/Status pages" + "On-call/Notification templates" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-component-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Templates Read** (`on-call`) |\n\n## Usage\n\n- Pass `000000000000000000000001` as `template_id` to retrieve the built-in preset template for the caller's account locale.", + "href": "/en/api-reference/on-call/notification-templates/template-read-info", "metadata": { - "sidebarTitle": "Delete status page component" + "sidebarTitle": "Get template detail" } } } }, - "/status-page/component/upsert": { + "/template/list": { "post": { - "description": "Create or update a service component on a status page.", - "operationId": "statusPageComponentUpsert", + "description": "Return a paginated list of notification templates.", + "operationId": "template-read-list", "requestBody": { "content": { "application/json": { "example": { - "components": [ - { - "description": "Main web interface", - "name": "Web Console", - "order_id": 1, - "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2" - } - ], - "page_id": 5750613685214 + "asc": false, + "is_my_team": false, + "limit": 20, + "orderby": "updated_at", + "p": 1 }, "schema": { - "$ref": "#/components/schemas/UpsertStatusPageComponentRequest" + "$ref": "#/components/schemas/TemplateListRequest" } } }, @@ -57770,9 +63694,36 @@ "application/json": { "example": { "data": { - "component_ids": [ - "01KP032KMN9YFBMPWANJMFZFG1" - ] + "has_next_page": true, + "items": [ + { + "account_id": 10023, + "created_at": 1712700000, + "creator_id": 80011, + "description": "Default template for production incidents.", + "dingtalk": "", + "dingtalk_app": "", + "email": "Incident {{ .IncidentName }} on {{ .Severity }}", + "feishu": "", + "feishu_app": "", + "slack": "", + "slack_app": "", + "sms": "[Flashduty] {{ .IncidentName }} — {{ .Severity }}", + "status": "enabled", + "team_id": 0, + "teams_app": "", + "telegram": "", + "template_id": "6605a1b2c3d4e5f6a7b8c9d0", + "template_name": "Prod incident default", + "updated_at": 1712702400, + "updated_by": 80011, + "voice": "", + "wecom": "", + "wecom_app": "", + "zoom": "" + } + ], + "total": 47 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -57784,7 +63735,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/UpsertStatusPageComponentResponse" + "$ref": "#/components/schemas/TemplateListResponse" } }, "type": "object" @@ -57808,35 +63759,38 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Upsert status page component", + "summary": "List templates", "tags": [ - "On-call/Status pages" + "On-call/Notification templates" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-component-upsert", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Templates Read** (`on-call`) or **Templates Manage** (`on-call`) |\n\n## Usage\n\n- Pagination defaults to page 1 with 20 rows. The response's `has_next_page` tells you whether another page exists without needing a separate count request.\n- When `is_my_team` is `true`, `team_ids` is ignored.", + "href": "/en/api-reference/on-call/notification-templates/template-read-list", "metadata": { - "sidebarTitle": "Upsert status page component" + "sidebarTitle": "List templates" } } } }, - "/status-page/create": { + "/template/preview": { "post": { - "description": "Create a new status page.", - "operationId": "statusPageCreate", + "description": "Render a notification template against incident data or mock data and return the output.", + "operationId": "template-read-preview", "requestBody": { "content": { "application/json": { "example": { - "contact_info": "mailto:support@example.com", - "name": "My Status Page", - "page_header": "Welcome to our status page", - "type": "public", - "url_name": "my-status-page" + "content": "Incident {{.Title}} is {{.Status}}", + "incident_card_hidden_fields": { + "feishu_app": [ + "responders" + ] + }, + "incident_id": "664a1b2c3d4e5f6a7b8c9d0e", + "type": "feishu_app" }, "schema": { - "$ref": "#/components/schemas/CreateStatusPageRequest" + "$ref": "#/components/schemas/PreviewTemplateRequest" } } }, @@ -57848,9 +63802,15 @@ "application/json": { "example": { "data": { - "page_id": 6294565612043, - "page_name": "My Status Page", - "page_url_name": "my-status-page" + "content": "Incident Database latency spike is Critical", + "fixed_fields": [ + { + "field": "channel", + "value": "Payment Alerts" + } + ], + "message": "", + "success": true }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -57862,7 +63822,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/CreateStatusPageResponse" + "$ref": "#/components/schemas/PreviewTemplateResponse" } }, "type": "object" @@ -57886,31 +63846,35 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create status page", + "summary": "Preview template", "tags": [ - "On-call/Status pages" + "On-call/Notification templates" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **60 requests/minute**; **10 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- `incident_card_hidden_fields` applies only to supported IM-card previews; unsupported app types or field names return `InvalidParameter`.\n- `fixed_fields` is returned only when the selected IM preview has a non-empty fixed incident-card value.", + "href": "/en/api-reference/on-call/notification-templates/template-read-preview", "metadata": { - "sidebarTitle": "Create status page" + "sidebarTitle": "Preview template" } } } }, - "/status-page/delete": { + "/template/update": { "post": { - "description": "Delete a status page.", - "operationId": "statusPageDelete", + "description": "Update an existing template. Only the fields present in the request are written: a channel you omit keeps its current content, and an explicit empty string clears it.", + "operationId": "template-write-update", "requestBody": { "content": { "application/json": { "example": { - "page_id": 5750613685214 + "description": "Updated description.", + "email": "Incident {{ .IncidentName }} on {{ .Severity }}", + "sms": "[Flashduty] {{ .IncidentName }} — {{ .Severity }}", + "template_id": "6605a1b2c3d4e5f6a7b8c9d0", + "template_name": "Prod incident default" }, "schema": { - "$ref": "#/components/schemas/DeleteStatusPageRequest" + "$ref": "#/components/schemas/TemplateUpdateRequest" } } }, @@ -57932,7 +63896,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/EmptyResponse" + "$ref": "#/components/schemas/EmptyObject" } }, "type": "object" @@ -57949,6 +63913,9 @@ "401": { "$ref": "#/components/responses/Unauthorized" }, + "403": { + "$ref": "#/components/responses/Forbidden" + }, "429": { "$ref": "#/components/responses/TooManyRequests" }, @@ -57956,44 +63923,32 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Delete status page", + "summary": "Update a template", "tags": [ - "On-call/Status pages" + "On-call/Notification templates" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Status Pages Manage** (`on-call`) |", - "href": "/en/api-reference/on-call/status-pages/status-page-delete", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Templates Manage** (`on-call`) |\n\n## Usage\n\n- Only the fields present in the request are written. A channel you omit keeps its current content; send it as an empty string to clear it.\n- The caller needs data-permission on the template's team; otherwise the response is `AccessDenied`.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", + "href": "/en/api-reference/on-call/notification-templates/template-write-update", "metadata": { - "sidebarTitle": "Delete status page" + "sidebarTitle": "Update a template" } } } }, - "/status-page/draft/create": { + "/webhook/history/detail": { "post": { - "description": "Store a status page event draft so a human can review and publish it from the console.", - "operationId": "statusPageDraftCreate", + "description": "Retrieve the detailed payload and response for a specific webhook delivery attempt.", + "operationId": "webhookHistoryDetail", "requestBody": { "content": { "application/json": { "example": { - "draft": { - "affected_components": [ - { - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "status": "degraded" - } - ], - "message": "We are investigating degraded performance affecting the web console.", - "name": "Web Console Degraded Performance", - "page_id": 5750613685214, - "type": "incident", - "v": 1 - }, - "source": "ai_sre:sess_01KC3H2A9ZQ8W7E6R5T4Y3U2I1" + "event_id": "20260412Xatt9hrXsgmFkBR78WF655", + "integration_id": 6113996590131 }, "schema": { - "$ref": "#/components/schemas/CreateStatusPageDraftRequest" + "$ref": "#/components/schemas/GetWebhookHistoryDetailRequest" } } }, @@ -58005,8 +63960,24 @@ "application/json": { "example": { "data": { - "created_at": 1788000000, - "draft_id": "draft_3xK9mQ2vN7pR4wT8yH1sJ5" + "attempt": 1, + "channel_id": 2551105804131, + "channel_name": "Production Alerts", + "duration": 132, + "endpoint": "https://example.com/webhook", + "event_id": "20260412Xatt9hrXsgmFkBR78WF655", + "event_time": "2026-04-12 13:31:11.357472", + "event_type": "a_update", + "integration_id": 5321026051131, + "ref_id": "69da3f0ef77b1b51f40e83cc", + "ref_title": "High CPU Usage on host-01", + "request_body": "{\"event_type\":\"a_update\",\"event_id\":\"d789d65951c0532ea9b6a1d99b707054\"}", + "request_headers": "{\"Content-Type\":\"application/json\"}", + "response_body": "{\"ok\":true}", + "response_headers": "{\"Content-Type\":\"application/json\"}", + "status": "success", + "status_code": 200, + "webhook_type": "alert" }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -58018,7 +63989,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageDraftCreateResponse" + "$ref": "#/components/schemas/WebhookHistoryDetail" } }, "type": "object" @@ -58042,84 +64013,64 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Create status page draft", + "summary": "Get webhook delivery detail", "tags": [ - "On-call/Status pages" + "On-call/Integrations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **300 requests/minute**; **20 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |\n\n## Usage\n\n- The `draft` payload is stored verbatim (up to 64 KB); the console publish form reads it back to prefill the event.\n- A draft lives for 30 days and is consumed exactly once when the event is published.\n- Every call is recorded in the account audit log. Don't put secrets in request fields.", - "href": "/en/api-reference/on-call/status-pages/status-page-draft-create", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) |", + "href": "/en/api-reference/on-call/integrations/webhook-history-detail", "metadata": { - "sidebarTitle": "Create status page draft" + "sidebarTitle": "Get webhook delivery detail" } } } }, - "/status-page/info": { - "get": { - "description": "Retrieve detailed configuration for a specific status page.", - "operationId": "statusPageInfo", - "parameters": [ - { - "description": "Status page ID.", - "in": "query", - "name": "page_id", - "required": true, - "schema": { - "format": "int64", - "type": "integer" + "/webhook/history/list": { + "post": { + "description": "List the delivery history for outbound webhook notifications.", + "operationId": "webhookHistoryList", + "requestBody": { + "content": { + "application/json": { + "example": { + "end_time": 1775203200000, + "integration_id": 6113996590131, + "limit": 20, + "start_time": 1775116800000, + "status": "success" + }, + "schema": { + "$ref": "#/components/schemas/ListWebhookHistoryRequest" + } } - } - ], + }, + "required": true + }, "responses": { "200": { "content": { "application/json": { "example": { "data": { - "components": [ - { - "available_since_seconds": 1765349358, - "component_id": "01KC3GAZ6ZJE40H55GM31RPWZE", - "name": "Web Console", - "order_id": 1, - "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2" - } - ], - "contact_info": "mailto:support@example.com", - "custom_domain": "status.example.com", - "custom_links": [ - { - "key": "Documentation", - "value": "https://docs.example.com" - } - ], - "date_view": "list", - "display_uptime_mode": "chart_and_percentage", - "favicon": "https://cdn.example.com/favicon.png", - "logo": "https://cdn.example.com/logo.png", - "managed_domain_feature_enabled": true, - "name": "Flashduty Status Page", - "page_footer": "2025 Example Corp", - "page_header": "Welcome to our status page", - "page_id": 5750613685214, - "sections": [ + "items": [ { - "description": "Our core services", - "hide_all": false, - "hide_uptime": false, - "name": "Core Services", - "order_id": 1, - "section_id": "01KC3FKKX5TSVG6Z3X1QNGF6V2" + "attempt": 1, + "channel_id": 2551105804131, + "duration": 132, + "endpoint": "https://example.com/webhook", + "event_id": "20260412Xatt9hrXsgmFkBR78WF655", + "event_time": "2026-04-12 13:31:11.357472", + "event_type": "a_update", + "integration_id": 5321026051131, + "ref_id": "69da3f0ef77b1b51f40e83cc", + "status": "success", + "status_code": 200, + "webhook_type": "alert" } ], - "subscription": { - "email": true, - "im": false - }, - "template_preference": "message", - "type": "public", - "url_name": "flashduty-statuspage" + "search_after_ctx": "eyJldmVudF90aW1lIjoiMjAyNi0wNC0xMlQxMzoxNToyNi4zODI1NDcrMDg6MDAiLCJldmVudF9pZCI6IjIwMjYwNDEybUdzeFAzZHJwRmZzNFpDUWQycFNEcCJ9", + "total": 346 }, "request_id": "01HK8XQE3Z7JM2NTFQ5YJ8P9R4" }, @@ -58131,7 +64082,7 @@ { "properties": { "data": { - "$ref": "#/components/schemas/StatusPageInfoResponse" + "$ref": "#/components/schemas/ListWebhookHistoryResponse" } }, "type": "object" @@ -58155,102 +64106,96 @@ "$ref": "#/components/responses/ServerError" } }, - "summary": "Get status page detail", + "summary": "List webhook delivery history", "tags": [ - "On-call/Status pages" + "On-call/Integrations" ], "x-mint": { - "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | None — any valid `app_key` can call this operation |", - "href": "/en/api-reference/on-call/status-pages/status-page-info", + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **1,000 requests/minute**; **50 requests/second** per account |\n| Permissions | **Integrations Read** (`on-call`) |", + "href": "/en/api-reference/on-call/integrations/webhook-history-list", "metadata": { - "sidebarTitle": "Get status page detail" + "sidebarTitle": "List webhook delivery history" } } } }, - "/status-page/list": { - "get": { - "description": "List all status pages owned by the account, including their components and sections.", - "operationId": "status-page-read-page-list", + "/member/notify": { + "post": { + "operationId": "memberNotify", + "summary": "Notify members", + "description": "Send an email to account members on behalf of the caller, with content the caller supplies. Only callable with a credential minted for an AI SRE session; any other credential is rejected with `AccessDenied`. Delivery is asynchronous — `accepted` means the email was queued, not that it was delivered.", + "tags": [ + "Platform/Members" + ], + "x-mint": { + "content": "## Restrictions\n\n| Aspect | Value |\n| ------ | ----- |\n| Rate limits | **200 requests/minute**; **10 requests/second** per account |\n| Permissions | None — callable only with an AI SRE session credential; any other credential is rejected with `AccessDenied` |\n\n## Usage\n\n- Recipients that are not active members of the caller's account, or that have no email address on file, are skipped rather than failing the whole request.\n- Whether email is included follows each recipient's own notification preferences for this kind of message; a recipient with no preference set defaults to receiving it.\n- Recipients receive exactly the sanitized `html` as the email body, with nothing added around it. The sender name shows the caller's name followed by \"(via AI SRE)\".\n- Before sending, the server inspects the submitted `html` and rejects the request with `400` / `InvalidParameter` when it contains constructs whose removal would change what recipients see (`