Skip to content

Make Access Decisions Expiry-Aware #58

Description

@Lakes41

Difficulty: Hard

Type: Bug

Summary

Update local access decisions so expired memberships are denied even when the active flag is still true.

Current Behaviour

computeAccessDecision() checks membership tier, role, and membership.active, but it does not evaluate membership.expiresAt. If a session contains active: true with an expired expiresAt, the local gate can still allow access.

Expected Behaviour

A membership with an expiry timestamp in the past should be denied. The denied result should include a safe, user-facing reason that can be shown by Gated and related UI components.

Suggested Implementation

Add an expiry check inside computeAccessDecision(). Parse membership.expiresAt only when present, deny access if the timestamp is valid and in the past, and handle malformed dates conservatively. Add tests for active expired memberships, active future memberships, missing expiry, and malformed expiry values.

Files or Areas Likely Affected

  • lib/api/access-decision.ts
  • components/gated.tsx
  • test/access-decision.test.ts
  • lib/api/types.ts

Acceptance Criteria

  • Active memberships with past expiresAt values are denied.
  • Active memberships with future expiresAt values can pass tier and role checks.
  • Missing expiresAt preserves current behaviour.
  • Invalid expiry strings do not crash the access gate.
  • Tests cover expired, valid, missing, and malformed expiry cases.

Additional Notes

This is a frontend safety check and should not replace backend authorisation. Backend access checks should remain the source of truth when available.

Metadata

Metadata

Assignees

Labels

GrantFox OSSIssue tracked in GrantFox OSSMaybe RewardedIssue may be eligible for a GrantFox rewardOfficial CampaignCampaign: Official Campaign

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions