Skip to content

Commit b127ac2

Browse files
authored
fix: add contextual dashboard hint as first property in all JSON responses (#13)
1 parent df39619 commit b127ac2

2 files changed

Lines changed: 27 additions & 7 deletions

File tree

cmd/onecli/main.go

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,10 @@ func main() {
6060
os.Exit(exitcode.Error)
6161
}
6262

63-
out.SetHint(hintForCommand(kCtx.Command(), config.APIHost()))
63+
cmd := kCtx.Command()
64+
out.SetHintFunc(func() string {
65+
return hintForCommand(cmd, config.APIHost())
66+
})
6467
err = kCtx.Run(out)
6568
if err != nil {
6669
handleError(out, err)

pkg/output/output.go

Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,10 @@ import (
1212
// Writer handles all structured output for the CLI.
1313
// All stdout/stderr writing must go through this. Never use fmt.Print or os.Stdout directly.
1414
type Writer struct {
15-
out io.Writer
16-
err io.Writer
17-
hint string
15+
out io.Writer
16+
err io.Writer
17+
hint string
18+
hintFn func() string
1819
}
1920

2021
// New creates a Writer that writes to stdout and stderr.
@@ -39,6 +40,21 @@ func (w *Writer) SetHint(msg string) {
3940
w.hint = msg
4041
}
4142

43+
// SetHintFunc sets a function that lazily resolves the hint message at write
44+
// time. This ensures the hint reflects state after the command has executed
45+
// (e.g. after `config set api-host` updates the host).
46+
func (w *Writer) SetHintFunc(fn func() string) {
47+
w.hintFn = fn
48+
}
49+
50+
// resolveHint returns the current hint, preferring hintFn if set.
51+
func (w *Writer) resolveHint() string {
52+
if w.hintFn != nil {
53+
return w.hintFn()
54+
}
55+
return w.hint
56+
}
57+
4258
// Write marshals v as indented JSON and writes it to stdout.
4359
// HTML escaping is disabled because this is a CLI tool, not a web page.
4460
func (w *Writer) Write(v any) error {
@@ -298,15 +314,16 @@ func (w *Writer) writeToOut(data []byte) error {
298314
// injectHint prepends a "hint" property to JSON objects or wraps arrays
299315
// in a {"hint": ..., "data": [...]} envelope.
300316
func (w *Writer) injectHint(data []byte) []byte {
301-
if w.hint == "" {
317+
hint := w.resolveHint()
318+
if hint == "" {
302319
return data
303320
}
304321
trimmed := bytes.TrimSpace(data)
305322
if len(trimmed) < 2 {
306323
return data
307324
}
308325

309-
hintVal, err := json.Marshal(w.hint)
326+
hintVal, err := json.Marshal(hint)
310327
if err != nil {
311328
return data
312329
}
@@ -315,7 +332,7 @@ func (w *Writer) injectHint(data []byte) []byte {
315332
case '{':
316333
return injectHintObject(data, hintVal)
317334
case '[':
318-
return injectHintArray(data, w.hint)
335+
return injectHintArray(data, hint)
319336
default:
320337
return data
321338
}

0 commit comments

Comments
 (0)