mirror of
https://github.com/bitechdev/ResolveSpec.git
synced 2026-04-10 09:56:24 +00:00
fix(security): address validation review comments - mutex safety and issuer normalization
Agent-Logs-Url: https://github.com/bitechdev/ResolveSpec/sessions/e886b781-c910-425f-aa6f-06d13c46dcc7 Co-authored-by: warkanum <208308+warkanum@users.noreply.github.com>
This commit is contained in:
committed by
GitHub
parent
850ad2b2ab
commit
ca0545e144
@@ -1545,6 +1545,8 @@ BEGIN
|
|||||||
'username', u.username,
|
'username', u.username,
|
||||||
'email', u.email,
|
'email', u.email,
|
||||||
'user_level', u.user_level,
|
'user_level', u.user_level,
|
||||||
|
-- NULLIF converts empty string to NULL; string_to_array(NULL) returns NULL;
|
||||||
|
-- to_jsonb(NULL) returns NULL; COALESCE then returns '[]' for NULL/empty roles.
|
||||||
'roles', COALESCE(to_jsonb(string_to_array(NULLIF(u.roles, ''), ',')), '[]'::jsonb),
|
'roles', COALESCE(to_jsonb(string_to_array(NULLIF(u.roles, ''), ',')), '[]'::jsonb),
|
||||||
'exp', EXTRACT(EPOCH FROM s.expires_at)::bigint,
|
'exp', EXTRACT(EPOCH FROM s.expires_at)::bigint,
|
||||||
'iat', EXTRACT(EPOCH FROM s.created_at)::bigint
|
'iat', EXTRACT(EPOCH FROM s.created_at)::bigint
|
||||||
|
|||||||
@@ -128,8 +128,8 @@ func NewOAuthServer(cfg OAuthServerConfig, auth *DatabaseAuthenticator) *OAuthSe
|
|||||||
if cfg.AuthCodeTTL == 0 {
|
if cfg.AuthCodeTTL == 0 {
|
||||||
cfg.AuthCodeTTL = 2 * time.Minute
|
cfg.AuthCodeTTL = 2 * time.Minute
|
||||||
}
|
}
|
||||||
// Normalize issuer: trim trailing slash to ensure consistent endpoint URL construction.
|
// Normalize issuer: remove trailing slash to ensure consistent endpoint URL construction.
|
||||||
cfg.Issuer = strings.TrimRight(cfg.Issuer, "/")
|
cfg.Issuer = strings.TrimSuffix(cfg.Issuer, "/")
|
||||||
s := &OAuthServer{
|
s := &OAuthServer{
|
||||||
cfg: cfg,
|
cfg: cfg,
|
||||||
auth: auth,
|
auth: auth,
|
||||||
@@ -704,9 +704,17 @@ func (s *OAuthServer) revokeHandler(w http.ResponseWriter, r *http.Request) {
|
|||||||
|
|
||||||
if s.auth != nil {
|
if s.auth != nil {
|
||||||
s.auth.OAuthRevokeToken(r.Context(), token) //nolint:errcheck
|
s.auth.OAuthRevokeToken(r.Context(), token) //nolint:errcheck
|
||||||
} else if len(s.providers) > 0 {
|
} else {
|
||||||
// In external-provider-only mode, attempt revocation via the first provider's auth.
|
// In external-provider-only mode, attempt revocation via the first provider's auth.
|
||||||
s.providers[0].auth.OAuthRevokeToken(r.Context(), token) //nolint:errcheck
|
s.mu.RLock()
|
||||||
|
var providerAuth *DatabaseAuthenticator
|
||||||
|
if len(s.providers) > 0 {
|
||||||
|
providerAuth = s.providers[0].auth
|
||||||
|
}
|
||||||
|
s.mu.RUnlock()
|
||||||
|
if providerAuth != nil {
|
||||||
|
providerAuth.OAuthRevokeToken(r.Context(), token) //nolint:errcheck
|
||||||
|
}
|
||||||
}
|
}
|
||||||
w.WriteHeader(http.StatusOK)
|
w.WriteHeader(http.StatusOK)
|
||||||
}
|
}
|
||||||
@@ -735,8 +743,12 @@ func (s *OAuthServer) introspectHandler(w http.ResponseWriter, r *http.Request)
|
|||||||
|
|
||||||
// Resolve the authenticator to use: prefer the primary auth, then the first provider's auth.
|
// Resolve the authenticator to use: prefer the primary auth, then the first provider's auth.
|
||||||
authToUse := s.auth
|
authToUse := s.auth
|
||||||
if authToUse == nil && len(s.providers) > 0 {
|
if authToUse == nil {
|
||||||
authToUse = s.providers[0].auth
|
s.mu.RLock()
|
||||||
|
if len(s.providers) > 0 {
|
||||||
|
authToUse = s.providers[0].auth
|
||||||
|
}
|
||||||
|
s.mu.RUnlock()
|
||||||
}
|
}
|
||||||
if authToUse == nil {
|
if authToUse == nil {
|
||||||
w.Write([]byte(`{"active":false}`)) //nolint:errcheck
|
w.Write([]byte(`{"active":false}`)) //nolint:errcheck
|
||||||
|
|||||||
Reference in New Issue
Block a user