@nxgt/janus-mongo 0.9.1 → 0.9.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -2
- package/dist/index.js.map +2 -2
- package/dist/stores/index.d.ts +4 -3
- package/dist/stores/index.d.ts.map +1 -1
- package/docs/guide/sync.md +2 -2
- package/docs/guide/wiring.md +3 -3
- package/docs/roadmap.md +3 -2
- package/docs/troubleshooting.md +3 -3
- package/package.json +3 -3
package/README.md
CHANGED
|
@@ -139,8 +139,8 @@ spend the same one.
|
|
|
139
139
|
minute. The core compares `expiresAt` on every read, and that is what expires
|
|
140
140
|
it.
|
|
141
141
|
- **`auth.collectExpired()` answers `UNSUPPORTED`** with this adapter. The TTL
|
|
142
|
-
|
|
143
|
-
deliberately not implemented.
|
|
142
|
+
indexes already drop lapsed sessions and tokens, so `deleteExpiredSessions`
|
|
143
|
+
and `deleteExpiredTokens` are deliberately not implemented.
|
|
144
144
|
- **No sync function is called for you** — `syncMongoAdapter`, or
|
|
145
145
|
`syncMongoStores` for identities alone. The core never manages a schema.
|
|
146
146
|
Without it there is no unique index, and nothing stops two concurrent sign-ups
|
package/dist/index.js.map
CHANGED
|
@@ -10,13 +10,13 @@
|
|
|
10
10
|
"import {\n\ttype CursorPage,\n\ttype Entity,\n\tisSubjectSet,\n\ttype RelationTuple,\n\ttype SubjectSet,\n} from '@nxgt/janus';\nimport type { ObjectPageRequest } from '@nxgt/janus/permissions';\nimport type { Filter } from 'mongodb';\nimport type { RelationDocument } from './collection';\nimport type { RelationContext } from './context';\nimport { keyOf } from './tuples';\n\nexport async function has(\n\t{ collection }: RelationContext,\n\ttuple: RelationTuple,\n): Promise<boolean> {\n\treturn (\n\t\t(await collection.findOne(\n\t\t\t{ _id: keyOf(tuple) },\n\t\t\t{ projection: { _id: 1 } },\n\t\t)) !== null\n\t);\n}\n\nexport async function findSubjectSets(\n\tcontext: RelationContext,\n\tobject: Entity,\n\trelation: string,\n): Promise<SubjectSet[]> {\n\treturn (await holding(context, object, relation, true)).map(\n\t\t(subject): SubjectSet => ({\n\t\t\ttype: subject.type,\n\t\t\tid: subject.id,\n\t\t\trelation: subject.relation as string,\n\t\t}),\n\t);\n}\n\nexport async function findEntities(\n\tcontext: RelationContext,\n\tobject: Entity,\n\trelation: string,\n): Promise<Entity[]> {\n\treturn (await holding(context, object, relation, false)).map(\n\t\t(subject): Entity => ({ type: subject.type, id: subject.id }),\n\t);\n}\n\n/** One hop from an object: its subject sets, or its entities. */\nasync function holding(\n\t{ collection }: RelationContext,\n\tobject: Entity,\n\trelation: string,\n\tsets: boolean,\n) {\n\treturn (\n\t\tawait collection\n\t\t\t.find({\n\t\t\t\t'_id.object.type': object.type,\n\t\t\t\t'_id.object.id': object.id,\n\t\t\t\t'_id.relation': relation,\n\t\t\t\t'_id.subject.relation': { $exists: sets },\n\t\t\t})\n\t\t\t.toArray()\n\t).map((document) => document._id.subject);\n}\n\n/** A page of object ids, in id order, after the cursor. */\nexport async function findObjects(\n\t{ collection }: RelationContext,\n\t{ type, relation, subject, after, limit }: ObjectPageRequest,\n): Promise<CursorPage<string>> {\n\tconst filter: Filter<RelationDocument> = {\n\t\t'_id.subject.type': subject.type,\n\t\t'_id.subject.id': subject.id,\n\t\t// `null` matches the missing field: an entity, not a set.\n\t\t'_id.subject.relation': isSubjectSet(subject) ? subject.relation : null,\n\t\t'_id.relation': relation,\n\t\t'_id.object.type': type,\n\t\t...(after === null ? {} : { '_id.object.id': { $gt: after } }),\n\t};\n\tconst found = await collection\n\t\t.find(filter, { projection: { '_id.object.id': 1 } })\n\t\t.sort({ '_id.object.id': 1 })\n\t\t.limit(limit + 1)\n\t\t.toArray();\n\tconst items = found.slice(0, limit).map((document) => document._id.object.id);\n\tconst last = items.at(-1);\n\treturn {\n\t\titems,\n\t\tnextCursor: found.length > limit && last !== undefined ? last : null,\n\t};\n}\n",
|
|
11
11
|
"import { isSubjectSet, type RelationTuple, type Subject } from '@nxgt/janus';\nimport type { Key } from './collection';\n\n/** The `_id` of a tuple, in the one field order MongoDB compares. */\nexport function keyOf(tuple: RelationTuple): Key {\n\treturn {\n\t\tobject: { type: tuple.object.type, id: tuple.object.id },\n\t\trelation: tuple.relation,\n\t\tsubject: subjectKey(tuple.subject),\n\t};\n}\n\nfunction subjectKey(subject: Subject): Key['subject'] {\n\treturn isSubjectSet(subject)\n\t\t? { type: subject.type, id: subject.id, relation: subject.relation }\n\t\t: { type: subject.type, id: subject.id };\n}\n",
|
|
12
12
|
"import type { Entity, RelationTuple } from '@nxgt/janus';\nimport type { ClientSession } from 'mongodb';\nimport type { Key } from './collection';\nimport type { RelationContext, Relations } from './context';\nimport { keyOf } from './tuples';\n\n/** One tuple in one driver call; more in one transaction. */\nexport async function write(\n\t{ db, collection }: RelationContext,\n\tadd: readonly RelationTuple[],\n\tremove: readonly RelationTuple[],\n): Promise<void> {\n\tconst removals = remove.map(keyOf);\n\tconst additions = add.map(keyOf);\n\n\tif (removals.length + additions.length <= 1) {\n\t\treturn apply(collection, additions, removals);\n\t}\n\n\tconst session = db.client.startSession();\n\ttry {\n\t\tsession.startTransaction();\n\t\tawait apply(collection, additions, removals, session);\n\t\tawait session.commitTransaction();\n\t} finally {\n\t\t// Ends — and so aborts — a transaction that did not commit.\n\t\tawait session.endSession();\n\t}\n}\n\n/** Removals first, then additions. */\nasync function apply(\n\tcollection: Relations,\n\tadditions: Key[],\n\tremovals: Key[],\n\tsession?: ClientSession,\n): Promise<void> {\n\tif (removals.length > 0) {\n\t\tawait collection.deleteMany(\n\t\t\t{ _id: { $in: removals } },\n\t\t\tsession === undefined ? {} : { session },\n\t\t);\n\t}\n\tif (additions.length > 0) {\n\t\t// A replace of a document by itself: a stored tuple is a no-op,\n\t\t// an absent one is inserted, and concurrent writers of one\n\t\t// tuple meet on the `_id` index, which the server retries.\n\t\tawait collection.bulkWrite(\n\t\t\tadditions.map((key) => ({\n\t\t\t\treplaceOne: {\n\t\t\t\t\tfilter: { _id: key },\n\t\t\t\t\treplacement: { _id: key },\n\t\t\t\t\tupsert: true,\n\t\t\t\t},\n\t\t\t})),\n\t\t\tsession === undefined ? {} : { session },\n\t\t);\n\t}\n}\n\n/** Every tuple naming the entity, as object or as subject. */\nexport async function deleteEntity(\n\t{ collection }: RelationContext,\n\tentity: Entity,\n): Promise<number> {\n\tconst result = await collection.deleteMany({\n\t\t$or: [\n\t\t\t{ '_id.object.type': entity.type, '_id.object.id': entity.id },\n\t\t\t{ '_id.subject.type': entity.type, '_id.subject.id': entity.id },\n\t\t],\n\t});\n\treturn result.deletedCount;\n}\n",
|
|
13
|
-
"import type { JanusStores } from '@nxgt/janus';\nimport {\n\ttype SyncOptions,\n\ttype SyncReport,\n\tsyncCollections,\n} from '@nxgt/mongo';\nimport type { Db } from 'mongodb';\nimport { janusCollections } from '../collections';\nimport { sessionStore } from './sessions';\nimport { tokenStore } from './tokens';\nimport { userStore } from './users';\n\n/**\n * The three stores `janus()` takes, over one MongoDB database.\n *\n * ```ts\n * const db = (await connectMongo(process.env.MONGO_URI)).db;\n * await syncMongoStores(db); // a deployment step: creates the indexes\n * const auth = janus({ user, password: { login: 'email' }, store: createMongoStores(db), hasher });\n * ```\n *\n * **Reads go through `@nxgt/mongo`'s `find*`, never its `get*`.** `findById`\n * answers `undefined` for an absence, so an absence arrives as a *value*,\n * turned into `null` here, and everything that arrives as a rejection is a\n * failure. There is no path on which an absence and an outage travel the same\n * channel, so there is none on which a `catch` could confuse them.\n *\n * **Every conditional write is one driver call** on `raw`, the driver's own\n * collection: `@nxgt/mongo` names no update conditioned on anything but its\n * own lock, and the port needs `version`, `revokedAt` and `kind`.\n *\n * `sessions.deleteExpiredSessions`
|
|
13
|
+
"import type { JanusStores } from '@nxgt/janus';\nimport {\n\ttype SyncOptions,\n\ttype SyncReport,\n\tsyncCollections,\n} from '@nxgt/mongo';\nimport type { Db } from 'mongodb';\nimport { janusCollections } from '../collections';\nimport { sessionStore } from './sessions';\nimport { tokenStore } from './tokens';\nimport { userStore } from './users';\n\n/**\n * The three stores `janus()` takes, over one MongoDB database.\n *\n * ```ts\n * const db = (await connectMongo(process.env.MONGO_URI)).db;\n * await syncMongoStores(db); // a deployment step: creates the indexes\n * const auth = janus({ user, password: { login: 'email' }, store: createMongoStores(db), hasher });\n * ```\n *\n * **Reads go through `@nxgt/mongo`'s `find*`, never its `get*`.** `findById`\n * answers `undefined` for an absence, so an absence arrives as a *value*,\n * turned into `null` here, and everything that arrives as a rejection is a\n * failure. There is no path on which an absence and an outage travel the same\n * channel, so there is none on which a `catch` could confuse them.\n *\n * **Every conditional write is one driver call** on `raw`, the driver's own\n * collection: `@nxgt/mongo` names no update conditioned on anything but its\n * own lock, and the port needs `version`, `revokedAt` and `kind`.\n *\n * `sessions.deleteExpiredSessions` and `tokens.deleteExpiredTokens` are not\n * implemented: a TTL index drops lapsed sessions and tokens, so\n * `auth.collectExpired()` answers `UNSUPPORTED` — which is what the port asks\n * of a store with its own expiry.\n */\nexport function createMongoStores(db: Db): JanusStores {\n\treturn {\n\t\tusers: userStore(db),\n\t\tsessions: sessionStore(db),\n\t\ttokens: tokenStore(db),\n\t};\n}\n\n/**\n * Creates the three collections, their validators and their indexes, and says\n * what it changed. Run it twice and the second run sends nothing.\n *\n * A deployment step, never a request-time one: it needs the `dbAdmin` role,\n * and the core never calls it (rule 6). An application that deploys with\n * `@nxgt/mongo`'s `syncAll(db)` already syncs these three with its own.\n */\nexport function syncMongoStores(\n\tdb: Db,\n\toptions?: SyncOptions,\n): Promise<SyncReport[]> {\n\treturn syncCollections(db, janusCollections, options);\n}\n",
|
|
14
14
|
"import type { SessionStore } from '@nxgt/janus';\nimport { getCollection, type TypedCollection } from '@nxgt/mongo';\nimport type { Db } from 'mongodb';\nimport { sessions } from '../collections';\nimport { run, settle, unexpectedDuplicate } from '../translate';\nimport { toSession, toSessionDocument } from './records';\n\ntype Sessions = TypedCollection<typeof sessions>;\n\nexport function sessionStore(db: Db): SessionStore {\n\tconst collection = getCollection(db, sessions);\n\tconst run$ = <T>(operation: string, body: () => Promise<T>) =>\n\t\trun('sessions', operation, body);\n\n\treturn {\n\t\tinsertSession: (record) =>\n\t\t\trun$('insertSession', async () => {\n\t\t\t\tconst outcome = await settle(\n\t\t\t\t\tcollection.raw.insertOne(toSessionDocument(record)),\n\t\t\t\t);\n\t\t\t\tif (!('duplicate' in outcome)) return;\n\n\t\t\t\t// Idempotent under retry: a session with this id is already there.\n\t\t\t\tif ((await collection.findById(record.id)) !== undefined) return;\n\t\t\t\tthrow unexpectedDuplicate(\n\t\t\t\t\t'sessions',\n\t\t\t\t\t'insertSession',\n\t\t\t\t\toutcome.duplicate,\n\t\t\t\t);\n\t\t\t}),\n\n\t\tfindSessionByTokenHash: (tokenHash) =>\n\t\t\trun$('findSessionByTokenHash', async () => {\n\t\t\t\tconst found = await collection.findFirst({ tokenHash });\n\t\t\t\treturn found === undefined ? null : toSession(found);\n\t\t\t}),\n\n\t\textendSession: (id, expiresAt) =>\n\t\t\trun$('extendSession', async () => {\n\t\t\t\t// `revokedAt: null` in the filter: an extension racing a revocation\n\t\t\t\t// matches nothing, and never brings the session back.\n\t\t\t\tconst written = await collection.raw.findOneAndUpdate(\n\t\t\t\t\t{ _id: id, revokedAt: null },\n\t\t\t\t\t{ $set: { expiresAt } },\n\t\t\t\t\t{ returnDocument: 'after' },\n\t\t\t\t);\n\t\t\t\treturn written === null ? null : toSession(written);\n\t\t\t}),\n\n\t\treauthenticateSession: (id, at) =>\n\t\t\trun$('reauthenticateSession', async () => {\n\t\t\t\t// The same filter as an extension's: a confirmation racing a\n\t\t\t\t// revocation matches nothing.\n\t\t\t\tconst written = await collection.raw.findOneAndUpdate(\n\t\t\t\t\t{ _id: id, revokedAt: null },\n\t\t\t\t\t{ $set: { authenticatedAt: at } },\n\t\t\t\t\t{ returnDocument: 'after' },\n\t\t\t\t);\n\t\t\t\treturn written === null ? null : toSession(written);\n\t\t\t}),\n\n\t\trevokeSession: (id, at) =>\n\t\t\trun$('revokeSession', () => revokeSession(collection, id, at)),\n\n\t\trevokeUserSessions: (userId, at, except) =>\n\t\t\trun$('revokeUserSessions', () =>\n\t\t\t\trevokeUserSessions(collection, userId, at, except),\n\t\t\t),\n\n\t\tdeleteUserSessions: (userId) =>\n\t\t\trun$('deleteUserSessions', async () => {\n\t\t\t\tconst result = await collection.raw.deleteMany({ userId });\n\t\t\t\treturn result.deletedCount;\n\t\t\t}),\n\t};\n}\n\nasync function revokeSession(\n\tcollection: Sessions,\n\tid: string,\n\tat: Date,\n): Promise<boolean> {\n\t// A pipeline, so a session already revoked keeps its first\n\t// `revokedAt` and still counts as matched.\n\tconst result = await collection.raw.updateOne({ _id: id }, [\n\t\t{ $set: { revokedAt: { $ifNull: ['$revokedAt', at] } } },\n\t]);\n\treturn result.matchedCount === 1;\n}\n\nasync function revokeUserSessions(\n\tcollection: Sessions,\n\tuserId: string,\n\tat: Date,\n\texcept: string | undefined,\n): Promise<number> {\n\tconst result = await collection.raw.updateMany(\n\t\texcept === undefined\n\t\t\t? { userId, revokedAt: null }\n\t\t\t: { userId, revokedAt: null, _id: { $ne: except } },\n\t\t{ $set: { revokedAt: at } },\n\t);\n\treturn result.modifiedCount;\n}\n",
|
|
15
15
|
"import type {\n\tId,\n\tSessionRecord,\n\tTokenRecord,\n\tUserPatch,\n\tUserRecord,\n} from '@nxgt/janus';\nimport type { DocumentOf } from '@nxgt/mongo';\nimport type { sessions, tokens, users } from '../collections';\n\n// ─── Documents and records ────────────────────────────────────────────────\n//\n// Each record is rebuilt field by field, never spread from a document: a\n// spread would hand the core `_id` and the `id` getter `@nxgt/mongo` adds,\n// and the port's records are exactly what it declares.\n\ntype UserDocument = DocumentOf<typeof users>;\ntype SessionDocument = DocumentOf<typeof sessions>;\ntype TokenDocument = DocumentOf<typeof tokens>;\n\nexport function toUserDocument(record: UserRecord): UserDocument {\n\treturn structuredClone({\n\t\t_id: record.id,\n\t\ttype: record.type,\n\t\tschemaVersion: record.schemaVersion,\n\t\tactive: record.active,\n\t\tfields: record.fields,\n\t\tlogins: [...record.logins],\n\t\tpassword: record.password,\n\t\tsecondFactor:\n\t\t\trecord.secondFactor === null\n\t\t\t\t? null\n\t\t\t\t: {\n\t\t\t\t\t\t...record.secondFactor,\n\t\t\t\t\t\trecoveryCodes: [...record.secondFactor.recoveryCodes],\n\t\t\t\t\t},\n\t\temailVerifiedAt: record.emailVerifiedAt,\n\t\tversion: record.version,\n\t\tcreatedAt: record.createdAt,\n\t\tupdatedAt: record.updatedAt,\n\t});\n}\n\n/**\n * The fields a patch names, as one `$set`. A key present with `undefined` is\n * absent, as the port says — never an erasure. `password: null` is named, and\n * removes the password.\n */\nexport function toUserSet(patch: UserPatch): Record<string, unknown> {\n\tconst set: Record<string, unknown> = { updatedAt: patch.updatedAt };\n\n\tfor (const field of [\n\t\t'schemaVersion',\n\t\t'active',\n\t\t'fields',\n\t\t'logins',\n\t\t'password',\n\t\t'secondFactor',\n\t\t'emailVerifiedAt',\n\t] as const) {\n\t\tif (patch[field] !== undefined) set[field] = patch[field];\n\t}\n\n\treturn structuredClone(set);\n}\n\nexport function toUser(document: UserDocument): UserRecord {\n\tconst password = document.password;\n\tconst secondFactor = document.secondFactor ?? null;\n\treturn {\n\t\tid: document._id as Id,\n\t\ttype: document.type,\n\t\tschemaVersion: document.schemaVersion,\n\t\tactive: document.active,\n\t\tfields: document.fields as UserRecord['fields'],\n\t\tlogins: [...document.logins],\n\t\tpassword:\n\t\t\tpassword === null\n\t\t\t\t? null\n\t\t\t\t: { hash: password.hash, updatedAt: password.updatedAt },\n\t\tsecondFactor:\n\t\t\tsecondFactor === null\n\t\t\t\t? null\n\t\t\t\t: {\n\t\t\t\t\t\tmethod: secondFactor.method,\n\t\t\t\t\t\tsecret: secondFactor.secret,\n\t\t\t\t\t\tconfirmedAt: secondFactor.confirmedAt,\n\t\t\t\t\t\tlastStep: secondFactor.lastStep,\n\t\t\t\t\t\trecoveryCodes: [...(secondFactor.recoveryCodes ?? [])],\n\t\t\t\t\t},\n\t\temailVerifiedAt: document.emailVerifiedAt,\n\t\tversion: document.version,\n\t\tcreatedAt: document.createdAt,\n\t\tupdatedAt: document.updatedAt,\n\t};\n}\n\nexport function toSessionDocument(record: SessionRecord): SessionDocument {\n\treturn {\n\t\t_id: record.id,\n\t\ttokenHash: record.tokenHash,\n\t\tuserId: record.userId,\n\t\tauthenticatedAt: record.authenticatedAt,\n\t\texpiresAt: record.expiresAt,\n\t\trevokedAt: record.revokedAt,\n\t\tcreatedAt: record.createdAt,\n\t};\n}\n\nexport function toSession(document: SessionDocument): SessionRecord {\n\treturn {\n\t\tid: document._id,\n\t\ttokenHash: document.tokenHash,\n\t\tuserId: document.userId as Id,\n\t\tauthenticatedAt: document.authenticatedAt,\n\t\texpiresAt: document.expiresAt,\n\t\trevokedAt: document.revokedAt,\n\t\tcreatedAt: document.createdAt,\n\t};\n}\n\nexport function toTokenDocument(record: TokenRecord): TokenDocument {\n\treturn {\n\t\t_id: record.tokenHash,\n\t\tkind: record.kind,\n\t\tuserId: record.userId,\n\t\taddress: record.address,\n\t\tcodeHash: record.codeHash,\n\t\tattempts: record.attempts,\n\t\texpiresAt: record.expiresAt,\n\t\tspentAt: record.spentAt,\n\t\tcreatedAt: record.createdAt,\n\t};\n}\n\nexport function toToken(document: TokenDocument): TokenRecord {\n\treturn {\n\t\ttokenHash: document._id,\n\t\tkind: document.kind,\n\t\tuserId: document.userId as Id,\n\t\taddress: document.address,\n\t\tcodeHash: document.codeHash ?? null,\n\t\tattempts: document.attempts ?? 0,\n\t\texpiresAt: document.expiresAt,\n\t\tspentAt: document.spentAt,\n\t\tcreatedAt: document.createdAt,\n\t};\n}\n",
|
|
16
16
|
"import type { TokenKind, TokenRecord, TokenStore } from '@nxgt/janus';\nimport { getCollection, type TypedCollection } from '@nxgt/mongo';\nimport type { Db } from 'mongodb';\nimport { tokens } from '../collections';\nimport { run, settle } from '../translate';\nimport { toToken, toTokenDocument } from './records';\n\ntype Tokens = TypedCollection<typeof tokens>;\n\nexport function tokenStore(db: Db): TokenStore {\n\tconst collection = getCollection(db, tokens);\n\tconst run$ = <T>(operation: string, body: () => Promise<T>) =>\n\t\trun('tokens', operation, body);\n\n\treturn {\n\t\tinsertToken: (record) =>\n\t\t\trun$('insertToken', async () => {\n\t\t\t\t// `_id` is the hash, the only unique index: a duplicate is a retry.\n\t\t\t\tawait settle(collection.raw.insertOne(toTokenDocument(record)));\n\t\t\t}),\n\n\t\tconsumeToken: (tokenHash, kind, at) =>\n\t\t\trun$('consumeToken', () => consumeToken(collection, tokenHash, kind, at)),\n\n\t\tcountAttempt: (tokenHash, kind) =>\n\t\t\trun$('countAttempt', () => countAttempt(collection, tokenHash, kind)),\n\n\t\tspendUserTokens: (userId, kind, at, except) =>\n\t\t\trun$('spendUserTokens', async () => {\n\t\t\t\t// Each document is matched and written in one step, as\n\t\t\t\t// `consumeToken` does: a token it spends at the same moment is\n\t\t\t\t// counted by exactly one of the two.\n\t\t\t\tconst result = await collection.raw.updateMany(\n\t\t\t\t\t{\n\t\t\t\t\t\tuserId,\n\t\t\t\t\t\tkind,\n\t\t\t\t\t\tspentAt: null,\n\t\t\t\t\t\t...(except === undefined ? {} : { _id: { $ne: except } }),\n\t\t\t\t\t},\n\t\t\t\t\t{ $set: { spentAt: at } },\n\t\t\t\t);\n\t\t\t\treturn result.modifiedCount;\n\t\t\t}),\n\n\t\tdeleteUserTokens: (userId) =>\n\t\t\trun$('deleteUserTokens', async () => {\n\t\t\t\tconst result = await collection.raw.deleteMany({ userId });\n\t\t\t\treturn result.deletedCount;\n\t\t\t}),\n\t};\n}\n\nasync function consumeToken(\n\tcollection: Tokens,\n\ttokenHash: string,\n\tkind: TokenKind,\n\tat: Date,\n): Promise<TokenRecord | null> {\n\t// **One conditional write**, answering the document as it was\n\t// before it. The pipeline keeps a first `spentAt`, so exactly one\n\t// caller ever reads `spentAt: null`.\n\tconst before = await collection.raw.findOneAndUpdate(\n\t\t{ _id: tokenHash, kind },\n\t\t[{ $set: { spentAt: { $ifNull: ['$spentAt', at] } } }],\n\t\t{ returnDocument: 'before' },\n\t);\n\treturn before === null ? null : toToken(before);\n}\n\nasync function countAttempt(\n\tcollection: Tokens,\n\ttokenHash: string,\n\tkind: TokenKind,\n): Promise<TokenRecord | null> {\n\t// **One conditional write**, answering the document after it: an\n\t// unspent token gets one more attempt, atomically. A spent one is\n\t// matched by the second read below, and written nothing.\n\tconst after = await collection.raw.findOneAndUpdate(\n\t\t{ _id: tokenHash, kind, spentAt: null },\n\t\t{ $inc: { attempts: 1 } },\n\t\t{ returnDocument: 'after' },\n\t);\n\tif (after !== null) return toToken(after);\n\tconst spent = await collection.raw.findOne({ _id: tokenHash, kind });\n\treturn spent === null ? null : toToken(spent);\n}\n",
|
|
17
17
|
"import type { UserPatch, UserRecord, UserStore } from '@nxgt/janus';\nimport { NotFoundError, StoreConflict } from '@nxgt/janus';\nimport { getCollection, type TypedCollection } from '@nxgt/mongo';\nimport type { Db } from 'mongodb';\nimport { users } from '../collections';\nimport { refuseDuplicate, run, settle } from '../translate';\nimport { toUser, toUserDocument, toUserSet } from './records';\n\ntype Users = TypedCollection<typeof users>;\n\nexport function userStore(db: Db): UserStore {\n\tconst collection = getCollection(db, users);\n\tconst run$ = <T>(operation: string, body: () => Promise<T>) =>\n\t\trun('users', operation, body);\n\n\treturn {\n\t\tinsertUser: (record) =>\n\t\t\trun$('insertUser', () => insertUser(collection, record)),\n\n\t\tfindUser: (id) => run$('findUser', () => findUser(collection, id)),\n\n\t\t// One query, whatever the number of ids: the core sends at most 100,\n\t\t// distinct, and puts the answer back in its caller's order.\n\t\tfindUsers: (ids) =>\n\t\t\trun$('findUsers', async () => {\n\t\t\t\tconst found = await collection.findMany({\n\t\t\t\t\tfilter: { _id: { $in: [...ids] } },\n\t\t\t\t});\n\t\t\t\treturn found.map(toUser);\n\t\t\t}),\n\n\t\tfindUserByLogin: (type, login) =>\n\t\t\trun$('findUserByLogin', async () => {\n\t\t\t\tconst found = await collection.findFirst({ type, logins: login });\n\t\t\t\treturn found === undefined ? null : toUser(found);\n\t\t\t}),\n\n\t\tlistUsers: ({ type, after, limit }) =>\n\t\t\trun$('listUsers', async () => {\n\t\t\t\t// One more than the page, to know whether another follows.\n\t\t\t\tconst found = await collection.findMany({\n\t\t\t\t\tfilter: after === null ? { type } : { type, _id: { $gt: after } },\n\t\t\t\t\tsort: { _id: 1 },\n\t\t\t\t\tlimit: limit + 1,\n\t\t\t\t});\n\t\t\t\tconst items = found.slice(0, limit).map(toUser);\n\t\t\t\tconst last = items.at(-1);\n\n\t\t\t\treturn {\n\t\t\t\t\titems,\n\t\t\t\t\tnextCursor:\n\t\t\t\t\t\tfound.length > limit && last !== undefined ? last.id : null,\n\t\t\t\t};\n\t\t\t}),\n\n\t\tupdateUser: (id, patch, ifVersion) =>\n\t\t\trun$('updateUser', () => updateUser(collection, id, patch, ifVersion)),\n\n\t\tdeleteUser: (id) =>\n\t\t\trun$('deleteUser', async () => {\n\t\t\t\tconst result = await collection.raw.deleteOne({ _id: id });\n\t\t\t\treturn result.deletedCount === 1;\n\t\t\t}),\n\t};\n}\n\nasync function findUser(\n\tcollection: Users,\n\tid: string,\n): Promise<UserRecord | null> {\n\tconst found = await collection.findById(id);\n\treturn found === undefined ? null : toUser(found);\n}\n\nasync function insertUser(\n\tcollection: Users,\n\trecord: UserRecord,\n): Promise<UserRecord> {\n\tconst document = toUserDocument(record);\n\tconst outcome = await settle(collection.raw.insertOne(document));\n\tif (!('duplicate' in outcome)) return toUser(document);\n\n\t// A retry whose first attempt landed: whichever index reported it,\n\t// the user with this id is there, and is the answer. That includes\n\t// their own logins, which are not taken by them.\n\tconst stored = await findUser(collection, record.id);\n\tif (stored !== null) return stored;\n\tthrow refuseDuplicate('insertUser', outcome.duplicate);\n}\n\nasync function updateUser(\n\tcollection: Users,\n\tid: string,\n\tpatch: UserPatch,\n\tifVersion: number,\n): Promise<UserRecord> {\n\tconst outcome = await settle(\n\t\tcollection.raw.findOneAndUpdate(\n\t\t\t{ _id: id, version: ifVersion },\n\t\t\t{ $set: toUserSet(patch), $inc: { version: 1 } },\n\t\t\t{ returnDocument: 'after' },\n\t\t),\n\t);\n\n\tif ('duplicate' in outcome) {\n\t\tthrow refuseDuplicate('updateUser', outcome.duplicate);\n\t}\n\tif (outcome.written !== null) return toUser(outcome.written);\n\n\t// The write matched nothing, which alone cannot tell an unknown id\n\t// from a moved version: read again, and say which.\n\tconst stored = await findUser(collection, id);\n\tif (stored === null) {\n\t\tthrow new NotFoundError('updateUser: no user has this id', {\n\t\t\tuserId: id,\n\t\t\toperation: 'updateUser',\n\t\t});\n\t}\n\tthrow new StoreConflict(\n\t\t'version',\n\t\t`updateUser: expected version ${ifVersion}, found ${stored.version}`,\n\t\t{\n\t\t\tuserId: id,\n\t\t\texpectedVersion: ifVersion,\n\t\t\tactualVersion: stored.version,\n\t\t\toperation: 'updateUser',\n\t\t},\n\t);\n}\n"
|
|
18
18
|
],
|
|
19
|
-
"mappings": "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",
|
|
19
|
+
"mappings": "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",
|
|
20
20
|
"debugId": "F77D618565EDC7F264756E2164756E21",
|
|
21
21
|
"names": []
|
|
22
22
|
}
|
package/dist/stores/index.d.ts
CHANGED
|
@@ -20,9 +20,10 @@ import type { Db } from 'mongodb';
|
|
|
20
20
|
* collection: `@nxgt/mongo` names no update conditioned on anything but its
|
|
21
21
|
* own lock, and the port needs `version`, `revokedAt` and `kind`.
|
|
22
22
|
*
|
|
23
|
-
* `sessions.deleteExpiredSessions`
|
|
24
|
-
*
|
|
25
|
-
*
|
|
23
|
+
* `sessions.deleteExpiredSessions` and `tokens.deleteExpiredTokens` are not
|
|
24
|
+
* implemented: a TTL index drops lapsed sessions and tokens, so
|
|
25
|
+
* `auth.collectExpired()` answers `UNSUPPORTED` — which is what the port asks
|
|
26
|
+
* of a store with its own expiry.
|
|
26
27
|
*/
|
|
27
28
|
export declare function createMongoStores(db: Db): JanusStores;
|
|
28
29
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/stores/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC/C,OAAO,EACN,KAAK,WAAW,EAChB,KAAK,UAAU,EAEf,MAAM,aAAa,CAAC;AACrB,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,SAAS,CAAC;AAMlC
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/stores/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC/C,OAAO,EACN,KAAK,WAAW,EAChB,KAAK,UAAU,EAEf,MAAM,aAAa,CAAC;AACrB,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,SAAS,CAAC;AAMlC;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAgB,iBAAiB,CAAC,EAAE,EAAE,EAAE,GAAG,WAAW,CAMrD;AAED;;;;;;;GAOG;AACH,wBAAgB,eAAe,CAC9B,EAAE,EAAE,EAAE,EACN,OAAO,CAAC,EAAE,WAAW,GACnB,OAAO,CAAC,UAAU,EAAE,CAAC,CAEvB"}
|
package/docs/guide/sync.md
CHANGED
|
@@ -162,8 +162,8 @@ only while no user has been given codes, which `@nxgt/janus` does from
|
|
|
162
162
|
MongoDB's TTL monitor runs every sixty seconds, so a lapsed session can stay
|
|
163
163
|
readable for up to a minute. The core compares `expiresAt` on every read, and
|
|
164
164
|
that is what expires it; the TTL index only keeps storage tidy. It is also why
|
|
165
|
-
`deleteExpiredSessions`
|
|
166
|
-
`UNSUPPORTED` with this adapter.
|
|
165
|
+
`deleteExpiredSessions` and `deleteExpiredTokens` are not implemented, and
|
|
166
|
+
`auth.collectExpired()` answers `UNSUPPORTED` with this adapter.
|
|
167
167
|
|
|
168
168
|
## See also
|
|
169
169
|
|
package/docs/guide/wiring.md
CHANGED
|
@@ -65,9 +65,9 @@ the first command goes out on the first call that needs one. `db` is a
|
|
|
65
65
|
collections of it.
|
|
66
66
|
|
|
67
67
|
Every method of the port is implemented except the optional
|
|
68
|
-
`deleteExpiredSessions`: a TTL index drops lapsed
|
|
69
|
-
`auth.collectExpired()` answers `UNSUPPORTED` with
|
|
70
|
-
schedule it. The other optional method, `findUsers` (since 0.8), is
|
|
68
|
+
`deleteExpiredSessions` and `deleteExpiredTokens`: a TTL index drops lapsed
|
|
69
|
+
sessions and tokens, so `auth.collectExpired()` answers `UNSUPPORTED` with
|
|
70
|
+
this adapter. Do not schedule it. The other optional method, `findUsers` (since 0.8), is
|
|
71
71
|
implemented: one `find` on `{ _id: { $in: ids } }`, so
|
|
72
72
|
`auth.<type>.findMany(ids)` reads up to 100 users in one round trip.
|
|
73
73
|
|
package/docs/roadmap.md
CHANGED
|
@@ -18,8 +18,9 @@ Nothing yet.
|
|
|
18
18
|
## Not planned
|
|
19
19
|
|
|
20
20
|
- **`collectExpired()` with this adapter** — it answers `UNSUPPORTED` on
|
|
21
|
-
purpose
|
|
22
|
-
|
|
21
|
+
purpose, and for tokens as well as sessions (`@nxgt/janus` 0.25 collects
|
|
22
|
+
lapsed tokens from the stores that implement `deleteExpiredTokens`). The TTL
|
|
23
|
+
indexes on `sessions` and `tokens` already drop lapsed records, and the core decides expiry on every read regardless.
|
|
23
24
|
- **Retrying a relation transaction for you** — the driver's
|
|
24
25
|
`withTransaction` would retry an outage for two minutes before answering. A
|
|
25
26
|
relation write is idempotent, so retry it yourself, on your own terms.
|
package/docs/troubleshooting.md
CHANGED
|
@@ -36,7 +36,7 @@ How the driver's errors become the port's:
|
|
|
36
36
|
- [`LOGIN_TAKEN` — `<operation>: the login is taken by another <type>`](#login_taken--operation-the-login-is-taken-by-another-type)
|
|
37
37
|
- [`STORE_FAILED` — `<slot>.<operation>: a duplicate key on <fields>, which this adapter never writes on purpose`](#store_failed--slotoperation-a-duplicate-key-on-fields-which-this-adapter-never-writes-on-purpose)
|
|
38
38
|
- [`NOT_FOUND` / `VERSION_CONFLICT` — `updateUser: …`](#not_found--version_conflict--updateuser-)
|
|
39
|
-
- [`UNSUPPORTED` — `collectExpired: store.sessions does not implement deleteExpiredSessions …`](#unsupported--collectexpired-storesessions-does-not-implement-deleteexpiredsessions--)
|
|
39
|
+
- [`UNSUPPORTED` — `collectExpired: store.sessions does not implement deleteExpiredSessions, nor store.tokens deleteExpiredTokens …`](#unsupported--collectexpired-storesessions-does-not-implement-deleteexpiredsessions-nor-storetokens-deleteexpiredtokens--)
|
|
40
40
|
- [Lapsed sessions and tokens are still in the collection](#lapsed-sessions-and-tokens-are-still-in-the-collection)
|
|
41
41
|
- [`findObjects` answers ids in a different order than JavaScript sorts them](#findobjects-answers-ids-in-a-different-order-than-javascript-sorts-them)
|
|
42
42
|
|
|
@@ -174,10 +174,10 @@ if (error instanceof JanusError && error.code === 'STORE_FAILED') {
|
|
|
174
174
|
**Why:** the write matched nothing, and the adapter reads again to tell an unknown id from a version that moved. On a conflict nothing was written.
|
|
175
175
|
**Fix:** for a conflict, read the user again and retry; see `VERSION_CONFLICT` in the core's troubleshooting.
|
|
176
176
|
|
|
177
|
-
### `UNSUPPORTED` — `collectExpired: store.sessions does not implement deleteExpiredSessions — …`
|
|
177
|
+
### `UNSUPPORTED` — `collectExpired: store.sessions does not implement deleteExpiredSessions, nor store.tokens deleteExpiredTokens — …`
|
|
178
178
|
|
|
179
179
|
**When:** `auth.collectExpired()`.
|
|
180
|
-
**Why:** deliberate. The `expiry` TTL
|
|
180
|
+
**Why:** deliberate. The `expiry` TTL indexes already delete lapsed sessions and tokens, so this adapter implements neither `deleteExpiredSessions` nor `deleteExpiredTokens`.
|
|
181
181
|
**Fix:** do not schedule `collectExpired` with this adapter. Nothing is lost: expiry never depended on it.
|
|
182
182
|
|
|
183
183
|
### Lapsed sessions and tokens are still in the collection
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nxgt/janus-mongo",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.3",
|
|
4
4
|
"description": "The MongoDB adapter for @nxgt/janus: users, sessions, one-time tokens and permission tuples",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
@@ -48,7 +48,7 @@
|
|
|
48
48
|
]
|
|
49
49
|
},
|
|
50
50
|
"devDependencies": {
|
|
51
|
-
"@nxgt/janus": "^0.
|
|
51
|
+
"@nxgt/janus": "^0.26.0",
|
|
52
52
|
"@nxgt/mongo": "^0.19.3",
|
|
53
53
|
"@types/bun": "^1.4.2",
|
|
54
54
|
"mongodb": "^7.6.0",
|
|
@@ -56,7 +56,7 @@
|
|
|
56
56
|
"zod": "^4.6.5"
|
|
57
57
|
},
|
|
58
58
|
"peerDependencies": {
|
|
59
|
-
"@nxgt/janus": "^0.
|
|
59
|
+
"@nxgt/janus": "^0.26.0",
|
|
60
60
|
"@nxgt/mongo": ">=0.17.0 <1",
|
|
61
61
|
"mongodb": ">=7.0.0 <8",
|
|
62
62
|
"typescript": "^6.0.3 || ^7.0.0",
|