From 26e1f93ceb9afc2697aea69fd9cc1584d6a4c32f Mon Sep 17 00:00:00 2001 From: Abhijit Date: Thu, 8 Oct 2026 09:51:31 +0530 Subject: [PATCH] Describe cometcli on its own terms MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Drop comparisons to another product from the README, docs, release header and code comments. Compatibility facts stay, worded generically: the settings and hook formats common to AI agents, the standard .mcp.json file, capitalized tool-name aliases (Bash, Read…) and mode aliases. Co-Authored-By: Claude Opus 5.5 --- .goreleaser.yaml | 4 ++-- README.md | 11 +++++------ docs/COMMANDS.md | 2 +- docs/EXTENDING.md | 6 +++--- internal/agent/commands.go | 2 +- internal/agent/policy.go | 4 ++-- internal/cli/mcpservers.go | 2 +- internal/cli/ui.go | 2 +- internal/hooks/hooks.go | 2 +- internal/hooks/hooks_test.go | 2 +- internal/settings/settings.go | 6 +++--- internal/toolkit/perm.go | 8 ++++---- internal/tui/chat.go | 2 +- internal/tui/chatui/art.go | 4 ++-- internal/tui/chatui/chatui.go | 12 ++++++------ 15 files changed, 34 insertions(+), 35 deletions(-) diff --git a/.goreleaser.yaml b/.goreleaser.yaml index aaf83ae..ba48105 100644 --- a/.goreleaser.yaml +++ b/.goreleaser.yaml @@ -67,8 +67,8 @@ release: ## cometcli v{{ .Version }} An agentic SRE terminal for Cosmos SDK and Cosmos-EVM validators — talk to - your machine and nodes the way you use Claude Code; incidents worked through - to the fix, every change and transaction approved by you. + your machine and nodes in plain language; incidents worked through to the + fix, every change and transaction approved by you. ```bash curl -fsSL https://raw.githubusercontent.com/abhijitkrm/cometcli/main/scripts/install.sh | bash diff --git a/README.md b/README.md index 253dff8..e823196 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@
cometcli

cometcli

-

An agentic SRE terminal for Cosmos validators — Claude Code for your nodes

+

An agentic SRE terminal for Cosmos validators

