@pluv/client 2.0.2 → 2.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.
@@ -1,5 +1,5 @@
1
1
 
2
- > @pluv/client@2.0.2 build /home/runner/work/pluv/pluv/packages/client
2
+ > @pluv/client@2.2.0 build /home/runner/work/pluv/pluv/packages/client
3
3
  > tsup src/index.ts --format esm,cjs --dts
4
4
 
5
5
  CLI Building entry: src/index.ts
@@ -8,11 +8,11 @@
8
8
  CLI Target: es6
9
9
  ESM Build start
10
10
  CJS Build start
11
- CJS dist/index.js 58.82 KB
12
- CJS ⚡️ Build success in 123ms
13
- ESM dist/index.mjs 57.33 KB
14
- ESM ⚡️ Build success in 131ms
11
+ ESM dist/index.mjs 63.81 KB
12
+ ESM ⚡️ Build success in 137ms
13
+ CJS dist/index.js 65.55 KB
14
+ CJS ⚡️ Build success in 136ms
15
15
  DTS Build start
16
- DTS ⚡️ Build success in 4303ms
17
- DTS dist/index.d.mts 21.88 KB
18
- DTS dist/index.d.ts 21.88 KB
16
+ DTS ⚡️ Build success in 4812ms
17
+ DTS dist/index.d.mts 20.11 KB
18
+ DTS dist/index.d.ts 20.11 KB
package/CHANGELOG.md CHANGED
@@ -1,5 +1,146 @@
1
1
  # @pluv/client
2
2
 
