@memberjunction/realtime-runtime 6.2.0-edge.2 → 6.2.0-edge.4

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.
Files changed (98) hide show
  1. package/README.md +75 -0
  2. package/dist/channels/base-realtime-channel-client.d.ts +535 -28
  3. package/dist/channels/base-realtime-channel-client.d.ts.map +1 -1
  4. package/dist/channels/base-realtime-channel-client.js +864 -10
  5. package/dist/channels/base-realtime-channel-client.js.map +1 -1
  6. package/dist/channels/channel-action-dispatcher.d.ts +70 -0
  7. package/dist/channels/channel-action-dispatcher.d.ts.map +1 -0
  8. package/dist/channels/channel-action-dispatcher.js +136 -0
  9. package/dist/channels/channel-action-dispatcher.js.map +1 -0
  10. package/dist/channels/channel-catalog-note.d.ts +48 -0
  11. package/dist/channels/channel-catalog-note.d.ts.map +1 -0
  12. package/dist/channels/channel-catalog-note.js +119 -0
  13. package/dist/channels/channel-catalog-note.js.map +1 -0
  14. package/dist/channels/channel-contract-types.d.ts +107 -0
  15. package/dist/channels/channel-contract-types.d.ts.map +1 -0
  16. package/dist/channels/channel-contract-types.js +12 -0
  17. package/dist/channels/channel-contract-types.js.map +1 -0
  18. package/dist/channels/channel-descriptor-synthesis.d.ts +56 -0
  19. package/dist/channels/channel-descriptor-synthesis.d.ts.map +1 -0
  20. package/dist/channels/channel-descriptor-synthesis.js +90 -0
  21. package/dist/channels/channel-descriptor-synthesis.js.map +1 -0
  22. package/dist/channels/channel-perception.d.ts +82 -0
  23. package/dist/channels/channel-perception.d.ts.map +1 -0
  24. package/dist/channels/channel-perception.js +120 -0
  25. package/dist/channels/channel-perception.js.map +1 -0
  26. package/dist/channels/channel-schema-format.d.ts +17 -0
  27. package/dist/channels/channel-schema-format.d.ts.map +1 -0
  28. package/dist/channels/channel-schema-format.js +45 -0
  29. package/dist/channels/channel-schema-format.js.map +1 -0
  30. package/dist/channels/channel-state-delta.d.ts +59 -0
  31. package/dist/channels/channel-state-delta.d.ts.map +1 -0
  32. package/dist/channels/channel-state-delta.js +116 -0
  33. package/dist/channels/channel-state-delta.js.map +1 -0
  34. package/dist/channels/channel-surface-placement.d.ts +25 -0
  35. package/dist/channels/channel-surface-placement.d.ts.map +1 -0
  36. package/dist/channels/channel-surface-placement.js +29 -0
  37. package/dist/channels/channel-surface-placement.js.map +1 -0
  38. package/dist/channels/channel-visual-pump.d.ts +126 -0
  39. package/dist/channels/channel-visual-pump.d.ts.map +1 -0
  40. package/dist/channels/channel-visual-pump.js +174 -0
  41. package/dist/channels/channel-visual-pump.js.map +1 -0
  42. package/dist/hosts/IRealtimeMediaHost.d.ts +61 -4
  43. package/dist/hosts/IRealtimeMediaHost.d.ts.map +1 -1
  44. package/dist/hosts/IRealtimeMediaHost.js +2 -1
  45. package/dist/hosts/IRealtimeMediaHost.js.map +1 -1
  46. package/dist/index.d.ts +21 -2
  47. package/dist/index.d.ts.map +1 -1
  48. package/dist/index.js +24 -0
  49. package/dist/index.js.map +1 -1
  50. package/dist/session/RealtimeSessionRuntime.d.ts +730 -70
  51. package/dist/session/RealtimeSessionRuntime.d.ts.map +1 -1
  52. package/dist/session/RealtimeSessionRuntime.js +1761 -241
  53. package/dist/session/RealtimeSessionRuntime.js.map +1 -1
  54. package/dist/session/RecordingShardQueue.d.ts +77 -0
  55. package/dist/session/RecordingShardQueue.d.ts.map +1 -0
  56. package/dist/session/RecordingShardQueue.js +172 -0
  57. package/dist/session/RecordingShardQueue.js.map +1 -0
  58. package/dist/session/app-client-tool-registry.d.ts +76 -0
  59. package/dist/session/app-client-tool-registry.d.ts.map +1 -0
  60. package/dist/session/app-client-tool-registry.js +100 -0
  61. package/dist/session/app-client-tool-registry.js.map +1 -0
  62. package/dist/session/avatar-notice.d.ts +43 -0
  63. package/dist/session/avatar-notice.d.ts.map +1 -0
  64. package/dist/session/avatar-notice.js +60 -0
  65. package/dist/session/avatar-notice.js.map +1 -0
  66. package/dist/session/call-end.d.ts +21 -0
  67. package/dist/session/call-end.d.ts.map +1 -0
  68. package/dist/session/call-end.js +19 -0
  69. package/dist/session/call-end.js.map +1 -0
  70. package/dist/session/channel-exposure-preferences.d.ts +70 -0
  71. package/dist/session/channel-exposure-preferences.d.ts.map +1 -0
  72. package/dist/session/channel-exposure-preferences.js +138 -0
  73. package/dist/session/channel-exposure-preferences.js.map +1 -0
  74. package/dist/session/channel-session-scope.d.ts +142 -0
  75. package/dist/session/channel-session-scope.d.ts.map +1 -0
  76. package/dist/session/channel-session-scope.js +128 -0
  77. package/dist/session/channel-session-scope.js.map +1 -0
  78. package/dist/session/client-session-deadline.d.ts +28 -0
  79. package/dist/session/client-session-deadline.d.ts.map +1 -0
  80. package/dist/session/client-session-deadline.js +50 -0
  81. package/dist/session/client-session-deadline.js.map +1 -0
  82. package/dist/session/realtime-captures.d.ts +236 -0
  83. package/dist/session/realtime-captures.d.ts.map +1 -0
  84. package/dist/session/realtime-captures.js +383 -0
  85. package/dist/session/realtime-captures.js.map +1 -0
  86. package/dist/session/realtime-microphone.d.ts +50 -0
  87. package/dist/session/realtime-microphone.d.ts.map +1 -0
  88. package/dist/session/realtime-microphone.js +51 -0
  89. package/dist/session/realtime-microphone.js.map +1 -0
  90. package/dist/session/session-event-hub.d.ts +72 -0
  91. package/dist/session/session-event-hub.d.ts.map +1 -0
  92. package/dist/session/session-event-hub.js +151 -0
  93. package/dist/session/session-event-hub.js.map +1 -0
  94. package/dist/session/session-launcher.d.ts +128 -0
  95. package/dist/session/session-launcher.d.ts.map +1 -0
  96. package/dist/session/session-launcher.js +160 -0
  97. package/dist/session/session-launcher.js.map +1 -0
  98. package/package.json +9 -9
