Files
auth/token.go
T
2026-09-26 20:42:42 -04:00

60 lines
1.5 KiB
Go

package auth
import (
"crypto/sha256"
"sync"
)
// SimpleTokenValidator is a concurrent in-memory allowlist of opaque tokens.
// Its zero value is ready to use. Tokens have no automatic expiration; use JWT
// for signed expiry or RemoveToken for explicit revocation.
type SimpleTokenValidator struct {
tokens map[[32]byte]struct{} // keyed by SHA-256(token)
mu sync.RWMutex
}
// NewSimpleTokenValidator creates token validator
func NewSimpleTokenValidator() *SimpleTokenValidator {
return &SimpleTokenValidator{
tokens: make(map[[32]byte]struct{}),
}
}
// ValidateToken checks if token is valid
func (v *SimpleTokenValidator) ValidateToken(token string) bool {
if token == "" || len(token) > MaxTokenLen {
return false
}
h := sha256.Sum256([]byte(token))
v.mu.RLock()
defer v.mu.RUnlock()
_, ok := v.tokens[h]
return ok
}
// AddToken adds a token to the allowlist. Empty and oversized tokens are ignored.
// Provision high-entropy tokens, e.g. with crypto/rand.Text; do not use passwords.
func (v *SimpleTokenValidator) AddToken(token string) {
if token == "" || len(token) > MaxTokenLen {
return
}
h := sha256.Sum256([]byte(token))
v.mu.Lock()
defer v.mu.Unlock()
if v.tokens == nil {
v.tokens = make(map[[32]byte]struct{})
}
v.tokens[h] = struct{}{}
}
// RemoveToken removes token from validator
func (v *SimpleTokenValidator) RemoveToken(token string) {
if token == "" || len(token) > MaxTokenLen {
return
}
h := sha256.Sum256([]byte(token))
v.mu.Lock()
defer v.mu.Unlock()
delete(v.tokens, h)
}