@nolag/chat 0.1.3 → 0.2.0
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/ChatRoom.d.ts +30 -1
- package/dist/MessageStore.d.ts +5 -0
- package/dist/MessageStream.d.ts +56 -0
- package/dist/browser.js +1 -1
- package/dist/browser.js.map +1 -1
- package/dist/constants.d.ts +4 -0
- package/dist/index.cjs +227 -6
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.mjs +227 -6
- package/dist/index.mjs.map +1 -1
- package/dist/types.d.ts +45 -2
- package/package.json +1 -1
package/dist/ChatRoom.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import type { RoomContext } from '@nolag/js-sdk';
|
|
2
2
|
import { EventEmitter } from './EventEmitter';
|
|
3
|
-
import type { ChatRoomEvents, ChatMessage, ChatUser, ChatPresenceData, ResolvedChatOptions, SendMessageOptions } from './types';
|
|
3
|
+
import type { ChatRoomEvents, ChatMessage, ChatUser, ChatPresenceData, ResolvedChatOptions, SendMessageOptions, StreamMessageOptions, MessageStream } from './types';
|
|
4
4
|
/**
|
|
5
5
|
* ChatRoom — a single chat room with messages, users, and typing indicators.
|
|
6
6
|
*
|
|
@@ -36,6 +36,33 @@ export declare class ChatRoom extends EventEmitter<ChatRoomEvents> {
|
|
|
36
36
|
* Send a text message to this room. Returns an optimistic ChatMessage.
|
|
37
37
|
*/
|
|
38
38
|
sendMessage(text: string, options?: SendMessageOptions): ChatMessage;
|
|
39
|
+
/**
|
|
40
|
+
* Begin a streamed message (e.g. an AI response). Returns a handle you append
|
|
41
|
+
* tokens to. Receivers see the message appear and grow live; on `complete()`
|
|
42
|
+
* the full message is persisted like a normal message.
|
|
43
|
+
*
|
|
44
|
+
* @example
|
|
45
|
+
* ```ts
|
|
46
|
+
* const stream = room.startStream();
|
|
47
|
+
* for await (const token of llm) stream.append(token);
|
|
48
|
+
* stream.complete();
|
|
49
|
+
* ```
|
|
50
|
+
*/
|
|
51
|
+
startStream(options?: StreamMessageOptions): MessageStream;
|
|
52
|
+
/**
|
|
53
|
+
* Stream a message from a token source (sync or async iterable) — drops in
|
|
54
|
+
* for an LLM stream. Appends each chunk, finalizes on completion, and aborts
|
|
55
|
+
* (re-throwing) if the source errors.
|
|
56
|
+
*
|
|
57
|
+
* @example
|
|
58
|
+
* ```ts
|
|
59
|
+
* // OpenAI / Anthropic style streams yield text chunks
|
|
60
|
+
* await room.streamMessage(tokenIterable);
|
|
61
|
+
* ```
|
|
62
|
+
*/
|
|
63
|
+
streamMessage(source: AsyncIterable<string> | Iterable<string>, options?: StreamMessageOptions): Promise<ChatMessage>;
|
|
64
|
+
/** @internal Publish a final message on the persisted `messages` topic. */
|
|
65
|
+
private _publishFinalMessage;
|
|
39
66
|
/**
|
|
40
67
|
* Get all messages (alias for the messages getter).
|
|
41
68
|
*/
|
|
@@ -77,6 +104,8 @@ export declare class ChatRoom extends EventEmitter<ChatRoomEvents> {
|
|
|
77
104
|
/** @internal Unsubscribe and clean up */
|
|
78
105
|
_cleanup(): void;
|
|
79
106
|
private _handleIncomingMessage;
|
|
107
|
+
/** Handle an incoming live stream control payload (start / delta / abort). */
|
|
108
|
+
private _handleStreamEvent;
|
|
80
109
|
private _markRead;
|
|
81
110
|
private _setPresence;
|
|
82
111
|
}
|
package/dist/MessageStore.d.ts
CHANGED
|
@@ -23,6 +23,11 @@ export declare class MessageStore {
|
|
|
23
23
|
* Check if a message ID exists.
|
|
24
24
|
*/
|
|
25
25
|
has(id: string): boolean;
|
|
26
|
+
/**
|
|
27
|
+
* Get a message by ID. Returns the live reference (mutating it mutates the
|
|
28
|
+
* stored message), or undefined if not present.
|
|
29
|
+
*/
|
|
30
|
+
get(id: string): ChatMessage | undefined;
|
|
26
31
|
/**
|
|
27
32
|
* Clear all messages.
|
|
28
33
|
*/
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import type { ChatMessage, MessageStream as IMessageStream } from './types';
|
|
2
|
+
/**
|
|
3
|
+
* Wire payload for the ephemeral `_stream` control topic.
|
|
4
|
+
*
|
|
5
|
+
* Only the live preview travels here (start + coalesced deltas + abort); the
|
|
6
|
+
* authoritative, persisted final message is published on the `messages` topic
|
|
7
|
+
* by `complete()`, which is what finalizes receivers and shows in replay.
|
|
8
|
+
*/
|
|
9
|
+
export type StreamWirePayload = {
|
|
10
|
+
type: 'start';
|
|
11
|
+
id: string;
|
|
12
|
+
userId: string;
|
|
13
|
+
username: string;
|
|
14
|
+
avatar?: string;
|
|
15
|
+
timestamp: number;
|
|
16
|
+
} | {
|
|
17
|
+
type: 'delta';
|
|
18
|
+
id: string;
|
|
19
|
+
text: string;
|
|
20
|
+
} | {
|
|
21
|
+
type: 'abort';
|
|
22
|
+
id: string;
|
|
23
|
+
error?: string;
|
|
24
|
+
};
|
|
25
|
+
/** Callbacks the room wires into the controller. */
|
|
26
|
+
export interface MessageStreamHooks {
|
|
27
|
+
/** Publish a control payload on the ephemeral `_stream` topic. */
|
|
28
|
+
publishStream: (payload: StreamWirePayload) => void;
|
|
29
|
+
/** Publish the final, full message on the persisted `messages` topic. */
|
|
30
|
+
publishFinal: (message: ChatMessage) => void;
|
|
31
|
+
emitStart: (message: ChatMessage) => void;
|
|
32
|
+
emitChunk: (message: ChatMessage, delta: string) => void;
|
|
33
|
+
emitEnd: (message: ChatMessage) => void;
|
|
34
|
+
emitAbort: (message: ChatMessage, error?: string) => void;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Producer-side controller for an outgoing streamed message.
|
|
38
|
+
*
|
|
39
|
+
* `append()` updates the local message immediately and buffers the token; a
|
|
40
|
+
* timer flushes buffered tokens as a single network delta at most every
|
|
41
|
+
* `flushIntervalMs`, so a token-per-character source doesn't flood the broker.
|
|
42
|
+
*/
|
|
43
|
+
export declare class MessageStreamController implements IMessageStream {
|
|
44
|
+
private readonly _flushIntervalMs;
|
|
45
|
+
private readonly _hooks;
|
|
46
|
+
readonly message: ChatMessage;
|
|
47
|
+
private _buffer;
|
|
48
|
+
private _flushTimer;
|
|
49
|
+
private _closed;
|
|
50
|
+
constructor(message: ChatMessage, _flushIntervalMs: number, _hooks: MessageStreamHooks);
|
|
51
|
+
append(text: string): void;
|
|
52
|
+
complete(): ChatMessage;
|
|
53
|
+
abort(error?: string): void;
|
|
54
|
+
private _flush;
|
|
55
|
+
private _clearTimer;
|
|
56
|
+
}
|
package/dist/browser.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{NoLag as e}from"@nolag/js-sdk";class t{constructor(){this._handlers=new Map}on(e,t){return this._handlers.has(e)||this._handlers.set(e,new Set),this._handlers.get(e).add(t),this}off(e,t){return t?this._handlers.get(e)?.delete(t):this._handlers.delete(e),this}removeAllListeners(){return this._handlers.clear(),this}emit(e,...t){const s=this._handlers.get(e);if(s)for(const o of s)try{o(...t)}catch(t){console.error(`Error in ${String(e)} handler:`,t)}}listenerCount(e){return this._handlers.get(e)?.size??0}}class s{constructor(e){this._messages=[],this._ids=new Set,this._maxSize=e}add(e){if(this._ids.has(e.id))return!1;for(this._ids.add(e.id),this._messages.push(e),this._messages.length>1&&e.timestamp<this._messages[this._messages.length-2].timestamp&&this._messages.sort((e,t)=>e.timestamp-t.timestamp);this._messages.length>this._maxSize;){const e=this._messages.shift();this._ids.delete(e.id)}return!0}getAll(){return[...this._messages]}get size(){return this._messages.length}has(e){return this._ids.has(e)}clear(){this._messages=[],this._ids.clear()}}class o{constructor(e){this._users=new Map,this._actorToUserId=new Map,this._localActorId=e}addFromPresence(e,t,s){if(e===this._localActorId)return null;const o=this._actorToUserId.get(e),i=t.userId||o||e,n={userId:i,actorTokenId:e,username:t.username,avatar:t.avatar,metadata:t.metadata,status:t.status||"online",joinedAt:s||Date.now(),isLocal:!1};return this._users.set(i,n),this._actorToUserId.set(e,i),n}removeByActorId(e){if(e===this._localActorId)return null;const t=this._actorToUserId.get(e);if(!t)return null;const s=this._users.get(t)||null;return this._users.delete(t),this._actorToUserId.delete(e),s}getUser(e){return this._users.get(e)}getUserByActorId(e){const t=this._actorToUserId.get(e);return t?this._users.get(t):void 0}getAll(){return Array.from(this._users.values())}get users(){return this._users}clear(){this._users.clear(),this._actorToUserId.clear()}}class i{constructor(e){this._localTimer=null,this._localTyping=!1,this._remoteTimers=new Map,this._typingUserIds=new Set,this._onSend=null,this._onChange=null,this._timeout=e}onSend(e){this._onSend=e}onChange(e){this._onChange=e}startTyping(){this._localTyping||(this._localTyping=!0,this._onSend?.(!0)),this._localTimer&&clearTimeout(this._localTimer),this._localTimer=setTimeout(()=>{this.stopTyping()},this._timeout)}stopTyping(){this._localTyping&&(this._localTyping=!1,this._localTimer&&(clearTimeout(this._localTimer),this._localTimer=null),this._onSend?.(!1))}handleRemote(e,t){const s=this._remoteTimers.get(e);s&&clearTimeout(s),t?(this._typingUserIds.add(e),this._remoteTimers.set(e,setTimeout(()=>{this._typingUserIds.delete(e),this._remoteTimers.delete(e),this._onChange?.()},this._timeout+1e3))):(this._typingUserIds.delete(e),this._remoteTimers.delete(e)),this._onChange?.()}getTypingUserIds(){return this._typingUserIds}get isLocalTyping(){return this._localTyping}dispose(){this._localTimer&&clearTimeout(this._localTimer);for(const e of this._remoteTimers.values())clearTimeout(e);this._remoteTimers.clear(),this._typingUserIds.clear(),this._localTyping=!1,this._onSend=null,this._onChange=null}}function n(){return"undefined"!=typeof crypto&&"function"==typeof crypto.randomUUID?crypto.randomUUID():"xxxx-xxxx-xxxx-xxxx".replace(/x/g,()=>Math.floor(16*Math.random()).toString(16))}function r(e,t){return t?(...t)=>{console.log(`[${e}]`,...t)}:(...e)=>{}}const a="messages",h="_typing";class c extends t{constructor(e,t,n,r,a){super(),this._unreadCount=0,this._active=!1,this.name=e,this._roomContext=t,this._localUser=n,this._options=r,this._log=a,this._presenceManager=new o(n.actorTokenId),this._typingManager=new i(r.typingTimeout),this._messageStore=new s(r.maxMessageCache),this._typingManager.onSend(e=>{this._roomContext.emit(h,{userId:this._localUser.userId,typing:e},{echo:!1})}),this._typingManager.onChange(()=>{this.emit("typing",{users:this.typingUsers})})}get users(){return this._presenceManager.users}get messages(){return this._messageStore.getAll()}get typingUsers(){const e=this._typingManager.getTypingUserIds(),t=[];for(const s of e){const e=this._presenceManager.getUser(s);e&&t.push(e)}return t}get unreadCount(){return this._unreadCount}get active(){return this._active}markRead(){0!==this._unreadCount&&(this._unreadCount=0,this.emit("unreadChanged",{room:this.name,count:0}))}sendMessage(e,t){const s={id:n(),userId:this._localUser.userId,username:this._localUser.username,avatar:this._localUser.avatar,text:e,data:t?.data,timestamp:Date.now(),status:"sending",isReplay:!1};return this._messageStore.add(s),this.emit("messageSent",s),this._roomContext.emit(a,{id:s.id,userId:s.userId,username:s.username,avatar:s.avatar,text:s.text,data:s.data,timestamp:s.timestamp},{echo:!1}),s.status="sent",this._typingManager.stopTyping(),s}getMessages(){return this._messageStore.getAll()}startTyping(){this._typingManager.startTyping()}stopTyping(){this._typingManager.stopTyping()}getUsers(){return this._presenceManager.getAll()}getUser(e){return this._presenceManager.getUser(e)}_subscribe(){this._log("Room subscribe:",this.name),this._roomContext.subscribe(a),this._roomContext.subscribe(h),this._roomContext.on(a,(e,t)=>{this._handleIncomingMessage(e,t)}),this._roomContext.on(h,e=>{const{userId:t,typing:s}=e;t!==this._localUser.userId&&this._typingManager.handleRemote(t,s)})}_activate(){this._log("Room activate:",this.name),this._active=!0,this._markRead(),this._setPresence(),this._roomContext.fetchPresence().then(e=>{this._log("Room presence fetched:",this.name,e.length,"actors");for(const t of e)if(t.presence){const e=this._presenceManager.addFromPresence(t.actorTokenId,t.presence,t.joinedAt);e&&this.emit("userJoined",e)}}).catch(e=>{this._log("Failed to fetch room presence:",e)})}_deactivate(){this._log("Room deactivate:",this.name),this._active=!1,this._presenceManager.clear()}_handlePresenceJoin(e,t){const s=this._presenceManager.addFromPresence(e,t);s&&(this._log("User joined room:",this.name,s.username),this.emit("userJoined",s))}_handlePresenceLeave(e){const t=this._presenceManager.removeByActorId(e);t&&(this._log("User left room:",this.name,t.username),this._typingManager.handleRemote(t.userId,!1),this.emit("userLeft",t))}_handlePresenceUpdate(e,t){this._presenceManager.addFromPresence(e,t)}_handleReplayStart(e){this.emit("replayStart",{count:e})}_handleReplayEnd(e){this.emit("replayEnd",{replayed:e})}_updateLocalPresence(){this._setPresence()}_cleanup(){this._log("Room cleanup:",this.name),this._roomContext.unsubscribe(a),this._roomContext.unsubscribe(h),this._roomContext.off(a),this._roomContext.off(h),this._typingManager.dispose(),this._messageStore.clear(),this._presenceManager.clear(),this.removeAllListeners()}_handleIncomingMessage(e,t){const s=e,o={id:s.id,userId:s.userId,username:s.username,avatar:s.avatar,text:s.text,data:s.data,timestamp:s.timestamp,status:"delivered",isReplay:t.isReplay??!1};this._messageStore.add(o)&&(this.emit("message",o),this._active||o.isReplay||(this._unreadCount++,this.emit("unreadChanged",{room:this.name,count:this._unreadCount})))}_markRead(){0!==this._unreadCount&&(this._unreadCount=0,this.emit("unreadChanged",{room:this.name,count:0}))}_setPresence(){const e={userId:this._localUser.userId,username:this._localUser.username,avatar:this._localUser.avatar,status:this._localUser.status,metadata:this._localUser.metadata};this._roomContext.setPresence(e)}}class l extends t{constructor(e,t){super(),this._client=null,this._localUser=null,this._rooms=new Map,this._lobby=null,this._onlineUsers=new Map,this._actorToUserId=new Map,this._activeRoom=null,this._token=e,this._userId=n(),this._options={username:t.username,avatar:t.avatar,metadata:t.metadata,appName:t.appName??"chat",url:t.url,typingTimeout:t.typingTimeout??3e3,maxMessageCache:t.maxMessageCache??500,debug:t.debug??!1,reconnect:t.reconnect??!0,rooms:t.rooms??[]},this._log=r("NoLagChat",this._options.debug)}get connected(){return this._client?.connected??!1}get localUser(){return this._localUser}get rooms(){return this._rooms}async connect(){this._log("Connecting...");const t={debug:this._options.debug,reconnect:this._options.reconnect};this._options.url&&(t.url=this._options.url),this._client=e(this._token,t),this._client.on("connect",()=>{this._log("Connected"),this._rooms.size>0&&(this._log("Reconnected — restoring rooms..."),this._restoreRooms(),this.emit("reconnected"))}),this._client.on("disconnect",e=>{this._log("Disconnected:",e),this.emit("disconnected",e)}),this._client.on("reconnect",()=>{this._log("Reconnecting...")}),this._client.on("error",e=>{this._log("Error:",e),this.emit("error",e)}),this._client.on("replay:start",e=>{const t=e;for(const e of this._rooms.values())e._handleReplayStart(t.count)}),this._client.on("replay:end",e=>{const t=e;for(const e of this._rooms.values())e._handleReplayEnd(t.replayed)}),await this._client.connect(),this._client.on("presence:join",e=>{this._handleRoomPresenceJoin(e)}),this._client.on("presence:leave",e=>{this._handleRoomPresenceLeave(e)}),this._client.on("presence:update",e=>{this._handleRoomPresenceUpdate(e)}),this._localUser={userId:this._userId,actorTokenId:this._client.actorId,username:this._options.username,avatar:this._options.avatar,metadata:this._options.metadata,status:"online",joinedAt:Date.now(),isLocal:!0},this._log("Local user:",this._localUser.userId,"→",this._localUser.actorTokenId),await this._setupLobby();for(const e of this._options.rooms)this._subscribeRoom(e);this.emit("connected"),setTimeout(()=>{this._lobby&&this._client?.connected&&this._lobby.fetchPresence().then(e=>{this._hydrateOnlineUsers(e)}).catch(()=>{})},2e3)}disconnect(){this._log("Disconnecting...");for(const e of[...this._rooms.keys()])this.leaveRoom(e);this._lobby?.unsubscribe(),this._lobby=null,this._client?.disconnect(),this._client=null,this._onlineUsers.clear(),this._actorToUserId.clear(),this._localUser=null}joinRoom(e){if(!this._client||!this._localUser)throw new Error("Not connected — call connect() first");if(this._activeRoom&&this._activeRoom!==e){const e=this._rooms.get(this._activeRoom);e&&e._deactivate()}let t=this._rooms.get(e);return t||(t=this._subscribeRoom(e)),this._activeRoom=e,t._activate(),t}leaveRoom(e){const t=this._rooms.get(e);t&&(this._log("Leaving room:",e),t._cleanup(),this._rooms.delete(e),this._activeRoom===e&&(this._activeRoom=null))}getRooms(){return Array.from(this._rooms.values())}getOnlineUsers(){return Array.from(this._onlineUsers.values())}setStatus(e){if(this._localUser&&(this._localUser.status=e),this._activeRoom){const e=this._rooms.get(this._activeRoom);e&&e._updateLocalPresence()}}updateProfile(e){if(this._localUser&&(void 0!==e.username&&(this._localUser.username=e.username,this._options.username=e.username),void 0!==e.avatar&&(this._localUser.avatar=e.avatar,this._options.avatar=e.avatar),void 0!==e.metadata&&(this._localUser.metadata={...this._localUser.metadata,...e.metadata},this._options.metadata=this._localUser.metadata),this._activeRoom)){const e=this._rooms.get(this._activeRoom);e&&e._updateLocalPresence()}}_subscribeRoom(e){if(!this._client||!this._localUser)throw new Error("Not connected — call connect() first");this._log("Subscribing room:",e);const t=this._client.setApp(this._options.appName).setRoom(e),s=new c(e,t,this._localUser,this._options,r(`ChatRoom:${e}`,this._options.debug));return this._rooms.set(e,s),s._subscribe(),s}_handleRoomPresenceJoin(e){if(e.actorTokenId===this._localUser?.actorTokenId)return;const t=e.presence;if(!t?.userId)return;const s=this._presenceToUser(e.actorTokenId,t);this._actorToUserId.set(e.actorTokenId,s.userId),this._onlineUsers.has(s.userId)||(this._onlineUsers.set(s.userId,s),this.emit("userOnline",s));const o=this._activeRoom?this._rooms.get(this._activeRoom):void 0;o&&o._handlePresenceJoin(e.actorTokenId,t)}_handleRoomPresenceLeave(e){if(e.actorTokenId===this._localUser?.actorTokenId)return;const t=this._activeRoom?this._rooms.get(this._activeRoom):void 0;t&&t._handlePresenceLeave(e.actorTokenId)}_handleRoomPresenceUpdate(e){if(e.actorTokenId===this._localUser?.actorTokenId)return;const t=e.presence;if(!t?.userId)return;if(this._onlineUsers.has(t.userId)){const s=this._presenceToUser(e.actorTokenId,t);this._onlineUsers.set(s.userId,s),this.emit("userUpdated",s)}const s=this._activeRoom?this._rooms.get(this._activeRoom):void 0;s&&s._handlePresenceUpdate(e.actorTokenId,t)}async _setupLobby(){if(!this._client)return;this._lobby=this._client.setApp(this._options.appName).setLobby("online");const e=e=>t=>{const s=t;"join"===e?this._handleLobbyJoin(s):"leave"===e?this._handleLobbyLeave(s):this._handleLobbyUpdate(s)};this._client.on("lobbyPresence:join",e("join")),this._client.on("lobbyPresence:leave",e("leave")),this._client.on("lobbyPresence:update",e("update"));try{const e=await this._lobby.subscribe();this._hydrateOnlineUsers(e),this._log("Lobby subscribed, online users:",this._onlineUsers.size)}catch(e){this._log("Lobby subscription failed:",e)}}_handleLobbyJoin(e){const{actorId:t,data:s}=e;if(t===this._localUser?.actorTokenId)return;const o=s;if(!o.userId)return;const i=this._presenceToUser(t,o);this._actorToUserId.set(t,i.userId),this._onlineUsers.has(i.userId)||(this._onlineUsers.set(i.userId,i),this.emit("userOnline",i))}_handleLobbyLeave(e){const{actorId:t,data:s}=e;if(t===this._localUser?.actorTokenId)return;const o=s,i=o?.userId||this._actorToUserId.get(t)||this._findUserIdByActorId(t);if(i){const e=this._onlineUsers.get(i);e&&(this._onlineUsers.delete(i),this._actorToUserId.delete(t),this.emit("userOffline",e))}}_handleLobbyUpdate(e){const{actorId:t,data:s}=e;if(t===this._localUser?.actorTokenId)return;const o=s;if(!o.userId)return;const i=this._presenceToUser(t,o);this._onlineUsers.set(i.userId,i),this.emit("userUpdated",i)}_hydrateOnlineUsers(e){for(const t of Object.keys(e)){const s=e[t];for(const e of Object.keys(s)){if(e===this._localUser?.actorTokenId)continue;const t=s[e],o=t?.presence??t;if(o?.userId){const t=this._presenceToUser(e,o);this._actorToUserId.set(e,t.userId),this._onlineUsers.has(t.userId)||(this._onlineUsers.set(t.userId,t),this.emit("userOnline",t))}}}}_presenceToUser(e,t){return{userId:t.userId,actorTokenId:e,username:t.username,avatar:t.avatar,metadata:t.metadata,status:t.status||"online",joinedAt:Date.now(),isLocal:!1}}_findUserIdByActorId(e){for(const t of this._onlineUsers.values())if(t.actorTokenId===e)return t.userId}_restoreRooms(){if(this._activeRoom){const e=this._rooms.get(this._activeRoom);e&&e._updateLocalPresence()}this._lobby?.fetchPresence().then(e=>{this._onlineUsers.clear(),this._actorToUserId.clear(),this._hydrateOnlineUsers(e)}).catch(e=>{this._log("Failed to re-fetch lobby presence:",e)})}}export{c as ChatRoom,t as EventEmitter,l as NoLagChat};
|
|
1
|
+
import{NoLag as e}from"@nolag/js-sdk";class t{constructor(){this._handlers=new Map}on(e,t){return this._handlers.has(e)||this._handlers.set(e,new Set),this._handlers.get(e).add(t),this}off(e,t){return t?this._handlers.get(e)?.delete(t):this._handlers.delete(e),this}removeAllListeners(){return this._handlers.clear(),this}emit(e,...t){const s=this._handlers.get(e);if(s)for(const i of s)try{i(...t)}catch(t){console.error(`Error in ${String(e)} handler:`,t)}}listenerCount(e){return this._handlers.get(e)?.size??0}}class s{constructor(e){this._messages=[],this._ids=new Set,this._maxSize=e}add(e){if(this._ids.has(e.id))return!1;for(this._ids.add(e.id),this._messages.push(e),this._messages.length>1&&e.timestamp<this._messages[this._messages.length-2].timestamp&&this._messages.sort((e,t)=>e.timestamp-t.timestamp);this._messages.length>this._maxSize;){const e=this._messages.shift();this._ids.delete(e.id)}return!0}getAll(){return[...this._messages]}get size(){return this._messages.length}has(e){return this._ids.has(e)}get(e){if(this._ids.has(e))return this._messages.find(t=>t.id===e)}clear(){this._messages=[],this._ids.clear()}}class i{constructor(e){this._users=new Map,this._actorToUserId=new Map,this._localActorId=e}addFromPresence(e,t,s){if(e===this._localActorId)return null;const i=this._actorToUserId.get(e),r=t.userId||i||e,o={userId:r,actorTokenId:e,username:t.username,avatar:t.avatar,metadata:t.metadata,status:t.status||"online",joinedAt:s||Date.now(),isLocal:!1};return this._users.set(r,o),this._actorToUserId.set(e,r),o}removeByActorId(e){if(e===this._localActorId)return null;const t=this._actorToUserId.get(e);if(!t)return null;const s=this._users.get(t)||null;return this._users.delete(t),this._actorToUserId.delete(e),s}getUser(e){return this._users.get(e)}getUserByActorId(e){const t=this._actorToUserId.get(e);return t?this._users.get(t):void 0}getAll(){return Array.from(this._users.values())}get users(){return this._users}clear(){this._users.clear(),this._actorToUserId.clear()}}class r{constructor(e){this._localTimer=null,this._localTyping=!1,this._remoteTimers=new Map,this._typingUserIds=new Set,this._onSend=null,this._onChange=null,this._timeout=e}onSend(e){this._onSend=e}onChange(e){this._onChange=e}startTyping(){this._localTyping||(this._localTyping=!0,this._onSend?.(!0)),this._localTimer&&clearTimeout(this._localTimer),this._localTimer=setTimeout(()=>{this.stopTyping()},this._timeout)}stopTyping(){this._localTyping&&(this._localTyping=!1,this._localTimer&&(clearTimeout(this._localTimer),this._localTimer=null),this._onSend?.(!1))}handleRemote(e,t){const s=this._remoteTimers.get(e);s&&clearTimeout(s),t?(this._typingUserIds.add(e),this._remoteTimers.set(e,setTimeout(()=>{this._typingUserIds.delete(e),this._remoteTimers.delete(e),this._onChange?.()},this._timeout+1e3))):(this._typingUserIds.delete(e),this._remoteTimers.delete(e)),this._onChange?.()}getTypingUserIds(){return this._typingUserIds}get isLocalTyping(){return this._localTyping}dispose(){this._localTimer&&clearTimeout(this._localTimer);for(const e of this._remoteTimers.values())clearTimeout(e);this._remoteTimers.clear(),this._typingUserIds.clear(),this._localTyping=!1,this._onSend=null,this._onChange=null}}function o(){return"undefined"!=typeof crypto&&"function"==typeof crypto.randomUUID?crypto.randomUUID():"xxxx-xxxx-xxxx-xxxx".replace(/x/g,()=>Math.floor(16*Math.random()).toString(16))}function a(e,t){return t?(...t)=>{console.log(`[${e}]`,...t)}:(...e)=>{}}const n="messages",h="_typing",c="_stream";class l{constructor(e,t,s){this._flushIntervalMs=t,this._hooks=s,this._buffer="",this._flushTimer=null,this._closed=!1,this.message=e,this._hooks.publishStream({type:"start",id:e.id,userId:e.userId,username:e.username,avatar:e.avatar,timestamp:e.timestamp}),this._hooks.emitStart(e)}append(e){!this._closed&&e&&(this.message.text+=e,this._buffer+=e,this._hooks.emitChunk(this.message,e),this._flushTimer||(this._flushTimer=setTimeout(()=>this._flush(),this._flushIntervalMs)))}complete(){return this._closed||(this._flush(),this._closed=!0,this._clearTimer(),this.message.status="sent",this._hooks.publishFinal(this.message),this._hooks.emitEnd(this.message)),this.message}abort(e){this._closed||(this._closed=!0,this._clearTimer(),this._buffer="",this.message.status="aborted",this._hooks.publishStream({type:"abort",id:this.message.id,error:e}),this._hooks.emitAbort(this.message,e))}_flush(){this._clearTimer(),this._buffer&&(this._hooks.publishStream({type:"delta",id:this.message.id,text:this._buffer}),this._buffer="")}_clearTimer(){this._flushTimer&&(clearTimeout(this._flushTimer),this._flushTimer=null)}}class _ extends t{constructor(e,t,o,a,n){super(),this._unreadCount=0,this._active=!1,this.name=e,this._roomContext=t,this._localUser=o,this._options=a,this._log=n,this._presenceManager=new i(o.actorTokenId),this._typingManager=new r(a.typingTimeout),this._messageStore=new s(a.maxMessageCache),this._typingManager.onSend(e=>{this._roomContext.emit(h,{userId:this._localUser.userId,typing:e},{echo:!1})}),this._typingManager.onChange(()=>{this.emit("typing",{users:this.typingUsers})})}get users(){return this._presenceManager.users}get messages(){return this._messageStore.getAll()}get typingUsers(){const e=this._typingManager.getTypingUserIds(),t=[];for(const s of e){const e=this._presenceManager.getUser(s);e&&t.push(e)}return t}get unreadCount(){return this._unreadCount}get active(){return this._active}markRead(){0!==this._unreadCount&&(this._unreadCount=0,this.emit("unreadChanged",{room:this.name,count:0}))}sendMessage(e,t){const s={id:o(),userId:this._localUser.userId,username:this._localUser.username,avatar:this._localUser.avatar,text:e,data:t?.data,timestamp:Date.now(),status:"sending",isReplay:!1};return this._messageStore.add(s),this.emit("messageSent",s),this._publishFinalMessage(s),s.status="sent",this._typingManager.stopTyping(),s}startStream(e){const t={id:o(),userId:this._localUser.userId,username:this._localUser.username,avatar:this._localUser.avatar,text:"",data:e?.data,timestamp:Date.now(),status:"streaming",isReplay:!1};return this._messageStore.add(t),this._typingManager.stopTyping(),new l(t,e?.flushIntervalMs??60,{publishStream:e=>this._roomContext.emit(c,e,{echo:!1}),publishFinal:e=>this._publishFinalMessage(e),emitStart:e=>this.emit("streamStart",e),emitChunk:(e,t)=>this.emit("streamChunk",{message:e,delta:t}),emitEnd:e=>this.emit("streamEnd",e),emitAbort:(e,t)=>this.emit("streamAbort",{message:e,error:t})})}async streamMessage(e,t){const s=this.startStream(t);try{for await(const t of e)s.append(t);return s.complete()}catch(e){throw s.abort(e instanceof Error?e.message:String(e)),e}}_publishFinalMessage(e){this._roomContext.emit(n,{id:e.id,userId:e.userId,username:e.username,avatar:e.avatar,text:e.text,data:e.data,timestamp:e.timestamp},{echo:!1})}getMessages(){return this._messageStore.getAll()}startTyping(){this._typingManager.startTyping()}stopTyping(){this._typingManager.stopTyping()}getUsers(){return this._presenceManager.getAll()}getUser(e){return this._presenceManager.getUser(e)}_subscribe(){this._log("Room subscribe:",this.name),this._roomContext.subscribe(n),this._roomContext.subscribe(h),this._roomContext.subscribe(c),this._roomContext.on(n,(e,t)=>{this._handleIncomingMessage(e,t)}),this._roomContext.on(h,e=>{const{userId:t,typing:s}=e;t!==this._localUser.userId&&this._typingManager.handleRemote(t,s)}),this._roomContext.on(c,e=>{this._handleStreamEvent(e)})}_activate(){this._log("Room activate:",this.name),this._active=!0,this._markRead(),this._setPresence(),this._roomContext.fetchPresence().then(e=>{this._log("Room presence fetched:",this.name,e.length,"actors");for(const t of e)if(t.presence){const e=this._presenceManager.addFromPresence(t.actorTokenId,t.presence,t.joinedAt);e&&this.emit("userJoined",e)}}).catch(e=>{this._log("Failed to fetch room presence:",e)})}_deactivate(){this._log("Room deactivate:",this.name),this._active=!1,this._presenceManager.clear()}_handlePresenceJoin(e,t){const s=this._presenceManager.addFromPresence(e,t);s&&(this._log("User joined room:",this.name,s.username),this.emit("userJoined",s))}_handlePresenceLeave(e){const t=this._presenceManager.removeByActorId(e);t&&(this._log("User left room:",this.name,t.username),this._typingManager.handleRemote(t.userId,!1),this.emit("userLeft",t))}_handlePresenceUpdate(e,t){this._presenceManager.addFromPresence(e,t)}_handleReplayStart(e){this.emit("replayStart",{count:e})}_handleReplayEnd(e){this.emit("replayEnd",{replayed:e})}_updateLocalPresence(){this._setPresence()}_cleanup(){this._log("Room cleanup:",this.name),this._roomContext.unsubscribe(n),this._roomContext.unsubscribe(h),this._roomContext.unsubscribe(c),this._roomContext.off(n),this._roomContext.off(h),this._roomContext.off(c),this._typingManager.dispose(),this._messageStore.clear(),this._presenceManager.clear(),this.removeAllListeners()}_handleIncomingMessage(e,t){const s=e,i=s.id,r=this._messageStore.get(i);if(r&&"streaming"===r.status)return r.text=s.text,r.data=s.data,r.status="delivered",this.emit("streamEnd",r),this.emit("message",r),void(this._active||r.isReplay||(this._unreadCount++,this.emit("unreadChanged",{room:this.name,count:this._unreadCount})));const o={id:i,userId:s.userId,username:s.username,avatar:s.avatar,text:s.text,data:s.data,timestamp:s.timestamp,status:"delivered",isReplay:t.isReplay??!1};this._messageStore.add(o)&&(this.emit("message",o),this._active||o.isReplay||(this._unreadCount++,this.emit("unreadChanged",{room:this.name,count:this._unreadCount})))}_handleStreamEvent(e){const t=e;if(t&&t.id)switch(t.type){case"start":{if(t.userId===this._localUser.userId)return;const e={id:t.id,userId:t.userId,username:t.username,avatar:t.avatar,text:"",timestamp:t.timestamp,status:"streaming",isReplay:!1};this._messageStore.add(e)&&this.emit("streamStart",e);break}case"delta":{const e=this._messageStore.get(t.id);e&&"streaming"===e.status&&(e.text+=t.text,this.emit("streamChunk",{message:e,delta:t.text}));break}case"abort":{const e=this._messageStore.get(t.id);e&&"streaming"===e.status&&(e.status="aborted",this.emit("streamAbort",{message:e,error:t.error}));break}}}_markRead(){0!==this._unreadCount&&(this._unreadCount=0,this.emit("unreadChanged",{room:this.name,count:0}))}_setPresence(){const e={userId:this._localUser.userId,username:this._localUser.username,avatar:this._localUser.avatar,status:this._localUser.status,metadata:this._localUser.metadata};this._roomContext.setPresence(e)}}class d extends t{constructor(e,t){super(),this._client=null,this._localUser=null,this._rooms=new Map,this._lobby=null,this._onlineUsers=new Map,this._actorToUserId=new Map,this._activeRoom=null,this._token=e,this._userId=o(),this._options={username:t.username,avatar:t.avatar,metadata:t.metadata,appName:t.appName??"chat",url:t.url,typingTimeout:t.typingTimeout??3e3,maxMessageCache:t.maxMessageCache??500,debug:t.debug??!1,reconnect:t.reconnect??!0,rooms:t.rooms??[]},this._log=a("NoLagChat",this._options.debug)}get connected(){return this._client?.connected??!1}get localUser(){return this._localUser}get rooms(){return this._rooms}async connect(){this._log("Connecting...");const t={debug:this._options.debug,reconnect:this._options.reconnect};this._options.url&&(t.url=this._options.url),this._client=e(this._token,t),this._client.on("connect",()=>{this._log("Connected"),this._rooms.size>0&&(this._log("Reconnected — restoring rooms..."),this._restoreRooms(),this.emit("reconnected"))}),this._client.on("disconnect",e=>{this._log("Disconnected:",e),this.emit("disconnected",e)}),this._client.on("reconnect",()=>{this._log("Reconnecting...")}),this._client.on("error",e=>{this._log("Error:",e),this.emit("error",e)}),this._client.on("replay:start",e=>{const t=e;for(const e of this._rooms.values())e._handleReplayStart(t.count)}),this._client.on("replay:end",e=>{const t=e;for(const e of this._rooms.values())e._handleReplayEnd(t.replayed)}),await this._client.connect(),this._client.on("presence:join",e=>{this._handleRoomPresenceJoin(e)}),this._client.on("presence:leave",e=>{this._handleRoomPresenceLeave(e)}),this._client.on("presence:update",e=>{this._handleRoomPresenceUpdate(e)}),this._localUser={userId:this._userId,actorTokenId:this._client.actorId,username:this._options.username,avatar:this._options.avatar,metadata:this._options.metadata,status:"online",joinedAt:Date.now(),isLocal:!0},this._log("Local user:",this._localUser.userId,"→",this._localUser.actorTokenId),await this._setupLobby();for(const e of this._options.rooms)this._subscribeRoom(e);this.emit("connected"),setTimeout(()=>{this._lobby&&this._client?.connected&&this._lobby.fetchPresence().then(e=>{this._hydrateOnlineUsers(e)}).catch(()=>{})},2e3)}disconnect(){this._log("Disconnecting...");for(const e of[...this._rooms.keys()])this.leaveRoom(e);this._lobby?.unsubscribe(),this._lobby=null,this._client?.disconnect(),this._client=null,this._onlineUsers.clear(),this._actorToUserId.clear(),this._localUser=null}joinRoom(e){if(!this._client||!this._localUser)throw new Error("Not connected — call connect() first");if(this._activeRoom&&this._activeRoom!==e){const e=this._rooms.get(this._activeRoom);e&&e._deactivate()}let t=this._rooms.get(e);return t||(t=this._subscribeRoom(e)),this._activeRoom=e,t._activate(),t}leaveRoom(e){const t=this._rooms.get(e);t&&(this._log("Leaving room:",e),t._cleanup(),this._rooms.delete(e),this._activeRoom===e&&(this._activeRoom=null))}getRooms(){return Array.from(this._rooms.values())}getOnlineUsers(){return Array.from(this._onlineUsers.values())}setStatus(e){if(this._localUser&&(this._localUser.status=e),this._activeRoom){const e=this._rooms.get(this._activeRoom);e&&e._updateLocalPresence()}}updateProfile(e){if(this._localUser&&(void 0!==e.username&&(this._localUser.username=e.username,this._options.username=e.username),void 0!==e.avatar&&(this._localUser.avatar=e.avatar,this._options.avatar=e.avatar),void 0!==e.metadata&&(this._localUser.metadata={...this._localUser.metadata,...e.metadata},this._options.metadata=this._localUser.metadata),this._activeRoom)){const e=this._rooms.get(this._activeRoom);e&&e._updateLocalPresence()}}_subscribeRoom(e){if(!this._client||!this._localUser)throw new Error("Not connected — call connect() first");this._log("Subscribing room:",e);const t=this._client.setApp(this._options.appName).setRoom(e),s=new _(e,t,this._localUser,this._options,a(`ChatRoom:${e}`,this._options.debug));return this._rooms.set(e,s),s._subscribe(),s}_handleRoomPresenceJoin(e){if(e.actorTokenId===this._localUser?.actorTokenId)return;const t=e.presence;if(!t?.userId)return;const s=this._presenceToUser(e.actorTokenId,t);this._actorToUserId.set(e.actorTokenId,s.userId),this._onlineUsers.has(s.userId)||(this._onlineUsers.set(s.userId,s),this.emit("userOnline",s));const i=this._activeRoom?this._rooms.get(this._activeRoom):void 0;i&&i._handlePresenceJoin(e.actorTokenId,t)}_handleRoomPresenceLeave(e){if(e.actorTokenId===this._localUser?.actorTokenId)return;const t=this._activeRoom?this._rooms.get(this._activeRoom):void 0;t&&t._handlePresenceLeave(e.actorTokenId)}_handleRoomPresenceUpdate(e){if(e.actorTokenId===this._localUser?.actorTokenId)return;const t=e.presence;if(!t?.userId)return;if(this._onlineUsers.has(t.userId)){const s=this._presenceToUser(e.actorTokenId,t);this._onlineUsers.set(s.userId,s),this.emit("userUpdated",s)}const s=this._activeRoom?this._rooms.get(this._activeRoom):void 0;s&&s._handlePresenceUpdate(e.actorTokenId,t)}async _setupLobby(){if(!this._client)return;this._lobby=this._client.setApp(this._options.appName).setLobby("online");const e=e=>t=>{const s=t;"join"===e?this._handleLobbyJoin(s):"leave"===e?this._handleLobbyLeave(s):this._handleLobbyUpdate(s)};this._client.on("lobbyPresence:join",e("join")),this._client.on("lobbyPresence:leave",e("leave")),this._client.on("lobbyPresence:update",e("update"));try{const e=await this._lobby.subscribe();this._hydrateOnlineUsers(e),this._log("Lobby subscribed, online users:",this._onlineUsers.size)}catch(e){this._log("Lobby subscription failed:",e)}}_handleLobbyJoin(e){const{actorId:t,data:s}=e;if(t===this._localUser?.actorTokenId)return;const i=s;if(!i.userId)return;const r=this._presenceToUser(t,i);this._actorToUserId.set(t,r.userId),this._onlineUsers.has(r.userId)||(this._onlineUsers.set(r.userId,r),this.emit("userOnline",r))}_handleLobbyLeave(e){const{actorId:t,data:s}=e;if(t===this._localUser?.actorTokenId)return;const i=s,r=i?.userId||this._actorToUserId.get(t)||this._findUserIdByActorId(t);if(r){const e=this._onlineUsers.get(r);e&&(this._onlineUsers.delete(r),this._actorToUserId.delete(t),this.emit("userOffline",e))}}_handleLobbyUpdate(e){const{actorId:t,data:s}=e;if(t===this._localUser?.actorTokenId)return;const i=s;if(!i.userId)return;const r=this._presenceToUser(t,i);this._onlineUsers.set(r.userId,r),this.emit("userUpdated",r)}_hydrateOnlineUsers(e){for(const t of Object.keys(e)){const s=e[t];for(const e of Object.keys(s)){if(e===this._localUser?.actorTokenId)continue;const t=s[e],i=t?.presence??t;if(i?.userId){const t=this._presenceToUser(e,i);this._actorToUserId.set(e,t.userId),this._onlineUsers.has(t.userId)||(this._onlineUsers.set(t.userId,t),this.emit("userOnline",t))}}}}_presenceToUser(e,t){return{userId:t.userId,actorTokenId:e,username:t.username,avatar:t.avatar,metadata:t.metadata,status:t.status||"online",joinedAt:Date.now(),isLocal:!1}}_findUserIdByActorId(e){for(const t of this._onlineUsers.values())if(t.actorTokenId===e)return t.userId}_restoreRooms(){if(this._activeRoom){const e=this._rooms.get(this._activeRoom);e&&e._updateLocalPresence()}this._lobby?.fetchPresence().then(e=>{this._onlineUsers.clear(),this._actorToUserId.clear(),this._hydrateOnlineUsers(e)}).catch(e=>{this._log("Failed to re-fetch lobby presence:",e)})}}export{_ as ChatRoom,t as EventEmitter,d as NoLagChat};
|
|
2
2
|
//# sourceMappingURL=browser.js.map
|
package/dist/browser.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"browser.js","sources":["../src/EventEmitter.ts","../src/MessageStore.ts","../src/PresenceManager.ts","../src/TypingManager.ts","../src/utils.ts","../src/constants.ts","../src/ChatRoom.ts","../src/NoLagChat.ts"],"sourcesContent":[null,null,null,null,null,null,null,null],"names":["EventEmitter","constructor","this","_handlers","Map","on","event","handler","has","set","Set","get","add","off","delete","removeAllListeners","clear","emit","args","handlers","e","console","error","String","listenerCount","size","MessageStore","maxSize","_messages","_ids","_maxSize","message","id","push","length","timestamp","sort","a","b","removed","shift","getAll","PresenceManager","localActorId","_users","_actorToUserId","_localActorId","addFromPresence","actorTokenId","presence","joinedAt","existing","userId","user","username","avatar","metadata","status","Date","now","isLocal","removeByActorId","getUser","getUserByActorId","undefined","Array","from","values","users","TypingManager","timeout","_localTimer","_localTyping","_remoteTimers","_typingUserIds","_onSend","_onChange","_timeout","onSend","cb","onChange","startTyping","clearTimeout","setTimeout","stopTyping","handleRemote","typing","getTypingUserIds","isLocalTyping","dispose","timer","generateId","crypto","randomUUID","replace","Math","floor","random","toString","createLogger","prefix","enabled","log","_args","TOPIC_MESSAGES","TOPIC_TYPING","ChatRoom","name","roomContext","localUser","options","super","_unreadCount","_active","_roomContext","_localUser","_options","_log","_presenceManager","_typingManager","typingTimeout","_messageStore","maxMessageCache","echo","typingUsers","messages","typingIds","unreadCount","active","markRead","room","count","sendMessage","text","data","isReplay","getMessages","getUsers","_subscribe","subscribe","meta","_handleIncomingMessage","_activate","_markRead","_setPresence","fetchPresence","then","actors","actor","catch","err","_deactivate","_handlePresenceJoin","presenceData","_handlePresenceLeave","_handlePresenceUpdate","_handleReplayStart","_handleReplayEnd","replayed","_updateLocalPresence","_cleanup","unsubscribe","msg","chatMessage","setPresence","NoLagChat","token","_client","_rooms","_lobby","_onlineUsers","_activeRoom","_token","_userId","appName","url","debug","reconnect","rooms","connected","connect","clientOptions","NoLag","_restoreRooms","reason","_handleRoomPresenceJoin","_handleRoomPresenceLeave","_handleRoomPresenceUpdate","actorId","_setupLobby","roomName","_subscribeRoom","state","_hydrateOnlineUsers","disconnect","keys","leaveRoom","joinRoom","Error","prev","getRooms","getOnlineUsers","setStatus","activeRoom","updateProfile","updates","setApp","setRoom","_presenceToUser","setLobby","lobbyHandler","type","_handleLobbyJoin","_handleLobbyLeave","_handleLobbyUpdate","initialState","_findUserIdByActorId","roomId","Object","roomPresence","raw"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"browser.js","sources":["../src/EventEmitter.ts","../src/MessageStore.ts","../src/PresenceManager.ts","../src/TypingManager.ts","../src/utils.ts","../src/constants.ts","../src/MessageStream.ts","../src/ChatRoom.ts","../src/NoLagChat.ts"],"sourcesContent":[null,null,null,null,null,null,null,null,null],"names":["EventEmitter","constructor","this","_handlers","Map","on","event","handler","has","set","Set","get","add","off","delete","removeAllListeners","clear","emit","args","handlers","e","console","error","String","listenerCount","size","MessageStore","maxSize","_messages","_ids","_maxSize","message","id","push","length","timestamp","sort","a","b","removed","shift","getAll","find","m","PresenceManager","localActorId","_users","_actorToUserId","_localActorId","addFromPresence","actorTokenId","presence","joinedAt","existing","userId","user","username","avatar","metadata","status","Date","now","isLocal","removeByActorId","getUser","getUserByActorId","undefined","Array","from","values","users","TypingManager","timeout","_localTimer","_localTyping","_remoteTimers","_typingUserIds","_onSend","_onChange","_timeout","onSend","cb","onChange","startTyping","clearTimeout","setTimeout","stopTyping","handleRemote","typing","getTypingUserIds","isLocalTyping","dispose","timer","generateId","crypto","randomUUID","replace","Math","floor","random","toString","createLogger","prefix","enabled","log","_args","TOPIC_MESSAGES","TOPIC_TYPING","TOPIC_STREAM","MessageStreamController","_flushIntervalMs","_hooks","_buffer","_flushTimer","_closed","publishStream","type","emitStart","append","text","emitChunk","_flush","complete","_clearTimer","publishFinal","emitEnd","abort","emitAbort","ChatRoom","name","roomContext","localUser","options","super","_unreadCount","_active","_roomContext","_localUser","_options","_log","_presenceManager","_typingManager","typingTimeout","_messageStore","maxMessageCache","echo","typingUsers","messages","typingIds","unreadCount","active","markRead","room","count","sendMessage","data","isReplay","_publishFinalMessage","startStream","flushIntervalMs","payload","delta","streamMessage","source","stream","chunk","err","Error","getMessages","getUsers","_subscribe","subscribe","meta","_handleIncomingMessage","_handleStreamEvent","_activate","_markRead","_setPresence","fetchPresence","then","actors","actor","catch","_deactivate","_handlePresenceJoin","presenceData","_handlePresenceLeave","_handlePresenceUpdate","_handleReplayStart","_handleReplayEnd","replayed","_updateLocalPresence","_cleanup","unsubscribe","msg","streaming","chatMessage","evt","setPresence","NoLagChat","token","_client","_rooms","_lobby","_onlineUsers","_activeRoom","_token","_userId","appName","url","debug","reconnect","rooms","connected","connect","clientOptions","NoLag","_restoreRooms","reason","_handleRoomPresenceJoin","_handleRoomPresenceLeave","_handleRoomPresenceUpdate","actorId","_setupLobby","roomName","_subscribeRoom","state","_hydrateOnlineUsers","disconnect","keys","leaveRoom","joinRoom","prev","getRooms","getOnlineUsers","setStatus","activeRoom","updateProfile","updates","setApp","setRoom","_presenceToUser","setLobby","lobbyHandler","_handleLobbyJoin","_handleLobbyLeave","_handleLobbyUpdate","initialState","_findUserIdByActorId","roomId","Object","roomPresence","raw"],"mappings":"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"}
|
package/dist/constants.d.ts
CHANGED
|
@@ -8,5 +8,9 @@ export declare const DEFAULT_MAX_MESSAGE_CACHE = 500;
|
|
|
8
8
|
export declare const TOPIC_MESSAGES = "messages";
|
|
9
9
|
/** Topic name for typing indicators within a room */
|
|
10
10
|
export declare const TOPIC_TYPING = "_typing";
|
|
11
|
+
/** Topic name for live streamed message chunks within a room (ephemeral) */
|
|
12
|
+
export declare const TOPIC_STREAM = "_stream";
|
|
13
|
+
/** Default coalesce/flush interval for streamed token chunks (ms) */
|
|
14
|
+
export declare const DEFAULT_STREAM_FLUSH_MS = 60;
|
|
11
15
|
/** Lobby ID for global online presence */
|
|
12
16
|
export declare const LOBBY_ID = "online";
|
package/dist/index.cjs
CHANGED
|
@@ -113,6 +113,15 @@ class MessageStore {
|
|
|
113
113
|
has(id) {
|
|
114
114
|
return this._ids.has(id);
|
|
115
115
|
}
|
|
116
|
+
/**
|
|
117
|
+
* Get a message by ID. Returns the live reference (mutating it mutates the
|
|
118
|
+
* stored message), or undefined if not present.
|
|
119
|
+
*/
|
|
120
|
+
get(id) {
|
|
121
|
+
if (!this._ids.has(id))
|
|
122
|
+
return undefined;
|
|
123
|
+
return this._messages.find((m) => m.id === id);
|
|
124
|
+
}
|
|
116
125
|
/**
|
|
117
126
|
* Clear all messages.
|
|
118
127
|
*/
|
|
@@ -353,9 +362,89 @@ const DEFAULT_MAX_MESSAGE_CACHE = 500;
|
|
|
353
362
|
const TOPIC_MESSAGES = 'messages';
|
|
354
363
|
/** Topic name for typing indicators within a room */
|
|
355
364
|
const TOPIC_TYPING = '_typing';
|
|
365
|
+
/** Topic name for live streamed message chunks within a room (ephemeral) */
|
|
366
|
+
const TOPIC_STREAM = '_stream';
|
|
367
|
+
/** Default coalesce/flush interval for streamed token chunks (ms) */
|
|
368
|
+
const DEFAULT_STREAM_FLUSH_MS = 60;
|
|
356
369
|
/** Lobby ID for global online presence */
|
|
357
370
|
const LOBBY_ID = 'online';
|
|
358
371
|
|
|
372
|
+
/**
|
|
373
|
+
* Producer-side controller for an outgoing streamed message.
|
|
374
|
+
*
|
|
375
|
+
* `append()` updates the local message immediately and buffers the token; a
|
|
376
|
+
* timer flushes buffered tokens as a single network delta at most every
|
|
377
|
+
* `flushIntervalMs`, so a token-per-character source doesn't flood the broker.
|
|
378
|
+
*/
|
|
379
|
+
class MessageStreamController {
|
|
380
|
+
constructor(message, _flushIntervalMs, _hooks) {
|
|
381
|
+
this._flushIntervalMs = _flushIntervalMs;
|
|
382
|
+
this._hooks = _hooks;
|
|
383
|
+
this._buffer = '';
|
|
384
|
+
this._flushTimer = null;
|
|
385
|
+
this._closed = false;
|
|
386
|
+
this.message = message;
|
|
387
|
+
// Announce the stream so receivers can render a live placeholder at once.
|
|
388
|
+
this._hooks.publishStream({
|
|
389
|
+
type: 'start',
|
|
390
|
+
id: message.id,
|
|
391
|
+
userId: message.userId,
|
|
392
|
+
username: message.username,
|
|
393
|
+
avatar: message.avatar,
|
|
394
|
+
timestamp: message.timestamp,
|
|
395
|
+
});
|
|
396
|
+
this._hooks.emitStart(message);
|
|
397
|
+
}
|
|
398
|
+
append(text) {
|
|
399
|
+
if (this._closed || !text)
|
|
400
|
+
return;
|
|
401
|
+
this.message.text += text;
|
|
402
|
+
this._buffer += text;
|
|
403
|
+
this._hooks.emitChunk(this.message, text);
|
|
404
|
+
if (!this._flushTimer) {
|
|
405
|
+
this._flushTimer = setTimeout(() => this._flush(), this._flushIntervalMs);
|
|
406
|
+
}
|
|
407
|
+
}
|
|
408
|
+
complete() {
|
|
409
|
+
if (this._closed)
|
|
410
|
+
return this.message;
|
|
411
|
+
this._flush(); // send any buffered tokens
|
|
412
|
+
this._closed = true;
|
|
413
|
+
this._clearTimer();
|
|
414
|
+
this.message.status = 'sent';
|
|
415
|
+
this._hooks.publishFinal(this.message); // persisted final → finalizes receivers
|
|
416
|
+
this._hooks.emitEnd(this.message);
|
|
417
|
+
return this.message;
|
|
418
|
+
}
|
|
419
|
+
abort(error) {
|
|
420
|
+
if (this._closed)
|
|
421
|
+
return;
|
|
422
|
+
this._closed = true;
|
|
423
|
+
this._clearTimer();
|
|
424
|
+
this._buffer = '';
|
|
425
|
+
this.message.status = 'aborted';
|
|
426
|
+
this._hooks.publishStream({ type: 'abort', id: this.message.id, error });
|
|
427
|
+
this._hooks.emitAbort(this.message, error);
|
|
428
|
+
}
|
|
429
|
+
_flush() {
|
|
430
|
+
this._clearTimer();
|
|
431
|
+
if (this._buffer) {
|
|
432
|
+
this._hooks.publishStream({
|
|
433
|
+
type: 'delta',
|
|
434
|
+
id: this.message.id,
|
|
435
|
+
text: this._buffer,
|
|
436
|
+
});
|
|
437
|
+
this._buffer = '';
|
|
438
|
+
}
|
|
439
|
+
}
|
|
440
|
+
_clearTimer() {
|
|
441
|
+
if (this._flushTimer) {
|
|
442
|
+
clearTimeout(this._flushTimer);
|
|
443
|
+
this._flushTimer = null;
|
|
444
|
+
}
|
|
445
|
+
}
|
|
446
|
+
}
|
|
447
|
+
|
|
359
448
|
/**
|
|
360
449
|
* ChatRoom — a single chat room with messages, users, and typing indicators.
|
|
361
450
|
*
|
|
@@ -442,6 +531,76 @@ class ChatRoom extends EventEmitter {
|
|
|
442
531
|
this._messageStore.add(message);
|
|
443
532
|
this.emit('messageSent', message);
|
|
444
533
|
// Publish to room (echo: false prevents duplicate)
|
|
534
|
+
this._publishFinalMessage(message);
|
|
535
|
+
// Mark as sent
|
|
536
|
+
message.status = 'sent';
|
|
537
|
+
// Stop typing on send
|
|
538
|
+
this._typingManager.stopTyping();
|
|
539
|
+
return message;
|
|
540
|
+
}
|
|
541
|
+
// ============ Streaming ============
|
|
542
|
+
/**
|
|
543
|
+
* Begin a streamed message (e.g. an AI response). Returns a handle you append
|
|
544
|
+
* tokens to. Receivers see the message appear and grow live; on `complete()`
|
|
545
|
+
* the full message is persisted like a normal message.
|
|
546
|
+
*
|
|
547
|
+
* @example
|
|
548
|
+
* ```ts
|
|
549
|
+
* const stream = room.startStream();
|
|
550
|
+
* for await (const token of llm) stream.append(token);
|
|
551
|
+
* stream.complete();
|
|
552
|
+
* ```
|
|
553
|
+
*/
|
|
554
|
+
startStream(options) {
|
|
555
|
+
const message = {
|
|
556
|
+
id: generateId(),
|
|
557
|
+
userId: this._localUser.userId,
|
|
558
|
+
username: this._localUser.username,
|
|
559
|
+
avatar: this._localUser.avatar,
|
|
560
|
+
text: '',
|
|
561
|
+
data: options?.data,
|
|
562
|
+
timestamp: Date.now(),
|
|
563
|
+
status: 'streaming',
|
|
564
|
+
isReplay: false,
|
|
565
|
+
};
|
|
566
|
+
// Optimistic: appears in room.messages and grows as tokens arrive.
|
|
567
|
+
this._messageStore.add(message);
|
|
568
|
+
this._typingManager.stopTyping();
|
|
569
|
+
return new MessageStreamController(message, options?.flushIntervalMs ?? DEFAULT_STREAM_FLUSH_MS, {
|
|
570
|
+
publishStream: (payload) => this._roomContext.emit(TOPIC_STREAM, payload, { echo: false }),
|
|
571
|
+
publishFinal: (m) => this._publishFinalMessage(m),
|
|
572
|
+
emitStart: (m) => this.emit('streamStart', m),
|
|
573
|
+
emitChunk: (m, delta) => this.emit('streamChunk', { message: m, delta }),
|
|
574
|
+
emitEnd: (m) => this.emit('streamEnd', m),
|
|
575
|
+
emitAbort: (m, error) => this.emit('streamAbort', { message: m, error }),
|
|
576
|
+
});
|
|
577
|
+
}
|
|
578
|
+
/**
|
|
579
|
+
* Stream a message from a token source (sync or async iterable) — drops in
|
|
580
|
+
* for an LLM stream. Appends each chunk, finalizes on completion, and aborts
|
|
581
|
+
* (re-throwing) if the source errors.
|
|
582
|
+
*
|
|
583
|
+
* @example
|
|
584
|
+
* ```ts
|
|
585
|
+
* // OpenAI / Anthropic style streams yield text chunks
|
|
586
|
+
* await room.streamMessage(tokenIterable);
|
|
587
|
+
* ```
|
|
588
|
+
*/
|
|
589
|
+
async streamMessage(source, options) {
|
|
590
|
+
const stream = this.startStream(options);
|
|
591
|
+
try {
|
|
592
|
+
for await (const chunk of source) {
|
|
593
|
+
stream.append(chunk);
|
|
594
|
+
}
|
|
595
|
+
return stream.complete();
|
|
596
|
+
}
|
|
597
|
+
catch (err) {
|
|
598
|
+
stream.abort(err instanceof Error ? err.message : String(err));
|
|
599
|
+
throw err;
|
|
600
|
+
}
|
|
601
|
+
}
|
|
602
|
+
/** @internal Publish a final message on the persisted `messages` topic. */
|
|
603
|
+
_publishFinalMessage(message) {
|
|
445
604
|
this._roomContext.emit(TOPIC_MESSAGES, {
|
|
446
605
|
id: message.id,
|
|
447
606
|
userId: message.userId,
|
|
@@ -451,11 +610,6 @@ class ChatRoom extends EventEmitter {
|
|
|
451
610
|
data: message.data,
|
|
452
611
|
timestamp: message.timestamp,
|
|
453
612
|
}, { echo: false });
|
|
454
|
-
// Mark as sent
|
|
455
|
-
message.status = 'sent';
|
|
456
|
-
// Stop typing on send
|
|
457
|
-
this._typingManager.stopTyping();
|
|
458
|
-
return message;
|
|
459
613
|
}
|
|
460
614
|
/**
|
|
461
615
|
* Get all messages (alias for the messages getter).
|
|
@@ -496,6 +650,7 @@ class ChatRoom extends EventEmitter {
|
|
|
496
650
|
// Subscribe to topics
|
|
497
651
|
this._roomContext.subscribe(TOPIC_MESSAGES);
|
|
498
652
|
this._roomContext.subscribe(TOPIC_TYPING);
|
|
653
|
+
this._roomContext.subscribe(TOPIC_STREAM);
|
|
499
654
|
// Listen for messages
|
|
500
655
|
this._roomContext.on(TOPIC_MESSAGES, (data, meta) => {
|
|
501
656
|
this._handleIncomingMessage(data, meta);
|
|
@@ -507,6 +662,10 @@ class ChatRoom extends EventEmitter {
|
|
|
507
662
|
this._typingManager.handleRemote(userId, typing);
|
|
508
663
|
}
|
|
509
664
|
});
|
|
665
|
+
// Listen for live streamed messages (start / delta / abort)
|
|
666
|
+
this._roomContext.on(TOPIC_STREAM, (data) => {
|
|
667
|
+
this._handleStreamEvent(data);
|
|
668
|
+
});
|
|
510
669
|
}
|
|
511
670
|
/** @internal Set presence and fetch room members (active room only) */
|
|
512
671
|
_activate() {
|
|
@@ -575,8 +734,10 @@ class ChatRoom extends EventEmitter {
|
|
|
575
734
|
this._log('Room cleanup:', this.name);
|
|
576
735
|
this._roomContext.unsubscribe(TOPIC_MESSAGES);
|
|
577
736
|
this._roomContext.unsubscribe(TOPIC_TYPING);
|
|
737
|
+
this._roomContext.unsubscribe(TOPIC_STREAM);
|
|
578
738
|
this._roomContext.off(TOPIC_MESSAGES);
|
|
579
739
|
this._roomContext.off(TOPIC_TYPING);
|
|
740
|
+
this._roomContext.off(TOPIC_STREAM);
|
|
580
741
|
this._typingManager.dispose();
|
|
581
742
|
this._messageStore.clear();
|
|
582
743
|
this._presenceManager.clear();
|
|
@@ -585,8 +746,25 @@ class ChatRoom extends EventEmitter {
|
|
|
585
746
|
// ============ Private ============
|
|
586
747
|
_handleIncomingMessage(data, meta) {
|
|
587
748
|
const msg = data;
|
|
749
|
+
const id = msg.id;
|
|
750
|
+
// If this is the persisted final for a message we streamed live, finalize
|
|
751
|
+
// the existing placeholder in place (authoritative text) rather than adding
|
|
752
|
+
// a duplicate. This also catches a late delta race — the final wins.
|
|
753
|
+
const streaming = this._messageStore.get(id);
|
|
754
|
+
if (streaming && streaming.status === 'streaming') {
|
|
755
|
+
streaming.text = msg.text;
|
|
756
|
+
streaming.data = msg.data;
|
|
757
|
+
streaming.status = 'delivered';
|
|
758
|
+
this.emit('streamEnd', streaming);
|
|
759
|
+
this.emit('message', streaming);
|
|
760
|
+
if (!this._active && !streaming.isReplay) {
|
|
761
|
+
this._unreadCount++;
|
|
762
|
+
this.emit('unreadChanged', { room: this.name, count: this._unreadCount });
|
|
763
|
+
}
|
|
764
|
+
return;
|
|
765
|
+
}
|
|
588
766
|
const chatMessage = {
|
|
589
|
-
id
|
|
767
|
+
id,
|
|
590
768
|
userId: msg.userId,
|
|
591
769
|
username: msg.username,
|
|
592
770
|
avatar: msg.avatar,
|
|
@@ -605,6 +783,49 @@ class ChatRoom extends EventEmitter {
|
|
|
605
783
|
}
|
|
606
784
|
}
|
|
607
785
|
}
|
|
786
|
+
/** Handle an incoming live stream control payload (start / delta / abort). */
|
|
787
|
+
_handleStreamEvent(data) {
|
|
788
|
+
const evt = data;
|
|
789
|
+
if (!evt || !evt.id)
|
|
790
|
+
return;
|
|
791
|
+
switch (evt.type) {
|
|
792
|
+
case 'start': {
|
|
793
|
+
// Ignore our own (echo:false should prevent it, but be safe).
|
|
794
|
+
if (evt.userId === this._localUser.userId)
|
|
795
|
+
return;
|
|
796
|
+
const message = {
|
|
797
|
+
id: evt.id,
|
|
798
|
+
userId: evt.userId,
|
|
799
|
+
username: evt.username,
|
|
800
|
+
avatar: evt.avatar,
|
|
801
|
+
text: '',
|
|
802
|
+
timestamp: evt.timestamp,
|
|
803
|
+
status: 'streaming',
|
|
804
|
+
isReplay: false,
|
|
805
|
+
};
|
|
806
|
+
if (this._messageStore.add(message)) {
|
|
807
|
+
this.emit('streamStart', message);
|
|
808
|
+
}
|
|
809
|
+
break;
|
|
810
|
+
}
|
|
811
|
+
case 'delta': {
|
|
812
|
+
const message = this._messageStore.get(evt.id);
|
|
813
|
+
if (message && message.status === 'streaming') {
|
|
814
|
+
message.text += evt.text;
|
|
815
|
+
this.emit('streamChunk', { message, delta: evt.text });
|
|
816
|
+
}
|
|
817
|
+
break;
|
|
818
|
+
}
|
|
819
|
+
case 'abort': {
|
|
820
|
+
const message = this._messageStore.get(evt.id);
|
|
821
|
+
if (message && message.status === 'streaming') {
|
|
822
|
+
message.status = 'aborted';
|
|
823
|
+
this.emit('streamAbort', { message, error: evt.error });
|
|
824
|
+
}
|
|
825
|
+
break;
|
|
826
|
+
}
|
|
827
|
+
}
|
|
828
|
+
}
|
|
608
829
|
_markRead() {
|
|
609
830
|
if (this._unreadCount !== 0) {
|
|
610
831
|
this._unreadCount = 0;
|