@@ -0,0 +1,142 @@
1
+ /**
2
+ * @fileoverview The **session-scoping helpers** of the realtime runtime — turning the channel plugins
3
+ * a session *could* have into the channels it *does* have.
4
+ *
5
+ * The decision itself (`ResolveRealtimeChannelScope`) is pure and lives in `@memberjunction/ai-core-plus`
6
+ * so the server and the browser make it identically. What lives here is the browser-side plumbing around it:
7
+ *
8
+ * - {@link PreparedChannel} — a plugin that has been *resolved* (from the registry or declared by the
9
+ * host) but not yet *initialized*. Preparing is side-effect free, which is what lets the runtime
10
+ * report candidates to the server at mint without having started anything the server may then veto.
11
+ * - {@link BuildChannelCandidate} / {@link ResolveLocalChannelScope} — the facts the browser reports,
12
+ * and the scope it resolves on its own when no server policy comes back (a legacy server, or a host
13
+ * that mints through its own proxy).
14
+ * - {@link ReconcileChannelsWithPolicy} — maps a resolved policy back onto the prepared plugins.
15
+ * - {@link MergeToolMetadata} — layers a host's registered tool handlers over the manifest the host
16
+ * streamed, so "available tools" messages can describe them.
17
+ *
18
+ * Framework-free and DOM-free: importable in plain Node tests.
19
+ *
20
+ * @module @memberjunction/realtime-runtime
21
+ */
22
+ import type { JSONObject, RealtimeToolDefinition } from '@memberjunction/ai';
23
+ import { type ClientToolMetadata, type RealtimeChannelCandidate, type RealtimeChannelDescriptor, type RealtimeChannelDisplayPolicy, type RealtimeChannelRegistryState, type RealtimeChannelScopeResult, type ResolvedRealtimeChannel } from '@memberjunction/ai-core-plus';
24
+ import type { BaseRealtimeChannelClient } from '../channels/base-realtime-channel-client.js';
25
+ /**
26
+ * A channel the HOST brings to a session — the way a page or app adds a channel that has no
27
+ * `MJ: AI Agent Channels` row, which is the ONLY way a connect-only (anonymous embed) session
28
+ * gets channels, because that kind of session has no entity metadata to read the registry from.
29
+ *
30
+ * Supply either {@link ClientPluginClass} (a ClassFactory key, exactly like a registry row's
31
+ * `ClientPluginClass`) or {@link Create} (a factory — for a channel the host constructs itself, e.g.
32
+ * with injected collaborators). If both are given, {@link Create} wins.
33
+ *
34
+ * A host *adds* channels and supplies *defaults*; it cannot lift an agent or app `exclude`, and its
35
+ * `Config` / `DisplayPolicy` are overridden by the agent/app layers. An inactive registry row for the
36
+ * same channel still switches it off.
37
+ */
38
+ export interface RealtimeHostChannelDeclaration {
39
+ /** ClassFactory key of the channel plugin (`@RegisterClass(BaseRealtimeChannelClient, '<key>')`). */
40
+ ClientPluginClass?: string;
41
+ /** Factory that builds the plugin; use when the host constructs it with its own collaborators. */
42
+ Create?: () => BaseRealtimeChannelClient;
43
+ /** Default per-channel configuration; agent/app `channels.config` overrides it. */
44
+ Config?: JSONObject;
45
+ /** Default display for this host; agent/app `channels.displayPolicy` overrides it. */
46
+ DisplayPolicy?: RealtimeChannelDisplayPolicy;
47
+ }
48
+ /**
49
+ * Per-start options of {@link RealtimeSessionRuntime.StartRealtimeSession} that are not part of the
50
+ * mint contract. Every field is optional; omit the whole object for the behavior hosts always had.
51
+ */
52
+ export interface RealtimeSessionStartOptions {
53
+ /** Channels the host brings to this session (see {@link RealtimeHostChannelDeclaration}). */
54
+ HostChannels?: RealtimeHostChannelDeclaration[];
55
+ /** The fork (`MJ: Conversation Branches.ID`) the session starts on; omitted or null is Main. */
56
+ ConversationBranchID?: string | null;
57
+ /**
58
+ * Have the user check the camera before the agent sees it. The call's first camera start opens the camera for the
59
+ * user only: the camera's state is `starting` with `Checking` set and the stream to preview, and nothing reaches the
60
+ * agent until the host calls `ConfirmCamera`. Later starts in the same call skip the check. Set it only when the host
61
+ * shows the check; otherwise the camera waits for a confirmation that never comes.
62
+ */
63
+ CameraCheck?: boolean;
64
+ }
65
+ /** A resolved-but-not-yet-initialized channel plugin, with what the scope decision needs to know about it. */
66
+ export interface PreparedChannel {
67
+ /** The plugin instance (constructed, NOT initialized). */
68
+ Plugin: BaseRealtimeChannelClient;
69
+ /** Its key (the plugin's `ChannelName`). */
70
+ Key: string;
71
+ /** Registry state: `'active'`, `'inactive'` (the kill switch), or `'none'` (host-declared only). */
72
+ Registry: RealtimeChannelRegistryState;
73
+ /** The host declaration that brought it, when one did. */
74
+ HostDeclaration?: RealtimeHostChannelDeclaration;
75
+ }
76
+ /** Looks a prepared channel up by key, case-insensitively. */
77
+ export declare function FindPreparedChannel(prepared: ReadonlyArray<PreparedChannel>, key: string): PreparedChannel | undefined;
78
+ /**
79
+ * Whether a session with these prepared channels could show the agent's video: one of them shows it (it sinks outbound
80
+ * video, as the Avatar channel does) and is not switched off in the registry. A policy can only select among the
81
+ * prepared plugins, so with none the session never asks for the agent's video at connect, whatever the server scopes:
82
+ * the mint can then ask the model for no avatar (`showsAgentVideo: false`).
83
+ *
84
+ * @param prepared The channels prepared for the session.
85
+ */
86
+ export declare function PreparedChannelsShowAgentVideo(prepared: ReadonlyArray<PreparedChannel>): boolean;
87
+ /**
88
+ * The facts the browser reports about one channel at mint (also the input to the local scope
89
+ * decision). Reads the plugin's descriptor and tools; never initializes it.
90
+ *
91
+ * @param prepared The prepared channel.
92
+ * @param descriptor The plugin's descriptor (passed in so callers read it once).
93
+ */
94
+ export declare function BuildChannelCandidate(prepared: PreparedChannel, descriptor: RealtimeChannelDescriptor): RealtimeChannelCandidate & {
95
+ Registry: RealtimeChannelRegistryState;
96
+ };
97
+ /**
98
+ * Resolves the scope from code defaults and host declarations alone — what the browser decides when
99
+ * no server policy arrives. Identical to the server's decision in the absence of an agent/app layer.
100
+ *
101
+ * @param candidates The reported candidates (with registry state).
102
+ */
103
+ export declare function ResolveLocalChannelScope(candidates: ReadonlyArray<RealtimeChannelCandidate & {
104
+ Registry: RealtimeChannelRegistryState;
105
+ }>): RealtimeChannelScopeResult;
106
+ /** The tools of each candidate, keyed by channel key — the input `SelectNativeChannelTools` wants. */
107
+ export declare function ToolsByChannelKey(candidates: ReadonlyArray<RealtimeChannelCandidate>): Map<string, ReadonlyArray<RealtimeToolDefinition>>;
108
+ /** A policy channel paired with the prepared plugin it names. */
109
+ export interface ReconciledChannel {
110
+ /** The prepared plugin. */
111
+ Prepared: PreparedChannel;
112
+ /** What the policy resolved for it. */
113
+ Resolved: ResolvedRealtimeChannel;
114
+ }
115
+ /** The outcome of {@link ReconcileChannelsWithPolicy}. */
116
+ export interface ChannelReconciliation {
117
+ /** Channels the policy puts in the session, in policy order. */
118
+ InSession: ReconciledChannel[];
119
+ /** Prepared plugins the policy left out — never initialized; the runtime just drops them. */
120
+ Dropped: PreparedChannel[];
121
+ /** Policy channels the browser has no plugin for (a stale or foreign policy); logged by the caller. */
122
+ Unknown: string[];
123
+ }
124
+ /**
125
+ * Maps a resolved policy back onto the prepared plugins. A policy can only select among plugins the
126
+ * browser actually has — it can never conjure one — so a key with no plugin is reported, not honored.
127
+ *
128
+ * @param prepared Every prepared plugin.
129
+ * @param channels The policy's in-session channels.
130
+ */
131
+ export declare function ReconcileChannelsWithPolicy(prepared: ReadonlyArray<PreparedChannel>, channels: ReadonlyArray<ResolvedRealtimeChannel>): ChannelReconciliation;
132
+ /**
133
+ * Overlays the metadata of tools a host registered handlers for onto the manifest it streamed, by
134
+ * name (case-insensitive). A registered tool's own description/schema wins when it supplied one; a
135
+ * bare `{ Name, Handler }` registration (what most hosts do) inherits the manifest's description and
136
+ * schema instead of showing up with none.
137
+ *
138
+ * @param registered The registry's tools as metadata.
139
+ * @param manifest The tools the host's app-context snapshot advertises (may be empty).
140
+ */
141
+ export declare function MergeToolMetadata(registered: ReadonlyArray<ClientToolMetadata>, manifest: ReadonlyArray<ClientToolMetadata>): ClientToolMetadata[];
142
+ //# sourceMappingURL=channel-session-scope.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"channel-session-scope.d.ts","sourceRoot":"","sources":["../../src/session/channel-session-scope.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,128 @@
1
+ /**
2
+ * @fileoverview The **session-scoping helpers** of the realtime runtime — turning the channel plugins
3
+ * a session *could* have into the channels it *does* have.
4
+ *
5
+ * The decision itself (`ResolveRealtimeChannelScope`) is pure and lives in `@memberjunction/ai-core-plus`
6
+ * so the server and the browser make it identically. What lives here is the browser-side plumbing around it:
7
+ *
8
+ * - {@link PreparedChannel} — a plugin that has been *resolved* (from the registry or declared by the
9
+ * host) but not yet *initialized*. Preparing is side-effect free, which is what lets the runtime
10
+ * report candidates to the server at mint without having started anything the server may then veto.
11
+ * - {@link BuildChannelCandidate} / {@link ResolveLocalChannelScope} — the facts the browser reports,
12
+ * and the scope it resolves on its own when no server policy comes back (a legacy server, or a host
13
+ * that mints through its own proxy).
14
+ * - {@link ReconcileChannelsWithPolicy} — maps a resolved policy back onto the prepared plugins.
15
+ * - {@link MergeToolMetadata} — layers a host's registered tool handlers over the manifest the host
16
+ * streamed, so "available tools" messages can describe them.
17
+ *
18
+ * Framework-free and DOM-free: importable in plain Node tests.
19
+ *
20
+ * @module @memberjunction/realtime-runtime
21
+ */
22
+ import { NormalizeChannelKey, ResolveRealtimeChannelScope, } from '@memberjunction/ai-core-plus';
23
+ /** Looks a prepared channel up by key, case-insensitively. */
24
+ export function FindPreparedChannel(prepared, key) {
25
+ const id = NormalizeChannelKey(key);
26
+ return prepared.find((p) => NormalizeChannelKey(p.Key) === id);
27
+ }
28
+ /**
29
+ * Whether a session with these prepared channels could show the agent's video: one of them shows it (it sinks outbound
30
+ * video, as the Avatar channel does) and is not switched off in the registry. A policy can only select among the
31
+ * prepared plugins, so with none the session never asks for the agent's video at connect, whatever the server scopes:
32
+ * the mint can then ask the model for no avatar (`showsAgentVideo: false`).
33
+ *
34
+ * @param prepared The channels prepared for the session.
35
+ */
36
+ export function PreparedChannelsShowAgentVideo(prepared) {
37
+ return prepared.some((p) => p.Registry !== 'inactive' && p.Plugin.ShowsAgentVideo);
38
+ }
39
+ /**
40
+ * The facts the browser reports about one channel at mint (also the input to the local scope
41
+ * decision). Reads the plugin's descriptor and tools; never initializes it.
42
+ *
43
+ * @param prepared The prepared channel.
44
+ * @param descriptor The plugin's descriptor (passed in so callers read it once).
45
+ */
46
+ export function BuildChannelCandidate(prepared, descriptor) {
47
+ const candidate = {
48
+ Key: prepared.Key,
49
+ DefaultAvailability: descriptor.DefaultAvailability,
50
+ DisplayPolicy: descriptor.DisplayPolicy,
51
+ MaxExposure: descriptor.MaxExposure,
52
+ ToolNamePrefix: prepared.Plugin.ToolNamePrefix,
53
+ Tools: prepared.Plugin.GetToolDefinitions(),
54
+ Registry: prepared.Registry,
55
+ };
56
+ const declaration = prepared.HostDeclaration;
57
+ if (declaration) {
58
+ candidate.HostDeclared = true;
59
+ if (declaration.Config) {
60
+ candidate.HostConfig = declaration.Config;
61
+ }
62
+ if (declaration.DisplayPolicy) {
63
+ candidate.HostDisplayPolicy = declaration.DisplayPolicy;
64
+ }
65
+ }
66
+ return candidate;
67
+ }
68
+ /**
69
+ * Resolves the scope from code defaults and host declarations alone — what the browser decides when
70
+ * no server policy arrives. Identical to the server's decision in the absence of an agent/app layer.
71
+ *
72
+ * @param candidates The reported candidates (with registry state).
73
+ */
74
+ export function ResolveLocalChannelScope(candidates) {
75
+ return ResolveRealtimeChannelScope({ Candidates: candidates.map((c) => ({ ...c })) });
76
+ }
77
+ /** The tools of each candidate, keyed by channel key — the input `SelectNativeChannelTools` wants. */
78
+ export function ToolsByChannelKey(candidates) {
79
+ return new Map(candidates.map((c) => [c.Key, c.Tools]));
80
+ }
81
+ /**
82
+ * Maps a resolved policy back onto the prepared plugins. A policy can only select among plugins the
83
+ * browser actually has — it can never conjure one — so a key with no plugin is reported, not honored.
84
+ *
85
+ * @param prepared Every prepared plugin.
86
+ * @param channels The policy's in-session channels.
87
+ */
88
+ export function ReconcileChannelsWithPolicy(prepared, channels) {
89
+ const inSession = [];
90
+ const unknown = [];
91
+ const used = new Set();
92
+ for (const resolved of channels) {
93
+ const match = FindPreparedChannel(prepared, resolved.Key);
94
+ if (match && !used.has(match)) {
95
+ used.add(match);
96
+ inSession.push({ Prepared: match, Resolved: resolved });
97
+ }
98
+ else if (!match) {
99
+ unknown.push(resolved.Key);
100
+ }
101
+ }
102
+ return { InSession: inSession, Dropped: prepared.filter((p) => !used.has(p)), Unknown: unknown };
103
+ }
104
+ /**
105
+ * Overlays the metadata of tools a host registered handlers for onto the manifest it streamed, by
106
+ * name (case-insensitive). A registered tool's own description/schema wins when it supplied one; a
107
+ * bare `{ Name, Handler }` registration (what most hosts do) inherits the manifest's description and
108
+ * schema instead of showing up with none.
109
+ *
110
+ * @param registered The registry's tools as metadata.
111
+ * @param manifest The tools the host's app-context snapshot advertises (may be empty).
112
+ */
113
+ export function MergeToolMetadata(registered, manifest) {
114
+ const fromManifest = new Map(manifest.map((t) => [t.Name.trim().toLowerCase(), t]));
115
+ return registered.map((tool) => {
116
+ const advertised = fromManifest.get(tool.Name.trim().toLowerCase());
117
+ if (!advertised) {
118
+ return tool;
119
+ }
120
+ return {
121
+ ...advertised,
122
+ ...tool,
123
+ Description: tool.Description || advertised.Description,
124
+ InputSchema: Object.keys(tool.InputSchema ?? {}).length > 0 ? tool.InputSchema : advertised.InputSchema,
125
+ };
126
+ });
127
+ }
128
+ //# sourceMappingURL=channel-session-scope.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"channel-session-scope.js","sourceRoot":"","sources":["../../src/session/channel-session-scope.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,28 @@
1
+ import { Observable } from 'rxjs';
2
+ /**
3
+ * The client's view of when its session must end — the CLIENT half of a limit the server enforces
4
+ * authoritatively (the janitor closes a session past its stored deadline whatever a client does).
5
+ *
6
+ * The client keeps a copy so it can end the call gracefully before the server does, and show a
7
+ * countdown. It follows one rule: **the server's word moves the deadline only later** when it arrives
8
+ * as an extension (identity verification relaxes a session's limits) — a stale or hostile value can
9
+ * therefore never cut a session short here, and nothing a client does with this class extends the
10
+ * server's deadline.
11
+ */
12
+ export declare class ClientSessionDeadline {
13
+ private readonly subject;
14
+ /** Emits the current deadline (or `null` when none is known), then every change. */
15
+ readonly Deadline$: Observable<Date | null>;
16
+ /** The current deadline, or `null` when none is known. */
17
+ get Value(): Date | null;
18
+ /** Sets the baseline deadline outright (a host that knows the session's cap at start). `null` clears it. */
19
+ Set(deadline: Date | null): void;
20
+ /**
21
+ * Applies a server-announced deadline: adopted when none is known or when it is LATER than the one
22
+ * held; ignored when earlier, equal or unparseable. Returns whether the deadline changed.
23
+ */
24
+ Extend(deadlineIso: string | undefined): boolean;
25
+ /** Forgets the deadline (session ended). */
26
+ Clear(): void;
27
+ }
28
+ //# sourceMappingURL=client-session-deadline.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client-session-deadline.d.ts","sourceRoot":"","sources":["../../src/session/client-session-deadline.ts"],"names":[],"mappings":"AAAA,OAAO,EAAmB,UAAU,EAAE,MAAM,MAAM,CAAC;AAEnD;;;;;;;;;GASG;AACH,qBAAa,qBAAqB;IAChC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAA0C;IAElE,oFAAoF;IACpF,SAAgB,SAAS,EAAE,UAAU,CAAC,IAAI,GAAG,IAAI,CAAC,CAA+B;IAEjF,0DAA0D;IAC1D,IAAW,KAAK,IAAI,IAAI,GAAG,IAAI,CAE9B;IAED,4GAA4G;IACrG,GAAG,CAAC,QAAQ,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI;IAIvC;;;OAGG;IACI,MAAM,CAAC,WAAW,EAAE,MAAM,GAAG,SAAS,GAAG,OAAO;IAgBvD,4CAA4C;IACrC,KAAK,IAAI,IAAI;CAGrB"}
@@ -0,0 +1,50 @@
1
+ import { BehaviorSubject } from 'rxjs';
2
+ /**
3
+ * The client's view of when its session must end — the CLIENT half of a limit the server enforces
4
+ * authoritatively (the janitor closes a session past its stored deadline whatever a client does).
5
+ *
6
+ * The client keeps a copy so it can end the call gracefully before the server does, and show a
7
+ * countdown. It follows one rule: **the server's word moves the deadline only later** when it arrives
8
+ * as an extension (identity verification relaxes a session's limits) — a stale or hostile value can
9
+ * therefore never cut a session short here, and nothing a client does with this class extends the
10
+ * server's deadline.
11
+ */
12
+ export class ClientSessionDeadline {
13
+ constructor() {
14
+ this.subject = new BehaviorSubject(null);
15
+ /** Emits the current deadline (or `null` when none is known), then every change. */
16
+ this.Deadline$ = this.subject.asObservable();
17
+ }
18
+ /** The current deadline, or `null` when none is known. */
19
+ get Value() {
20
+ return this.subject.value;
21
+ }
22
+ /** Sets the baseline deadline outright (a host that knows the session's cap at start). `null` clears it. */
23
+ Set(deadline) {
24
+ this.subject.next(deadline && Number.isFinite(deadline.getTime()) ? deadline : null);
25
+ }
26
+ /**
27
+ * Applies a server-announced deadline: adopted when none is known or when it is LATER than the one
28
+ * held; ignored when earlier, equal or unparseable. Returns whether the deadline changed.
29
+ */
30
+ Extend(deadlineIso) {
31
+ if (!deadlineIso) {
32
+ return false;
33
+ }
34
+ const parsed = new Date(deadlineIso);
35
+ if (!Number.isFinite(parsed.getTime())) {
36
+ return false;
37
+ }
38
+ const current = this.subject.value;
39
+ if (current !== null && parsed.getTime() <= current.getTime()) {
40
+ return false;
41
+ }
42
+ this.subject.next(parsed);
43
+ return true;
44
+ }
45
+ /** Forgets the deadline (session ended). */
46
+ Clear() {
47
+ this.subject.next(null);
48
+ }
49
+ }
50
+ //# sourceMappingURL=client-session-deadline.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client-session-deadline.js","sourceRoot":"","sources":["../../src/session/client-session-deadline.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAc,MAAM,MAAM,CAAC;AAEnD;;;;;;;;;GASG;AACH,MAAM,OAAO,qBAAqB;IAAlC;QACmB,YAAO,GAAG,IAAI,eAAe,CAAc,IAAI,CAAC,CAAC;QAElE,oFAAoF;QACpE,cAAS,GAA4B,IAAI,CAAC,OAAO,CAAC,YAAY,EAAE,CAAC;IAoCnF,CAAC;IAlCC,0DAA0D;IAC1D,IAAW,KAAK;QACd,OAAO,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC;IAC5B,CAAC;IAED,4GAA4G;IACrG,GAAG,CAAC,QAAqB;QAC9B,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,QAAQ,IAAI,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC;IACvF,CAAC;IAED;;;OAGG;IACI,MAAM,CAAC,WAA+B;QAC3C,IAAI,CAAC,WAAW,EAAE,CAAC;YACjB,OAAO,KAAK,CAAC;QACf,CAAC;QACD,MAAM,MAAM,GAAG,IAAI,IAAI,CAAC,WAAW,CAAC,CAAC;QACrC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,EAAE,CAAC,EAAE,CAAC;YACvC,OAAO,KAAK,CAAC;QACf,CAAC;QACD,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC;QACnC,IAAI,OAAO,KAAK,IAAI,IAAI,MAAM,CAAC,OAAO,EAAE,IAAI,OAAO,CAAC,OAAO,EAAE,EAAE,CAAC;YAC9D,OAAO,KAAK,CAAC;QACf,CAAC;QACD,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QAC1B,OAAO,IAAI,CAAC;IACd,CAAC;IAED,4CAA4C;IACrC,KAAK;QACV,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC1B,CAAC;CACF"}
@@ -0,0 +1,236 @@
1
+ /**
2
+ * @fileoverview The camera and the screen share of one realtime session: what the user chooses to show the agent
3
+ * besides the channels' own surfaces.
4
+ *
5
+ * A capture starts only when the user asks (a click in the host's UI) and in this order:
6
+ * 0. the session's policy must allow it ({@link RealtimeCapturesOptions.Admit}: the runtime admits a capture only while
7
+ * the channel that fronts it is in the session and lets the agent see pixels);
8
+ * 1. the model must be able to take it: an inbound video track is already live, or one is added now
9
+ * (`AddTrack`; a session never requests video before anyone shares, so it is not billed or limited for it);
10
+ * 2. the device or surface is opened: the camera through the host's `ILocalMediaController`, a screen, window or
11
+ * tab through the host's `RequestDisplayCapture`;
12
+ * 3. frames are sampled at the rate the track negotiated, by the host's sampler or the DOM default, and it becomes a
13
+ * source of the session's video source arbiter, which decides what the model sees and tells it when that changes.
14
+ * A sampler that cannot start fails the capture as `unsupported`: the capture does not report on, and the model is
15
+ * never told it can see it.
16
+ *
17
+ * With the camera check on ({@link RealtimeCapturesOptions.CameraCheck}), the first camera start waits between 2 and 3:
18
+ * the camera is open for the user to look at, and becomes a source only once the user confirms
19
+ * ({@link RealtimeCaptures.ConfirmCamera}).
20
+ *
21
+ * Stopping undoes all three. The track is removed again only when this class added it, no capture is left, and the
22
+ * arbiter has no other source: a video track the session was minted with (a channel's) stays, and so does one a channel
23
+ * started sending on while a capture was on. A camera that goes away (unplugged) or a share the user ends from the
24
+ * browser's own bar stops the capture the same way.
25
+ *
26
+ * @module @memberjunction/realtime-runtime
27
+ */
28
+ import { type Observable } from 'rxjs';
29
+ import { type BaseRealtimeClient, type CapturedDisplaySurface, type DisplayCaptureOptions, type FrameSamplerOptions, type ILocalMediaController, type MediaDevice } from '@memberjunction/ai-realtime-client';
30
+ import type { IRealtimeFrameSampler, IRealtimeMediaHost } from '../hosts/IRealtimeMediaHost.js';
31
+ /** What the user can show the agent besides a channel's surface. */
32
+ export type RealtimeCaptureKind = 'camera' | 'screen';
33
+ /** Why a capture did not start. */
34
+ export type RealtimeCaptureFailure =
35
+ /** There is no live session to show it to. */
36
+ 'no-session'
37
+ /** The model takes no (more) video, or the host cannot open this kind of capture. */
38
+ | 'unsupported'
39
+ /** The user, the operating system or the page's permissions policy refused. */
40
+ | 'denied'
41
+ /** There is no camera, or not the one asked for. */
42
+ | 'not-found'
43
+ /** The camera exists, but another application is using it. */
44
+ | 'in-use'
45
+ /** The user closed the browser's share picker without choosing. */
46
+ | 'cancelled'
47
+ /** The call's policy does not allow it: the channel that fronts it is not in the call, or may not show the agent video. */
48
+ | 'policy'
49
+ /** Anything else; see the message. */
50
+ | 'error';
51
+ /** One capture. */
52
+ export interface RealtimeCaptureState {
53
+ Status: 'off' | 'starting' | 'on' | 'failed';
54
+ /**
55
+ * The camera is open for the user to check, and the agent sees nothing until {@link RealtimeCaptures.ConfirmCamera}.
56
+ * Set only on a starting camera.
57
+ */
58
+ Checking?: boolean;
59
+ /**
60
+ * The live stream while on, or while the user checks the camera: the camera (show it mirrored) or the shared surface
61
+ * (show it as is).
62
+ */
63
+ Stream?: MediaStream;
64
+ /** What a screen share shows, while on. */
65
+ Surface?: CapturedDisplaySurface;
66
+ /**
67
+ * The shared panel's name, while a share of one panel of the page is on and the host named it
68
+ * (`DisplayCaptureOptions.PanelLabel`). The agent sees the share as "<name> (shared panel)".
69
+ */
70
+ PanelLabel?: string;
71
+ /** The camera in use, while the camera is open (being checked or on). */
72
+ DeviceID?: string;
73
+ /**
74
+ * The cameras the browser lists, while the camera is open: what {@link RealtimeCaptures.SwitchCamera} can move it to.
75
+ * A browser gives their names only once the user has allowed the camera.
76
+ */
77
+ Devices?: MediaDevice[];
78
+ /** Why the last start failed, while failed. */
79
+ Failure?: RealtimeCaptureFailure;
80
+ /** What to tell the user about the failure. */
81
+ Message?: string;
82
+ }
83
+ /** Both captures. */
84
+ export interface RealtimeCaptureStates {
85
+ Camera: RealtimeCaptureState;
86
+ Screen: RealtimeCaptureState;
87
+ }
88
+ /** Which captures a call offers the user: those it could start now. */
89
+ export interface RealtimeCaptureOffers {
90
+ Camera: boolean;
91
+ Screen: boolean;
92
+ }
93
+ /** Neither capture offered: what a host shows outside a call. */
94
+ export declare const REALTIME_CAPTURE_OFFERS_NONE: RealtimeCaptureOffers;
95
+ /**
96
+ * Creates the sampler for one capture, as {@link IRealtimeMediaHost.CreateFrameSampler} does: the runtime passes the
97
+ * host's; the default draws through the DOM; a test passes one that needs none.
98
+ */
99
+ export type RealtimeFrameSamplerFactory = (stream: MediaStream, options: FrameSamplerOptions) => IRealtimeFrameSampler;
100
+ /**
101
+ * The session's policy for one capture: refused with a reason for the user, or admitted with the channel it belongs to
102
+ * and whether the agent may see it yet.
103
+ */
104
+ export type RealtimeCaptureAdmission = {
105
+ Admitted: false;
106
+ Message: string;
107
+ } | {
108
+ Admitted: true;
109
+ /** The channel that fronts the capture: the user's "agent can see" choice for it is kept under this key. */
110
+ ChannelKey?: string;
111
+ /** Whether the agent may see it now. When not, it runs for the user only until {@link RealtimeCaptures.SetVisibleToAgent}. */
112
+ VisibleToAgent: boolean;
113
+ };
114
+ export interface RealtimeCapturesOptions {
115
+ /** The session's realtime client: the arbiter's sink and the owner of the video track. */
116
+ Client: BaseRealtimeClient;
117
+ /** The host's camera-and-microphone controller; without one there is no camera. */
118
+ LocalMedia: ILocalMediaController | null;
119
+ /** The host, for screen sharing (`RequestDisplayCapture`); without it there is no screen share. */
120
+ Host: IRealtimeMediaHost;
121
+ /**
122
+ * Creates each capture's frame sampler: the host's ({@link IRealtimeMediaHost.CreateFrameSampler}), which the runtime
123
+ * passes here. Defaults to a DOM {@link FrameSampler}, which cannot start without a DOM.
124
+ */
125
+ CreateSampler?: RealtimeFrameSamplerFactory;
126
+ /** Asked before each start, before anything is added or opened. Default: admitted, visible, with no channel. */
127
+ Admit?: (kind: RealtimeCaptureKind) => RealtimeCaptureAdmission;
128
+ /**
129
+ * Hold the first camera start for the user's check: the camera opens, and reaches the agent only after
130
+ * {@link RealtimeCaptures.ConfirmCamera}. Later starts skip the check. Default: off.
131
+ */
132
+ CameraCheck?: boolean;
133
+ }
134
+ /** Both captures off: what a host shows outside a session. */
135
+ export declare const REALTIME_CAPTURES_OFF: RealtimeCaptureStates;
136
+ /**
137
+ * The ids the camera and the screen share go by on the session's video source arbiter, and so on the runtime's
138
+ * `VideoSources$`; prefixed so they never meet a channel's (`Key#instance`). A host or channel finds a capture's source
139
+ * by its id there, to tell whether the model is being sent its frames (`Enabled` and `Active`).
140
+ */
141
+ export declare const REALTIME_CAPTURE_SOURCE_IDS: Readonly<Record<RealtimeCaptureKind, string>>;
142
+ /** The camera and the screen share of one session. Created once the session is connected; disposed at its end. */
143
+ export declare class RealtimeCaptures {
144
+ private readonly options;
145
+ private readonly states;
146
+ private readonly live;
147
+ /** Bumped by every Stop, so a start that resolves after it knows it was cancelled. */
148
+ private readonly generation;
149
+ /** Whether this class added the session's inbound video track, and so may remove it. */
150
+ private addedVideoTrack;
151
+ /** Whether the user has confirmed the camera check; later camera starts skip it. */
152
+ private cameraChecked;
153
+ private disposed;
154
+ /** How each capture is shown to the agent: set at its start, kept up to date by {@link SetVisibleToAgent}. */
155
+ private readonly showing;
156
+ constructor(options: RealtimeCapturesOptions);
157
+ /** Both captures now. */
158
+ get States(): RealtimeCaptureStates;
159
+ /** Both captures, now and on every change. Completes on {@link Dispose}. */
160
+ get States$(): Observable<RealtimeCaptureStates>;
161
+ /**
162
+ * Starts a capture and shows it to the agent. Already starting or on, it returns where it is. Always resolves;
163
+ * a failure is a state, with a message for the user. A camera that waits for the user's check resolves still
164
+ * starting, with `Checking` set and the stream to preview.
165
+ *
166
+ * @param kind The camera or a screen share.
167
+ * @param options The camera's device id, or what the share picker offers first (and a panel to share).
168
+ */
169
+ Start(kind: 'camera', options?: {
170
+ DeviceID?: string;
171
+ }): Promise<RealtimeCaptureState>;
172
+ Start(kind: 'screen', options?: DisplayCaptureOptions): Promise<RealtimeCaptureState>;
173
+ /**
174
+ * The user checked the camera and turned it on: it is shown to the agent from now on, and later camera starts skip the
175
+ * check. Returns the camera's state; unless the camera is waiting for its check, nothing changes. When frames cannot be
176
+ * taken from the camera, it fails as `unsupported` and the camera is released.
177
+ */
178
+ ConfirmCamera(): RealtimeCaptureState;
179
+ /**
180
+ * Moves the open camera (being checked or on) to another of its {@link RealtimeCaptureState.Devices}. The stream stays
181
+ * the same, so the preview and the agent's frames carry on from the new camera. When the new camera cannot open, the
182
+ * host's controller goes back to the one in use; when that fails too, the camera stops. Resolves with the camera's
183
+ * state; nothing changes while the camera is not open.
184
+ */
185
+ SwitchCamera(deviceId: string): Promise<RealtimeCaptureState>;
186
+ /**
187
+ * Lets the agent see a capture, or hides it from the agent while it keeps running for the user (the policy of the
188
+ * channel that fronts it changed). Applies to a capture that is still starting too. Quiet: the channel tells the model.
189
+ */
190
+ SetVisibleToAgent(kind: RealtimeCaptureKind, visible: boolean): void;
191
+ /** Stops a capture: no more frames, out of the arbiter, the device or share released. Safe when it is off. */
192
+ Stop(kind: RealtimeCaptureKind): void;
193
+ /** Stops both captures and completes {@link States$}. */
194
+ Dispose(): void;
195
+ private stateOf;
196
+ private setState;
197
+ private fail;
198
+ /**
199
+ * Fails a capture whose device or share opened but whose frames cannot be taken for the agent (its sampler could not
200
+ * start): lets go of what opened, reports `unsupported`, and gives the track back.
201
+ */
202
+ private failToShow;
203
+ /** The camera in use and the cameras to choose from, as the host's controller reports them now. */
204
+ private cameraDevices;
205
+ /**
206
+ * Keeps the open camera's device and list current as the controller reports them: a switch, a camera plugged in or
207
+ * removed, names that appear once the user allows the camera. While a switch is under way the device in use stays.
208
+ */
209
+ private followCamera;
210
+ /**
211
+ * Makes sure an inbound video track is live: the one the session already has, or one added now.
212
+ *
213
+ * @returns Why the model cannot take video, or `null` when it can.
214
+ */
215
+ private ensureVideoTrack;
216
+ /**
217
+ * Removes the video track this class added, once no capture is on or starting and the arbiter has no other source.
218
+ * A channel that started sending on the track while a capture was on (one opened mid-call before it had a track of its
219
+ * own) is such a source: removing the track would leave it sending nothing, right after the model was told it can see
220
+ * that channel. The track then stays for the session, as a channel's own does.
221
+ */
222
+ private releaseVideoTrack;
223
+ /**
224
+ * Samples the capture at the negotiated rate and registers it with the arbiter under `label`, as its channel's and as
225
+ * visible as the policy allows. The sampler starts first: one that cannot start (no DOM, and no sampler from the host)
226
+ * leaves nothing registered, so the model is never told it can see a capture that would send it nothing.
227
+ *
228
+ * @returns The running sampler, or `null` when sampling could not start.
229
+ */
230
+ private showToAgent;
231
+ /** Opens the camera through the host's controller, and stops the capture if the camera goes away. */
232
+ private openCamera;
233
+ /** Asks the host for a screen, window, tab or panel, and stops the capture when the share ends. */
234
+ private openScreen;
235
+ }
236
+ //# sourceMappingURL=realtime-captures.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"realtime-captures.d.ts","sourceRoot":"","sources":["../../src/session/realtime-captures.ts"],"names":[],"mappings":"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"}