crowdsecurity/crowdsec · error
failed to seal allowlist cookie: %w
Error message
failed to seal allowlist cookie: %w
What it means
SealAllowlistCookie mints an AES-GCM-sealed allowlist-bypass challenge cookie, encrypting the envelope under the master cookie key. This wrapper error means the underlying sealCookieV0 call failed, so no allowlist cookie could be produced and GrantChallengeCookie cannot grant the bypass. It always wraps one of the crypto-layer errors: reason too long, proto marshal failure, size-limit breach, or entropy failure.
Source
Thrown at pkg/appsec/challenge/challenge.go:754
// SealAllowlistCookie mints an allowlist-bypass cookie (no fingerprint, with
// the operator reason) so GrantChallengeCookie can let trusted bots skip the
// challenge UI while still hitting on_challenge rules via fingerprint.Allowlisted.
// not_after honors c.cookieTTL unless ttlOverride (>0) is given; reason is
// bounded by MaxAllowlistReasonLen (crypto.go).
func (c *ChallengeRuntime) SealAllowlistCookie(request *http.Request, reason string, ttlOverride *time.Duration) (*cookie.AppsecCookie, error) {
if c == nil {
return nil, errors.New("challenge runtime not initialized")
}
ttl := c.cookieTTL
if ttlOverride != nil && *ttlOverride > 0 {
ttl = *ttlOverride
}
notAfter := time.Now().Add(ttl).Unix()
cookieValue, err := sealCookieV0(&pb.ChallengeCookie{}, c.keys.MasterCookieKey(), notAfter, cookieFlagAllowlisted, reason, []byte(request.UserAgent()), c.maxCookieLen)
if err != nil {
return nil, fmt.Errorf("failed to seal allowlist cookie: %w", err)
}
ck := cookie.NewAppsecCookie(ChallengeCookieName).HttpOnly().Path("/").SameSite(cookie.SameSiteLax).ExpiresIn(ttl).Value(cookieValue)
if request.URL.Scheme == "https" {
ck = ck.Secure()
}
return ck, nil
}
// CookieData bundles the decoded fingerprint with cookie-envelope metadata for
// re-challenge decisions. Allowlisted/AllowlistReason mark cookies minted by
// SealAllowlistCookie; they are zero for real-submission cookies.
type CookieData struct {
Fingerprint FingerprintData
PowDifficulty int
Allowlisted bool
AllowlistReason stringView on GitHub (pinned to 909b515798)
Solutions
- Shorten the reason string passed to SealAllowlistCookie/GrantChallengeCookie to at most 256 bytes.
- If ErrCookieTooLarge is wrapped, raise the max_cookie_size challenge config value or reduce the cookie payload.
- Check the wrapped error (%w chain) to identify the exact crypto-layer cause; entropy failures (rand.Read) indicate a broken system CSPRNG.
- Verify the runtime was initialized (nil runtime returns a different error, but a half-initialized keyring is worth ruling out).
Example fix
// before
ck, err := rt.SealAllowlistCookie(req, "allowlisted for support ticket #4821 - trusted corporate proxy scanning partner integration from the security operations center", nil)
// after
reason := "support ticket #4821 - trusted proxy"
if len(reason) > challenge.MaxAllowlistReasonLen {
reason = reason[:challenge.MaxAllowlistReasonLen]
}
ck, err := rt.SealAllowlistCookie(req, reason, nil) Defensive patterns
Strategy: validation
Validate before calling
if len(reason) > challenge.MaxAllowlistReasonLen {
return fmt.Errorf("allowlist reason too long: %d > %d", len(reason), challenge.MaxAllowlistReasonLen)
} Try / catch
if _, err := rt.SealAllowlistCookie(req, reason, nil); err != nil {
if errors.Is(err, challenge.ErrAllowlistReasonSize) { /* truncate reason and retry */ }
return err
} Prevention
- Clamp reason strings at the API boundary before granting allowlist cookies.
- Keep allowlist reasons to short identifiers, not descriptions.
- Cover GrantChallengeCookie with a test using a 257-byte reason.
When it happens
Trigger: Calling ChallengeRuntime.SealAllowlistCookie (via GrantChallengeCookie) with an operator reason longer than MaxAllowlistReasonLen (256 bytes), or when the resulting plaintext exceeds the configured max cookie size, or an internal crypto/entropy failure.
Common situations: Operators passing a long human-readable allowlist reason (e.g. a URL, ticket ID, or description) through the allowlist API; deployments with a reduced max_cookie_size config value sealing larger envelopes.
Related errors
- failed to seal challenge cookie: %w
- cookie expired
- unknown cookie version
- unable to seal allowlist cookie: %w
- generate PoW salt: %w
AI-assisted analysis of crowdsecurity/crowdsec@909b515798 (2026-09-06).
Data as JSON: /api/errors/7d50440af11dbfd8.
Report an issue: GitHub.