Merge pull request #125836 from mjudeikis/mjudeikis/auth.token.getter
Extend service accounts with optional tokenGetter provider
This commit is contained in:
		@@ -132,6 +132,9 @@ type ServiceAccountAuthenticationOptions struct {
 | 
			
		||||
	JWKSURI          string
 | 
			
		||||
	MaxExpiration    time.Duration
 | 
			
		||||
	ExtendExpiration bool
 | 
			
		||||
	// OptionalTokenGetter is a function that returns a service account token getter.
 | 
			
		||||
	// If not set, the default token getter will be used.
 | 
			
		||||
	OptionalTokenGetter func(factory informers.SharedInformerFactory) serviceaccount.ServiceAccountTokenGetter
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// TokenFileAuthenticationOptions contains token file authentication options for API Server
 | 
			
		||||
@@ -207,7 +210,20 @@ func (o *BuiltInAuthenticationOptions) WithRequestHeader() *BuiltInAuthenticatio
 | 
			
		||||
 | 
			
		||||
// WithServiceAccounts set default value for service account authentication
 | 
			
		||||
func (o *BuiltInAuthenticationOptions) WithServiceAccounts() *BuiltInAuthenticationOptions {
 | 
			
		||||
	o.ServiceAccounts = &ServiceAccountAuthenticationOptions{Lookup: true, ExtendExpiration: true}
 | 
			
		||||
	if o.ServiceAccounts == nil {
 | 
			
		||||
		o.ServiceAccounts = &ServiceAccountAuthenticationOptions{}
 | 
			
		||||
	}
 | 
			
		||||
	o.ServiceAccounts.Lookup = true
 | 
			
		||||
	o.ServiceAccounts.ExtendExpiration = true
 | 
			
		||||
	return o
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// WithTokenGetterFunction set optional service account token getter function
 | 
			
		||||
func (o *BuiltInAuthenticationOptions) WithTokenGetterFunction(f func(factory informers.SharedInformerFactory) serviceaccount.ServiceAccountTokenGetter) *BuiltInAuthenticationOptions {
 | 
			
		||||
	if o.ServiceAccounts == nil {
 | 
			
		||||
		o.ServiceAccounts = &ServiceAccountAuthenticationOptions{}
 | 
			
		||||
	}
 | 
			
		||||
	o.ServiceAccounts.OptionalTokenGetter = f
 | 
			
		||||
	return o
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -673,6 +689,11 @@ func (o *BuiltInAuthenticationOptions) ApplyTo(
 | 
			
		||||
	if utilfeature.DefaultFeatureGate.Enabled(features.ServiceAccountTokenNodeBindingValidation) {
 | 
			
		||||
		nodeLister = versionedInformer.Core().V1().Nodes().Lister()
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// If the optional token getter function is set, use it. Otherwise, use the default token getter.
 | 
			
		||||
	if o.ServiceAccounts != nil && o.ServiceAccounts.OptionalTokenGetter != nil {
 | 
			
		||||
		authenticatorConfig.ServiceAccountTokenGetter = o.ServiceAccounts.OptionalTokenGetter(versionedInformer)
 | 
			
		||||
	} else {
 | 
			
		||||
		authenticatorConfig.ServiceAccountTokenGetter = serviceaccountcontroller.NewGetterFromClient(
 | 
			
		||||
			extclient,
 | 
			
		||||
			versionedInformer.Core().V1().Secrets().Lister(),
 | 
			
		||||
@@ -680,6 +701,7 @@ func (o *BuiltInAuthenticationOptions) ApplyTo(
 | 
			
		||||
			versionedInformer.Core().V1().Pods().Lister(),
 | 
			
		||||
			nodeLister,
 | 
			
		||||
		)
 | 
			
		||||
	}
 | 
			
		||||
	authenticatorConfig.SecretsWriter = extclient.CoreV1()
 | 
			
		||||
 | 
			
		||||
	if authenticatorConfig.BootstrapToken {
 | 
			
		||||
 
 | 
			
		||||
@@ -17,6 +17,7 @@ limitations under the License.
 | 
			
		||||
package options
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"context"
 | 
			
		||||
	"os"
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"strings"
 | 
			
		||||
@@ -34,12 +35,17 @@ import (
 | 
			
		||||
	"k8s.io/apiserver/pkg/authentication/authenticatorfactory"
 | 
			
		||||
	"k8s.io/apiserver/pkg/authentication/request/headerrequest"
 | 
			
		||||
	"k8s.io/apiserver/pkg/features"
 | 
			
		||||
	genericapiserver "k8s.io/apiserver/pkg/server"
 | 
			
		||||
	apiserveroptions "k8s.io/apiserver/pkg/server/options"
 | 
			
		||||
	utilfeature "k8s.io/apiserver/pkg/util/feature"
 | 
			
		||||
	"k8s.io/client-go/informers"
 | 
			
		||||
	"k8s.io/client-go/kubernetes/fake"
 | 
			
		||||
	"k8s.io/component-base/featuregate"
 | 
			
		||||
	featuregatetesting "k8s.io/component-base/featuregate/testing"
 | 
			
		||||
	openapicommon "k8s.io/kube-openapi/pkg/common"
 | 
			
		||||
	kubefeatures "k8s.io/kubernetes/pkg/features"
 | 
			
		||||
	kubeauthenticator "k8s.io/kubernetes/pkg/kubeapiserver/authenticator"
 | 
			
		||||
	"k8s.io/kubernetes/pkg/serviceaccount"
 | 
			
		||||
	"k8s.io/utils/pointer"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
@@ -478,6 +484,39 @@ func TestBuiltInAuthenticationOptionsAddFlags(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestWithTokenGetterFunction(t *testing.T) {
 | 
			
		||||
	featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, kubefeatures.ServiceAccountTokenNodeBindingValidation, false)
 | 
			
		||||
	fakeClientset := fake.NewSimpleClientset()
 | 
			
		||||
	versionedInformer := informers.NewSharedInformerFactory(fakeClientset, 0)
 | 
			
		||||
	{
 | 
			
		||||
		var called bool
 | 
			
		||||
		f := func(factory informers.SharedInformerFactory) serviceaccount.ServiceAccountTokenGetter {
 | 
			
		||||
			called = true
 | 
			
		||||
			return nil
 | 
			
		||||
		}
 | 
			
		||||
		opts := NewBuiltInAuthenticationOptions().WithTokenGetterFunction(f)
 | 
			
		||||
		err := opts.ApplyTo(context.Background(), &genericapiserver.AuthenticationInfo{}, nil, nil, &openapicommon.Config{}, nil, fakeClientset, versionedInformer, "")
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			t.Fatal(err)
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if opts.ServiceAccounts.OptionalTokenGetter == nil {
 | 
			
		||||
			t.Fatal("expected token getter function to be set")
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if !called {
 | 
			
		||||
			t.Fatal("expected token getter function to be called")
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	{
 | 
			
		||||
		opts := NewBuiltInAuthenticationOptions().WithServiceAccounts()
 | 
			
		||||
		err := opts.ApplyTo(context.Background(), &genericapiserver.AuthenticationInfo{}, nil, nil, &openapicommon.Config{}, nil, fakeClientset, versionedInformer, "")
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			t.Fatal(err)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestToAuthenticationConfig_Anonymous(t *testing.T) {
 | 
			
		||||
	featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.StructuredAuthenticationConfiguration, true)
 | 
			
		||||
	testCases := []struct {
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user