Skip to content

feat: Support IPSIE session_expiry claim#245

Draft
tanya732 wants to merge 2 commits into
v2from
feat/add-ipsie-support
Draft

feat: Support IPSIE session_expiry claim#245
tanya732 wants to merge 2 commits into
v2from
feat/add-ipsie-support

Conversation

@tanya732

@tanya732 tanya732 commented Jun 19, 2026

Copy link
Copy Markdown
Contributor

Summary

This PR adds support for the IPSIE SL1 session_expiry ID token claim, which represents an absolute upper bound (Unix timestamp in seconds) on a session's lifetime.

The claim is asserted by the upstream IdP and emitted by Auth0 when the enterprise connection has id_token_session_expiry_supported: true.

Since this library is a stateless core (it does not own or manage application sessions), it provides the primitives required to enforce the session ceiling while leaving session persistence and redirect behavior to the application.

Specifically, this PR:

  • Reads and validates the session_expiry claim during the Authorization Code flow.
  • Stores the validated value on Tokens.
  • Exposes:
    • Tokens.getSessionExpiresAt()
    • Tokens.isSessionExpired()
    • Tokens.isSessionExpired(long leeway)
  • Allows applications to persist the value and check isSessionExpired() whenever a session is read, integrating with their existing redirect-to-login flow.

Changes

Tokens

  • Added an optional sessionExpiresAt field.
  • Added a new 8-argument constructor.
  • Added:
    • getSessionExpiresAt()
    • isSessionExpired()
    • isSessionExpired(long leeway)
  • Introduced a default 30-second clock-skew tolerance via DEFAULT_SESSION_EXPIRY_LEEWAY.
  • serialVersionUID remains unchanged, so previously serialized sessions deserialize with sessionExpiresAt == null, preserving backward compatibility.

RequestProcessor

Reads session_expiry from the verified ID token after token merge and validates it before stamping it onto Tokens.

Validation rules:

  • Non-numeric values are ignored ("no ceiling").
  • Millisecond-scale values (>= 10_000_000_000) are ignored to prevent a Post-Login Action that accidentally emits milliseconds from silently disabling enforcement.
  • If session_expiry <= iat, login fails instead of creating an already-expired session.

IdentityVerificationException

Added:

  • a0.session_expiry_in_past error code
  • isSessionExpiryError() helper

Documentation

Updated EXAMPLES.md with an IPSIE session_expiry section covering:

  • Persisting the value at login
  • Enforcing it on session reads
  • Default leeway behavior

Tests

Added coverage for:

  • RequestProcessorTest
    • Claim is stamped correctly
    • Missing claim
    • Past-iat validation failure
    • Millisecond guard
  • TokensTest

Semantics

  • null means no session ceiling and is never considered expired, making rollout backward compatible.
  • All comparisons use integer Unix seconds.
  • session_expiry is independent of both:
    • the token exp claim
    • application-defined idle or absolute session timeouts

Out of Scope / Follow-up

Refresh token enforcement

This library does not currently expose a refresh-token API, so the session ceiling is enforced only:

  • during login, and
  • when reading an existing session.

A TODO has been added to AuthenticationController documenting the intended behavior once the MRRT renewal flow is implemented:

  1. Reject grant_type=refresh_token requests once the session ceiling has passed, returning session_expired.
  2. Preserve the original login-time session_expiry across refreshes (write once; never re-derive it from refresh responses).

Documentation

Cross-linking from the session management documentation is not included in this PR.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant