@pylonsync/loro 0.22.26 → 0.22.28

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pylonsync/loro",
3
- "version": "0.22.26",
3
+ "version": "0.22.28",
4
4
  "description": "Pylon's local-first React layer — wraps loro-crdt with a registry, useLoroDoc hook, and the binary WS wire-format decoder that mirrors crates/router/encode_crdt_frame.",
5
5
  "publishConfig": {
6
6
  "access": "public"
@@ -17,8 +17,8 @@
17
17
  "check": "tsc -p tsconfig.json --noEmit"
18
18
  },
19
19
  "dependencies": {
20
- "@pylonsync/react": "0.22.26",
21
- "@pylonsync/sync": "0.22.26",
20
+ "@pylonsync/react": "0.22.28",
21
+ "@pylonsync/sync": "0.22.28",
22
22
  "loro-crdt": "^1.10.6"
23
23
  },
24
24
  "peerDependencies": {
@@ -0,0 +1,52 @@
1
+ import { expect, test } from "bun:test";
2
+ import { LoroDoc, LoroText } from "loro-crdt";
3
+ import { SyncEngine } from "@pylonsync/sync";
4
+ import { LoroRegistry } from "./registry";
5
+ import { CRDT_FRAME_SNAPSHOT, encodeCrdtFrame } from "./wire";
6
+
7
+ test("a late follower requests full history after incremental frames", () => {
8
+ const source = new LoroDoc();
9
+ const text = source.getMap("row").setContainer("body", new LoroText());
10
+ text.insert(0, "baseline");
11
+ source.commit();
12
+ const baseline = source.export({ mode: "snapshot" });
13
+ const version = source.version();
14
+ text.insert(text.length, " plus delta");
15
+ source.commit();
16
+ const delta = source.export({ mode: "update", from: version });
17
+ const frame = (bytes: Uint8Array) => encodeCrdtFrame(CRDT_FRAME_SNAPSHOT, "Doc", "row", bytes);
18
+ const incomplete = new LoroRegistry();
19
+ incomplete.applyBinaryFrame(frame(delta));
20
+ expect(incomplete.doc("Doc", "row").toJSON()).not.toEqual(source.toJSON());
21
+
22
+ const engine = new SyncEngine({ baseUrl: "http://test.invalid", multiTab: false, persist: false });
23
+ const internal = engine as unknown as {
24
+ dispatchBinaryFrame(bytes: Uint8Array): void;
25
+ sendWs(message: unknown): void;
26
+ broadcastToTabs(message: { type: string; bytes?: Uint8Array }): void;
27
+ subscriptions: { handleForwardedRegister(message: Record<string, unknown>, tab: string): void };
28
+ };
29
+ const requests: unknown[] = [];
30
+ internal.sendWs = (message) => { requests.push(message); };
31
+ engine.subscribeCrdt("Doc", "row");
32
+ internal.dispatchBinaryFrame(frame(baseline));
33
+ internal.dispatchBinaryFrame(frame(delta));
34
+ const late = new LoroRegistry();
35
+ let forwarded = 0;
36
+ internal.broadcastToTabs = (message) => {
37
+ if (message.type === "binary") {
38
+ forwarded++;
39
+ late.applyBinaryFrame(message.bytes!);
40
+ }
41
+ };
42
+ const requestCount = requests.length;
43
+ const interest = { kind: "crdt", key: "Doc\x00row", entity: "Doc", rowId: "row" };
44
+ internal.subscriptions.handleForwardedRegister(interest, "late-tab");
45
+ expect(requests).toHaveLength(requestCount + 1);
46
+ expect(requests.at(-1)).toEqual({ type: "crdt-subscribe", entity: "Doc", rowId: "row" });
47
+ expect(forwarded).toBe(0);
48
+ internal.dispatchBinaryFrame(frame(source.export({ mode: "snapshot" })));
49
+ expect(late.doc("Doc", "row").toJSON()).toEqual(source.toJSON());
50
+ internal.subscriptions.handleForwardedRegister(interest, "late-tab");
51
+ expect(requests).toHaveLength(requestCount + 1);
52
+ });
@@ -148,7 +148,7 @@ test("two registries hydrated from snapshots converge after exchange", () => {
148
148
  const aText = a.doc("Note", "n1").getText("body").toString();
149
149
  const bText = b.doc("Note", "n1").getText("body").toString();
150
150
  expect(aText).toBe(bText);
151
- expect(aText.length).toBeGreaterThan(0);
151
+ expect([...aText].sort()).toEqual([..."from-afrom-b"].sort());
152
152
  });
153
153
 
154
154
  test("touch bumps the version and notifies — optimistic local renders", () => {