@cr_docs_t/dts 0.0.10-alpha.0 → 0.0.10

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,8 +1,7 @@
1
- declare class CTNode {
1
+ export declare class CTNode {
2
2
  uid: string;
3
3
  character?: string;
4
4
  cause?: CTNode;
5
5
  constructor(uid: string);
6
6
  }
7
- export default CTNode;
8
7
  //# sourceMappingURL=CTNode.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"CTNode.d.ts","sourceRoot":"","sources":["../../src/CausalTree/CTNode.ts"],"names":[],"mappings":"AAAA,cAAM,MAAM;IACR,GAAG,EAAE,MAAM,CAAC;IACZ,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;gBAEH,GAAG,EAAE,MAAM;CAG1B;AAED,eAAe,MAAM,CAAC"}
1
+ {"version":3,"file":"CTNode.d.ts","sourceRoot":"","sources":["../../src/CausalTree/CTNode.ts"],"names":[],"mappings":"AAAA,qBAAa,MAAM;IACf,GAAG,EAAE,MAAM,CAAC;IACZ,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;gBAEH,GAAG,EAAE,MAAM;CAG1B"}
@@ -1,6 +1,5 @@
1
- class CTNode {
1
+ export class CTNode {
2
2
  constructor(uid) {
3
3
  this.uid = uid;
4
4
  }
5
5
  }
6
- export default CTNode;
@@ -1,7 +1,6 @@
1
- import CTNode from "./CTNode";
2
- declare class CasualTree {
1
+ import { CTNode } from "./CTNode";
2
+ export declare class CasualTree {
3
3
  root: CTNode;
4
4
  constructor(root: CTNode);
5
5
  }
6
- export default CasualTree;
7
6
  //# sourceMappingURL=CausalTree.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"CausalTree.d.ts","sourceRoot":"","sources":["../../src/CausalTree/CausalTree.ts"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,UAAU,CAAC;AAE9B,cAAM,UAAU;IAWZ,IAAI,EAAE,MAAM,CAAC;gBAED,IAAI,EAAE,MAAM;CAG3B;AAED,eAAe,UAAU,CAAC"}
1
+ {"version":3,"file":"CausalTree.d.ts","sourceRoot":"","sources":["../../src/CausalTree/CausalTree.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAElC,qBAAa,UAAU;IAWnB,IAAI,EAAE,MAAM,CAAC;gBAED,IAAI,EAAE,MAAM;CAG3B"}
@@ -1,6 +1,5 @@
1
- class CasualTree {
1
+ export class CasualTree {
2
2
  constructor(root) {
3
3
  this.root = root;
4
4
  }
5
5
  }
6
- export default CasualTree;
@@ -1,7 +1,6 @@
1
- declare class FNode<P> {
1
+ export declare class FNode<P> {
2
2
  value?: string;
3
3
  position: P;
4
4
  constructor(position: P, value?: string);
5
5
  }
6
- export default FNode;
7
6
  //# sourceMappingURL=FNode.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"FNode.d.ts","sourceRoot":"","sources":["../../src/Fugue/FNode.ts"],"names":[],"mappings":"AAAA,cAAM,KAAK,CAAC,CAAC;IACT,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,CAAC,CAAC;gBAEA,QAAQ,EAAE,CAAC,EAAE,KAAK,CAAC,EAAE,MAAM;CAI1C;AAED,eAAe,KAAK,CAAC"}
1
+ {"version":3,"file":"FNode.d.ts","sourceRoot":"","sources":["../../src/Fugue/FNode.ts"],"names":[],"mappings":"AAAA,qBAAa,KAAK,CAAC,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,CAAC,CAAC;gBAEA,QAAQ,EAAE,CAAC,EAAE,KAAK,CAAC,EAAE,MAAM;CAI1C"}
@@ -1,7 +1,6 @@
1
- class FNode {
1
+ export class FNode {
2
2
  constructor(position, value) {
3
3
  this.value = value;
4
4
  this.position = position;
5
5
  }
6
6
  }
7
- export default FNode;
@@ -1,29 +1,63 @@
1
1
  import { FugueState } from "../types/Fugue";
2
- import UniquelyDenseTotalOrder from "../TotalOrder/UniquelyDenseTotalOrder";
2
+ import { UniquelyDenseTotalOrder } from "../TotalOrder/UniquelyDenseTotalOrder";
3
3
  import { FugueMessage } from "../types/Message";
4
4
  /**
5
5
  * A Fugue List CRDT, with insert and delete operations
6
6
  */
7
- declare class FugueList<P> {
7
+ export declare class FugueList<P> {
8
8
  state: FugueState<P>;
9
9
  totalOrder: UniquelyDenseTotalOrder<P>;
10
10
  positionCounter: number;
11
11
  ws: WebSocket | null;
12
12
  constructor(totalOrder: UniquelyDenseTotalOrder<P>, ws: WebSocket | null);
13
13
  private propagate;
14
+ /**
15
+ * Inserts a value at a given position
16
+ * @param position - Position to insert at
17
+ * @param value - Value to insert
18
+ */
19
+ private insertAtPosition;
20
+ /**
21
+ * Generates unique position for new element at 'index'
22
+ * @param index - Index to generate position for
23
+ * @returns Generated position
24
+ */
25
+ private generatePosition;
14
26
  /**
15
27
  * Inserts new element with 'value' at 'index' in the list
16
28
  * @param index - Index to insert 'value' at
17
29
  * @param value - Value to insert
18
30
  */
19
31
  insert(index: number, value: string): void;
32
+ /**
33
+ * Deletes value at given position
34
+ * @param position - Position to delete at
35
+ */
36
+ private deleteAtPosition;
37
+ /**
38
+ * Finds the position of the visible value at index
39
+ * this ignores tombstoned values
40
+ * @param index - Index of the visible value
41
+ */
42
+ findVisiblePosition(index: number): P | undefined;
43
+ /**
44
+ * Finds the visible index of the value at position
45
+ * this ignores tombstoned values
46
+ * @param position - Position to find visible index for
47
+ * @returns
48
+ */
49
+ findVisibleIndex(position: P): number | undefined;
20
50
  /**
21
51
  * Delete value in the list at index
22
52
  * @param index - Index of the value to delete
23
53
  */
24
54
  delete(index: number): void;
55
+ /**
56
+ * Observes the current visible state of the list
57
+ * @returns The current visible state of the list as a string
58
+ */
25
59
  observe(): string;
26
- effect(msg: FugueMessage): void;
60
+ effect(msg: FugueMessage<P>): void;
61
+ replicaId(): string;
27
62
  }
28
- export default FugueList;
29
63
  //# sourceMappingURL=FugueList.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"FugueList.d.ts","sourceRoot":"","sources":["../../src/Fugue/FugueList.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAC5C,OAAO,uBAAuB,MAAM,uCAAuC,CAAC;AAC5E,OAAO,EAAE,YAAY,EAAa,MAAM,kBAAkB,CAAC;AAE3D;;GAEG;AACH,cAAM,SAAS,CAAC,CAAC;IACb,KAAK,EAAE,UAAU,CAAC,CAAC,CAAC,CAAM;IAC1B,UAAU,EAAE,uBAAuB,CAAC,CAAC,CAAC,CAAC;IACvC,eAAe,SAAK;IACpB,EAAE,EAAE,SAAS,GAAG,IAAI,CAAC;gBAET,UAAU,EAAE,uBAAuB,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,SAAS,GAAG,IAAI;IAKxE,OAAO,CAAC,SAAS;IAMjB;;;;OAIG;IACH,MAAM,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM;IAsCnC;;;OAGG;IACH,MAAM,CAAC,KAAK,EAAE,MAAM;IAgBpB,OAAO,IAAI,MAAM;IAgBjB,MAAM,CAAC,GAAG,EAAE,YAAY;CAgB3B;AAED,eAAe,SAAS,CAAC"}
1
+ {"version":3,"file":"FugueList.d.ts","sourceRoot":"","sources":["../../src/Fugue/FugueList.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAC5C,OAAO,EAAE,uBAAuB,EAAE,MAAM,uCAAuC,CAAC;AAChF,OAAO,EAAE,YAAY,EAAa,MAAM,kBAAkB,CAAC;AAE3D;;GAEG;AACH,qBAAa,SAAS,CAAC,CAAC;IACpB,KAAK,EAAE,UAAU,CAAC,CAAC,CAAC,CAAM;IAC1B,UAAU,EAAE,uBAAuB,CAAC,CAAC,CAAC,CAAC;IACvC,eAAe,SAAK;IACpB,EAAE,EAAE,SAAS,GAAG,IAAI,CAAC;gBAET,UAAU,EAAE,uBAAuB,CAAC,CAAC,CAAC,EAAE,EAAE,EAAE,SAAS,GAAG,IAAI;IAKxE,OAAO,CAAC,SAAS;IAMjB;;;;OAIG;IACH,OAAO,CAAC,gBAAgB;IAiCxB;;;;OAIG;IACH,OAAO,CAAC,gBAAgB;IASxB;;;;OAIG;IACH,MAAM,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM;IAcnC;;;OAGG;IACH,OAAO,CAAC,gBAAgB;IAcxB;;;;OAIG;IACH,mBAAmB,CAAC,KAAK,EAAE,MAAM,GAAG,CAAC,GAAG,SAAS;IAajD;;;;;OAKG;IACH,gBAAgB,CAAC,QAAQ,EAAE,CAAC,GAAG,MAAM,GAAG,SAAS;IAejD;;;OAGG;IACH,MAAM,CAAC,KAAK,EAAE,MAAM;IAoBpB;;;OAGG;IACH,OAAO,IAAI,MAAM;IAmBjB,MAAM,CAAC,GAAG,EAAE,YAAY,CAAC,CAAC,CAAC;IAc3B,SAAS,IAAI,MAAM;CAGtB"}
@@ -1,9 +1,9 @@
1
- import FNode from "./FNode";
1
+ import { FNode } from "./FNode";
2
2
  import { Operation } from "../types/Message";
3
3
  /**
4
4
  * A Fugue List CRDT, with insert and delete operations
5
5
  */
6
- class FugueList {
6
+ export class FugueList {
7
7
  constructor(totalOrder, ws) {
8
8
  this.state = [];
9
9
  this.positionCounter = 0;
@@ -16,95 +16,173 @@ class FugueList {
16
16
  this.ws.send(JSON.stringify(msg));
17
17
  }
18
18
  /**
19
- * Inserts new element with 'value' at 'index' in the list
20
- * @param index - Index to insert 'value' at
19
+ * Inserts a value at a given position
20
+ * @param position - Position to insert at
21
21
  * @param value - Value to insert
22
22
  */
23
- insert(index, value) {
24
- if (index >= this.state.length)
25
- this.state.push([]);
26
- let i = this.state.length - 1;
27
- while (i > index) {
28
- this.state[i] = this.state[i - 1];
29
- i--;
30
- }
31
- const atIndex = this.state[index];
32
- if (index > 0 && index < this.state.length - 1) {
33
- const before = this.state[index - 1];
34
- const after = this.state[index + 1];
35
- if (atIndex.length == 0) {
36
- atIndex.push(new FNode(this.totalOrder.createBetween(before[before.length - 1].position), value));
37
- }
38
- else {
39
- const a = atIndex[atIndex.length - 1];
40
- atIndex.push(new FNode(this.totalOrder.createBetween(a.position, after[after.length - 1].position), value));
23
+ insertAtPosition(position, value) {
24
+ let index = this.state.length;
25
+ for (let i = 0; i < this.state.length; ++i) {
26
+ const n = this.state[i][0];
27
+ // Compare positions, if the value should be
28
+ // ordered before this one, we found our index
29
+ // this should fix the issue with inserting in the
30
+ // middle messing up order
31
+ if (this.totalOrder.compare(position, n.position) < 0) {
32
+ index = i;
33
+ break;
41
34
  }
42
35
  }
36
+ console.log({ insertIndex: index });
37
+ if (index >= this.state.length) {
38
+ this.state.push([]);
39
+ }
43
40
  else {
44
- if (atIndex.length == 0) {
45
- atIndex.push(new FNode(this.totalOrder.createBetween(), value));
46
- }
47
- else {
48
- const a = atIndex[atIndex.length - 1];
49
- atIndex.push(new FNode(this.totalOrder.createBetween(a.position), value));
50
- }
41
+ this.state.splice(index, 0, []);
51
42
  }
52
- // Send to replicas
43
+ // Check if this position already exists at this index
44
+ // If it does, we don't insert again
45
+ const cell = this.state[index];
46
+ const existing = cell.find((n) => this.totalOrder.compare(n.position, position) === 0);
47
+ if (existing)
48
+ return;
49
+ cell.push(new FNode(position, value));
50
+ }
51
+ /**
52
+ * Generates unique position for new element at 'index'
53
+ * @param index - Index to generate position for
54
+ * @returns Generated position
55
+ */
56
+ generatePosition(index) {
57
+ // If this is the first thing in the document
58
+ if (this.state.length === 0)
59
+ return this.totalOrder.createBetween();
60
+ const prev = index > 0 ? this.findVisiblePosition(index - 1) : undefined;
61
+ const next = this.findVisiblePosition(index);
62
+ return this.totalOrder.createBetween(prev, next);
63
+ }
64
+ /**
65
+ * Inserts new element with 'value' at 'index' in the list
66
+ * @param index - Index to insert 'value' at
67
+ * @param value - Value to insert
68
+ */
69
+ insert(index, value) {
70
+ const pos = this.generatePosition(index);
71
+ console.log({ index, pos });
72
+ this.insertAtPosition(pos, value);
53
73
  this.propagate({
74
+ replicaId: this.totalOrder.getReplicaId(),
54
75
  operation: Operation.INSERT,
55
- position: index,
76
+ position: pos,
56
77
  data: value,
57
78
  });
58
79
  }
80
+ /**
81
+ * Deletes value at given position
82
+ * @param position - Position to delete at
83
+ */
84
+ deleteAtPosition(position) {
85
+ // Find the cell containing this position
86
+ for (let i = 0; i < this.state.length; ++i) {
87
+ const cell = this.state[i];
88
+ const node = cell.find((n) => this.totalOrder.compare(n.position, position) === 0);
89
+ if (node) {
90
+ // Tombstone the node, TODO: Implement garbage collection
91
+ node.value = undefined;
92
+ return;
93
+ }
94
+ }
95
+ }
96
+ /**
97
+ * Finds the position of the visible value at index
98
+ * this ignores tombstoned values
99
+ * @param index - Index of the visible value
100
+ */
101
+ findVisiblePosition(index) {
102
+ let count = 0;
103
+ for (const cell of this.state) {
104
+ for (const n of cell) {
105
+ if (n.value !== undefined) {
106
+ if (count === index)
107
+ return n.position;
108
+ count++;
109
+ }
110
+ }
111
+ }
112
+ }
113
+ /**
114
+ * Finds the visible index of the value at position
115
+ * this ignores tombstoned values
116
+ * @param position - Position to find visible index for
117
+ * @returns
118
+ */
119
+ findVisibleIndex(position) {
120
+ let count = 0;
121
+ for (const cell of this.state) {
122
+ for (const n of cell) {
123
+ if (n.value !== undefined) {
124
+ if (this.totalOrder.compare(n.position, position) === 0)
125
+ return count;
126
+ count++;
127
+ }
128
+ }
129
+ }
130
+ return undefined;
131
+ }
59
132
  /**
60
133
  * Delete value in the list at index
61
134
  * @param index - Index of the value to delete
62
135
  */
63
136
  delete(index) {
64
- let i = index;
65
- while (i < this.state.length) {
66
- this.state[i] = this.state[i + 1];
67
- i++;
137
+ const position = this.findVisiblePosition(index);
138
+ console.log({ index, position });
139
+ if (!position) {
140
+ console.warn(`No element at position -> ${position}`);
141
+ return;
68
142
  }
69
- this.state.pop();
143
+ this.deleteAtPosition(position);
70
144
  // Send to replicas
71
145
  this.propagate({
146
+ replicaId: this.totalOrder.getReplicaId(),
72
147
  operation: Operation.DELETE,
73
- position: index,
148
+ position: position,
74
149
  data: null,
75
150
  });
76
151
  }
152
+ /**
153
+ * Observes the current visible state of the list
154
+ * @returns The current visible state of the list as a string
155
+ */
77
156
  observe() {
78
157
  let res = new String();
79
158
  for (const idx of this.state) {
80
- if (idx.length > 1) {
81
- res += idx
82
- .sort((a, b) => this.totalOrder.compare(a.position, b.position))
83
- .map((node) => node?.value || "ð")
84
- .join("");
85
- }
86
- else {
87
- res += idx[0]?.value || "ð";
159
+ // Filter out tombstoned nodes and sort by unique position
160
+ const nodes = idx
161
+ .filter((n) => n.value !== undefined)
162
+ .sort((a, b) => this.totalOrder.compare(a.position, b.position));
163
+ // Then append to resultdkjand if somehow
164
+ //a value is undefined append the placeholder thorn
165
+ for (const n of nodes) {
166
+ res += n.value || "Þ";
88
167
  }
89
168
  }
90
169
  return res.toString();
91
170
  }
92
171
  effect(msg) {
93
- // On
94
- const { operation, data, position } = msg;
172
+ const { replicaId, operation, data, position } = msg;
173
+ if (replicaId == this.totalOrder.getReplicaId())
174
+ return;
95
175
  switch (operation) {
96
- // Operation.INSERT -> insert
97
176
  case Operation.INSERT:
98
177
  if (!data)
99
178
  throw Error("Data is required for Operation.INSERT");
100
- this.insert(position, data);
101
- break;
102
- // Operation.DELETE -> delete
179
+ return this.insertAtPosition(position, data);
103
180
  case Operation.DELETE:
104
- this.delete(position);
105
- break;
181
+ return this.deleteAtPosition(position);
106
182
  }
107
183
  throw Error("Invalid operation");
108
184
  }
185
+ replicaId() {
186
+ return this.totalOrder.getReplicaId();
187
+ }
109
188
  }
110
- export default FugueList;
@@ -1,7 +1,9 @@
1
- import UniquelyDenseTotalOrder from "./UniquelyDenseTotalOrder";
2
- export default class StringTotalOrder implements UniquelyDenseTotalOrder<string> {
1
+ import { UniquelyDenseTotalOrder } from "./UniquelyDenseTotalOrder";
2
+ export type StringPosition = string;
3
+ export declare class StringTotalOrder implements UniquelyDenseTotalOrder<StringPosition> {
3
4
  readonly replicaID: string;
4
5
  private counter;
6
+ getReplicaId(): string;
5
7
  compare(a: string, b: string): number;
6
8
  constructor(replicaID: string);
7
9
  createBetween(a?: string, b?: string): string;
@@ -1 +1 @@
1
- {"version":3,"file":"StringTotalOrder.d.ts","sourceRoot":"","sources":["../../src/TotalOrder/StringTotalOrder.ts"],"names":[],"mappings":"AAAA,OAAO,uBAAuB,MAAM,2BAA2B,CAAC;AAEhE,MAAM,CAAC,OAAO,OAAO,gBAAiB,YAAW,uBAAuB,CAAC,MAAM,CAAC;IAC5E,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,OAAO,CAAC,OAAO,CAAK;IAEpB,OAAO,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM;gBAIzB,SAAS,EAAE,MAAM;IAI7B,aAAa,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM;CA6BhD"}
1
+ {"version":3,"file":"StringTotalOrder.d.ts","sourceRoot":"","sources":["../../src/TotalOrder/StringTotalOrder.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,2BAA2B,CAAC;AAEpE,MAAM,MAAM,cAAc,GAAG,MAAM,CAAC;AAEpC,qBAAa,gBAAiB,YAAW,uBAAuB,CAAC,cAAc,CAAC;IAC5E,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,OAAO,CAAC,OAAO,CAAK;IAEpB,YAAY,IAAI,MAAM;IAItB,OAAO,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM;gBAIzB,SAAS,EAAE,MAAM;IAI7B,aAAa,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM;CA6BhD"}
@@ -1,4 +1,7 @@
1
- export default class StringTotalOrder {
1
+ export class StringTotalOrder {
2
+ getReplicaId() {
3
+ return this.replicaID;
4
+ }
2
5
  compare(a, b) {
3
6
  return a.localeCompare(b);
4
7
  }
@@ -15,13 +18,13 @@ export default class StringTotalOrder {
15
18
  }
16
19
  // If node is the first position at that index
17
20
  if (!a) {
18
- return b + uniqueStr + "R";
21
+ return b.slice(0, -1) + "L" + uniqueStr + "R";
19
22
  }
20
23
  // If node is the last position at that index
21
24
  if (!b) {
22
25
  return a + uniqueStr + "R";
23
26
  }
24
- const isAPrefixOfB = b.substring(0, a.length).localeCompare(a);
27
+ const isAPrefixOfB = b.startsWith(a);
25
28
  // If a is not a prefix of b append a globally unique new string to a and return that +R
26
29
  if (!isAPrefixOfB) {
27
30
  return a + uniqueStr + "R";
@@ -4,7 +4,8 @@
4
4
  *
5
5
  * @type P The type of positions. Treated as immutable.
6
6
  */
7
- export default interface UniquelyDenseTotalOrder<P> {
7
+ export interface UniquelyDenseTotalOrder<P> {
8
+ getReplicaId(): string;
8
9
  /**
9
10
  * Usual compare function for sorts: returns negative if a < b in
10
11
  * their sort order, positive if a > b.
@@ -1 +1 @@
1
- {"version":3,"file":"UniquelyDenseTotalOrder.d.ts","sourceRoot":"","sources":["../../src/TotalOrder/UniquelyDenseTotalOrder.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,MAAM,CAAC,OAAO,WAAW,uBAAuB,CAAC,CAAC;IAC9C;;;OAGG;IACH,OAAO,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC;IAE5B;;;;;;;;;;OAUG;IACH,aAAa,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC;CAClC"}
1
+ {"version":3,"file":"UniquelyDenseTotalOrder.d.ts","sourceRoot":"","sources":["../../src/TotalOrder/UniquelyDenseTotalOrder.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,MAAM,WAAW,uBAAuB,CAAC,CAAC;IACtC,YAAY,IAAI,MAAM,CAAC;IAEvB;;;OAGG;IACH,OAAO,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC;IAE5B;;;;;;;;;;OAUG;IACH,aAAa,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC;CAClC"}
package/dist/index.d.ts CHANGED
@@ -1,8 +1,7 @@
1
- import FugueList from "./Fugue/FugueList";
2
- import CausalTree from "./CausalTree/CausalTree";
3
- import UniquelyDenseTotalOrder from "./TotalOrder/UniquelyDenseTotalOrder";
4
- import StringTotalOrder from "./TotalOrder/StringTotalOrder";
5
- import { FugueMessage, Operation, Data } from "./types/Message";
6
- import { FugueState } from "./types/Fugue";
7
- export { FugueList, CausalTree, UniquelyDenseTotalOrder, StringTotalOrder, FugueMessage, FugueState, Operation, Data, };
1
+ export * from "./Fugue/FugueList";
2
+ export * from "./CausalTree/CausalTree";
3
+ export * from "./TotalOrder/UniquelyDenseTotalOrder";
4
+ export * from "./TotalOrder/StringTotalOrder";
5
+ export * from "./types/Message";
6
+ export * from "./types/Fugue";
8
7
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,SAAS,MAAM,mBAAmB,CAAC;AAC1C,OAAO,UAAU,MAAM,yBAAyB,CAAC;AACjD,OAAO,uBAAuB,MAAM,sCAAsC,CAAC;AAC3E,OAAO,gBAAgB,MAAM,+BAA+B,CAAC;AAC7D,OAAO,EAAE,YAAY,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,iBAAiB,CAAC;AAChE,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAE3C,OAAO,EAEH,SAAS,EACT,UAAU,EAEV,uBAAuB,EACvB,gBAAgB,EAGhB,YAAY,EACZ,UAAU,EACV,SAAS,EACT,IAAI,GACP,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,mBAAmB,CAAC;AAClC,cAAc,yBAAyB,CAAC;AAExC,cAAc,sCAAsC,CAAC;AACrD,cAAc,+BAA+B,CAAC;AAC9C,cAAc,iBAAiB,CAAC;AAChC,cAAc,eAAe,CAAC"}
package/dist/index.js CHANGED
@@ -1,7 +1,6 @@
1
- import FugueList from "./Fugue/FugueList";
2
- import CausalTree from "./CausalTree/CausalTree";
3
- import StringTotalOrder from "./TotalOrder/StringTotalOrder";
4
- import { Operation } from "./types/Message";
5
- export {
6
- // Data Types
7
- FugueList, CausalTree, StringTotalOrder, Operation, };
1
+ export * from "./Fugue/FugueList";
2
+ export * from "./CausalTree/CausalTree";
3
+ export * from "./TotalOrder/UniquelyDenseTotalOrder";
4
+ export * from "./TotalOrder/StringTotalOrder";
5
+ export * from "./types/Message";
6
+ export * from "./types/Fugue";
@@ -1,3 +1,3 @@
1
- import FNode from "../Fugue/FNode";
1
+ import { FNode } from "../Fugue/FNode";
2
2
  export type FugueState<P> = FNode<P>[][];
3
3
  //# sourceMappingURL=Fugue.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"Fugue.d.ts","sourceRoot":"","sources":["../../src/types/Fugue.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,gBAAgB,CAAC;AAEnC,MAAM,MAAM,UAAU,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAA"}
1
+ {"version":3,"file":"Fugue.d.ts","sourceRoot":"","sources":["../../src/types/Fugue.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,MAAM,gBAAgB,CAAC;AAEvC,MAAM,MAAM,UAAU,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC"}
@@ -2,11 +2,11 @@ export declare enum Operation {
2
2
  INSERT = 0,
3
3
  DELETE = 1
4
4
  }
5
- export type Position = number;
6
5
  export type Data = string;
7
- export interface FugueMessage {
6
+ export interface FugueMessage<P> {
7
+ replicaId: string;
8
8
  operation: Operation;
9
- position: number;
9
+ position: P;
10
10
  data: Data | null;
11
11
  }
12
12
  //# sourceMappingURL=Message.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"Message.d.ts","sourceRoot":"","sources":["../../src/types/Message.ts"],"names":[],"mappings":"AAAA,oBAAY,SAAS;IACjB,MAAM,IAAA;IACN,MAAM,IAAA;CACT;AAED,MAAM,MAAM,QAAQ,GAAG,MAAM,CAAC;AAE9B,MAAM,MAAM,IAAI,GAAG,MAAM,CAAC;AAE1B,MAAM,WAAW,YAAY;IACzB,SAAS,EAAE,SAAS,CAAC;IACrB,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,IAAI,GAAG,IAAI,CAAC;CACrB"}
1
+ {"version":3,"file":"Message.d.ts","sourceRoot":"","sources":["../../src/types/Message.ts"],"names":[],"mappings":"AAAA,oBAAY,SAAS;IACjB,MAAM,IAAA;IACN,MAAM,IAAA;CACT;AAGD,MAAM,MAAM,IAAI,GAAG,MAAM,CAAC;AAE1B,MAAM,WAAW,YAAY,CAAC,CAAC;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,SAAS,CAAC;IACrB,QAAQ,EAAE,CAAC,CAAC;IACZ,IAAI,EAAE,IAAI,GAAG,IAAI,CAAC;CACrB"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cr_docs_t/dts",
3
- "version": "0.0.10-alpha.0",
3
+ "version": "0.0.10",
4
4
  "description": "",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -1,2 +0,0 @@
1
- export {};
2
- //# sourceMappingURL=FugueTest.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"FugueTest.d.ts","sourceRoot":"","sources":["../../src/Fugue/FugueTest.ts"],"names":[],"mappings":""}
@@ -1,22 +0,0 @@
1
- import FugueList from "./FugueList";
2
- import { randomString } from "../utils/index";
3
- import StringTotalOrder from "../TotalOrder/StringTotalOrder";
4
- const test1 = new FugueList(new StringTotalOrder(randomString(5)));
5
- const test2 = new FugueList(new StringTotalOrder(randomString(5)));
6
- const word1 = "SHADOW WIZARD MONEY GANG";
7
- const word2 = "BALLING";
8
- // Randomly insert words into the list from different simulated users
9
- async function simulateUser(list, word) {
10
- for (let i = 0; i < word.length; i++) {
11
- await new Promise((resolve) => setTimeout(resolve, Math.random() * 150));
12
- list.insert(i, word.charAt(i));
13
- console.log(list.observe());
14
- console.log(list.state);
15
- }
16
- }
17
- Promise.all([
18
- simulateUser(test1, word1), //
19
- simulateUser(test2, word2),
20
- ])
21
- .then(() => console.log(`Done:\t${test1.observe()}\n\t${test2.observe()}`))
22
- .catch(console.error);
@@ -1,34 +0,0 @@
1
- /**
2
- * Helper interface for sorting and creating unique immutable positions,
3
- * suitable for use in a List CRDT. Taken from mattweidner.com/2022/10/21/basic-list-crdt.html
4
- *
5
- * @type P The type of positions. Treated as immutable.
6
- */
7
- export interface UniquelyDenseTotalOrder<P> {
8
- /**
9
- * Usual compare function for sorts: returns negative if a < b in
10
- * their sort order, positive if a > b.
11
- */
12
- compare(a: P, b: P): number;
13
- /**
14
- * Returns a globally unique new position c such that a < c < b.
15
- *
16
- * "Globally unique" means that the created position must be distinct
17
- * from all other created positions, including ones created concurrently
18
- * by other users.
19
- *
20
- * When a is undefined, it is treated as the start of the list, i.e.,
21
- * this returns c such that c < b. Likewise, undefined b is treated
22
- * as the end of the list.
23
- */
24
- createBetween(a?: P, b?: P): P;
25
- }
26
- export declare class StringTotalOrder implements UniquelyDenseTotalOrder<string> {
27
- readonly replicaID: string;
28
- private counter;
29
- compare(a: string, b: string): number;
30
- constructor(replicaID: string);
31
- createBetween(a?: string, b?: string): string;
32
- }
33
- export declare function randomString(length?: number): string;
34
- //# sourceMappingURL=utils.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/Fugue/utils.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,MAAM,WAAW,uBAAuB,CAAC,CAAC;IACtC;;;OAGG;IACH,OAAO,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC;IAE5B;;;;;;;;;;OAUG;IACH,aAAa,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC;CAClC;AAED,qBAAa,gBAAiB,YAAW,uBAAuB,CAAC,MAAM,CAAC;IACpE,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,OAAO,CAAC,OAAO,CAAK;IAEpB,OAAO,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM;gBAIzB,SAAS,EAAE,MAAM;IAI7B,aAAa,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,EAAE,MAAM,GAAG,MAAM;CA6BhD;AAED,wBAAgB,YAAY,CAAC,MAAM,GAAE,MAAW,GAAG,MAAM,CAIxD"}
@@ -1,41 +0,0 @@
1
- export class StringTotalOrder {
2
- compare(a, b) {
3
- return a.localeCompare(b);
4
- }
5
- constructor(replicaID) {
6
- this.counter = 0;
7
- this.replicaID = replicaID;
8
- }
9
- createBetween(a, b) {
10
- // Create a wholly unique string using a causal dot, i.e. (replicaID, counter)
11
- const uniqueStr = `${this.replicaID}${this.counter++}`;
12
- // If node is the first ever position in the document
13
- if (!a && !b) {
14
- return uniqueStr + "R";
15
- }
16
- // If node is the first position at that index
17
- if (!a) {
18
- return b + uniqueStr + "R";
19
- }
20
- // If node is the last position at that index
21
- if (!b) {
22
- return a + uniqueStr + "R";
23
- }
24
- const isAPrefixOfB = b.substring(0, a.length).localeCompare(a);
25
- // If a is not a prefix of b append a globally unique new string to a and return that +R
26
- if (!isAPrefixOfB) {
27
- return a + uniqueStr + "R";
28
- }
29
- else {
30
- // If a is a prefix of b replace the R at the end of b with L.
31
- // Then append a globally unique string to it and return it +R.
32
- return b.slice(0, -1) + "L" + uniqueStr + "R";
33
- }
34
- }
35
- }
36
- export function randomString(length = 10) {
37
- let res = new Array(length);
38
- for (let i = 0; i < length; i++)
39
- res[i] = String.fromCharCode(97 + Math.floor(Math.random() * 26));
40
- return res.join("");
41
- }