github.com/anchore/syft@v1.38.2/cmd/syft/internal/options/registry.go (about) 1 package options 2 3 import ( 4 "os" 5 6 "github.com/anchore/clio" 7 "github.com/anchore/stereoscope/pkg/image" 8 ) 9 10 type RegistryCredentials struct { 11 Authority string `yaml:"authority" json:"authority" mapstructure:"authority"` 12 // IMPORTANT: do not show any credential information, use secret type to automatically redact the values 13 Username secret `yaml:"username" json:"username" mapstructure:"username"` 14 Password secret `yaml:"password" json:"password" mapstructure:"password"` 15 Token secret `yaml:"token" json:"token" mapstructure:"token"` 16 17 TLSCert string `yaml:"tls-cert,omitempty" json:"tls-cert,omitempty" mapstructure:"tls-cert"` 18 TLSKey string `yaml:"tls-key,omitempty" json:"tls-key,omitempty" mapstructure:"tls-key"` 19 } 20 21 type registryConfig struct { 22 InsecureSkipTLSVerify bool `yaml:"insecure-skip-tls-verify" json:"insecure-skip-tls-verify" mapstructure:"insecure-skip-tls-verify"` 23 InsecureUseHTTP bool `yaml:"insecure-use-http" json:"insecure-use-http" mapstructure:"insecure-use-http"` 24 Auth []RegistryCredentials `yaml:"auth" json:"auth" mapstructure:"auth"` 25 CACert string `yaml:"ca-cert" json:"ca-cert" mapstructure:"ca-cert"` 26 } 27 28 var _ interface { 29 clio.PostLoader 30 clio.FieldDescriber 31 } = (*registryConfig)(nil) 32 33 func (cfg *registryConfig) PostLoad() error { 34 // there may be additional credentials provided by env var that should be appended to the set of credentials 35 authority, username, password, token, tlsCert, tlsKey := 36 os.Getenv("SYFT_REGISTRY_AUTH_AUTHORITY"), 37 os.Getenv("SYFT_REGISTRY_AUTH_USERNAME"), 38 os.Getenv("SYFT_REGISTRY_AUTH_PASSWORD"), 39 os.Getenv("SYFT_REGISTRY_AUTH_TOKEN"), 40 os.Getenv("SYFT_REGISTRY_AUTH_TLS_CERT"), 41 os.Getenv("SYFT_REGISTRY_AUTH_TLS_KEY") 42 43 if hasNonEmptyCredentials(username, password, token, tlsCert, tlsKey) { 44 // note: we prepend the credentials such that the environment variables take precedence over on-disk configuration. 45 // since this PostLoad is called before the PostLoad on the Auth credentials list, 46 // all appropriate redactions will be added 47 cfg.Auth = append([]RegistryCredentials{ 48 { 49 Authority: authority, 50 Username: secret(username), 51 Password: secret(password), 52 Token: secret(token), 53 TLSCert: tlsCert, 54 TLSKey: tlsKey, 55 }, 56 }, cfg.Auth...) 57 } 58 return nil 59 } 60 61 func (cfg *registryConfig) DescribeFields(descriptions clio.FieldDescriptionSet) { 62 descriptions.Add(&cfg.InsecureSkipTLSVerify, "skip TLS verification when communicating with the registry") 63 descriptions.Add(&cfg.InsecureUseHTTP, "use http instead of https when connecting to the registry") 64 descriptions.Add(&cfg.CACert, "filepath to a CA certificate (or directory containing *.crt, *.cert, *.pem) used to generate the client certificate") 65 descriptions.Add(&cfg.Auth, `Authentication credentials for specific registries. Each entry describes authentication for a specific authority: 66 - authority: the registry authority URL the URL to the registry (e.g. "docker.io", "localhost:5000", etc.) (env: SYFT_REGISTRY_AUTH_AUTHORITY) 67 username: a username if using basic credentials (env: SYFT_REGISTRY_AUTH_USERNAME) 68 password: a corresponding password (env: SYFT_REGISTRY_AUTH_PASSWORD) 69 token: a token if using token-based authentication, mutually exclusive with username/password (env: SYFT_REGISTRY_AUTH_TOKEN) 70 tls-cert: filepath to the client certificate used for TLS authentication to the registry (env: SYFT_REGISTRY_AUTH_TLS_CERT) 71 tls-key: filepath to the client key used for TLS authentication to the registry (env: SYFT_REGISTRY_AUTH_TLS_KEY) 72 `) 73 } 74 75 func hasNonEmptyCredentials(username, password, token, tlsCert, tlsKey string) bool { 76 hasUserPass := username != "" && password != "" 77 hasToken := token != "" 78 hasTLSMaterial := tlsCert != "" && tlsKey != "" 79 return hasUserPass || hasToken || hasTLSMaterial 80 } 81 82 func (cfg *registryConfig) ToOptions() *image.RegistryOptions { 83 var auth = make([]image.RegistryCredentials, len(cfg.Auth)) 84 for i, a := range cfg.Auth { 85 auth[i] = image.RegistryCredentials{ 86 Authority: a.Authority, 87 Username: a.Username.String(), 88 Password: a.Password.String(), 89 Token: a.Token.String(), 90 ClientCert: a.TLSCert, 91 ClientKey: a.TLSKey, 92 } 93 } 94 95 return &image.RegistryOptions{ 96 InsecureSkipTLSVerify: cfg.InsecureSkipTLSVerify, 97 InsecureUseHTTP: cfg.InsecureUseHTTP, 98 Credentials: auth, 99 CAFileOrDir: cfg.CACert, 100 } 101 }