diff --git a/go.mod b/go.mod index 2ba9e93..e1a0a0c 100644 --- a/go.mod +++ b/go.mod @@ -3,7 +3,7 @@ module github.com/flashcatcloud/flashduty-cli go 1.25.1 require ( - github.com/flashcatcloud/go-flashduty v0.5.13 + github.com/flashcatcloud/go-flashduty v0.6.0 github.com/mattn/go-runewidth v0.0.24 github.com/spf13/cobra v1.10.2 github.com/spf13/pflag v1.0.10 diff --git a/go.sum b/go.sum index ab838a9..119388f 100644 --- a/go.sum +++ b/go.sum @@ -1,8 +1,8 @@ github.com/clipperhouse/uax29/v2 v2.2.0 h1:ChwIKnQN3kcZteTXMgb1wztSgaU+ZemkgWdohwgs8tY= github.com/clipperhouse/uax29/v2 v2.2.0/go.mod h1:EFJ2TJMRUaplDxHKj1qAEhCtQPW2tJSwu5BF98AuoVM= github.com/cpuguy83/go-md2man/v2 v2.0.6/go.mod h1:oOW0eioCTA6cOiMLiUPZOpcVxMig6NIQQ7OS05n1F4g= -github.com/flashcatcloud/go-flashduty v0.5.13 h1:4z75ojq3bTpWUD1uGulljhY2tmyA5Zk86sVNDA02vKY= -github.com/flashcatcloud/go-flashduty v0.5.13/go.mod h1:aA0RtZEs0AYOwwdNKdtVeD8YMOdnmVY1zAlVD+9Ovx8= +github.com/flashcatcloud/go-flashduty v0.6.0 h1:N4nFJ7+ROBRJRUYkN5KPUcheKqyTwcuYhbi2svNJ0oY= +github.com/flashcatcloud/go-flashduty v0.6.0/go.mod h1:aA0RtZEs0AYOwwdNKdtVeD8YMOdnmVY1zAlVD+9Ovx8= github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw= github.com/mattn/go-runewidth v0.0.24 h1:cpokDiIn0MGnhdHwuWnJBITySJ20QyNGnY2kR/ay2DU= diff --git a/internal/cli/zz_generated_automations.go b/internal/cli/zz_generated_automations.go index d848e69..8644ee0 100644 --- a/internal/cli/zz_generated_automations.go +++ b/internal/cli/zz_generated_automations.go @@ -237,7 +237,7 @@ Request fields: --prompt string (required) — Task prompt sent to the AI SRE agent on each run. (≥1 chars) --schedule-trigger-enabled bool — Whether the schedule trigger is enabled. Defaults to true when omitted; HTTP-POST-only rules should send false. --team-id int — Scope team ID. 0 or omitted means a personal rule; >0 means a team in the account. Immutable after creation. (min 0) - --timezone string — IANA timezone 'cron_expr' is evaluated in, e.g. 'Asia/Shanghai'. Must be a timezone name loadable by the server; an invalid value is rejected. Defaults to the caller's member timezone, then the account timezone, then UTC when omitted. + --timezone string — IANA timezone 'cron_expr' is evaluated in, e.g. 'Asia/Shanghai'. Must be a timezone name loadable by the server; an invalid value is rejected. Defaults to the caller's member timezone, then the account timezone, then the server default (Asia/Shanghai) when omitted. Response fields ('data' envelope is unwrapped — these fields are at the top level): - account_id (integer) (required) — Account ID. @@ -339,7 +339,7 @@ Response fields ('data' envelope is unwrapped — these fields are at the top le cmd.Flags().StringVar(&fPrompt, "prompt", "", "Task prompt sent to the AI SRE agent on each run. (required) (≥1 chars)") cmd.Flags().BoolVar(&fScheduleTriggerEnabled, "schedule-trigger-enabled", false, "Whether the schedule trigger is enabled. Defaults to true when omitted; HTTP-POST-only rules should send false.") cmd.Flags().Int64Var(&fTeamID, "team-id", 0, "Scope team ID. 0 or omitted means a personal rule; >0 means a team in the account. Immutable after creation. (min 0)") - cmd.Flags().StringVar(&fTimezone, "timezone", "", "IANA timezone 'cron_expr' is evaluated in, e.g. 'Asia/Shanghai'. Must be a timezone name loadable by the server; an invalid value is rejected. Defaults to the caller's member timezone, then the account timezone, then UTC when omitted.") + cmd.Flags().StringVar(&fTimezone, "timezone", "", "IANA timezone 'cron_expr' is evaluated in, e.g. 'Asia/Shanghai'. Must be a timezone name loadable by the server; an invalid value is rejected. Defaults to the caller's member timezone, then the account timezone, then the server default (Asia/Shanghai) when omitted.") cmd.Flags().StringVar(&dataJSON, "data", "", "Full request body as JSON; positional arguments and typed flags override its fields. Accepts inline JSON, or - to read stdin.") return cmd } diff --git a/internal/cli/zz_generated_channels.go b/internal/cli/zz_generated_channels.go index bf284ef..7ba46b2 100644 --- a/internal/cli/zz_generated_channels.go +++ b/internal/cli/zz_generated_channels.go @@ -72,7 +72,7 @@ Request fields: - method (string) (required) — Grouping method: 'i' intelligent, 'p' pattern, 'n' none. [i, p, n] - storm_threshold (integer) — Alert storm threshold. (0-10000) - storm_thresholds (array) — Multi-level storm thresholds. - - time_window (integer) — Grouping time window in seconds. (min 0) + - time_window (integer) — Grouping time window in minutes. Default max is 1440 minutes (24 h); extended accounts may allow up to 43200 minutes (30 days). (min 0) - window_type (string) — Window type. Defaults to 'tumbling'. [tumbling, sliding] Response fields ('data' envelope is unwrapped — these fields are at the top level): diff --git a/internal/cli/zz_generated_data_sources.go b/internal/cli/zz_generated_data_sources.go index f198826..8851179 100644 --- a/internal/cli/zz_generated_data_sources.go +++ b/internal/cli/zz_generated_data_sources.go @@ -16,7 +16,7 @@ func genDataSourcesReadInfoCmd() *cobra.Command { Short: "Get datasource detail", Long: `Get datasource detail. -Retrieve full details of a single data source by its ID, including the 'payload' configuration, with credential fields masked as '******'. +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. API: POST /monit/datasource/info (monit-datasource-read-info) diff --git a/internal/cli/zz_generated_status_pages.go b/internal/cli/zz_generated_status_pages.go index 6984220..4fea9c8 100644 --- a/internal/cli/zz_generated_status_pages.go +++ b/internal/cli/zz_generated_status_pages.go @@ -1063,26 +1063,40 @@ Response fields ('data' envelope is unwrapped — these fields are at the top le func genStatusPagesDeleteCmd() *cobra.Command { var dataJSON string + var fPageID int64 cmd := &cobra.Command{ - Use: "delete", + Use: "delete ", Short: "Delete status page", Long: `Delete status page. Delete a status page. API: POST /status-page/delete (statusPageDelete) + +Request fields: + --page-id int (required) — Status page ID. `, + Args: requireBodyFieldOrExactArg("page_id", "page-id"), Example: ` flashduty status-page delete --data '{"page_id":5750613685214}'`, RunE: func(cmd *cobra.Command, args []string) error { return runCommand(cmd, args, func(ctx *RunContext) error { body, err := genAssembleBody(dataJSON, func(body map[string]any) error { + if err := genFoldPositional(args, body, "page_id", "int"); err != nil { + return err + } + if cmd.Flags().Changed("page-id") { + body["page_id"] = fPageID + } return nil }) if err != nil { return err } - _ = body - resp, err := ctx.Client.StatusPages.Delete(cmdContext(ctx.Cmd)) + req := new(flashduty.DeleteStatusPageRequest) + if err := genBindBody(body, req); err != nil { + return err + } + resp, err := ctx.Client.StatusPages.Delete(cmdContext(ctx.Cmd), req) if err != nil { return err } @@ -1094,6 +1108,7 @@ API: POST /status-page/delete (statusPageDelete) }) }, } + cmd.Flags().Int64Var(&fPageID, "page-id", 0, "Status page ID. (required)") cmd.Flags().StringVar(&dataJSON, "data", "", "Full request body as JSON; positional arguments and typed flags override its fields. Accepts inline JSON, or - to read stdin.") return cmd } @@ -1891,26 +1906,114 @@ Response fields ('data' envelope is unwrapped — these fields are at the top le func genStatusPagesUpdateCmd() *cobra.Command { var dataJSON string + var fContactInfo string + var fCustomDomain string + var fDarkLogo string + var fDateView string + var fDisplayUptimeMode string + var fFavicon string + var fLogo string + var fLogoURL string + var fName string + var fPageFooter string + var fPageHeader string + var fPageID int64 + var fPageTitle string + var fTemplatePreference string + var fURLName string cmd := &cobra.Command{ - Use: "update", + Use: "update ", Short: "Update status page", Long: `Update status page. Update an existing status page configuration. API: POST /status-page/update (statusPageUpdate) + +Request fields: + --contact-info string — Get-in-touch contact, such as a mailto or website URL. Omit to keep the existing value. + --custom-domain string — Custom domain for a public status page. Omit to keep the existing value. (≤255 chars) + --dark-logo string — Dark-mode logo image of the status page. Omit to keep the existing value. + --date-view string — How event dates are displayed. Omit to keep the existing value. [calendar, list] + --display-uptime-mode string — How uptime is displayed. Omit to keep the existing value. [chart_and_percentage, chart, none] + --favicon string — Favicon of the status page. Omit to keep the existing value. + --logo string — Logo image of the status page. Omit to keep the existing value. + --logo-url string — URL opened when the logo is clicked. Omit to keep the existing value. + --name string — Display name of the status page. Omit to keep the existing value. (≤255 chars) + --page-footer string — Footer content shown on the status page. Omit to keep the existing value. + --page-header string — Header content shown on the status page. Omit to keep the existing value. + --page-id int (required) — Status page ID. + --page-title string — Browser title shown for the status page. Omit to keep the existing value. + --template-preference string — Preferred change-event template type. Omit to keep the existing value. + --url-name string — URL-safe slug, unique per account and page type. Omit to keep the existing value. (≤255 chars) + custom_links (array, via --data) — Custom navigation links shown on the status page. Omit to keep the existing value. + subscription (object, via --data) + - email (boolean) — Whether email subscription is enabled. + - im (boolean) — Whether IM subscription is enabled. `, + Args: requireBodyFieldOrExactArg("page_id", "page-id"), Example: ` flashduty status-page update --data '{"contact_info":"mailto:support@example.com","name":"Flashduty Status Page (Updated)","page_header":"Updated status page header","page_id":5750613685214}'`, RunE: func(cmd *cobra.Command, args []string) error { return runCommand(cmd, args, func(ctx *RunContext) error { body, err := genAssembleBody(dataJSON, func(body map[string]any) error { + if err := genFoldPositional(args, body, "page_id", "int"); err != nil { + return err + } + if cmd.Flags().Changed("contact-info") { + body["contact_info"] = fContactInfo + } + if cmd.Flags().Changed("custom-domain") { + body["custom_domain"] = fCustomDomain + } + if cmd.Flags().Changed("dark-logo") { + body["dark_logo"] = fDarkLogo + } + if cmd.Flags().Changed("date-view") { + body["date_view"] = fDateView + } + if cmd.Flags().Changed("display-uptime-mode") { + body["display_uptime_mode"] = fDisplayUptimeMode + } + if cmd.Flags().Changed("favicon") { + body["favicon"] = fFavicon + } + if cmd.Flags().Changed("logo") { + body["logo"] = fLogo + } + if cmd.Flags().Changed("logo-url") { + body["logo_url"] = fLogoURL + } + if cmd.Flags().Changed("name") { + body["name"] = fName + } + if cmd.Flags().Changed("page-footer") { + body["page_footer"] = fPageFooter + } + if cmd.Flags().Changed("page-header") { + body["page_header"] = fPageHeader + } + if cmd.Flags().Changed("page-id") { + body["page_id"] = fPageID + } + if cmd.Flags().Changed("page-title") { + body["page_title"] = fPageTitle + } + if cmd.Flags().Changed("template-preference") { + body["template_preference"] = fTemplatePreference + } + if cmd.Flags().Changed("url-name") { + body["url_name"] = fURLName + } return nil }) if err != nil { return err } - _ = body - resp, err := ctx.Client.StatusPages.Update(cmdContext(ctx.Cmd)) + req := new(flashduty.UpdateStatusPageRequest) + if err := genBindBody(body, req); err != nil { + return err + } + resp, err := ctx.Client.StatusPages.Update(cmdContext(ctx.Cmd), req) if err != nil { return err } @@ -1922,6 +2025,21 @@ API: POST /status-page/update (statusPageUpdate) }) }, } + cmd.Flags().StringVar(&fContactInfo, "contact-info", "", "Get-in-touch contact, such as a mailto or website URL. Omit to keep the existing value.") + cmd.Flags().StringVar(&fCustomDomain, "custom-domain", "", "Custom domain for a public status page. Omit to keep the existing value. (≤255 chars)") + cmd.Flags().StringVar(&fDarkLogo, "dark-logo", "", "Dark-mode logo image of the status page. Omit to keep the existing value.") + cmd.Flags().StringVar(&fDateView, "date-view", "", "How event dates are displayed. Omit to keep the existing value. [calendar, list]") + cmd.Flags().StringVar(&fDisplayUptimeMode, "display-uptime-mode", "", "How uptime is displayed. Omit to keep the existing value. [chart_and_percentage, chart, none]") + cmd.Flags().StringVar(&fFavicon, "favicon", "", "Favicon of the status page. Omit to keep the existing value.") + cmd.Flags().StringVar(&fLogo, "logo", "", "Logo image of the status page. Omit to keep the existing value.") + cmd.Flags().StringVar(&fLogoURL, "logo-url", "", "URL opened when the logo is clicked. Omit to keep the existing value.") + cmd.Flags().StringVar(&fName, "name", "", "Display name of the status page. Omit to keep the existing value. (≤255 chars)") + cmd.Flags().StringVar(&fPageFooter, "page-footer", "", "Footer content shown on the status page. Omit to keep the existing value.") + cmd.Flags().StringVar(&fPageHeader, "page-header", "", "Header content shown on the status page. Omit to keep the existing value.") + cmd.Flags().Int64Var(&fPageID, "page-id", 0, "Status page ID. (required)") + cmd.Flags().StringVar(&fPageTitle, "page-title", "", "Browser title shown for the status page. Omit to keep the existing value.") + cmd.Flags().StringVar(&fTemplatePreference, "template-preference", "", "Preferred change-event template type. Omit to keep the existing value.") + cmd.Flags().StringVar(&fURLName, "url-name", "", "URL-safe slug, unique per account and page type. Omit to keep the existing value. (≤255 chars)") cmd.Flags().StringVar(&dataJSON, "data", "", "Full request body as JSON; positional arguments and typed flags override its fields. Accepts inline JSON, or - to read stdin.") return cmd } diff --git a/skills/flashduty/reference/monit.md b/skills/flashduty/reference/monit.md index a5ac914..3bb5cfd 100644 --- a/skills/flashduty/reference/monit.md +++ b/skills/flashduty/reference/monit.md @@ -379,6 +379,7 @@ Invoke target tools ## Gotchas - **Datasource name is not guessable.** A `can not find datasource` 400 means the name is wrong — re-run `datasource-list` and copy the exact `Name`. Never invent variants. +- **`datasource-info` (and the `datasource-create`/`datasource-update` responses) return credentials exactly as configured — nothing is masked.** The `payload` object includes whatever passwords, API keys, tokens, and similar fields were set, in the clear. Treat the response as sensitive: don't dump it into logs or chat, don't echo it back beyond what the task needs, and don't pass it on to another tool. - **`query-rows` has no time flags.** There is no `--time-start` / `--time-end` / `--operation`. Embed all time range and bucketing inside `--expr`. Passing those flags is a silent no-op or error. - **`query-diagnose` time window via `--data`**, not flags. Pass `{"time_range":{"start":,"end":},...}`. Window wider than 6 hours is rejected server-side. Omitting `time_range` defaults to the last 15 minutes. - **`rule_configs` and nested arrays require `--data`.** The queries, thresholds, enabled_times, and labels objects cannot be expressed as flat flags — pass them as inline JSON via `--data '{"rule_configs":{...}}'`. Typed scalar flags (`--name`, `--enabled`, `--cron-pattern`, `--ds-type`) override matching `--data` keys. diff --git a/skills/flashduty/reference/safari.md b/skills/flashduty/reference/safari.md index 29ca44b..e42c945 100644 --- a/skills/flashduty/reference/safari.md +++ b/skills/flashduty/reference/safari.md @@ -121,7 +121,7 @@ Create Automation rule - `--prompt` string (required) — Task prompt sent to the AI SRE agent on each run. (≥1 chars) - `--schedule-trigger-enabled` bool — Whether the schedule trigger is enabled. Defaults to true when omitted; HTTP-POST-only rules should send false. - `--team-id` int64 — Scope team ID. 0 or omitted means a personal rule; >0 means a team in the account. Immutable after creation. (min 0) -- `--timezone` string — IANA timezone 'cron_expr' is evaluated in, e.g. 'Asia/Shanghai'. Must be a timezone name loadable by the server; an invalid value is rejected. Defaults to the caller's member timezone, then the account timezone, then UTC when omitted. +- `--timezone` string — IANA timezone 'cron_expr' is evaluated in, e.g. 'Asia/Shanghai'. Must be a timezone name loadable by the server; an invalid value is rejected. Defaults to the caller's member timezone, then the account timezone, then the server default (Asia/Shanghai) when omitted. - response: single object (`data` unwrapped to the top level) — fields: account_id (integer); can_edit (boolean); created_at (integer); cron_expr (string); enabled (boolean); environment_id (string); environment_kind (string); http_post_token (string); http_post_trigger_enabled (boolean); http_post_trigger_id (string); http_post_trigger_url (string); name (string); oncall_incident_channel_ids (array); oncall_incident_severities (array); oncall_incident_trigger_enabled (boolean); oncall_incident_trigger_id (string); owner_id (integer); prompt (string); rule_id (string); run_scope (string); schedule_next_fire_at_ms (integer); schedule_trigger_enabled (boolean); schedule_trigger_id (string); team_id (integer); timezone (string); updated_at (integer) ### automation-rule-delete diff --git a/skills/flashduty/reference/status-page.md b/skills/flashduty/reference/status-page.md index 5a60ea6..18cb219 100644 --- a/skills/flashduty/reference/status-page.md +++ b/skills/flashduty/reference/status-page.md @@ -148,8 +148,9 @@ Create status page - body-only (`--data`): custom_links (array); subscription (object) - response: single object (`data` unwrapped to the top level) — fields: page_id (integer); page_name (string); page_url_name (string) -### delete +### delete Delete status page +- `` (positional, required) int64 — Status page ID. ### info Get status page detail @@ -230,8 +231,24 @@ Upsert status page template - body-only (`--data`): template (object) (required) - response: single object (`data` unwrapped to the top level) — fields: template_id (string) -### update +### update Update status page +- `--contact-info` string — Get-in-touch contact, such as a mailto or website URL. Omit to keep the existing value. +- `--custom-domain` string — Custom domain for a public status page. Omit to keep the existing value. (≤255 chars) +- `--dark-logo` string — Dark-mode logo image of the status page. Omit to keep the existing value. +- `--date-view` string — How event dates are displayed. Omit to keep the existing value. · enum: calendar | list +- `--display-uptime-mode` string — How uptime is displayed. Omit to keep the existing value. · enum: chart_and_percentage | chart | none +- `--favicon` string — Favicon of the status page. Omit to keep the existing value. +- `--logo` string — Logo image of the status page. Omit to keep the existing value. +- `--logo-url` string — URL opened when the logo is clicked. Omit to keep the existing value. +- `--name` string — Display name of the status page. Omit to keep the existing value. (≤255 chars) +- `--page-footer` string — Footer content shown on the status page. Omit to keep the existing value. +- `--page-header` string — Header content shown on the status page. Omit to keep the existing value. +- `` (positional, required) int64 — Status page ID. +- `--page-title` string — Browser title shown for the status page. Omit to keep the existing value. +- `--template-preference` string — Preferred change-event template type. Omit to keep the existing value. +- `--url-name` string — URL-safe slug, unique per account and page type. Omit to keep the existing value. (≤255 chars) +- body-only (`--data`): custom_links (array); subscription (object)