Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 38 additions & 15 deletions pkg/auth/verifier.go
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ type Verifier struct {
restConfig *rest.Config
eventPolicyLister v1alpha1.EventPolicyLister
trustBundleConfigMapLister corev1listers.ConfigMapNamespaceLister
featureStore *feature.Store
m sync.RWMutex
provider *oidc.Provider
}
Expand All @@ -70,24 +71,15 @@ type IDToken struct {
}

func NewVerifier(ctx context.Context, eventPolicyLister listerseventingv1alpha1.EventPolicyLister, trustBundleConfigMapLister corev1listers.ConfigMapNamespaceLister, cmw configmap.Watcher) *Verifier {
featureStore := feature.NewStore(logging.FromContext(ctx).Named("feature-config-store"), func(name string, value interface{}) {})
featureStore.WatchConfigs(cmw)

tokenHandler := &Verifier{
logger: logging.FromContext(ctx).With("component", "oidc-token-handler"),
restConfig: injection.GetConfig(ctx),
eventPolicyLister: eventPolicyLister,
trustBundleConfigMapLister: trustBundleConfigMapLister,
}

featureStore := feature.NewStore(logging.FromContext(ctx).Named("feature-config-store"), func(name string, value interface{}) {
if features, ok := value.(feature.Flags); ok {
if err := tokenHandler.initOIDCProvider(ctx, features); err != nil {
tokenHandler.logger.Error(fmt.Sprintf("could not initialize provider after config update. You can ignore this message, when the %s feature is disabled", feature.OIDCAuthentication), zap.Error(err))
}
}
})
featureStore.WatchConfigs(cmw)

if err := tokenHandler.initOIDCProvider(ctx, featureStore.Load()); err != nil {
tokenHandler.logger.Error(fmt.Sprintf("could not initialize provider. You can ignore this message, when the %s feature is disabled", feature.OIDCAuthentication), zap.Error(err))
featureStore: featureStore,
}

return tokenHandler
Expand All @@ -100,6 +92,11 @@ func (v *Verifier) VerifyRequest(ctx context.Context, features feature.Flags, re
return nil
}

if err := v.ensureProvider(ctx, features); err != nil {
resp.WriteHeader(http.StatusInternalServerError)
return fmt.Errorf("failed to initialize OIDC provider: %w", err)
}

idToken, err := v.verifyAuthN(ctx, requiredOIDCAudience, req, resp)
if err != nil {
return fmt.Errorf("authentication of request could not be verified: %w", err)
Expand All @@ -123,6 +120,11 @@ func (v *Verifier) VerifyRequestFromSubject(ctx context.Context, features featur
return nil
}

if err := v.ensureProvider(ctx, features); err != nil {
resp.WriteHeader(http.StatusInternalServerError)
return fmt.Errorf("failed to initialize OIDC provider: %w", err)
}

idToken, err := v.verifyAuthN(ctx, requiredOIDCAudience, req, resp)
if err != nil {
return fmt.Errorf("authentication of request could not be verified: %w", err)
Expand All @@ -147,6 +149,11 @@ func (v *Verifier) VerifyRequestFromSubjectsWithFilters(ctx context.Context, fea
return nil
}

if err := v.ensureProvider(ctx, features); err != nil {
resp.WriteHeader(http.StatusInternalServerError)
return fmt.Errorf("failed to initialize OIDC provider: %w", err)
}

idToken, err := v.verifyAuthN(ctx, requiredOIDCAudience, req, resp)
if err != nil {
return fmt.Errorf("authentication of request could not be verified: %w", err)
Expand Down Expand Up @@ -236,6 +243,24 @@ func (v *Verifier) verifyAuthZBySubjectsWithFilters(ctx context.Context, feature
return nil
}

func (v *Verifier) ensureProvider(ctx context.Context, features feature.Flags) error {
v.m.RLock()
if v.provider != nil {
v.m.RUnlock()
return nil
}
v.m.RUnlock()

v.m.Lock()
defer v.m.Unlock()

if v.provider != nil {
return nil
}

return v.initOIDCProvider(ctx, features)
}

// verifyJWT verifies the given JWT for the expected audience and returns the parsed ID token.
func (v *Verifier) verifyJWT(ctx context.Context, jwt, audience string) (*IDToken, error) {
v.m.RLock()
Expand Down Expand Up @@ -289,8 +314,6 @@ func (v *Verifier) initOIDCProvider(ctx context.Context, features feature.Flags)
}

// provider is valid, update it
v.m.Lock()
defer v.m.Unlock()
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I removed the lock from initOIDCProvider() because the caller now holds the lock.

v.provider = provider

v.logger.Debug("updated OIDC provider config", zap.Any("discovery-config", discovery))
Expand Down
Loading