users_ops_retention_get
What this product keeps and for how long.
What this product keeps and for how long. Returns the EFFECTIVE retention windows (spent one-time tokens, expired flow attempts, expired sessions and their refresh tokens) next to the documented defaults, the separate waitlist-entry window, the single cron that performs every sweep, and — deliberately — the list of what is NEVER swept and why. For the waitlist it also answers the two questions a published retention promise raises: whether this product's window is WIDER than the 180 days Lessly published (`waitlistWiderThanPromised`, a flag rather than a refusal), and whether the job that honours it is actually running — `lastSweep` carries the last pass this replica performed, counting THIS product's erasures only, and is NULL when it has observed none — which is not the same as a pass that erased zero. The windows are GRACE PERIODS ON TOP OF EXPIRY, never lifetimes: every live read carries its own expiry predicate, so an unswept expired row is inert and a window of 0 shortens nothing. Change them with users_config_upsert `retention`.
Behavior
- HTTP
POST /users/ops/retention
Arguments
No arguments.
Response
| Field | Type | Always | Description |
|---|---|---|---|
| sweep | object | • | The single retention job. There is exactly one — it replaced the sessions reaper and the waitlist sweep. |
| windows | object | • | This product’s EFFECTIVE windows — what it configured, with the documented default filling anything it did not. |
| defaults | object | • | The documented defaults, so a reader can tell a deliberate window from an inherited one without a second call. |
| notSwept | array | • | What this service deliberately keeps forever, and why. Reading a retention surface that lists only what IS deleted is how an operator concludes the audit log ages out — it does not. |
| lastSweep | object | • | The last sweep this replica performed, or NULL when it has observed none. Null and a run with `erased: 0` are DIFFERENT STATES and must never be collapsed: one means the job is working and there was nothing due, the other means this replica has no evidence the job ran at all. The durable per-entry trail is elsewhere — the append-only `waitlist.erased` audit rows. |
| waitlistRetentionDays | integer | • | How long an UNCONVERTED waitlist entry — still pending, or invited and never registered — is kept, counted from SIGN-UP. It lives in the `waitlist` config block rather than in `retention`, because it is not a grace period on a dead row: such an entry never expires on its own, so this window is the whole of what makes it go away — and the sweep ERASES it (audit row, `users/waitlist-entry.erased`) rather than deleting it. |
| waitlistPromisedMaxDays | integer | • | What Lessly PUBLISHED, in its Privacy Policy §6: a waitlist address that never converted is deleted 6 months from sign-up. It rides along so the window above can be read against the promise it came from, rather than as a number with no provenance. |
| waitlistWiderThanPromised | boolean | • | True when this product configured a window WIDER than the published 180 days. Nothing refuses such a value and nothing clamps it — §6 is Lessly’s own policy and a client Product answers to its own, under which a longer window may be perfectly lawful. This flag exists INSTEAD of that ceiling: a deliberate divergence from what Lessly published must be diagnosable in one call rather than found by comparing two numbers nobody thought to compare. |
Try it
What this product keeps and for how long.