// Validate check if all necessary fields from CreateBasicAuthSecretOptions are present. func (o CreateBasicAuthSecretOptions) Validate() error { if len(o.SecretName) == 0 { return errors.New("basic authentication secret name must be present") } if o.PromptForPassword { if len(o.Password) != 0 { return errors.New("must provide either --prompt or --password flag") } if cmdutil.IsTerminal(o.Reader) { o.Password = cmdutil.PromptForPasswordString(o.Reader, o.Out, "Password: "******"password must be provided") } } else { return errors.New("provided reader is not a terminal") } } else { if len(o.Username) == 0 && len(o.Password) == 0 && len(o.CertificatePath) == 0 { return errors.New("must provide basic authentication credentials") } } return nil }
// Complete fills CreateBasicAuthSecretOptions fields with data and checks for mutual exclusivity // between flags from different option groups. func (o *CreateBasicAuthSecretOptions) Complete(f *kcmdutil.Factory, args []string) error { if len(args) != 1 { return errors.New("must have exactly one argument: secret name") } o.SecretName = args[0] if o.PromptForPassword { if len(o.Password) != 0 { return errors.New("must provide either --prompt or --password flag") } if !term.IsTerminal(o.Reader) { return errors.New("provided reader is not a terminal") } o.Password = cmdutil.PromptForPasswordString(o.Reader, o.Out, "Password: "******"password must be provided") } } if f != nil { client, err := f.Client() if err != nil { return err } namespace, _, err := f.DefaultNamespace() if err != nil { return err } o.SecretsInterface = client.Secrets(namespace) } return nil }
func (c *BasicChallengeHandler) HandleChallenge(requestURL string, headers http.Header) (http.Header, bool, error) { if c.prompted { glog.V(2).Info("already prompted for challenge, won't prompt again") return nil, false, nil } if c.handled { glog.V(2).Info("already handled basic challenge") return nil, false, nil } username := c.Username password := c.Password missingUsername := len(username) == 0 missingPassword := len(password) == 0 if (missingUsername || missingPassword) && c.Reader != nil { w := c.Writer if w == nil { w = os.Stdout } if _, realm := basicRealm(headers); len(realm) > 0 { fmt.Fprintf(w, "Authentication required for %s (%s)\n", c.Host, realm) } else { fmt.Fprintf(w, "Authentication required for %s\n", c.Host) } if missingUsername { username = util.PromptForString(c.Reader, w, "Username: "******"Username: %s\n", username) } if missingPassword { password = util.PromptForPasswordString(c.Reader, w, "Password: "******":") { return nil, false, fmt.Errorf("username %s is invalid for basic auth", username) } responseHeaders := http.Header{} responseHeaders.Set("Authorization", getBasicHeader(username, password)) // remember so we don't re-handle non-interactively c.handled = true return responseHeaders, true, nil } glog.V(2).Info("no username or password available") return nil, false, nil }
func (c *BasicChallengeHandler) HandleChallenge(headers http.Header) (http.Header, bool, error) { if c.prompted { glog.V(2).Info("already prompted for challenge, won't prompt again") return nil, false, nil } if c.Reader == nil && c.handled { glog.V(2).Info("already handled basic challenge, no reader to alter inputs") return nil, false, nil } username := c.Username password := c.Password missingUsername := len(username) == 0 missingPassword := len(password) == 0 if (missingUsername || missingPassword) && c.Reader != nil { w := c.Writer if w == nil { w = os.Stdout } if _, realm := basicRealm(headers); len(realm) > 0 { fmt.Fprintf(w, "Authentication required for %s (%s)\n", c.Host, realm) } else { fmt.Fprintf(w, "Authentication required for %s\n", c.Host) } if missingUsername { username = util.PromptForString(c.Reader, w, "Username: "******"Username: %s\n", username) } if missingPassword { password = util.PromptForPasswordString(c.Reader, w, "Password: "******"Authorization", getBasicHeader(username, password)) // remember so we don't re-handle non-interactively c.handled = true return responseHeaders, true, nil } glog.V(2).Info("no username or password available") return nil, false, nil }
// Do watches for unauthorized challenges. If we know to respond, we respond to the challenge func (client *challengingClient) Do(req *http.Request) (*http.Response, error) { // Set custom header required by server to avoid CSRF attacks on browsers using basic auth if req.Header == nil { req.Header = http.Header{} } req.Header.Set(CSRFTokenHeader, "1") resp, err := client.delegate.Do(req) if err != nil { return nil, err } if resp.StatusCode == http.StatusUnauthorized { if wantsBasicAuth, realm := isBasicAuthChallenge(resp); wantsBasicAuth { username := client.defaultUsername password := client.defaultPassword missingUsername := len(username) == 0 missingPassword := len(password) == 0 url := *req.URL url.Path, url.RawQuery, url.Fragment = "", "", "" if (missingUsername || missingPassword) && client.reader != nil { fmt.Printf("Authentication required for %s (%s)\n", &url, realm) if missingUsername { username = util.PromptForString(client.reader, "Username: "******"Password: ") } } if len(username) > 0 || len(password) > 0 { client.delegate.Transport = kclient.NewBasicAuthRoundTripper(username, password, client.delegate.Transport) return client.delegate.Do(resp.Request) } } } return resp, err }