func newAuthenticator(config configapi.MasterConfig, restOptionsGetter restoptions.Getter, tokenGetter serviceaccount.ServiceAccountTokenGetter, apiClientCAs *x509.CertPool, groupMapper identitymapper.UserToGroupMapper) (authenticator.Request, error) { authenticators := []authenticator.Request{} // ServiceAccount token if len(config.ServiceAccountConfig.PublicKeyFiles) > 0 { publicKeys := []*rsa.PublicKey{} for _, keyFile := range config.ServiceAccountConfig.PublicKeyFiles { publicKey, err := serviceaccount.ReadPublicKey(keyFile) if err != nil { return nil, fmt.Errorf("Error reading service account key file %s: %v", keyFile, err) } publicKeys = append(publicKeys, publicKey) } tokenAuthenticator := serviceaccount.JWTTokenAuthenticator(publicKeys, true, tokenGetter) authenticators = append(authenticators, bearertoken.New(tokenAuthenticator, true)) } // OAuth token if config.OAuthConfig != nil { tokenAuthenticator, err := getEtcdTokenAuthenticator(restOptionsGetter, groupMapper) if err != nil { return nil, fmt.Errorf("Error building OAuth token authenticator: %v", err) } tokenRequestAuthenticators := []authenticator.Request{ bearertoken.New(tokenAuthenticator, true), // Allow token as access_token param for WebSockets paramtoken.New("access_token", tokenAuthenticator, true), } authenticators = append(authenticators, // if you have a bearer token, you're a human (usually) // if you change this, have a look at the impersonationFilter where we attach groups to the impersonated user group.NewGroupAdder(unionrequest.NewUnionAuthentication(tokenRequestAuthenticators...), []string{bootstrappolicy.AuthenticatedOAuthGroup})) } if configapi.UseTLS(config.ServingInfo.ServingInfo) { // build cert authenticator // TODO: add "system:" prefix in authenticator, limit cert to username // TODO: add "system:" prefix to groups in authenticator, limit cert to group name opts := x509request.DefaultVerifyOptions() opts.Roots = apiClientCAs certauth := x509request.New(opts, x509request.SubjectToUserConversion) authenticators = append(authenticators, certauth) } ret := &unionrequest.Authenticator{ FailOnError: true, Handlers: []authenticator.Request{ // if you change this, have a look at the impersonationFilter where we attach groups to the impersonated user group.NewGroupAdder(unionrequest.NewUnionAuthentication(authenticators...), []string{bootstrappolicy.AuthenticatedGroup}), anonymous.NewAuthenticator(), }, } return ret, nil }
func (c *AuthConfig) getAuthenticationRequestHandler() (authenticator.Request, error) { var authRequestHandlers []authenticator.Request if c.SessionAuth != nil { authRequestHandlers = append(authRequestHandlers, c.SessionAuth) } for _, identityProvider := range c.Options.IdentityProviders { identityMapper, err := identitymapper.NewIdentityUserMapper(c.IdentityRegistry, c.UserRegistry, identitymapper.MappingMethodType(identityProvider.MappingMethod)) if err != nil { return nil, err } if configapi.IsPasswordAuthenticator(identityProvider) { passwordAuthenticator, err := c.getPasswordAuthenticator(identityProvider) if err != nil { return nil, err } authRequestHandlers = append(authRequestHandlers, basicauthrequest.NewBasicAuthAuthentication(identityProvider.Name, passwordAuthenticator, true)) } else { switch provider := identityProvider.Provider.(type) { case (*configapi.RequestHeaderIdentityProvider): var authRequestHandler authenticator.Request authRequestConfig := &headerrequest.Config{ IDHeaders: provider.Headers, NameHeaders: provider.NameHeaders, EmailHeaders: provider.EmailHeaders, PreferredUsernameHeaders: provider.PreferredUsernameHeaders, } authRequestHandler = headerrequest.NewAuthenticator(identityProvider.Name, authRequestConfig, identityMapper) // Wrap with an x509 verifier if len(provider.ClientCA) > 0 { caData, err := ioutil.ReadFile(provider.ClientCA) if err != nil { return nil, fmt.Errorf("Error reading %s: %v", provider.ClientCA, err) } opts := x509request.DefaultVerifyOptions() opts.Roots = x509.NewCertPool() if ok := opts.Roots.AppendCertsFromPEM(caData); !ok { return nil, fmt.Errorf("Error loading certs from %s: %v", provider.ClientCA, err) } authRequestHandler = x509request.NewVerifier(opts, authRequestHandler, sets.NewString(provider.ClientCommonNames...)) } authRequestHandlers = append(authRequestHandlers, authRequestHandler) } } } authRequestHandler := unionrequest.NewUnionAuthentication(authRequestHandlers...) return authRequestHandler, nil }
func newAuthenticator(config configapi.MasterConfig, etcdHelper storage.Interface, tokenGetter serviceaccount.ServiceAccountTokenGetter, apiClientCAs *x509.CertPool, groupMapper identitymapper.UserToGroupMapper) authenticator.Request { authenticators := []authenticator.Request{} // ServiceAccount token if len(config.ServiceAccountConfig.PublicKeyFiles) > 0 { publicKeys := []*rsa.PublicKey{} for _, keyFile := range config.ServiceAccountConfig.PublicKeyFiles { publicKey, err := serviceaccount.ReadPublicKey(keyFile) if err != nil { glog.Fatalf("Error reading service account key file %s: %v", keyFile, err) } publicKeys = append(publicKeys, publicKey) } tokenAuthenticator := serviceaccount.JWTTokenAuthenticator(publicKeys, true, tokenGetter) authenticators = append(authenticators, bearertoken.New(tokenAuthenticator, true)) } // OAuth token if config.OAuthConfig != nil { tokenAuthenticator := getEtcdTokenAuthenticator(etcdHelper, groupMapper) authenticators = append(authenticators, bearertoken.New(tokenAuthenticator, true)) // Allow token as access_token param for WebSockets authenticators = append(authenticators, paramtoken.New("access_token", tokenAuthenticator, true)) } if configapi.UseTLS(config.ServingInfo.ServingInfo) { // build cert authenticator // TODO: add "system:" prefix in authenticator, limit cert to username // TODO: add "system:" prefix to groups in authenticator, limit cert to group name opts := x509request.DefaultVerifyOptions() opts.Roots = apiClientCAs certauth := x509request.New(opts, x509request.SubjectToUserConversion) authenticators = append(authenticators, certauth) } // TODO: make anonymous auth optional? ret := &unionrequest.Authenticator{ FailOnError: true, Handlers: []authenticator.Request{ group.NewGroupAdder(unionrequest.NewUnionAuthentication(authenticators...), []string{bootstrappolicy.AuthenticatedGroup}), authenticator.RequestFunc(func(req *http.Request) (user.Info, bool, error) { return &user.DefaultInfo{Name: unauthenticatedUsername, Groups: []string{bootstrappolicy.UnauthenticatedGroup}}, true, nil }), }, } return ret }
func newAuthenticator(authenticationClient unversionedauthentication.TokenReviewsGetter, clientCAs *x509.CertPool, cacheTTL time.Duration, cacheSize int) (authenticator.Request, error) { authenticators := []oauthenticator.Request{} // API token auth var ( tokenAuthenticator oauthenticator.Token err error ) // Authenticate against the remote master tokenAuthenticator, err = authnremote.NewAuthenticator(authenticationClient) if err != nil { return nil, err } // Cache results if cacheTTL > 0 && cacheSize > 0 { tokenAuthenticator, err = authncache.NewAuthenticator(tokenAuthenticator, cacheTTL, cacheSize) if err != nil { return nil, err } } authenticators = append(authenticators, bearertoken.New(tokenAuthenticator, true)) // Client-cert auth if clientCAs != nil { opts := x509request.DefaultVerifyOptions() opts.Roots = clientCAs certauth := x509request.New(opts, x509request.SubjectToUserConversion) authenticators = append(authenticators, certauth) } ret := &unionrequest.Authenticator{ // Anonymous requests will pass the token and cert checks without errors // Bad tokens or bad certs will produce errors, in which case we should not continue to authenticate them as "system:anonymous" FailOnError: true, Handlers: []oauthenticator.Request{ // Add the "system:authenticated" group to users that pass token/cert authentication group.NewGroupAdder(unionrequest.NewUnionAuthentication(authenticators...), []string{bootstrappolicy.AuthenticatedGroup}), // Fall back to the "system:anonymous" user anonymous.NewAuthenticator(), }, } return ret, nil }