3
+ ## 2.2.0
4
+
5
+ ### Minor Changes
6
+
7
+ - 3ce1547: Updated typings for `PluvRoom.getDoc` to be narrower to get the native doc type.
8
+
9
+ ```ts
10
+ import { createClient } from "@pluv/client";
11
+ import { yjs } from "@pluv/crdt-yjs";
12
+ import type { Doc as YDoc } from "yjs";
13
+
14
+ const client = createClient({
15
+ // ...
16
+ crdt: yjs,
17
+ });
18
+ const room = client.createRoom("example-room");
19
+
20
+ const doc = room.getDoc();
21
+
22
+ // This is now typed as the native YDoc
23
+ doc.value;
24
+ // ^? const value: YDoc
25
+ ```
26
+
27
+ - fd3bfe2: Added the ability to listen to the room's underlying websocket's event listeners.
28
+ - aee40cb: Updated `presence` types to be more lenient (i.e. no-longer extends `JsonObject`). This is to enable types like `.passthrough` with zod, which can be useful for integrating `yjs.awareness` with libraries such as [lexical](https://lexical.dev/).
29
+ - edd1789: **DEPRECATED** `PluvRoom.storageLoaded` will be removed in v3. Added `PluvRoom.getStorageLoaded` with improved detection of when the storage was synced.
30
+
31
+ ```ts
32
+ const room = client.createRoom("example-room");
33
+
34
+ // Before
35
+ room.storageLoaded;
36
+
37
+ // After
38
+ room.getStorageLoaded();
39
+ ```
40
+
41
+ ### Patch Changes
42
+
43
+ - 48191fa: Fixed `PluvRoom.getDoc` not returning a stable doc reference for a single connection.
44
+ - @pluv/crdt@2.2.0
45
+ - @pluv/types@2.2.0
46
+
47
+ ## 2.1.0
48
+
49
+ ### Minor Changes
50
+
51
+ - e8d8fbc: **DEPRECATED** Subscribing to data via string parameters on `PluvRoom.subscribe` is deprecated, to be removed in v3. To subscribe to things such as `myself`, `my-presence` and `others`, you must now do so via nested properties on the `subscribe` object (see example below).
52
+
53
+ ```ts
54
+ const room = client.createRoom("example-room");
55
+
56
+ // Before (now deprecated)
57
+ room.subscribe("connection", (state) => {});
58
+ room.subscribe("my-presence", (myPresence) => {});
59
+ room.subscribe("myself", (myself) => {});
60
+ room.subscribe("others", (others) => {});
61
+ room.subscribe("storage-loaded", (storageLoaded) => {});
62
+
63
+ // After
64
+ room.subscribe.connection((state) => {});
65
+ room.subscribe.myPresence((myPresence) => {});
66
+ room.subscribe.myself((myself) => {});
67
+ room.subscribe.others((others) => {});
68
+ room.subscribe.storageLoaded((storageLoaded) => {});
69
+ ```
70
+
71
+ - d5ac29e: **DEPRECATED** `PluvRoom.event`, `PluvRoom.storage`, `PluvRoom.storageRoot` and `PluvRoom.other` have all been deprecated, to be removed in v3. These now exist under `PluvRoom.subscribe` instead.
72
+
73
+ ```ts
74
+ const room = client.createRoom("example-room");
75
+
76
+ // Before (now deprecated)
77
+ room.event.receiveMessage((event) => {});
78
+ room.storage.messages((messages) => {});
79
+ room.storageRoot((storage) => {});
80
+ room.other(("id_...", other) => {});
81
+
82
+ // After
83
+ room.subscribe.event.receiveMessage((event) => {});
84
+ room.subscribe.storage.messages((messages) => {});
85
+ room.subscribe.storageRoot((storage) => {});
86
+ room.subscribe.other(("id_...", other) => {});
87
+ ```
88
+
89
+ - 5ca5cb6: Updated `PluvRoom.storage` to also allow subscribing to storage fields as nested properties.
90
+
91
+ ```ts
92
+ const client = createClient({
93
+ // ...
94
+ initialStorage: yjs.doc((t) => ({
95
+ messages: yjs.array<string>(),
96
+ })),
97
+ });
98
+
99
+ const room = client.createRoom("example-room");
100
+
101
+ // The two statements below are equivalent.
102
+ room.storage("messages", (value) => {});
103
+
104
+ // You can now subscribe to storage fields as nested properties like so
105
+ room.storage.messages((value) => {});
106
+ ```
107
+
108
+ - 4acbe1e: Updated `PluvRoom.storage` to also allow subscribing to the root storage when no field is provided.
109
+
110
+ ```ts
111
+ const client = createClient({
112
+ // ...
113
+ initialStorage: yjs.doc((t) => ({
114
+ messages: yjs.array<string>(),
115
+ })),
116
+ });
117
+
118
+ const room = client.createRoom("example-room");
119
+
120
+ room.storage("messages", (value) => {});
121
+ // ^? const value: string[];
122
+
123
+ // You can now subscribe to the storage root when no key is provided
124
+ room.storage((value) => {});
125
+ // ^? const value: { messages: string[] };
126
+ ```
127
+
128
+ - e8d8fbc: Updated `PluvRoom.subscribe` so that `PluvRoom.event` and `PluvRoom.storage` can be accessed as properties under `PluvRoom.subscribe`.
129
+
130
+ ```ts
131
+ const room = client.createRoom("example-room");
132
+
133
+ // These are now available under the subscribe object
134
+ room.subscribe.event.receiveEvent((event) => {});
135
+ room.subscribe.storage.messages((data) => {});
136
+ ```
137
+
138
+ ### Patch Changes
139
+
140
+ - a86ff5e: Updated internal types to simplify the type for `PluvRoom.broadcast` and `PluvRoom.event`.
141
+ - @pluv/crdt@2.1.0
142
+ - @pluv/types@2.1.0
143
+
3
144
  ## 2.0.2
4
145
 
5
146
  ### Patch Changes
package/dist/index.d.mts CHANGED
@@ -1,8 +1,7 @@
1
- import { CrdtType, AbstractCrdtDocFactory, NoopCrdtDocFactory, InferStorage, InferCrdtJson } from '@pluv/crdt';
1
+ import { AbstractCrdtDocFactory, InferDocLike, NoopCrdtDocFactory, InferStorage, InferDoc, InferCrdtJson } from '@pluv/crdt';
2
2
  export { CrdtType, InferCrdtJson } from '@pluv/crdt';
3
- import { IOLike, JsonObject, EventRecord, CrdtDocLike, UserInfo, MaybePromise, Id, ConnectionState, ProcedureLike, InputZodLike, IORouterLike, WebSocketState, InferIOAuthorizeUser, InferIOAuthorize, BaseUser, RoomLike, InferIOOutput, InferIOInput, MergeEvents, EventNotifierSubscriptionCallback, OtherNotifierSubscriptionCallback, UpdateMyPresenceAction } from '@pluv/types';
4
- export { BaseUser, ConnectionState, EventMessage, EventNotifierSubscriptionCallback, EventRecord, IOEventMessage, MergeEvents, RoomLike, UserInfo, WebSocketState } from '@pluv/types';
5
- import { Subject } from 'wonka';
3
+ import { IOLike, JsonObject, EventRecord, CrdtDocLike, UserInfo, MaybePromise, Id, ProcedureLike, InputZodLike, IORouterLike, InferIOAuthorizeUser, InferIOAuthorize, BaseUser, RoomLike, InferIOOutput, InferIOInput, RoomEventListenerMap, BroadcastProxy, EventProxy, WebSocketConnection, OtherSubscriptionCallback, StorageProxy, SubscribeProxy, UpdateMyPresenceAction, MergeEvents } from '@pluv/types';
4
+ export { BaseUser, ConnectionState, EventMessage, EventNotifierSubscriptionCallback, EventRecord, IOEventMessage, MergeEvents, RoomLike, UserInfo, WebSocketConnection, WebSocketState } from '@pluv/types';
6
5
 
7
6
  declare abstract class AbstractStorageStore {
8
7
  room: string;
@@ -22,9 +21,9 @@ type InferCallback<TIO extends IOLike<any, any>> = (i: typeof identity) => {
22
21
  };
23
22
  declare const infer: <TIO extends IOLike<any, any>>(callback: InferCallback<TIO>) => InferCallback<TIO>;
24
23
 
25
- type EventResolver<TIO extends IOLike = IOLike, TInput extends JsonObject = {}, TOutput extends EventRecord<string, any> = {}, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}> = (data: TInput, context: EventResolverContext<TIO, TPresence, TStorage>) => MaybePromise<TOutput | void>;
26
- interface EventResolverContext<TIO extends IOLike = IOLike, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}> {
27
- doc: CrdtDocLike<TStorage>;
24
+ type EventResolver<TIO extends IOLike, TInput extends JsonObject, TOutput extends EventRecord<string, any>, TPresence extends Record<string, any>, TDocLike extends CrdtDocLike<any, any>> = (data: TInput, context: EventResolverContext<TIO, TPresence, TDocLike>) => MaybePromise<TOutput | void>;
25
+ interface EventResolverContext<TIO extends IOLike, TPresence extends Record<string, any>, TDocLike extends CrdtDocLike<any, any>> {
26
+ doc: TDocLike;
28
27
  others: readonly UserInfo<TIO, TPresence>[];
29
28
  room: string;
30
29
  user: UserInfo<TIO, TPresence>;
@@ -46,75 +45,47 @@ interface PublicKeyParams<TMetadata extends JsonObject> {
46
45
  metadata: TMetadata;
47
46
  }
48
47
  type PublicKey<TMetadata extends JsonObject> = string | ((params: PublicKeyParams<TMetadata>) => string);
49
- interface WebSocketConnection {
50
- /**
51
- * @description How many times a connection attempt was made. This will increment upon each
52
- * unsuccessful attempt, and will reset upon a successful connection.
53
- * @date April 13, 2025
54
- */
55
- attempts: number;
56
- /**
57
- * @description How many times the user has connected to the room. This can be more than 1 in
58
- * the case of reconnects. This is tracked because on the very first connection (i.e. when
59
- * count is 0) we don't want to send the storage state as an update to the room and overwrite
60
- * the upstream state.
61
- * @date April 13, 2025
62
- */
63
- count: number;
64
- id: string | null;
65
- state: ConnectionState;
66
- }
67
48
  type WithMetadata<TMetadata extends JsonObject = {}> = keyof TMetadata extends never ? {
68
49
  metadata?: undefined;
69
50
  } : {
70
51
  metadata: TMetadata;
71
52
  };
72
53
 
73
- interface PluvProcedureConfig<TIO extends IOLike = IOLike, TInput extends JsonObject = {}, TOutput extends EventRecord<string, any> = {}, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}> {
74
- broadcast?: EventResolver<TIO, TInput, TOutput, TPresence, TStorage> | null;
54
+ interface PluvProcedureConfig<TIO extends IOLike, TInput extends JsonObject, TOutput extends EventRecord<string, any>, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>> {
55
+ broadcast?: EventResolver<TIO, TInput, TOutput, TPresence, InferDocLike<TCrdt>> | null;
75
56
  input?: InputZodLike<TInput>;
76
57
  }
77
- declare class PluvProcedure<TIO extends IOLike = IOLike, TInput extends JsonObject = {}, TOutput extends EventRecord<string, any> = {}, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}, TFilled extends "input" | "broadcast" | "" = ""> implements ProcedureLike<TInput, TOutput> {
58
+ declare class PluvProcedure<TIO extends IOLike, TInput extends JsonObject, TOutput extends EventRecord<string, any>, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TFilled extends "input" | "broadcast" | ""> implements ProcedureLike<TInput, TOutput> {
78
59
  private _broadcast;
79
60
  private _input;
80
61
  get config(): ProcedureLike<TInput, TOutput>["config"];
81
- constructor(config?: PluvProcedureConfig<TIO, TInput, TOutput, TPresence, TStorage>);
82
- broadcast<TResult extends EventRecord<string, any> = {}>(resolver: EventResolver<TIO, TInput, TResult, TPresence, TStorage>): Omit<PluvProcedure<TIO, TInput, MergeEventRecords<[TOutput, TResult]>, TPresence, TStorage, TFilled | "input" | "broadcast">, TFilled | "input" | "broadcast">;
83
- input<TData extends JsonObject>(input: InputZodLike<TData>): Omit<PluvProcedure<TIO, TData, {}, TPresence, TStorage, TFilled | "input">, TFilled | "input">;
62
+ constructor(config?: PluvProcedureConfig<TIO, TInput, TOutput, TPresence, TCrdt>);
63
+ broadcast<TResult extends EventRecord<string, any> = {}>(resolver: EventResolver<TIO, TInput, TResult, TPresence, InferDocLike<TCrdt>>): Omit<PluvProcedure<TIO, TInput, MergeEventRecords<[TOutput, TResult]>, TPresence, TCrdt, TFilled | "input" | "broadcast">, TFilled | "input" | "broadcast">;
64
+ input<TData extends JsonObject>(input: InputZodLike<TData>): Omit<PluvProcedure<TIO, TData, {}, TPresence, TCrdt, TFilled | "input">, TFilled | "input">;
84
65
  private _resolver;
85
66
  }
86
67
 
87
- type CrdtManagerOptions<TCrdt extends AbstractCrdtDocFactory<any>> = {
68
+ type CrdtManagerOptions<TCrdt extends AbstractCrdtDocFactory<any, any>> = {
88
69
  initialStorage?: TCrdt;
89
70
  };
90
71
 
91
- type PluvRouterEventConfig<TIO extends IOLike = IOLike, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}> = {
92
- [P: string]: Pick<PluvProcedure<TIO, any, any, TPresence, TStorage>, "config">;
72
+ type PluvRouterEventConfig<TIO extends IOLike, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>> = {
73
+ [P: string]: Pick<PluvProcedure<TIO, any, any, TPresence, TCrdt, "">, "config">;
93
74
  };
94
- type MergedRouter<TRouters extends PluvRouter<TIO, TPresence, TStorage, any>[] = [], TIO extends IOLike = IOLike, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}, TRoot extends TRouters[0]["_defs"]["events"] = {}> = TRouters extends [
95
- infer IHead extends PluvRouter<TIO, TPresence, TStorage, any>,
96
- ...infer ITail extends PluvRouter<TIO, TPresence, TStorage, any>[]
97
- ] ? MergedRouter<ITail, TIO, TPresence, TStorage, TRoot & IHead["_defs"]["events"]> : PluvRouter<TIO, TPresence, TStorage, TRoot>;
98
- declare class PluvRouter<TIO extends IOLike = IOLike, TPresence extends JsonObject = {}, TStorage extends Record<string, CrdtType<any, any>> = {}, TEvents extends PluvRouterEventConfig<TIO, TPresence, TStorage> = {}> implements IORouterLike<TEvents> {
75
+ type MergedRouter<TRouters extends PluvRouter<TIO, TPresence, TCrdt, any>[], TIO extends IOLike, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TRoot extends TRouters[0]["_defs"]["events"]> = TRouters extends [
76
+ infer IHead extends PluvRouter<TIO, TPresence, TCrdt, any>,
77
+ ...infer ITail extends PluvRouter<TIO, TPresence, TCrdt, any>[]
78
+ ] ? MergedRouter<ITail, TIO, TPresence, TCrdt, TRoot & IHead["_defs"]["events"]> : PluvRouter<TIO, TPresence, TCrdt, TRoot>;
79
+ declare class PluvRouter<TIO extends IOLike, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, TCrdt> = {}> implements IORouterLike<TEvents> {
99
80
  readonly _defs: {
100
81
  events: TEvents;
101
82
  };
102
83
  constructor(events: TEvents);
103
- static merge<TRouters extends PluvRouter<any, any, any, any>[]>(...routers: TRouters): MergedRouter<TRouters>;
84
+ static merge<TRouters extends PluvRouter<TIO, TPresence, TCrdt, any>[], TIO extends IOLike, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>>(...routers: TRouters): MergedRouter<TRouters, TIO, TPresence, TCrdt, {}>;
104
85
  private _isValidEventName;
105
86
  }
106
87
 
107
- interface StateNotifierSubjects<TIO extends IOLike, TPresence extends JsonObject> {
108
- connection: Subject<Id<WebSocketState<TIO>>>;
109
- "my-presence": Subject<TPresence | null>;
110
- myself: Subject<Readonly<Id<UserInfo<TIO>>> | null>;
111
- others: Subject<readonly Id<UserInfo<TIO>>[]>;
112
- "storage-loaded": Subject<boolean>;
113
- }
114
- type InferSubjectValue<TIO extends IOLike, TPresence extends JsonObject, TSubject extends keyof StateNotifierSubjects<TIO, TPresence>> = StateNotifierSubjects<TIO, TPresence>[TSubject] extends Subject<infer IValue> ? Id<IValue> : never;
115
- type SubscriptionCallback<TIO extends IOLike, TPresence extends JsonObject, TSubject extends keyof StateNotifierSubjects<TIO, TPresence>> = (value: InferSubjectValue<TIO, TPresence, TSubject>) => void;
116
-
117
- type UsersManagerConfig<TPresence extends JsonObject = {}> = {
88
+ type UsersManagerConfig<TPresence extends Record<string, any> = {}> = {
118
89
  initialPresence?: TPresence;
119
90
  limits: PluvClientLimits;
120
91
  presence?: InputZodLike<TPresence>;
@@ -144,8 +115,8 @@ type RoomEndpoints<TIO extends IOLike<any, any>, TMetadata extends JsonObject> =
144
115
  } : {
145
116
  authEndpoint?: undefined;
146
117
  });
147
- type PluvRoomAddon<TIO extends IOLike, TMetadata extends JsonObject, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>> = (input: PluvRoomAddonInput<TIO, TMetadata, TPresence, TCrdt>) => Partial<PluvRoomAddonResult>;
148
- interface PluvRoomAddonInput<TIO extends IOLike, TMetadata extends JsonObject, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>> {
118
+ type PluvRoomAddon<TIO extends IOLike, TMetadata extends JsonObject, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>> = (input: PluvRoomAddonInput<TIO, TMetadata, TPresence, TCrdt>) => Partial<PluvRoomAddonResult>;
119
+ interface PluvRoomAddonInput<TIO extends IOLike, TMetadata extends JsonObject, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>> {
149
120
  room: PluvRoom<TIO, TMetadata, TPresence, TCrdt>;
150
121
  }
151
122
  interface PluvRoomAddonResult {
@@ -160,7 +131,7 @@ interface ReconnectTimeoutMsParams {
160
131
  attempts: number;
161
132
  }
162
133
  type ReconnectTimeoutMs = number | ((params: ReconnectTimeoutMsParams) => number);
163
- type RoomConfig<TIO extends IOLike, TMetadata extends JsonObject, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>>> = Id<{
134
+ type RoomConfig<TIO extends IOLike, TMetadata extends JsonObject, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>>> = Id<{
164
135
  addons?: readonly PluvRoomAddon<TIO, TMetadata, TPresence, TCrdt>[];
165
136
  debug?: boolean | PluvRoomDebug<TIO>;
166
137
  limits: PluvClientLimits;
@@ -170,7 +141,7 @@ type RoomConfig<TIO extends IOLike, TMetadata extends JsonObject, TPresence exte
170
141
  reconnectTimeoutMs?: ReconnectTimeoutMs;
171
142
  router?: PluvRouter<TIO, TPresence, InferStorage<TCrdt>, TEvents>;
172
143
  } & RoomEndpoints<TIO, TMetadata> & Pick<CrdtManagerOptions<TCrdt>, "initialStorage"> & UsersManagerConfig<TPresence>>;
173
- declare class PluvRoom<TIO extends IOLike<any, any>, TMetadata extends JsonObject = {}, TPresence extends JsonObject = {}, TCrdt extends AbstractCrdtDocFactory<any> = NoopCrdtDocFactory, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>> = {}> implements RoomLike<TIO, TPresence, InferStorage<TCrdt>> {
144
+ declare class PluvRoom<TIO extends IOLike<any, any>, TMetadata extends JsonObject = {}, TPresence extends Record<string, any> = {}, TCrdt extends AbstractCrdtDocFactory<any, any> = NoopCrdtDocFactory, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>> = {}> implements RoomLike<TIO, InferDoc<TCrdt>, TPresence, InferStorage<TCrdt>> {
174
145
  readonly _endpoints: RoomEndpoints<TIO, TMetadata>;
175
146
  readonly id: string;
176
147
  readonly metadata?: InputZodLike<TMetadata>;
@@ -180,8 +151,8 @@ declare class PluvRoom<TIO extends IOLike<any, any>, TMetadata extends JsonObjec
180
151
  private readonly _eventNotifier;
181
152
  private readonly _intervals;
182
153
  private readonly _limits;
154
+ private readonly _listenerManager;
183
155
  private readonly _listeners;
184
- private readonly _otherNotifier;
185
156
  private readonly _publicKey;
186
157
  private readonly _reconnectTimeoutMs;
187
158
  private readonly _router;
@@ -190,21 +161,29 @@ declare class PluvRoom<TIO extends IOLike<any, any>, TMetadata extends JsonObjec
190
161
  private readonly _subscriptions;
191
162
  private readonly _timeouts;
192
163
  private readonly _usersManager;
164
+ private readonly _usersNotifier;
193
165
  private _lastMetadata;
194
166
  private _state;
195
167
  private _windowListeners;
196
168
  private _wsListeners;
197
169
  constructor(room: string, options: RoomConfig<TIO, TMetadata, TPresence, TCrdt, TEvents>);
170
+ /**
171
+ * @deprecated To be removed in v3. Use `getStorageLoaded` instead.
172
+ */
198
173
  get storageLoaded(): boolean;
199
174
  get webSocket(): WebSocket | null;
200
- broadcast: (<TEvent extends keyof InferIOInput<MergeEvents<TEvents, TIO>>>(event: TEvent, data: Id<InferIOInput<MergeEvents<TEvents, TIO>>[TEvent]>) => Promise<void>) & { [PEvent in keyof InferIOInput<MergeEvents<TEvents, TIO>>]: (data: Id<InferIOInput<MergeEvents<TEvents, TIO>>[PEvent]>) => Promise<void>; };
175
+ addEventListener<TKind extends keyof RoomEventListenerMap>(kind: TKind, handler: RoomEventListenerMap[TKind]): () => void;
176
+ broadcast: BroadcastProxy<TIO, TEvents>;
201
177
  canRedo: () => boolean;
202
178
  canUndo: () => boolean;
203
179
  connect(...args: RoomConnectParams<TMetadata>): Promise<void>;
204
180
  disconnect(): Promise<void>;
205
- event: (<TEvent extends keyof InferIOOutput<MergeEvents<TEvents, TIO>>>(event: TEvent, callback: EventNotifierSubscriptionCallback<MergeEvents<TEvents, TIO>, TEvent>) => () => void) & { [PEvent in keyof InferIOOutput<MergeEvents<TEvents, TIO>>]: (callback: EventNotifierSubscriptionCallback<MergeEvents<TEvents, TIO>, PEvent>) => () => void; };
181
+ /**
182
+ * @deprecated To be removed in v3. Use PluvRoom.subscribe.event instead
183
+ */
184
+ event: EventProxy<TIO, TEvents>;
206
185
  getConnection: () => WebSocketConnection;
207
- getDoc: () => CrdtDocLike<InferStorage<TCrdt>>;
186
+ getDoc: () => CrdtDocLike<InferDoc<TCrdt>, InferStorage<TCrdt>>;
208
187
  getMyPresence: () => TPresence;
209
188
  getMyself: () => Id<UserInfo<TIO, TPresence>> | null;
210
189
  getOther: (connectionId: string) => Id<UserInfo<TIO, TPresence>> | null;
@@ -212,11 +191,22 @@ declare class PluvRoom<TIO extends IOLike<any, any>, TMetadata extends JsonObjec
212
191
  getStorage: <TKey extends keyof InferStorage<TCrdt>>(type: TKey) => InferStorage<TCrdt>[TKey] | null;
213
192
  getStorageJson(): InferCrdtJson<InferStorage<TCrdt>> | null;
214
193
  getStorageJson<TKey extends keyof InferStorage<TCrdt>>(type: TKey): InferCrdtJson<InferStorage<TCrdt>[TKey]> | null;
215
- other: (connectionId: string, callback: OtherNotifierSubscriptionCallback<TIO, TPresence>) => (() => void);
194
+ getStorageLoaded: () => boolean;
195
+ /**
196
+ * @deprecated To be removed in v3. Use PluvRoom.subscribe.other instead
197
+ */
198
+ other: (connectionId: string, callback: OtherSubscriptionCallback<TIO, TPresence>) => (() => void);
216
199
  redo: () => void;
217
- storage: <TKey extends keyof InferStorage<TCrdt>>(key: TKey, fn: (value: InferCrdtJson<InferStorage<TCrdt>[TKey]>) => void) => (() => void);
218
- storageRoot: (fn: (value: { [P in keyof InferStorage<TCrdt>]: InferCrdtJson<InferStorage<TCrdt>[P]>; }) => void) => (() => void);
219
- subscribe: <TSubject extends keyof StateNotifierSubjects<TIO, TPresence>>(name: TSubject, callback: SubscriptionCallback<TIO, TPresence, TSubject>) => (() => void);
200
+ /**
201
+ * @deprecated To be removed in v3. Use PluvRoom.subscribe.storage instead
202
+ */
203
+ storage: StorageProxy<InferStorage<TCrdt>>;
204
+ /**
205
+ * @deprecated To be removed in v3. Use PluvRoom.subscribe.storage instead
206
+ * @description Subscribes to the root storage object (serialized)
207
+ */
208
+ storageRoot: (callback: (value: { [P in keyof InferStorage<TCrdt>]: InferCrdtJson<InferStorage<TCrdt>[P]>; }) => void) => (() => void);
209
+ subscribe: SubscribeProxy<TIO, TPresence, InferStorage<TCrdt>, TEvents>;
220
210
  transact: (fn: (storage: InferStorage<TCrdt>) => void, origin?: string) => void;
221
211
  undo: () => void;
222
212
  updateMyPresence: (presence: UpdateMyPresenceAction<TPresence>) => void;
@@ -268,7 +258,7 @@ declare class PluvRoom<TIO extends IOLike<any, any>, TMetadata extends JsonObjec
268
258
  private _updateState;
269
259
  }
270
260
 
271
- type PluvClientOptions<TIO extends IOLike<any, any>, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>, TMetadata extends JsonObject> = RoomEndpoints<TIO, TMetadata> & {
261
+ type PluvClientOptions<TIO extends IOLike<any, any>, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TMetadata extends JsonObject> = RoomEndpoints<TIO, TMetadata> & {
272
262
  debug?: boolean;
273
263
  initialStorage?: TCrdt;
274
264
  /**
@@ -281,7 +271,7 @@ type PluvClientOptions<TIO extends IOLike<any, any>, TPresence extends JsonObjec
281
271
  publicKey?: PublicKey<TMetadata>;
282
272
  types: InferCallback<TIO>;
283
273
  };
284
- type CreateRoomOptions<TIO extends IOLike<any, any>, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>, TMetadata extends JsonObject, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>> = {}> = {
274
+ type CreateRoomOptions<TIO extends IOLike<any, any>, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TMetadata extends JsonObject, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>> = {}> = {
285
275
  addons?: readonly PluvRoomAddon<TIO, TMetadata, TPresence, InferStorage<TCrdt>>[];
286
276
  debug?: boolean | PluvRoomDebug<TIO>;
287
277
  initialPresence?: TPresence;
@@ -291,7 +281,7 @@ type CreateRoomOptions<TIO extends IOLike<any, any>, TPresence extends JsonObjec
291
281
  router?: PluvRouter<TIO, TPresence, InferStorage<TCrdt>, TEvents>;
292
282
  };
293
283
  type EnterRoomParams<TMetadata extends JsonObject = {}> = keyof TMetadata extends never ? [] : [WithMetadata<TMetadata>];
294
- declare class PluvClient<TIO extends IOLike<any, any>, TPresence extends JsonObject = {}, TCrdt extends AbstractCrdtDocFactory<any> = NoopCrdtDocFactory, TMetadata extends JsonObject = {}> {
284
+ declare class PluvClient<TIO extends IOLike<any, any>, TPresence extends Record<string, any> = {}, TCrdt extends AbstractCrdtDocFactory<any, any> = NoopCrdtDocFactory, TMetadata extends JsonObject = {}> {
295
285
  readonly metadata?: InputZodLike<TMetadata>;
296
286
  private readonly _authEndpoint;
297
287
  private readonly _debug;
@@ -304,7 +294,7 @@ declare class PluvClient<TIO extends IOLike<any, any>, TPresence extends JsonObj
304
294
  get _defs(): {
305
295
  initialStorage: TCrdt | undefined;
306
296
  };
307
- get procedure(): PluvProcedure<TIO, {}, {}, TPresence, InferStorage<TCrdt>>;
297
+ get procedure(): PluvProcedure<TIO, {}, {}, TPresence, TCrdt, "">;
308
298
  constructor(options: PluvClientOptions<TIO, TPresence, TCrdt, TMetadata>);
309
299
  createRoom: <TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>> = {}>(room: string, options?: CreateRoomOptions<TIO, TPresence, TCrdt, TMetadata, TEvents>) => PluvRoom<TIO, TMetadata, TPresence, TCrdt, TEvents>;
310
300
  enter: (room: string | PluvRoom<TIO, TMetadata, any, any, any>, ...args: EnterRoomParams<TMetadata>) => Promise<PluvRoom<TIO, TMetadata, TPresence, TCrdt, any>>;
@@ -315,37 +305,41 @@ declare class PluvClient<TIO extends IOLike<any, any>, TPresence extends JsonObj
315
305
  private _logDebug;
316
306
  }
317
307
 
318
- declare const createClient: <TIO extends IOLike<any, any>, TPresence extends JsonObject = {}, TCrdt extends AbstractCrdtDocFactory<any> = NoopCrdtDocFactory, TMetadata extends JsonObject = {}>(options: PluvClientOptions<TIO, TPresence, TCrdt, TMetadata>) => PluvClient<TIO, TPresence, TCrdt, TMetadata>;
308
+ declare const createClient: <TIO extends IOLike<any, any>, TPresence extends Record<string, any> = {}, TCrdt extends AbstractCrdtDocFactory<any, any> = NoopCrdtDocFactory, TMetadata extends JsonObject = {}>(options: PluvClientOptions<TIO, TPresence, TCrdt, TMetadata>) => PluvClient<TIO, TPresence, TCrdt, TMetadata>;
319
309
 
320
310
  type MockedRoomEvents<TIO extends IOLike> = Partial<{
321
311
  [P in keyof InferIOInput<TIO>]: (data: Id<InferIOInput<TIO>[P]>) => Partial<InferIOOutput<TIO>>;
322
312
  }>;
323
- type MockedRoomConfig<TIO extends IOLike, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>>> = {
313
+ type MockedRoomConfig<TIO extends IOLike, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>>> = {
324
314
  events?: MockedRoomEvents<MergeEvents<TEvents, TIO>>;
325
315
  limits?: PluvClientLimits;
326
316
  router?: PluvRouter<TIO, TPresence, InferStorage<TCrdt>, TEvents>;
327
317
  } & Pick<CrdtManagerOptions<TCrdt>, "initialStorage"> & Omit<UsersManagerConfig<TPresence>, "limits">;
328
- declare class MockedRoom<TIO extends IOLike, TPresence extends JsonObject, TCrdt extends AbstractCrdtDocFactory<any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>>> implements RoomLike<TIO, TPresence, InferStorage<TCrdt>> {
318
+ declare class MockedRoom<TIO extends IOLike, TPresence extends Record<string, any>, TCrdt extends AbstractCrdtDocFactory<any, any>, TEvents extends PluvRouterEventConfig<TIO, TPresence, InferStorage<TCrdt>>> implements RoomLike<TIO, InferDoc<TCrdt>, TPresence, InferStorage<TCrdt>> {
329
319
  readonly id: string;
320
+ /**
321
+ * @deprecated To be removed in v3. Use `getStorageLoaded` instead.
322
+ */
323
+ readonly storageLoaded: boolean;
330
324
  private readonly _crdtManager;
331
325
  private readonly _crdtNotifier;
332
326
  private readonly _eventNotifier;
333
327
  private readonly _events?;
334
328
  private readonly _limits;
335
- private readonly _otherNotifier;
329
+ private readonly _usersNotifier;
336
330
  private readonly _router;
337
331
  private _state;
338
332
  private readonly _stateNotifier;
339
333
  private readonly _subscriptions;
340
334
  private readonly _usersManager;
341
335
  constructor(room: string, options: MockedRoomConfig<TIO, TPresence, TCrdt, TEvents>);
342
- get storageLoaded(): boolean;
343
- broadcast: (<TEvent extends keyof InferIOInput<MergeEvents<TEvents, TIO>>>(event: TEvent, data: Id<InferIOInput<MergeEvents<TEvents, TIO>>[TEvent]>) => Promise<void>) & { [event in keyof InferIOInput<TIO>]: (data: Id<InferIOInput<TIO>[event]>) => Promise<void>; };
336
+ addEventListener<TKind extends keyof RoomEventListenerMap>(kind: TKind, handler: RoomEventListenerMap[TKind]): () => void;
337
+ broadcast: BroadcastProxy<TIO, TEvents>;
344
338
  canRedo: () => boolean;
345
339
  canUndo: () => boolean;
346
- event: (<TEvent extends keyof InferIOOutput<MergeEvents<TEvents, TIO>>>(event: TEvent, callback: EventNotifierSubscriptionCallback<MergeEvents<TEvents, TIO>, TEvent>) => () => void) & { [event in keyof InferIOOutput<MergeEvents<TEvents, TIO>>]: (callback: EventNotifierSubscriptionCallback<MergeEvents<TEvents, TIO>, any>) => () => void; };
340
+ event: EventProxy<TIO, TEvents>;
347
341
  getConnection: () => WebSocketConnection;
348
- getDoc(): CrdtDocLike<InferStorage<TCrdt>>;
342
+ getDoc(): CrdtDocLike<InferDoc<TCrdt>, InferStorage<TCrdt>>;
349
343
  getMyPresence: () => TPresence;
350
344
  getMyself: () => Id<UserInfo<TIO, TPresence>> | null;
351
345
  getOther: (connectionId: string) => Id<UserInfo<TIO, TPresence>> | null;
@@ -353,11 +347,12 @@ declare class MockedRoom<TIO extends IOLike, TPresence extends JsonObject, TCrdt
353
347
  getStorage: <TKey extends keyof InferStorage<TCrdt>>(type: TKey) => InferStorage<TCrdt>[TKey] | null;
354
348
  getStorageJson(): InferCrdtJson<InferStorage<TCrdt>> | null;
355
349
  getStorageJson<TKey extends keyof InferStorage<TCrdt>>(type: TKey): InferCrdtJson<InferStorage<TCrdt>[TKey]> | null;
356
- other: (connectionId: string, callback: OtherNotifierSubscriptionCallback<TIO, TPresence>) => (() => void);
350
+ getStorageLoaded(): boolean;
351
+ other: (connectionId: string, callback: OtherSubscriptionCallback<TIO, TPresence>) => (() => void);
357
352
  redo: () => void;
358
- storage: <TKey extends keyof InferStorage<TCrdt>>(key: TKey, fn: (value: InferCrdtJson<InferStorage<TCrdt>[TKey]>) => void) => (() => void);
353
+ storage: StorageProxy<InferStorage<TCrdt>>;
359
354
  storageRoot: (fn: (value: { [P in keyof InferStorage<TCrdt>]: InferCrdtJson<InferStorage<TCrdt>[P]>; }) => void) => (() => void);
360
- subscribe: <TSubject extends keyof StateNotifierSubjects<TIO, TPresence>>(name: TSubject, callback: SubscriptionCallback<TIO, TPresence, TSubject>) => (() => void);
355
+ subscribe: SubscribeProxy<TIO, TPresence, InferStorage<TCrdt>, TEvents>;
361
356
  transact: (fn: (storage: InferStorage<TCrdt>) => void, origin?: string) => void;
362
357
  undo: () => void;
363
358
  updateMyPresence: (presence: UpdateMyPresenceAction<TPresence>) => void;
@@ -375,4 +370,4 @@ declare const register: <TMetadata extends JsonObject>(params: RegisterParams<TM
375
370
  wsEndpoint: (params: EndpointParams<TMetadata>) => string;
376
371
  };
377
372
 
378
- export { AbstractStorageStore, type CreateRoomOptions, type EnterRoomParams, type InferCallback, type InferMetadata, MockedRoom, type MockedRoomConfig, type MockedRoomEvents, PluvClient, type PluvClientOptions, type PluvProcedureConfig, PluvRoom, type PluvRoomAddon, type PluvRoomAddonInput, type PluvRoomAddonResult, type PluvRoomDebug, PluvRouter, type PluvRouterEventConfig, type PublicKey, type PublicKeyParams, type RegisterParams, type RoomConnectParams, type RoomEndpoints, type WebSocketConnection, createClient, infer, register };
373
+ export { AbstractStorageStore, type CreateRoomOptions, type EnterRoomParams, type InferCallback, type InferMetadata, MockedRoom, type MockedRoomConfig, type MockedRoomEvents, PluvClient, type PluvClientOptions, type PluvProcedureConfig, PluvRoom, type PluvRoomAddon, type PluvRoomAddonInput, type PluvRoomAddonResult, type PluvRoomDebug, PluvRouter, type PluvRouterEventConfig, type PublicKey, type PublicKeyParams, type RegisterParams, type RoomConnectParams, type RoomEndpoints, createClient, infer, register };