diff --git a/app.go b/app.go index edc7746..c1a4019 100644 --- a/app.go +++ b/app.go @@ -55,6 +55,10 @@ type App[C any] struct { Root *Node[C] // Greeting, if set, is printed after the version banner in interactive mode. Greeting string + // JSON, when true, registers a -json flag that switches Emit to JSON output. + // Leave it false for CLIs whose commands do not (yet) use cli.Emit, so they + // never advertise a flag they cannot honor. + JSON bool // DefaultServer is the -server default. If both it and ServerEnv are empty, // no -server flag is registered (local CLI). @@ -109,7 +113,10 @@ func (a *App[C]) Run(ctx context.Context, argv []string) error { serverFlag = fs.String("server", defaultServer, usage) } color := fs.Bool("color", true, "colorize output (default: on in the shell, off one-shot)") - jsonOut := fs.Bool("json", false, "emit JSON instead of text") + var jsonOut *bool + if a.JSON { + jsonOut = fs.Bool("json", false, "emit JSON instead of text") + } showVersion := fs.Bool("version", false, "print version and exit") if a.RegisterFlags != nil { a.RegisterFlags(fs) @@ -125,7 +132,8 @@ func (a *App[C]) Run(ctx context.Context, argv []string) error { fmt.Println(a.versionLine()) return nil } - if *jsonOut { + jsonMode := jsonOut != nil && *jsonOut + if jsonMode { SetFormat(FormatJSON) } @@ -145,7 +153,7 @@ func (a *App[C]) Run(ctx context.Context, argv []string) error { if colorExplicit { colorOn = *color } - if *jsonOut { + if jsonMode { colorOn = false } SetColor(colorOn) diff --git a/docs/design.md b/docs/design.md index c8e0ec0..5333a4c 100644 --- a/docs/design.md +++ b/docs/design.md @@ -7,7 +7,7 @@ SPDX-License-Identifier: Apache-2.0 | | | | --- | --- | -| **Status** | Describes shipped behavior as of `v1.2.0` | +| **Status** | Describes shipped behavior as of `v1.3.0` | | **Author** | Pim van Pelt `` | | **Last updated** | 2026-06-05 | | **Audience** | Contributors, and authors of CLIs built on this library | @@ -95,8 +95,9 @@ or JSON from the same code. **FR-5 `App` entry point** -- **FR-5.1** `App` MUST register `-color`, `-json`, `-version`, and `-server` - (only when a server is configured). +- **FR-5.1** `App` MUST register `-color` and `-version`; `-server` only when a + server is configured; and `-json` only when the app opts in (its commands use + `Emit`), so a CLI never advertises a flag it cannot honor. - **FR-5.2** `App` MUST NOT dial anything; the client is built in a caller's `Connect` callback. - **FR-5.3** `-version` MUST print and exit without connecting. diff --git a/example/main.go b/example/main.go index 8047e01..761475d 100644 --- a/example/main.go +++ b/example/main.go @@ -201,9 +201,10 @@ func buildTree() *cli.Node[inventory] { func main() { (&cli.App[inventory]{ Name: "example", - Version: "1.1.0", + Version: "1.3.0", Prompt: "inv> ", Root: buildTree(), + JSON: true, // commands use cli.Emit, so advertise -json Greeting: "golang-cli example — try: show server, ping db1, colors, '?' for help, TAB to complete", // Local CLI: no -server flag. Connect just hands over the in-memory data, // proving App is transport-agnostic (it never dials anything itself).