@llui/agent 0.0.44 → 0.0.46
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/dist/client/agentConnect.d.ts +53 -1
- package/dist/client/agentConnect.d.ts.map +1 -1
- package/dist/client/agentConnect.js +130 -5
- package/dist/client/agentConnect.js.map +1 -1
- package/dist/client/effect-handler.d.ts +11 -0
- package/dist/client/effect-handler.d.ts.map +1 -1
- package/dist/client/effect-handler.js +26 -5
- package/dist/client/effect-handler.js.map +1 -1
- package/dist/client/effects.d.ts +17 -0
- package/dist/client/effects.d.ts.map +1 -1
- package/dist/client/effects.js.map +1 -1
- package/dist/client/factory.d.ts +53 -1
- package/dist/client/factory.d.ts.map +1 -1
- package/dist/client/factory.js +105 -0
- package/dist/client/factory.js.map +1 -1
- package/dist/server/core.d.ts +19 -0
- package/dist/server/core.d.ts.map +1 -1
- package/dist/server/core.js +35 -2
- package/dist/server/core.js.map +1 -1
- package/dist/server/lap/active.d.ts +19 -0
- package/dist/server/lap/active.d.ts.map +1 -0
- package/dist/server/lap/active.js +25 -0
- package/dist/server/lap/active.js.map +1 -0
- package/dist/server/lap/confirm-result.d.ts.map +1 -1
- package/dist/server/lap/confirm-result.js +4 -1
- package/dist/server/lap/confirm-result.js.map +1 -1
- package/dist/server/lap/describe.d.ts.map +1 -1
- package/dist/server/lap/describe.js +10 -11
- package/dist/server/lap/describe.js.map +1 -1
- package/dist/server/lap/forward.d.ts.map +1 -1
- package/dist/server/lap/forward.js +12 -6
- package/dist/server/lap/forward.js.map +1 -1
- package/dist/server/lap/message.d.ts.map +1 -1
- package/dist/server/lap/message.js +4 -1
- package/dist/server/lap/message.js.map +1 -1
- package/dist/server/lap/observe.d.ts.map +1 -1
- package/dist/server/lap/observe.js +8 -3
- package/dist/server/lap/observe.js.map +1 -1
- package/dist/server/lap/paused.d.ts +30 -0
- package/dist/server/lap/paused.d.ts.map +1 -0
- package/dist/server/lap/paused.js +38 -0
- package/dist/server/lap/paused.js.map +1 -0
- package/dist/server/lap/wait.d.ts.map +1 -1
- package/dist/server/lap/wait.js +4 -1
- package/dist/server/lap/wait.js.map +1 -1
- package/dist/server/token-store.d.ts.map +1 -1
- package/dist/server/token-store.js +7 -0
- package/dist/server/token-store.js.map +1 -1
- package/package.json +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"token-store.js","sourceRoot":"","sources":["../../src/server/token-store.ts"],"names":[],"mappings":"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","sourcesContent":["import type { TokenRecord } from '../protocol.js'\n\n/**\n * Append-only, read-friendly storage for token records. See spec §10.3.\n *\n * Tokens are looked up by `tokenHash` (SHA-256 of the presented bearer\n * value) on every authenticated request. The `tid` index is kept for\n * the resume / revoke / sessions surfaces — those operate on session\n * IDs the user can see and copy.\n */\nexport interface TokenStore {\n create(record: TokenRecord): Promise<void>\n findByTid(tid: string): Promise<TokenRecord | null>\n /**\n * Look up a record by the SHA-256 hash of its bearer token. Returns\n * `null` when the hash isn't in the store (the typical \"this token\n * isn't ours / has been revoked / never existed\" case).\n */\n findByTokenHash(tokenHash: string): Promise<TokenRecord | null>\n listByIdentity(uid: string): Promise<TokenRecord[]>\n touch(tid: string, now: number): Promise<void>\n markPendingResume(tid: string, until: number): Promise<void>\n /** Transition to awaiting-claude: browser WS is connected, waiting for Claude's first call. */\n markAwaitingClaude(tid: string, now: number): Promise<void>\n markActive(tid: string, label: string, now: number): Promise<void>\n revoke(tid: string): Promise<void>\n /**\n * Replace the bearer token's hash and bump expiry. Used by the\n * resume-claim flow: the old token is invalidated (its hash is no\n * longer indexed) and a freshly-minted opaque token takes its\n * place. The `tid` stays stable so existing audit / pairing state\n * carries over.\n */\n rotateTokenHash(tid: string, newTokenHash: string, expiresAt: number): Promise<void>\n}\n\nexport class InMemoryTokenStore implements TokenStore {\n private byTid = new Map<string, TokenRecord>()\n // Secondary index for the auth hot path. Kept in sync with `byTid`\n // on `create`. Persistent stores would index this column at schema\n // time; the in-memory map is the same idea minus the DB.\n private tidByTokenHash = new Map<string, string>()\n\n async create(record: TokenRecord): Promise<void> {\n this.byTid.set(record.tid, { ...record })\n this.tidByTokenHash.set(record.tokenHash, record.tid)\n }\n\n async findByTid(tid: string): Promise<TokenRecord | null> {\n const r = this.byTid.get(tid)\n return r ? { ...r } : null\n }\n\n async findByTokenHash(tokenHash: string): Promise<TokenRecord | null> {\n const tid = this.tidByTokenHash.get(tokenHash)\n if (!tid) return null\n const r = this.byTid.get(tid)\n return r ? { ...r } : null\n }\n\n async listByIdentity(uid: string): Promise<TokenRecord[]> {\n const out: TokenRecord[] = []\n for (const r of this.byTid.values()) {\n if (r.uid === uid) out.push({ ...r })\n }\n return out\n }\n\n async touch(tid: string, now: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, lastSeenAt: now })\n }\n\n async markPendingResume(tid: string, until: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, status: 'pending-resume', pendingResumeUntil: until })\n }\n\n async markAwaitingClaude(tid: string, now: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, status: 'awaiting-claude', lastSeenAt: now })\n }\n\n async markActive(tid: string, label: string, now: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, {\n ...r,\n status: 'active',\n label,\n lastSeenAt: now,\n pendingResumeUntil: null,\n })\n }\n\n async revoke(tid: string): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, status: 'revoked', pendingResumeUntil: null })\n // Drop the hash index entry so revoked tokens fail at the auth\n // boundary even if the bearer leaks. The byTid record stays for\n // audit / replay purposes.\n this.tidByTokenHash.delete(r.tokenHash)\n }\n\n async rotateTokenHash(tid: string, newTokenHash: string, expiresAt: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.tidByTokenHash.delete(r.tokenHash)\n this.byTid.set(tid, { ...r, tokenHash: newTokenHash, expiresAt })\n this.tidByTokenHash.set(newTokenHash, tid)\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"token-store.js","sourceRoot":"","sources":["../../src/server/token-store.ts"],"names":[],"mappings":"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","sourcesContent":["import type { TokenRecord } from '../protocol.js'\n\n/**\n * Append-only, read-friendly storage for token records. See spec §10.3.\n *\n * Tokens are looked up by `tokenHash` (SHA-256 of the presented bearer\n * value) on every authenticated request. The `tid` index is kept for\n * the resume / revoke / sessions surfaces — those operate on session\n * IDs the user can see and copy.\n */\nexport interface TokenStore {\n create(record: TokenRecord): Promise<void>\n findByTid(tid: string): Promise<TokenRecord | null>\n /**\n * Look up a record by the SHA-256 hash of its bearer token. Returns\n * `null` when the hash isn't in the store (the typical \"this token\n * isn't ours / has been revoked / never existed\" case).\n */\n findByTokenHash(tokenHash: string): Promise<TokenRecord | null>\n listByIdentity(uid: string): Promise<TokenRecord[]>\n touch(tid: string, now: number): Promise<void>\n markPendingResume(tid: string, until: number): Promise<void>\n /** Transition to awaiting-claude: browser WS is connected, waiting for Claude's first call. */\n markAwaitingClaude(tid: string, now: number): Promise<void>\n markActive(tid: string, label: string, now: number): Promise<void>\n revoke(tid: string): Promise<void>\n /**\n * Replace the bearer token's hash and bump expiry. Used by the\n * resume-claim flow: the old token is invalidated (its hash is no\n * longer indexed) and a freshly-minted opaque token takes its\n * place. The `tid` stays stable so existing audit / pairing state\n * carries over.\n */\n rotateTokenHash(tid: string, newTokenHash: string, expiresAt: number): Promise<void>\n}\n\nexport class InMemoryTokenStore implements TokenStore {\n private byTid = new Map<string, TokenRecord>()\n // Secondary index for the auth hot path. Kept in sync with `byTid`\n // on `create`. Persistent stores would index this column at schema\n // time; the in-memory map is the same idea minus the DB.\n private tidByTokenHash = new Map<string, string>()\n\n async create(record: TokenRecord): Promise<void> {\n this.byTid.set(record.tid, { ...record })\n this.tidByTokenHash.set(record.tokenHash, record.tid)\n }\n\n async findByTid(tid: string): Promise<TokenRecord | null> {\n const r = this.byTid.get(tid)\n return r ? { ...r } : null\n }\n\n async findByTokenHash(tokenHash: string): Promise<TokenRecord | null> {\n const tid = this.tidByTokenHash.get(tokenHash)\n if (!tid) return null\n const r = this.byTid.get(tid)\n return r ? { ...r } : null\n }\n\n async listByIdentity(uid: string): Promise<TokenRecord[]> {\n const out: TokenRecord[] = []\n for (const r of this.byTid.values()) {\n if (r.uid === uid) out.push({ ...r })\n }\n return out\n }\n\n async touch(tid: string, now: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, lastSeenAt: now })\n }\n\n async markPendingResume(tid: string, until: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n // Only transition from a live state. Don't lift `revoked` back\n // to `pending-resume` if a stale WS-close fires after a deliberate\n // revoke — and don't bring an already-`expired`/`pending-resume`\n // record back to a fresh grace window when the close handler\n // re-fires for any reason.\n if (r.status !== 'active' && r.status !== 'awaiting-claude') return\n this.byTid.set(tid, { ...r, status: 'pending-resume', pendingResumeUntil: until })\n }\n\n async markAwaitingClaude(tid: string, now: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, status: 'awaiting-claude', lastSeenAt: now })\n }\n\n async markActive(tid: string, label: string, now: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, {\n ...r,\n status: 'active',\n label,\n lastSeenAt: now,\n pendingResumeUntil: null,\n })\n }\n\n async revoke(tid: string): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.byTid.set(tid, { ...r, status: 'revoked', pendingResumeUntil: null })\n // Drop the hash index entry so revoked tokens fail at the auth\n // boundary even if the bearer leaks. The byTid record stays for\n // audit / replay purposes.\n this.tidByTokenHash.delete(r.tokenHash)\n }\n\n async rotateTokenHash(tid: string, newTokenHash: string, expiresAt: number): Promise<void> {\n const r = this.byTid.get(tid)\n if (!r) return\n this.tidByTokenHash.delete(r.tokenHash)\n this.byTid.set(tid, { ...r, tokenHash: newTokenHash, expiresAt })\n this.tidByTokenHash.set(newTokenHash, tid)\n }\n}\n"]}
|