Skip to content

Commit 8c5498f

Browse files
committed
TUN-3715: Only read config file once, right before invoking the command
1 parent 2c746b3 commit 8c5498f

File tree

18 files changed

+125
-114
lines changed

18 files changed

+125
-114
lines changed

CHANGES.md

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,24 @@
11
**Experimental**: This is a new format for release notes. The format and availability is subject to change.
22

3+
## UNRELEASED
4+
5+
### Backward Incompatible Changes
6+
7+
- none
8+
9+
### New Features
10+
11+
- none
12+
13+
### Improvements
14+
15+
- nonw
16+
17+
### Bug Fixes
18+
19+
- Don't look for configuration file in default paths when `--config FILE` flag is present after `tunnel` subcommand.
20+
21+
322
## 2021.3.0
423

524
### New Features

cmd/cloudflared/access/cmd.go

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,7 @@ func Commands() []*cli.Command {
8484
Subcommands: []*cli.Command{
8585
{
8686
Name: "login",
87-
Action: cliutil.ErrorHandler(login),
87+
Action: cliutil.Action(login),
8888
Usage: "login <url of access application>",
8989
Description: `The login subcommand initiates an authentication flow with your identity provider.
9090
The subcommand will launch a browser. For headless systems, a url is provided.
@@ -100,7 +100,7 @@ func Commands() []*cli.Command {
100100
},
101101
{
102102
Name: "curl",
103-
Action: cliutil.ErrorHandler(curl),
103+
Action: cliutil.Action(curl),
104104
Usage: "curl [--allow-request, -ar] <url> [<curl args>...]",
105105
Description: `The curl subcommand wraps curl and automatically injects the JWT into a cf-access-token
106106
header when using curl to reach an application behind Access.`,
@@ -109,7 +109,7 @@ func Commands() []*cli.Command {
109109
},
110110
{
111111
Name: "token",
112-
Action: cliutil.ErrorHandler(generateToken),
112+
Action: cliutil.Action(generateToken),
113113
Usage: "token -app=<url of access application>",
114114
ArgsUsage: "url of Access application",
115115
Description: `The token subcommand produces a JWT which can be used to authenticate requests.`,
@@ -121,7 +121,7 @@ func Commands() []*cli.Command {
121121
},
122122
{
123123
Name: "tcp",
124-
Action: cliutil.ErrorHandler(ssh),
124+
Action: cliutil.Action(ssh),
125125
Aliases: []string{"rdp", "ssh", "smb"},
126126
Usage: "",
127127
ArgsUsage: "",
@@ -175,7 +175,7 @@ func Commands() []*cli.Command {
175175
},
176176
{
177177
Name: "ssh-config",
178-
Action: cliutil.ErrorHandler(sshConfig),
178+
Action: cliutil.Action(sshConfig),
179179
Usage: "",
180180
Description: `Prints an example configuration ~/.ssh/config`,
181181
Flags: []cli.Flag{
@@ -191,7 +191,7 @@ func Commands() []*cli.Command {
191191
},
192192
{
193193
Name: "ssh-gen",
194-
Action: cliutil.ErrorHandler(sshGen),
194+
Action: cliutil.Action(sshGen),
195195
Usage: "",
196196
Description: `Generates a short lived certificate for given hostname`,
197197
Flags: []cli.Flag{

cmd/cloudflared/cliutil/deprecated.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,12 @@ import (
99
func RemovedCommand(name string) *cli.Command {
1010
return &cli.Command{
1111
Name: name,
12-
Action: ErrorHandler(func(context *cli.Context) error {
12+
Action: func(context *cli.Context) error {
1313
return cli.Exit(
1414
fmt.Sprintf("%s command is no longer supported by cloudflared. Consult Argo Tunnel documentation for possible alternative solutions.", name),
1515
-1,
1616
)
17-
}),
17+
},
1818
Description: fmt.Sprintf("%s is deprecated", name),
1919
Hidden: true,
2020
}

cmd/cloudflared/cliutil/errors.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ package cliutil
22

33
import (
44
"fmt"
5+
56
"github.com/urfave/cli/v2"
67
)
78

@@ -21,7 +22,7 @@ func UsageError(format string, args ...interface{}) error {
2122
}
2223

2324
// Ensures exit with error code if actionFunc returns an error
24-
func ErrorHandler(actionFunc cli.ActionFunc) cli.ActionFunc {
25+
func WithErrorHandler(actionFunc cli.ActionFunc) cli.ActionFunc {
2526
return func(ctx *cli.Context) error {
2627
err := actionFunc(ctx)
2728
if err != nil {

cmd/cloudflared/cliutil/handler.go

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
package cliutil
2+
3+
import (
4+
"github.com/urfave/cli/v2"
5+
"github.com/urfave/cli/v2/altsrc"
6+
7+
"github.com/cloudflare/cloudflared/config"
8+
"github.com/cloudflare/cloudflared/logger"
9+
)
10+
11+
func Action(actionFunc cli.ActionFunc) cli.ActionFunc {
12+
return WithErrorHandler(func(c *cli.Context) error {
13+
if err := setFlagsFromConfigFile(c); err != nil {
14+
return err
15+
}
16+
return actionFunc(c)
17+
})
18+
}
19+
20+
func setFlagsFromConfigFile(c *cli.Context) error {
21+
const errorExitCode = 1
22+
log := logger.CreateLoggerFromContext(c, logger.EnableTerminalLog)
23+
inputSource, err := config.ReadConfigFile(c, log)
24+
if err != nil {
25+
if err == config.ErrNoConfigFile {
26+
return nil
27+
}
28+
return cli.Exit(err, errorExitCode)
29+
}
30+
31+
if err := applyConfig(c, inputSource); err != nil {
32+
return cli.Exit(err, errorExitCode)
33+
}
34+
return nil
35+
}
36+
37+
func applyConfig(c *cli.Context, inputSource altsrc.InputSourceContext) error {
38+
for _, context := range c.Lineage() {
39+
if context.Command == nil {
40+
// we've reached the placeholder root context not associated with the app
41+
break
42+
}
43+
targetFlags := context.Command.Flags
44+
if context.Command.Name == "" {
45+
// commands that define child subcommands are executed as if they were an app
46+
targetFlags = c.App.Flags
47+
}
48+
if err := altsrc.ApplyInputSourceValues(context, inputSource, targetFlags); err != nil {
49+
return err
50+
}
51+
}
52+
return nil
53+
}

cmd/cloudflared/linux_service.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ func runApp(app *cli.App, graceShutdownC chan struct{}) {
2424
{
2525
Name: "install",
2626
Usage: "Install Argo Tunnel as a system service",
27-
Action: cliutil.ErrorHandler(installLinuxService),
27+
Action: cliutil.Action(installLinuxService),
2828
Flags: []cli.Flag{
2929
&cli.BoolFlag{
3030
Name: "legacy",
@@ -35,7 +35,7 @@ func runApp(app *cli.App, graceShutdownC chan struct{}) {
3535
{
3636
Name: "uninstall",
3737
Usage: "Uninstall the Argo Tunnel service",
38-
Action: cliutil.ErrorHandler(uninstallLinuxService),
38+
Action: cliutil.Action(uninstallLinuxService),
3939
},
4040
},
4141
})

cmd/cloudflared/macos_service.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,12 +25,12 @@ func runApp(app *cli.App, graceShutdownC chan struct{}) {
2525
{
2626
Name: "install",
2727
Usage: "Install Argo Tunnel as an user launch agent",
28-
Action: cliutil.ErrorHandler(installLaunchd),
28+
Action: cliutil.Action(installLaunchd),
2929
},
3030
{
3131
Name: "uninstall",
3232
Usage: "Uninstall the Argo Tunnel launch agent",
33-
Action: cliutil.ErrorHandler(uninstallLaunchd),
33+
Action: cliutil.Action(uninstallLaunchd),
3434
},
3535
},
3636
})

cmd/cloudflared/main.go

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,6 @@ func main() {
7777
See https://developers.cloudflare.com/argo-tunnel/ for more in-depth documentation.`
7878
app.Flags = flags()
7979
app.Action = action(graceShutdownC)
80-
app.Before = tunnel.SetFlagsFromConfigFile
8180
app.Commands = commands(cli.ShowVersion)
8281

8382
tunnel.Init(Version, graceShutdownC) // we need this to support the tunnel sub command...
@@ -90,7 +89,7 @@ func commands(version func(c *cli.Context)) []*cli.Command {
9089
cmds := []*cli.Command{
9190
{
9291
Name: "update",
93-
Action: cliutil.ErrorHandler(updater.Update),
92+
Action: cliutil.Action(updater.Update),
9493
Usage: "Update the agent if a new version exists",
9594
Flags: []cli.Flag{
9695
&cli.BoolFlag{
@@ -145,7 +144,7 @@ func isEmptyInvocation(c *cli.Context) bool {
145144
}
146145

147146
func action(graceShutdownC chan struct{}) cli.ActionFunc {
148-
return cliutil.ErrorHandler(func(c *cli.Context) (err error) {
147+
return cliutil.Action(func(c *cli.Context) (err error) {
149148
if isEmptyInvocation(c) {
150149
return handleServiceMode(c, graceShutdownC)
151150
}

cmd/cloudflared/proxydns/cmd.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,8 @@ import (
1717
func Command(hidden bool) *cli.Command {
1818
return &cli.Command{
1919
Name: "proxy-dns",
20-
Action: cliutil.ErrorHandler(Run),
20+
Action: cliutil.Action(Run),
21+
2122
Usage: "Run a DNS over HTTPS proxy server.",
2223
Flags: []cli.Flag{
2324
&cli.StringFlag{

cmd/cloudflared/tunnel/cmd.go

Lines changed: 2 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ import (
77
"io/ioutil"
88
"net/url"
99
"os"
10-
"reflect"
1110
"runtime/trace"
1211
"strings"
1312
"sync"
@@ -120,8 +119,7 @@ func Commands() []*cli.Command {
120119
func buildTunnelCommand(subcommands []*cli.Command) *cli.Command {
121120
return &cli.Command{
122121
Name: "tunnel",
123-
Action: cliutil.ErrorHandler(TunnelCommand),
124-
Before: SetFlagsFromConfigFile,
122+
Action: cliutil.Action(TunnelCommand),
125123
Category: "Tunnel",
126124
Usage: "Make a locally-running web service accessible over the internet using Argo Tunnel.",
127125
ArgsUsage: " ",
@@ -369,26 +367,6 @@ func StartServer(
369367
return waitToShutdown(&wg, cancel, errC, graceShutdownC, c.Duration("grace-period"), log)
370368
}
371369

372-
func SetFlagsFromConfigFile(c *cli.Context) error {
373-
const exitCode = 1
374-
log := logger.CreateLoggerFromContext(c, logger.EnableTerminalLog)
375-
inputSource, err := config.ReadConfigFile(c, log)
376-
if err != nil {
377-
if err == config.ErrNoConfigFile {
378-
return nil
379-
}
380-
return cli.Exit(err, exitCode)
381-
}
382-
targetFlags := c.Command.Flags
383-
if c.Command.Name == "" {
384-
targetFlags = c.App.Flags
385-
}
386-
if err := altsrc.ApplyInputSourceValues(c, inputSource, targetFlags); err != nil {
387-
return cli.Exit(err, exitCode)
388-
}
389-
return nil
390-
}
391-
392370
func waitToShutdown(wg *sync.WaitGroup,
393371
cancelServerContext func(),
394372
errC <-chan error,
@@ -477,33 +455,6 @@ func addPortIfMissing(uri *url.URL, port int) string {
477455
return fmt.Sprintf("%s:%d", uri.Hostname(), port)
478456
}
479457

480-
// appendFlags will append extra flags to a slice of flags.
481-
//
482-
// The cli package will panic if two flags exist with the same name,
483-
// so if extraFlags contains a flag that was already defined, modify the
484-
// original flags to use the extra version.
485-
func appendFlags(flags []cli.Flag, extraFlags ...cli.Flag) []cli.Flag {
486-
for _, extra := range extraFlags {
487-
var found bool
488-
489-
// Check if an extra flag overrides an existing flag.
490-
for i, flag := range flags {
491-
if reflect.DeepEqual(extra.Names(), flag.Names()) {
492-
flags[i] = extra
493-
found = true
494-
break
495-
}
496-
}
497-
498-
// Append the extra flag if it has nothing to override.
499-
if !found {
500-
flags = append(flags, extra)
501-
}
502-
}
503-
504-
return flags
505-
}
506-
507458
func tunnelFlags(shouldHide bool) []cli.Flag {
508459
flags := configureCloudflaredFlags(shouldHide)
509460
flags = append(flags, configureProxyFlags(shouldHide)...)
@@ -652,6 +603,7 @@ func tunnelFlags(shouldHide bool) []cli.Flag {
652603
Aliases: []string{"n"},
653604
EnvVars: []string{"TUNNEL_NAME"},
654605
Usage: "Stable name to identify the tunnel. Using this flag will create, route and run a tunnel. For production usage, execute each command separately",
606+
Hidden: shouldHide,
655607
}),
656608
altsrc.NewBoolFlag(&cli.BoolFlag{
657609
Name: uiFlag,

0 commit comments

Comments
 (0)