@@ -24,7 +24,7 @@
-cometcli is a terminal you talk to, the way you use Claude Code, built for running +cometcli is an AI terminal you talk to in plain language, built for running [Cosmos SDK](https://github.com/cosmos/cosmos-sdk) and [Cosmos-EVM](https://github.com/cosmos/evm) validators. Ask *"is anyone jailed?"* or *"why is my validator missing blocks?"*. It inspects the node, chain and host, works @@ -39,8 +39,7 @@ out the cause, proposes the fix, and carries it out once you approve. - **Operate** — transactions, governance proposals and votes, upgrades, state sync, service control, security audits - **Watch** — live dashboard and alerts to Slack, Discord or Telegram -- **Extend** — settings, memory, custom commands, hooks, MCP servers and subagents, - as in Claude Code +- **Extend** — settings, memory, custom commands, hooks, MCP servers and subagents

cometcli starting in the terminal: a comet streaking over the COMETCLI wordmark, the welcome box and the prompt @@ -113,7 +112,7 @@ cometcli profile add myval \ ## The terminal -An inline chat like Claude Code's: answers land in your normal scrollback, and only +An inline chat: answers land in your normal scrollback, and only the bottom of the screen redraws. ``` @@ -287,7 +286,7 @@ agent. - **Tiers** — `observe → diagnose → local-change → on-chain`. Reads run; changes ask; transactions always ask. -- **Permission rules** — allow / ask / deny in Claude Code syntax +- **Permission rules** — allow / ask / deny patterns (`bash(docker logs:*)`, `read(./config/**)`, `node.*`); deny beats ask beats allow. Every shell command is classified first, scripts and `docker exec` included. - **Consensus keys are radioactive** — `priv_validator_key.json` is never read into diff --git a/docs/COMMANDS.md b/docs/COMMANDS.md index 1a108ed..94d0e5a 100644 --- a/docs/COMMANDS.md +++ b/docs/COMMANDS.md @@ -362,7 +362,7 @@ cometcli runbook run coordinated-upgrade ```bash cometcli # bare command = chat TUI (when a profile exists) -cometcli ui # chat-first TUI (Claude Code style): streamed answers, +cometcli ui # chat-first TUI: streamed answers, # /run tools, approval modals with diffs, txs broadcast # from the chat. Overview/fleet/logs/send panes on tabs cometcli serve --open # same agent in a local web chat (127.0.0.1 only, diff --git a/docs/EXTENDING.md b/docs/EXTENDING.md index 90bd38a..98017c9 100644 --- a/docs/EXTENDING.md +++ b/docs/EXTENDING.md @@ -1,7 +1,7 @@ # Extending cometcli Settings, memory, custom commands, hooks, MCP servers and subagents all live in plain -files. The formats follow Claude Code's, so configs written for it mostly carry over. +files, in the settings format common to AI coding agents, so existing configs mostly carry over. A **project** is the nearest directory above where you start cometcli that holds a `.cometcli/` folder, a `COMET.md` or a `.git`. @@ -124,7 +124,7 @@ Commands run at points in the loop. Events: `PreToolUse`, `PostToolUse`, ``` `matcher` is a case-insensitive regex over tool names (`bash`, `edit`, `node.status`, -`mcp__grafana__.*`; Claude Code's `Bash` works); empty or `*` matches all. Hooks run +`mcp__grafana__.*`; capitalized names like `Bash` work too); empty or `*` matches all. Hooks run from the project root with `COMETCLI_PROJECT_DIR` (and `CLAUDE_PROJECT_DIR`) set, and get the event as JSON on stdin: @@ -160,7 +160,7 @@ cometcli mcp remove grafana ``` Scopes: `user` (default, `~/.cometcli/settings.json`), `project` (`.mcp.json` — the -same file Claude Code reads), `local` (`.cometcli/settings.local.json`). `${VAR}` and +the standard project MCP file), `local` (`.cometcli/settings.local.json`). `${VAR}` and `${VAR:-default}` expand in commands, args, env, URLs and headers. Servers start with each session; their tools are named `mcp____` and, diff --git a/internal/agent/commands.go b/internal/agent/commands.go index 9e2ac7f..37fa266 100644 --- a/internal/agent/commands.go +++ b/internal/agent/commands.go @@ -77,7 +77,7 @@ func RunCommand(a *Agent, c *toolkit.Context, reg *toolkit.Registry, line string if err := needAgent(); err != nil { return CmdResult{}, err } - // the current setup, like Claude Code's /status; in node mode also + // the current setup; in node mode also // a live snapshot of the node (as a background job: never block) a.loadMemory() var b strings.Builder diff --git a/internal/agent/policy.go b/internal/agent/policy.go index 264af2c..28b60e1 100644 --- a/internal/agent/policy.go +++ b/internal/agent/policy.go @@ -30,8 +30,8 @@ const ( // Modes lists the approval postures in shift+tab cycling order. var Modes = []Mode{ModeOps, ModeAcceptEdits, ModeReadOnly, ModeBypass} -// ParseMode accepts ops | readonly | accept-edits | bypass, plus Claude -// Code's names (default, plan, acceptEdits, bypassPermissions). +// ParseMode accepts ops | readonly | accept-edits | bypass, plus the +// common aliases default, plan, acceptEdits and bypassPermissions. func ParseMode(s string) (Mode, error) { switch strings.ToLower(strings.TrimSpace(s)) { case "", "ops", "rw", "default": diff --git a/internal/cli/mcpservers.go b/internal/cli/mcpservers.go index a87d017..d8566ae 100644 --- a/internal/cli/mcpservers.go +++ b/internal/cli/mcpservers.go @@ -19,7 +19,7 @@ import ( ) // mcpScopePath returns the file a scope's servers live in: user settings, -// the project's .mcp.json (shared with Claude Code), or local settings. +// the project's .mcp.json (the standard project MCP file), or local settings. func mcpScopePath(scope string) (string, error) { switch scope { case "user", "": diff --git a/internal/cli/ui.go b/internal/cli/ui.go index a7a1530..b9ba00b 100644 --- a/internal/cli/ui.go +++ b/internal/cli/ui.go @@ -15,7 +15,7 @@ import ( ) // UICmd is the chat-first terminal app: an agent conversation on the front -// pane (Claude Code style) with overview/fleet/logs/send dashboards behind +// pane with overview/fleet/logs/send dashboards behind // it — all over the same registry and approval gate as the CLI. func UICmd(reg *toolkit.Registry) *cobra.Command { var interval int diff --git a/internal/hooks/hooks.go b/internal/hooks/hooks.go index 8022dbd..6cfab5f 100644 --- a/internal/hooks/hooks.go +++ b/internal/hooks/hooks.go @@ -1,5 +1,5 @@ // Package hooks runs operator-defined commands at points in the agent -// loop, with Claude Code's contract: the event arrives as JSON on stdin; +// loop, with the common agent-hook contract: the event arrives as JSON on stdin; // exit 0 passes (stdout may carry JSON decisions or extra context); exit // 2 blocks, with stderr as the reason; any other exit is a non-blocking // error shown to the operator. diff --git a/internal/hooks/hooks_test.go b/internal/hooks/hooks_test.go index c5c6592..64be73a 100644 --- a/internal/hooks/hooks_test.go +++ b/internal/hooks/hooks_test.go @@ -37,7 +37,7 @@ func TestExitCodes(t *testing.T) { } out = runner(t, PreToolUse, "Bash", `exit 2`).Run(ctx, Input{Event: PreToolUse, ToolName: "bash"}) if !out.Block { - t.Fatal("matcher should be case-insensitive (Claude Code's Bash)") + t.Fatal("matcher should be case-insensitive (Bash)") } } diff --git a/internal/settings/settings.go b/internal/settings/settings.go index 7c72431..32ecbc9 100644 --- a/internal/settings/settings.go +++ b/internal/settings/settings.go @@ -1,7 +1,7 @@ // Package settings discovers and merges cometcli's file-based // extensibility: settings.json at user, project and local scope, COMET.md // memory files, custom slash commands, subagent definitions and MCP -// server configs. Formats follow Claude Code's, so its configs carry over. +// server configs, in the settings format common to AI coding agents. // // Project-scope hooks and MCP servers execute commands, so they only take // effect once the project directory is trusted (`cometcli trust`). @@ -28,7 +28,7 @@ const ( ScopeLocal Scope = "local" // /.cometcli/settings.local.json ) -// Permissions mirrors Claude Code's permissions block. +// Permissions is the allow/ask/deny permissions block. type Permissions struct { Allow []string `json:"allow,omitempty"` Ask []string `json:"ask,omitempty"` @@ -143,7 +143,7 @@ func Load(cwd string) (*Settings, error) { s.Sources = append(s.Sources, sc.path) s.apply(f, sc.scope) } - // a project's .mcp.json (Claude Code's file) adds project servers + // a project's .mcp.json (the standard project MCP file) adds project servers if s.Root != "" { var mj struct { MCPServers map[string]MCPServer `json:"mcpServers"` diff --git a/internal/toolkit/perm.go b/internal/toolkit/perm.go index b8f42e6..ec36639 100644 --- a/internal/toolkit/perm.go +++ b/internal/toolkit/perm.go @@ -35,7 +35,7 @@ func (d Decision) String() string { return "default" } -// Rule is one permission pattern, in Claude Code's syntax: +// Rule is one permission pattern: // // bash any shell command // bash(git status) exactly this command @@ -46,7 +46,7 @@ func (d Decision) String() string { // val.unjail, node.* registry tools by name or prefix // // Tool names match case-insensitively, so Bash(...) and WebFetch(...) -// from Claude Code configs work too. +// from other agents' configs work too. type Rule struct { Raw string Tool string // lower-cased; may end in ".*" @@ -55,7 +55,7 @@ type Rule struct { var ruleRe = regexp.MustCompile(`^\s*([A-Za-z_][A-Za-z0-9_.*-]*)\s*(?:\((.*)\))?\s*$`) -// toolAliases maps Claude Code tool names onto ours. +// toolAliases maps common capitalized tool names (Bash, Read…) onto ours. var toolAliases = map[string]string{"webfetch": "web_fetch", "todowrite": "todo_write", "multiedit": "edit"} // ParseRule parses one rule string. @@ -130,7 +130,7 @@ func expandPattern(p, root string) string { case strings.HasPrefix(p, "~/"): home, _ := os.UserHomeDir() return filepath.Join(home, p[2:]) - case strings.HasPrefix(p, "//"): // Claude Code's absolute-path form + case strings.HasPrefix(p, "//"): // absolute-path form return p[1:] case filepath.IsAbs(p): return p diff --git a/internal/tui/chat.go b/internal/tui/chat.go index 5778dbd..b75d27b 100644 --- a/internal/tui/chat.go +++ b/internal/tui/chat.go @@ -18,7 +18,7 @@ import ( ) // chatPane is the conversational front-end: a transcript of user prompts, -// assistant text, tool calls, and approvals — Claude Code style. The agent +// assistant text, tool calls, and approvals. The agent // may be nil (no provider configured); slash commands and /run still work. type chatPane struct { agent *agent.Agent diff --git a/internal/tui/chatui/art.go b/internal/tui/chatui/art.go index 9850648..0073b46 100644 --- a/internal/tui/chatui/art.go +++ b/internal/tui/chatui/art.go @@ -8,7 +8,7 @@ import ( ) // The startup art: a comet streaking over "COMETCLI" in block letters, -// the way Claude Code greets you with its name. Drawn only when the +// as a startup greeting. Drawn only when the // terminal is wide enough; colors degrade with the terminal's profile. // glyphs is the ANSI Shadow figlet font, for the letters we need. @@ -79,7 +79,7 @@ func along(stops []rgb, t float64) lipgloss.Color { var ( // tail: deep violet far behind, through blue and cyan, to white-hot tailStops = []rgb{hex("#3B2A6B"), hex("#6A4FC9"), hex("#4F8EF7"), hex("#7FE3F5"), hex("#F2FBFF")} - // wordmark: comet gold through Claude-ish orange to violet + // wordmark: comet gold through coral to violet wordStops = []rgb{hex("#FFD27A"), hex("#F09A5B"), hex("#D97757"), hex("#C2609E"), hex("#8E6BE8")} headSt = lipgloss.NewStyle().Foreground(lipgloss.Color("#FFF7E0")).Bold(true) sparkSt = lipgloss.NewStyle().Foreground(lipgloss.Color("#FFD27A")) diff --git a/internal/tui/chatui/chatui.go b/internal/tui/chatui/chatui.go index 1e201f8..6add97c 100644 --- a/internal/tui/chatui/chatui.go +++ b/internal/tui/chatui/chatui.go @@ -1,5 +1,5 @@ // Package chatui is cometcli's interactive terminal: an inline, -// scrollback-friendly chat in the style of Claude Code. Finished messages +// scrollback-friendly chat. Finished messages // are printed into the terminal's normal scrollback; only a small live // region (streaming text, spinner, input, approval dialog, status line) // is redrawn. @@ -690,7 +690,7 @@ func (m *model) onEvent(e agent.Event) tea.Cmd { } // flushThinking closes a finished stretch of thinking into a collapsed -// line, the way Claude Code shows it; ctrl+o prints the text. +// line; ctrl+o prints the text. func (m *model) flushThinking() tea.Cmd { t := strings.TrimSpace(m.think) m.think = "" @@ -995,7 +995,7 @@ func (m *model) View() string { if s := strings.TrimSpace(m.live.String()); s != "" { b.WriteString("\n" + lastLines("⏺ "+strings.TrimLeft(m.markdown(s), "\n "), 16) + "\n") } - // running tool calls: blinking bullet, like Claude Code + // running tool calls: blinking bullet blink := "⏺" if time.Now().UnixMilli()/500%2 == 1 { blink = " " @@ -1273,7 +1273,7 @@ func (m *model) markdown(s string) string { zero := uint(0) cfg.Document.Margin = &zero cfg.Document.BlockPrefix, cfg.Document.BlockSuffix = "", "" - // Claude Code look: "- " bullets, headings as bold text + // "- " bullets, headings as bold text cfg.Item.BlockPrefix = "- " // inline code: just a color, no padding or background codeColor := "#B1B9F9" @@ -1311,7 +1311,7 @@ func userLine(s string) string { return "\n" + strings.Join(lines, "\n") } -// result indents text under the previous line with Claude Code's ⎿. +// result indents text under the previous line with ⎿. func result(s string) string { if strings.TrimSpace(s) == "" { return "" @@ -1431,7 +1431,7 @@ func todoLines(ts []agent.Todo) string { return strings.Join(out, "\n") } -// verbs for the spinner, one picked per turn (Claude Code style) +// verbs for the spinner, one picked per turn var verbs = []string{"Thinking", "Pondering", "Investigating", "Digging", "Checking", "Inspecting", "Crunching", "Mulling", "Percolating", "Synthesizing", "Ruminating", "Deliberating", "Tinkering", "Sleuthing", "Untangling"}