2016-02-19 17:42:51 -05:00
package flags
import (
"fmt"
"os"
"path/filepath"
2017-04-17 18:07:56 -04:00
cliconfig "github.com/docker/cli/cli/config"
2017-05-15 08:45:19 -04:00
"github.com/docker/cli/opts"
2016-02-19 17:42:51 -05:00
"github.com/docker/go-connections/tlsconfig"
2017-08-07 05:52:40 -04:00
"github.com/sirupsen/logrus"
2016-06-21 16:42:47 -04:00
"github.com/spf13/pflag"
2016-02-19 17:42:51 -05:00
)
const (
// DefaultCaFile is the default filename for the CA pem file
DefaultCaFile = "ca.pem"
// DefaultKeyFile is the default filename for the key pem file
DefaultKeyFile = "key.pem"
// DefaultCertFile is the default filename for the cert pem file
DefaultCertFile = "cert.pem"
2016-12-20 06:14:41 -05:00
// FlagTLSVerify is the flag name for the TLS verification option
2016-06-21 16:42:47 -04:00
FlagTLSVerify = "tlsverify"
2016-02-19 17:42:51 -05:00
)
var (
dockerCertPath = os . Getenv ( "DOCKER_CERT_PATH" )
dockerTLSVerify = os . Getenv ( "DOCKER_TLS_VERIFY" ) != ""
2018-02-06 03:27:05 -05:00
dockerTLS = os . Getenv ( "DOCKER_TLS" ) != ""
2016-02-19 17:42:51 -05:00
)
2016-06-21 16:42:47 -04:00
// CommonOptions are options common to both the client and the daemon.
type CommonOptions struct {
2017-12-20 13:06:15 -05:00
Debug bool
Hosts [ ] string
Orchestrator string
LogLevel string
TLS bool
TLSVerify bool
TLSOptions * tlsconfig . Options
2016-04-21 17:51:28 -04:00
}
2016-06-21 16:42:47 -04:00
// NewCommonOptions returns a new CommonOptions
func NewCommonOptions ( ) * CommonOptions {
2016-06-22 18:36:51 -04:00
return & CommonOptions { }
2016-06-21 16:42:47 -04:00
}
2016-02-19 17:42:51 -05:00
2016-06-21 16:42:47 -04:00
// InstallFlags adds flags for the common options on the FlagSet
func ( commonOpts * CommonOptions ) InstallFlags ( flags * pflag . FlagSet ) {
2016-02-19 17:42:51 -05:00
if dockerCertPath == "" {
2016-12-25 14:31:52 -05:00
dockerCertPath = cliconfig . Dir ( )
2016-02-19 17:42:51 -05:00
}
2016-06-21 16:42:47 -04:00
flags . BoolVarP ( & commonOpts . Debug , "debug" , "D" , false , "Enable debug mode" )
2017-02-08 03:31:16 -05:00
flags . StringVarP ( & commonOpts . LogLevel , "log-level" , "l" , "info" , ` Set the logging level ("debug"|"info"|"warn"|"error"|"fatal") ` )
2018-02-06 03:27:05 -05:00
flags . BoolVar ( & commonOpts . TLS , "tls" , dockerTLS , "Use TLS; implied by --tlsverify" )
2016-06-21 16:42:47 -04:00
flags . BoolVar ( & commonOpts . TLSVerify , FlagTLSVerify , dockerTLSVerify , "Use TLS and verify the remote" )
2018-01-02 17:56:07 -05:00
flags . StringVar ( & commonOpts . Orchestrator , "orchestrator" , "" , "Which orchestrator to use with the docker cli (swarm|kubernetes) (default swarm) (experimental)" )
flags . SetAnnotation ( "orchestrator" , "experimentalCLI" , nil )
2016-02-19 17:42:51 -05:00
2016-06-21 16:42:47 -04:00
// TODO use flag flags.String("identity"}, "i", "", "Path to libtrust key file")
2016-02-19 17:42:51 -05:00
2017-01-03 15:58:41 -05:00
commonOpts . TLSOptions = & tlsconfig . Options {
CAFile : filepath . Join ( dockerCertPath , DefaultCaFile ) ,
CertFile : filepath . Join ( dockerCertPath , DefaultCertFile ) ,
KeyFile : filepath . Join ( dockerCertPath , DefaultKeyFile ) ,
}
2016-06-21 16:42:47 -04:00
tlsOptions := commonOpts . TLSOptions
2017-01-03 15:58:41 -05:00
flags . Var ( opts . NewQuotedString ( & tlsOptions . CAFile ) , "tlscacert" , "Trust certs signed only by this CA" )
flags . Var ( opts . NewQuotedString ( & tlsOptions . CertFile ) , "tlscert" , "Path to TLS certificate file" )
flags . Var ( opts . NewQuotedString ( & tlsOptions . KeyFile ) , "tlskey" , "Path to TLS key file" )
2016-02-19 17:42:51 -05:00
2016-06-21 16:42:47 -04:00
hostOpt := opts . NewNamedListOptsRef ( "hosts" , & commonOpts . Hosts , opts . ValidateHost )
2016-06-22 18:36:51 -04:00
flags . VarP ( hostOpt , "host" , "H" , "Daemon socket(s) to connect to" )
2016-02-19 17:42:51 -05:00
}
2016-06-21 16:42:47 -04:00
// SetDefaultOptions sets default values for options after flag parsing is
// complete
func ( commonOpts * CommonOptions ) SetDefaultOptions ( flags * pflag . FlagSet ) {
2016-02-19 17:42:51 -05:00
// Regardless of whether the user sets it to true or false, if they
2016-12-20 06:14:41 -05:00
// specify --tlsverify at all then we need to turn on TLS
2016-02-19 17:42:51 -05:00
// TLSVerify can be true even if not set due to DOCKER_TLS_VERIFY env var, so we need
// to check that here as well
2016-06-21 16:42:47 -04:00
if flags . Changed ( FlagTLSVerify ) || commonOpts . TLSVerify {
commonOpts . TLS = true
2016-02-19 17:42:51 -05:00
}
2016-06-21 16:42:47 -04:00
if ! commonOpts . TLS {
commonOpts . TLSOptions = nil
2016-02-19 17:42:51 -05:00
} else {
2016-06-21 16:42:47 -04:00
tlsOptions := commonOpts . TLSOptions
tlsOptions . InsecureSkipVerify = ! commonOpts . TLSVerify
2016-02-19 17:42:51 -05:00
// Reset CertFile and KeyFile to empty string if the user did not specify
// the respective flags and the respective default files were not found.
2016-06-21 16:42:47 -04:00
if ! flags . Changed ( "tlscert" ) {
2016-02-19 17:42:51 -05:00
if _ , err := os . Stat ( tlsOptions . CertFile ) ; os . IsNotExist ( err ) {
tlsOptions . CertFile = ""
}
}
2016-06-21 16:42:47 -04:00
if ! flags . Changed ( "tlskey" ) {
2016-02-19 17:42:51 -05:00
if _ , err := os . Stat ( tlsOptions . KeyFile ) ; os . IsNotExist ( err ) {
tlsOptions . KeyFile = ""
}
}
}
}
2016-10-11 07:35:12 -04:00
// SetLogLevel sets the logrus logging level
func SetLogLevel ( logLevel string ) {
2016-02-19 17:42:51 -05:00
if logLevel != "" {
lvl , err := logrus . ParseLevel ( logLevel )
if err != nil {
fmt . Fprintf ( os . Stderr , "Unable to parse logging level: %s\n" , logLevel )
os . Exit ( 1 )
}
logrus . SetLevel ( lvl )
} else {
logrus . SetLevel ( logrus . InfoLevel )
}
}