Skip to content

Commit 24d49d4

Browse files
authored
💝 A general purpose WithCommand option. (#2)
A general purpose WithCommand option.
1 parent 176dc37 commit 24d49d4

File tree

9 files changed

+127
-54
lines changed

9 files changed

+127
-54
lines changed

.github/workflows/go.yml

+8-6
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@ on:
66
pull_request:
77
types: [opened, synchronize, reopened]
88

9+
env:
10+
FORCE_COLOR: true
11+
912
jobs:
1013

1114
build:
@@ -14,20 +17,19 @@ jobs:
1417
strategy:
1518
matrix:
1619
go-version:
17-
- '1.18'
20+
- '1.22'
21+
- '1.23'
1822
steps:
1923

2024
- name: Set up Go ${{ matrix.go-version }}
21-
uses: actions/setup-go@v2
25+
uses: actions/setup-go@v5
2226
with:
2327
go-version: ${{ matrix.go-version }}
2428
id: go
2529

2630
- name: Check out code into the Go module directory
27-
uses: actions/checkout@v2
31+
uses: actions/checkout@v4
2832

2933
- name: Test
30-
run: go run gotest.tools/gotestsum@v1.8.0 --format testname --
34+
run: go run gotest.tools/gotestsum@v1.12.0 --format testname --
3135
-race -count=1 -short ./...
32-
env:
33-
FORCE_COLOR: true

.golangci.yaml

+39
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
run:
2+
timeout: 5m
3+
4+
linters:
5+
disable-all: false
6+
presets:
7+
- bugs
8+
- unused
9+
- complexity
10+
- format
11+
- performance
12+
- style
13+
enable:
14+
- gci
15+
disable:
16+
- paralleltest
17+
- nlreturn
18+
- exhaustivestruct
19+
- wsl
20+
- godox
21+
- scopelint
22+
- maligned
23+
- interfacer
24+
- golint
25+
- ireturn
26+
- varnamelen
27+
- exhaustruct
28+
- depguard
29+
30+
issues:
31+
exclude-rules:
32+
- path: _test\.go
33+
linters:
34+
- wrapcheck
35+
36+
linters-settings:
37+
gomoddirectives:
38+
# List of allowed `replace` directives. Default is empty.
39+
replace-allow-list: []

types.go renamed to app.go

-33
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@ package commandline
22

33
import (
44
"errors"
5-
"io"
65
"os"
76

87
"github.com/spf13/cobra"
@@ -24,9 +23,6 @@ type CobraProvider interface {
2423
Command() *cobra.Command
2524
}
2625

27-
// Option is used to configure an App.
28-
type Option func(*App)
29-
3026
// New creates a new App from CobraProvider.
3127
func New(cp CobraProvider) *App {
3228
return &App{
@@ -42,35 +38,6 @@ func (a *App) ExecuteOrDie(options ...Option) {
4238
}
4339
}
4440

45-
// WithArgs creates an option which sets args.
46-
func WithArgs(args ...string) Option {
47-
return func(app *App) {
48-
app.root.SetArgs(args)
49-
}
50-
}
51-
52-
// WithInput creates an option witch sets os.Stdin.
53-
func WithInput(in io.Reader) Option {
54-
return func(app *App) {
55-
app.root.SetIn(in)
56-
}
57-
}
58-
59-
// WithOutput creates an option witch sets os.Stdout and os.Stderr.
60-
func WithOutput(out io.Writer) Option {
61-
return func(app *App) {
62-
app.root.SetOut(out)
63-
app.root.SetErr(out)
64-
}
65-
}
66-
67-
// WithExit creates an option which sets the exit function.
68-
func WithExit(fn func(code int)) Option {
69-
return func(app *App) {
70-
app.Exit = fn
71-
}
72-
}
73-
7441
// Execute will execute the application with the provided options and return
7542
// error if any.
7643
func (a *App) Execute(options ...Option) error {

types_test.go renamed to app_test.go

+7-5
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ package commandline_test
33
import (
44
"bytes"
55
"errors"
6-
"io/ioutil"
6+
"io"
77
"testing"
88

99
"github.com/spf13/cobra"
@@ -15,9 +15,11 @@ func TestExecuteOrDie(t *testing.T) {
1515
var buf bytes.Buffer
1616
var retcode int
1717
commandline.New(new(testApp)).ExecuteOrDie(
18-
commandline.WithOutput(&buf),
19-
commandline.WithInput(bytes.NewBufferString("Input")),
20-
commandline.WithArgs("arg1", "arg2"),
18+
commandline.WithCommand(func(cmd *cobra.Command) {
19+
cmd.SetOut(&buf)
20+
cmd.SetIn(bytes.NewBufferString("Input"))
21+
cmd.SetArgs([]string{"arg1", "arg2"})
22+
}),
2123
commandline.WithExit(func(code int) {
2224
retcode = code
2325
}),
@@ -46,7 +48,7 @@ func (t testApp) Command() *cobra.Command {
4648
SilenceUsage: true,
4749
SilenceErrors: true,
4850
RunE: func(cmd *cobra.Command, args []string) error {
49-
in, err := ioutil.ReadAll(cmd.InOrStdin())
51+
in, err := io.ReadAll(cmd.InOrStdin())
5052
if err != nil {
5153
return err
5254
}

go.mod

+5-5
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,15 @@
11
module github.com/wavesoftware/go-commandline
22

3-
go 1.18
3+
go 1.22.0
44

55
require (
6-
github.com/spf13/cobra v1.5.0
6+
github.com/spf13/cobra v1.8.1
77
github.com/wavesoftware/go-retcode v1.0.0
8-
gotest.tools/v3 v3.3.0
8+
gotest.tools/v3 v3.5.1
99
)
1010

1111
require (
12-
github.com/google/go-cmp v0.5.5 // indirect
13-
github.com/inconshreveable/mousetrap v1.0.0 // indirect
12+
github.com/google/go-cmp v0.6.0 // indirect
13+
github.com/inconshreveable/mousetrap v1.1.0 // indirect
1414
github.com/spf13/pflag v1.0.5 // indirect
1515
)

go.sum

+12
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,20 @@
11
github.com/cpuguy83/go-md2man/v2 v2.0.2/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o=
2+
github.com/cpuguy83/go-md2man/v2 v2.0.4/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o=
23
github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU=
34
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
5+
github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38=
6+
github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
7+
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
8+
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
49
github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM=
510
github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
11+
github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8=
12+
github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw=
613
github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
714
github.com/spf13/cobra v1.5.0 h1:X+jTBEBqF0bHN+9cSMgmfuvv2VHJ9ezmFNf9Y/XstYU=
815
github.com/spf13/cobra v1.5.0/go.mod h1:dWXEIy2H428czQCjInthrTRUg7yKbok+2Qi/yBIJoUM=
16+
github.com/spf13/cobra v1.8.1 h1:e5/vxKd/rZsfSJMUX1agtjeTDf+qv1/JdBF8gg5k9ZM=
17+
github.com/spf13/cobra v1.8.1/go.mod h1:wHxEcudfqmLYa8iTfL+OuZPbBZkmvliBWKIezN3kD9Y=
918
github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
1019
github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA=
1120
github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
@@ -37,5 +46,8 @@ golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1N
3746
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
3847
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
3948
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
49+
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
4050
gotest.tools/v3 v3.3.0 h1:MfDY1b1/0xN1CyMlQDac0ziEy9zJQd9CXBRRDHw2jJo=
4151
gotest.tools/v3 v3.3.0/go.mod h1:Mcr9QNxkg0uMvy/YElmo4SpXgJKWgQvYrT7Kw5RzJ1A=
52+
gotest.tools/v3 v3.5.1 h1:EENdUnS3pdur5nybKYIh2Vfgc8IUNBjxDPSjtiJcOzU=
53+
gotest.tools/v3 v3.5.1/go.mod h1:isy3WKz7GK6uNw/sbHzfKBLvlvXwUyV06n6brMxxopU=

options.go

+49
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
package commandline
2+
3+
import (
4+
"io"
5+
6+
"github.com/spf13/cobra"
7+
)
8+
9+
// Option is used to configure an App.
10+
type Option func(*App)
11+
12+
// WithArgs creates an option which sets args.
13+
// Deprecated: use WithCommand instead.
14+
func WithArgs(args ...string) Option {
15+
return WithCommand(func(cmd *cobra.Command) {
16+
cmd.SetArgs(args)
17+
})
18+
}
19+
20+
// WithInput creates an option witch sets os.Stdin.
21+
// Deprecated: use WithCommand instead.
22+
func WithInput(in io.Reader) Option {
23+
return WithCommand(func(cmd *cobra.Command) {
24+
cmd.SetIn(in)
25+
})
26+
}
27+
28+
// WithOutput creates an option witch sets os.Stdout and os.Stderr.
29+
// Deprecated: use WithCommand instead.
30+
func WithOutput(out io.Writer) Option {
31+
return WithCommand(func(cmd *cobra.Command) {
32+
cmd.SetOut(out)
33+
cmd.SetErr(out)
34+
})
35+
}
36+
37+
// WithCommand will allow one to change the cobra.Command.
38+
func WithCommand(fn func(cmd *cobra.Command)) Option {
39+
return func(app *App) {
40+
fn(app.root)
41+
}
42+
}
43+
44+
// WithExit creates an option which sets the exit function.
45+
func WithExit(fn func(code int)) Option {
46+
return func(app *App) {
47+
app.Exit = fn
48+
}
49+
}

test/cmd/main_test.go

+5-3
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,11 @@ import (
44
"bytes"
55
"testing"
66

7+
"github.com/spf13/cobra"
8+
"github.com/wavesoftware/go-commandline"
79
main "github.com/wavesoftware/go-commandline/test/cmd"
810
"github.com/wavesoftware/go-commandline/test/internal/cli"
911
"gotest.tools/v3/assert"
10-
11-
"github.com/wavesoftware/go-commandline"
1212
)
1313

1414
func TestTheMain(t *testing.T) {
@@ -26,7 +26,9 @@ type state struct {
2626

2727
func (s *state) opts() []commandline.Option {
2828
return []commandline.Option{
29-
commandline.WithOutput(&s.out),
29+
commandline.WithCommand(func(cmd *cobra.Command) {
30+
cmd.SetOut(&s.out)
31+
}),
3032
commandline.WithExit(func(code int) {
3133
s.exitCode = code
3234
}),

test/internal/cli/app.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -6,14 +6,14 @@ import (
66
)
77

88
// Opts is the list of commandline options to pass to the main function.
9-
var Opts []commandline.Option
9+
var Opts []commandline.Option //nolint:gochecknoglobals
1010

1111
type App struct{}
1212

1313
func (a App) Command() *cobra.Command {
1414
return &cobra.Command{
1515
Use: "example",
16-
Run: func(cmd *cobra.Command, args []string) {
16+
Run: func(cmd *cobra.Command, _ []string) {
1717
cmd.Println("Hello, world!")
1818
},
1919
}

0 commit comments

Comments
 (0)