@@ -20,11 +20,17 @@ type App struct {
20
20
Commands []Command
21
21
// List of flags to parse
22
22
Flags []Flag
23
+ // Boolean to enable bash completion commands
24
+ EnableBashCompletion bool
25
+ // An action to execute when the bash-completion flag is set
26
+ BashComplete func (context * Context )
23
27
// An action to execute before any subcommands are run, but after the context is ready
24
28
// If a non-nil error is returned, no subcommands are run
25
29
Before func (context * Context ) error
26
30
// The action to execute when no subcommands are specified
27
31
Action func (context * Context )
32
+ // Execute this function if the proper command cannot be found
33
+ CommandNotFound func (context * Context , command string )
28
34
// Compilation date
29
35
Compiled time.Time
30
36
// Author
@@ -46,13 +52,14 @@ func compileTime() time.Time {
46
52
// Creates a new cli Application with some reasonable defaults for Name, Usage, Version and Action.
47
53
func NewApp () * App {
48
54
return & App {
49
- Name : os .Args [0 ],
50
- Usage : "A new cli application" ,
51
- Version : "0.0.0" ,
52
- Action : helpCommand .Action ,
53
- Compiled : compileTime (),
54
- Author : "Author" ,
55
- Email : "unknown@email" ,
55
+ Name : os .Args [0 ],
56
+ Usage : "A new cli application" ,
57
+ Version : "0.0.0" ,
58
+ BashComplete : DefaultAppComplete ,
59
+ Action : helpCommand .Action ,
60
+ Compiled : compileTime (),
61
+ Author : "Author" ,
62
+ Email : "unknown@email" ,
56
63
}
57
64
}
58
65
@@ -64,8 +71,11 @@ func (a *App) Run(arguments []string) error {
64
71
}
65
72
66
73
//append version/help flags
67
- a .appendFlag (BoolFlag {"version, v" , "print the version" })
68
- a .appendFlag (BoolFlag {"help, h" , "show help" })
74
+ if a .EnableBashCompletion {
75
+ a .appendFlag (BashCompletionFlag )
76
+ }
77
+ a .appendFlag (VersionFlag )
78
+ a .appendFlag (HelpFlag )
69
79
70
80
// parse flags
71
81
set := flagSet (a .Name , a .Flags )
@@ -88,6 +98,10 @@ func (a *App) Run(arguments []string) error {
88
98
return err
89
99
}
90
100
101
+ if checkCompletions (context ) {
102
+ return nil
103
+ }
104
+
91
105
if checkHelp (context ) {
92
106
return nil
93
107
}
@@ -117,6 +131,85 @@ func (a *App) Run(arguments []string) error {
117
131
return nil
118
132
}
119
133
134
+ // Invokes the subcommand given the context, parses ctx.Args() to generate command-specific flags
135
+ func (a * App ) RunAsSubcommand (ctx * Context ) error {
136
+ // append help to commands
137
+ if len (a .Commands ) > 0 {
138
+ if a .Command (helpCommand .Name ) == nil {
139
+ a .Commands = append (a .Commands , helpCommand )
140
+ }
141
+ }
142
+
143
+ // append flags
144
+ if a .EnableBashCompletion {
145
+ a .appendFlag (BashCompletionFlag )
146
+ }
147
+ a .appendFlag (HelpFlag )
148
+
149
+ // parse flags
150
+ set := flagSet (a .Name , a .Flags )
151
+ set .SetOutput (ioutil .Discard )
152
+ err := set .Parse (ctx .Args ().Tail ())
153
+ nerr := normalizeFlags (a .Flags , set )
154
+ context := NewContext (a , set , set )
155
+
156
+ if nerr != nil {
157
+ fmt .Println (nerr )
158
+ if len (a .Commands ) > 0 {
159
+ ShowSubcommandHelp (context )
160
+ } else {
161
+ ShowCommandHelp (ctx , context .Args ().First ())
162
+ }
163
+ fmt .Println ("" )
164
+ return nerr
165
+ }
166
+
167
+ if err != nil {
168
+ fmt .Printf ("Incorrect Usage.\n \n " )
169
+ ShowSubcommandHelp (context )
170
+ return err
171
+ }
172
+
173
+ if checkCompletions (context ) {
174
+ return nil
175
+ }
176
+
177
+ if len (a .Commands ) > 0 {
178
+ if checkSubcommandHelp (context ) {
179
+ return nil
180
+ }
181
+ } else {
182
+ if checkCommandHelp (ctx , context .Args ().First ()) {
183
+ return nil
184
+ }
185
+ }
186
+
187
+ if a .Before != nil {
188
+ err := a .Before (context )
189
+ if err != nil {
190
+ return err
191
+ }
192
+ }
193
+
194
+ args := context .Args ()
195
+ if args .Present () {
196
+ name := args .First ()
197
+ c := a .Command (name )
198
+ if c != nil {
199
+ return c .Run (context )
200
+ }
201
+ }
202
+
203
+ // Run default Action
204
+ if len (a .Commands ) > 0 {
205
+ a .Action (context )
206
+ } else {
207
+ a .Action (ctx )
208
+ }
209
+
210
+ return nil
211
+ }
212
+
120
213
// Returns the named command on App. Returns nil if the command does not exist
121
214
func (a * App ) Command (name string ) * Command {
122
215
for _ , c := range a .Commands {
0 commit comments