reactronic 0.94.25030 → 0.94.25031

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/README.md CHANGED
@@ -231,7 +231,7 @@ class Component<P> extends React.Component<P> {
231
231
  }
232
232
 
233
233
  componentWillUnmount(): void {
234
- atomicAction(ReactiveSystem.dispose, this)
234
+ atomicAction(disposeObservableObject, this)
235
235
  }
236
236
  }
237
237
  ```
@@ -1,4 +1,5 @@
1
+ import { misuse } from "./util/Dbg.js";
1
2
  import { ObservableObject } from "./core/Mvcc.js";
2
3
  export class Pipe extends ObservableObject {
3
- static create(hint, capacity) { throw new Error("not implemented"); }
4
+ static create(hint, capacity) { throw misuse("not implemented"); }
4
5
  }
@@ -1,3 +1,4 @@
1
+ import { misuse } from "./util/Dbg.js";
1
2
  import { runAtomically, runNonReactively } from "./System.js";
2
3
  export function refs(owner) {
3
4
  return new Proxy(owner, RefGettingProxy);
@@ -34,7 +35,7 @@ export class Ref {
34
35
  return this.variable;
35
36
  }
36
37
  unobserve() {
37
- throw new Error("not implemented");
38
+ throw misuse("not implemented");
38
39
  }
39
40
  static sameRefs(v1, v2) {
40
41
  return v1.owner === v2.owner && v1.name === v2.name && v1.index === v2.index;
@@ -1,4 +1,4 @@
1
- import { Log } from "./util/Dbg.js";
1
+ import { Log, misuse } from "./util/Dbg.js";
2
2
  import { Kind, Isolation } from "./Enums.js";
3
3
  import { Meta, ObjectHandle } from "./core/Data.js";
4
4
  import { Changeset } from "./core/Changeset.js";
@@ -39,7 +39,7 @@ export function runSensitively(sensitivity, func, ...args) {
39
39
  return Mvcc.sensitive(sensitivity, func, ...args);
40
40
  }
41
41
  export function runContextually(p) {
42
- throw new Error("not implemented yet");
42
+ throw misuse("not implemented yet");
43
43
  }
44
44
  export function manageReactiveOperation(method) {
45
45
  return ReactiveOperationImpl.manageReactiveOperation(method);
@@ -1,4 +1,5 @@
1
1
  export { all, pause, proceedSyncOrAsync } from "./util/Utils.js";
2
+ export { Uri } from "./util/Uri.js";
2
3
  export { MergeList } from "./util/MergeList.js";
3
4
  export type { MergedItem, MergeListReader } from "./util/MergeList.js";
4
5
  export { SealedArray } from "./util/SealedArray.js";
@@ -1,4 +1,5 @@
1
1
  export { all, pause, proceedSyncOrAsync } from "./util/Utils.js";
2
+ export { Uri } from "./util/Uri.js";
2
3
  export { MergeList } from "./util/MergeList.js";
3
4
  export { SealedArray } from "./util/SealedArray.js";
4
5
  export { SealedMap } from "./util/SealedMap.js";
@@ -1,3 +1,4 @@
1
+ import { misuse } from "../util/Dbg.js";
1
2
  import { Isolation } from "../Enums.js";
2
3
  import { ObservableObject } from "./Mvcc.js";
3
4
  import { Meta, ContentFootprint } from "./Data.js";
@@ -38,7 +39,7 @@ export class JournalImpl extends Journal {
38
39
  if (this._unsaved === patch)
39
40
  this._unsaved = new Map();
40
41
  else
41
- throw new Error("not implemented");
42
+ throw misuse("not implemented");
42
43
  }
43
44
  undo(count = 1) {
44
45
  Transaction.run({ hint: "Journal.undo", isolation: Isolation.disjoinFromOuterAndInnerTransactions }, () => {
@@ -26,6 +26,7 @@ export declare abstract class ReactiveTreeNode<E = unknown> {
26
26
  abstract priority?: Priority;
27
27
  abstract childrenShuffling: boolean;
28
28
  abstract strictOrder: boolean;
29
+ abstract getUri(relativeTo?: ReactiveTreeNode<any>): string;
29
30
  abstract has(mode: Mode): boolean;
30
31
  abstract configureReactivity(options: Partial<ReactivityOptions>): ReactivityOptions;
31
32
  static get current(): ReactiveTreeNode;
@@ -38,6 +39,7 @@ export declare abstract class ReactiveTreeNode<E = unknown> {
38
39
  static triggerFinalization(node: ReactiveTreeNode<any>): void;
39
40
  static runNestedNodeScriptsThenDo(action: (error: unknown) => void): void;
40
41
  static markAsMounted(node: ReactiveTreeNode<any>, yes: boolean): void;
42
+ lookupTreeNodeByUri<E = unknown>(uri: string): ReactiveTreeNode<E> | undefined;
41
43
  static findMatchingHost<E = unknown, R = unknown>(node: ReactiveTreeNode<E>, match: Handler<ReactiveTreeNode<E>, boolean>): ReactiveTreeNode<R> | undefined;
42
44
  static findMatchingPrevSibling<E = unknown, R = unknown>(node: ReactiveTreeNode<E>, match: Handler<ReactiveTreeNode<E>, boolean>): ReactiveTreeNode<R> | undefined;
43
45
  static forEachChildRecursively<E = unknown>(node: ReactiveTreeNode<E>, action: Handler<ReactiveTreeNode<E>>): void;
@@ -90,7 +92,7 @@ export declare class ReactiveTreeVariable<T extends Object = Object> {
90
92
  get value(): T;
91
93
  get valueOrUndefined(): T | undefined;
92
94
  }
93
- export declare function generateKey(owner: ReactiveTreeNodeImpl): string;
95
+ export declare function generateKey(owner?: ReactiveTreeNodeImpl): string;
94
96
  export declare function getModeUsingBasisChain(declaration?: ReactiveTreeNodeDecl<any>): Mode;
95
97
  declare class ReactiveTreeNodeContextImpl<T extends Object = Object> extends ObservableObject implements ReactiveTreeNodeContext<T> {
96
98
  next: ReactiveTreeNodeContextImpl<object> | undefined;
@@ -118,6 +120,7 @@ declare class ReactiveTreeNodeImpl<E = unknown> extends ReactiveTreeNode<E> {
118
120
  priority: Priority;
119
121
  childrenShuffling: boolean;
120
122
  constructor(key: string, driver: ReactiveTreeNodeDriver<E>, declaration: Readonly<ReactiveTreeNodeDecl<E>>, owner: ReactiveTreeNodeImpl | undefined);
123
+ getUri(relativeTo?: ReactiveTreeNode<any>): string;
121
124
  get strictOrder(): boolean;
122
125
  set strictOrder(value: boolean);
123
126
  get isMoved(): boolean;
@@ -17,6 +17,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
17
17
  });
18
18
  };
19
19
  import { misuse } from "../util/Dbg.js";
20
+ import { Uri } from "../util/Uri.js";
20
21
  import { MergeList } from "../util/MergeList.js";
21
22
  import { emitLetters, getCallerInfo, proceedSyncOrAsync } from "../util/Utils.js";
22
23
  import { Priority, Mode, Isolation, Reentrance } from "../Enums.js";
@@ -50,7 +51,7 @@ export class ReactiveTreeNode {
50
51
  if (existing) {
51
52
  result = existing.instance;
52
53
  if (result.driver !== driver && driver !== undefined)
53
- throw new Error(`changing element driver is not yet supported: "${result.driver.name}" -> "${driver === null || driver === void 0 ? void 0 : driver.name}"`);
54
+ throw misuse(`changing element driver is not yet supported: "${result.driver.name}" -> "${driver === null || driver === void 0 ? void 0 : driver.name}"`);
54
55
  const exTriggers = result.declaration.triggers;
55
56
  if (observablesAreEqual(declaration.triggers, exTriggers))
56
57
  declaration.triggers = exTriggers;
@@ -62,7 +63,7 @@ export class ReactiveTreeNode {
62
63
  }
63
64
  }
64
65
  else {
65
- result = new ReactiveTreeNodeImpl(effectiveKey || "", driver, declaration, owner);
66
+ result = new ReactiveTreeNodeImpl(effectiveKey || generateKey(owner), driver, declaration, owner);
66
67
  result.slot = MergeList.createItem(result);
67
68
  triggerScriptRunViaSlot(result.slot);
68
69
  }
@@ -93,11 +94,22 @@ export class ReactiveTreeNode {
93
94
  static markAsMounted(node, yes) {
94
95
  const n = node;
95
96
  if (n.stamp < 0)
96
- throw new Error("deactivated node cannot be mounted or unmounted");
97
+ throw misuse("deactivated node cannot be mounted or unmounted");
97
98
  if (n.stamp >= Number.MAX_SAFE_INTEGER)
98
- throw new Error("node must be activated before mounting");
99
+ throw misuse("node must be activated before mounting");
99
100
  n.stamp = yes ? 0 : Number.MAX_SAFE_INTEGER - 1;
100
101
  }
102
+ lookupTreeNodeByUri(uri) {
103
+ var _a;
104
+ const t = Uri.parse(uri);
105
+ if (t.authority !== this.key)
106
+ throw misuse(`authority '${t.authority}' doesn't match root node key '${this.key}'`);
107
+ const segments = t.path.split("/");
108
+ let result = this;
109
+ for (let i = 1; i < segments.length && result !== undefined; i++)
110
+ result = (_a = result.children.lookup(segments[i])) === null || _a === void 0 ? void 0 : _a.instance;
111
+ return result;
112
+ }
101
113
  static findMatchingHost(node, match) {
102
114
  let p = node.host;
103
115
  while (p !== p.host && !match(p))
@@ -168,7 +180,7 @@ export class ReactiveTreeVariable {
168
180
  }
169
181
  }
170
182
  export function generateKey(owner) {
171
- const n = owner.numerator++;
183
+ const n = owner !== undefined ? owner.numerator++ : 0;
172
184
  const lettered = emitLetters(n);
173
185
  let result;
174
186
  if (ReactiveSystem.isLogging)
@@ -266,6 +278,16 @@ class ReactiveTreeNodeImpl extends ReactiveTreeNode {
266
278
  if (this.has(Mode.autonomous))
267
279
  ReactiveTreeNodeImpl.disposableNodeCount++;
268
280
  }
281
+ getUri(relativeTo) {
282
+ const path = [];
283
+ const authority = gatherAuthorityAndPath(this, path);
284
+ const result = Uri.from({
285
+ scheme: "node",
286
+ authority,
287
+ path: "/" + path.join("/"),
288
+ });
289
+ return result.toString();
290
+ }
269
291
  get strictOrder() {
270
292
  return this.children.isStrict;
271
293
  }
@@ -283,12 +305,12 @@ class ReactiveTreeNodeImpl extends ReactiveTreeNode {
283
305
  }
284
306
  configureReactivity(options) {
285
307
  if (this.stamp < Number.MAX_SAFE_INTEGER - 1 || !this.has(Mode.autonomous))
286
- throw new Error("reactronic can be configured only for elements with autonomous mode and only during preparation");
308
+ throw misuse("reactronic can be configured only for elements with autonomous mode and only during preparation");
287
309
  return manageReactiveOperation(this.script).configure(options);
288
310
  }
289
311
  static get nodeSlot() {
290
312
  if (!gNodeSlot)
291
- throw new Error("current element is undefined");
313
+ throw misuse("current element is undefined");
292
314
  return gNodeSlot;
293
315
  }
294
316
  static tryUseTreeVariableValue(variable) {
@@ -302,7 +324,7 @@ class ReactiveTreeNodeImpl extends ReactiveTreeNode {
302
324
  var _a;
303
325
  const result = (_a = ReactiveTreeNodeImpl.tryUseTreeVariableValue(variable)) !== null && _a !== void 0 ? _a : variable.defaultValue;
304
326
  if (!result)
305
- throw new Error("unknown node variable");
327
+ throw misuse("unknown node variable");
306
328
  return result;
307
329
  }
308
330
  static setTreeVariableValue(variable, value) {
@@ -345,6 +367,16 @@ __decorate([
345
367
  __metadata("design:paramtypes", [Object]),
346
368
  __metadata("design:returntype", void 0)
347
369
  ], ReactiveTreeNodeImpl.prototype, "script", null);
370
+ function gatherAuthorityAndPath(node, path, relativeTo) {
371
+ let authority;
372
+ if (node.owner !== node && node.owner !== relativeTo) {
373
+ authority = gatherAuthorityAndPath(node.owner, path);
374
+ path.push(node.key);
375
+ }
376
+ else
377
+ authority = node.key;
378
+ return authority;
379
+ }
348
380
  function getNodeKey(node) {
349
381
  return node.stamp >= 0 ? node.key : undefined;
350
382
  }
@@ -1,3 +1,4 @@
1
+ import { misuse } from "./Dbg.js";
1
2
  export class MergeList {
2
3
  constructor(getKey, strict = false) {
3
4
  this.getKey = getKey;
@@ -13,7 +14,7 @@ export class MergeList {
13
14
  get isStrict() { return this.strict; }
14
15
  set isStrict(value) {
15
16
  if (this.isMergeInProgress && this.current.count > 0)
16
- throw new Error("cannot change strict mode in the middle of merge");
17
+ throw misuse("cannot change strict mode in the middle of merge");
17
18
  this.strict = value;
18
19
  }
19
20
  get count() {
@@ -46,7 +47,7 @@ export class MergeList {
46
47
  tryMergeAsExisting(key, resolution, error) {
47
48
  const tag = this.tag;
48
49
  if (tag < 0)
49
- throw new Error(error !== null && error !== void 0 ? error : "merge is not in progress");
50
+ throw misuse(error !== null && error !== void 0 ? error : "merge is not in progress");
50
51
  let item = this.strictNextItem;
51
52
  if (key !== (item ? this.getKey(item.instance) : undefined))
52
53
  item = this.lookup(key);
@@ -65,7 +66,7 @@ export class MergeList {
65
66
  else if (resolution)
66
67
  resolution.isDuplicate = true;
67
68
  else
68
- throw new Error(`duplicate collection item: ${key}`);
69
+ throw misuse(`duplicate collection item: ${key}`);
69
70
  }
70
71
  else if (resolution)
71
72
  resolution.isDuplicate = false;
@@ -74,7 +75,7 @@ export class MergeList {
74
75
  mergeAsAdded(instance) {
75
76
  const key = this.getKey(instance);
76
77
  if (this.lookup(key) !== undefined)
77
- throw new Error(`key is already in use: ${key}`);
78
+ throw misuse(`key is already in use: ${key}`);
78
79
  let tag = this.tag;
79
80
  if (tag < 0) {
80
81
  tag = ~this.tag + 1;
@@ -98,11 +99,11 @@ export class MergeList {
98
99
  }
99
100
  }
100
101
  move(item, after) {
101
- throw new Error("not implemented");
102
+ throw misuse("not implemented");
102
103
  }
103
104
  beginMerge() {
104
105
  if (this.isMergeInProgress)
105
- throw new Error("merge is in progress already");
106
+ throw misuse("merge is in progress already");
106
107
  this.tag = ~this.tag + 1;
107
108
  this.strictNextItem = this.current.first;
108
109
  this.removed.grab(this.current, false);
@@ -110,7 +111,7 @@ export class MergeList {
110
111
  }
111
112
  endMerge(error) {
112
113
  if (!this.isMergeInProgress)
113
- throw new Error("merge is ended already");
114
+ throw misuse("merge is ended already");
114
115
  this.tag = ~this.tag;
115
116
  if (error === undefined) {
116
117
  const currentCount = this.current.count;
@@ -0,0 +1,20 @@
1
+ export interface UriComponents {
2
+ scheme: string;
3
+ authority?: string;
4
+ path?: string;
5
+ query?: string;
6
+ fragment?: string;
7
+ }
8
+ export declare class Uri implements UriComponents {
9
+ private static readonly regexp;
10
+ readonly scheme: string;
11
+ readonly authority: string;
12
+ readonly path: string;
13
+ readonly query: string;
14
+ readonly fragment: string;
15
+ protected constructor(scheme: string, authority?: string, path?: string, query?: string, fragment?: string);
16
+ equalsTo(uri: Uri): boolean;
17
+ toString(): string;
18
+ static parse(value: string): Uri;
19
+ static from(components: UriComponents): Uri;
20
+ }
@@ -0,0 +1,67 @@
1
+ import { misuse } from "./Dbg.js";
2
+ export class Uri {
3
+ constructor(scheme, authority, path, query, fragment) {
4
+ this.scheme = scheme;
5
+ this.authority = authority !== null && authority !== void 0 ? authority : "";
6
+ this.path = path !== null && path !== void 0 ? path : "";
7
+ this.query = query !== null && query !== void 0 ? query : "";
8
+ this.fragment = fragment !== null && fragment !== void 0 ? fragment : "";
9
+ validateUri(this);
10
+ }
11
+ equalsTo(uri) {
12
+ return this.scheme === uri.scheme &&
13
+ this.authority === uri.authority &&
14
+ this.path === uri.path &&
15
+ this.query === uri.query &&
16
+ this.fragment === uri.fragment;
17
+ }
18
+ toString() {
19
+ let result = `${this.scheme}://${this.authority}${this.path}`;
20
+ if (this.query) {
21
+ result += `?${this.query}`;
22
+ }
23
+ if (this.fragment) {
24
+ result += `#${this.fragment}`;
25
+ }
26
+ return result;
27
+ }
28
+ static parse(value) {
29
+ var _a, _b, _c, _d, _e;
30
+ let result;
31
+ const match = Uri.regexp.exec(value);
32
+ if (!match) {
33
+ result = new Uri("");
34
+ }
35
+ else {
36
+ result = new Uri((_a = match[2]) !== null && _a !== void 0 ? _a : "", (_b = match[4]) !== null && _b !== void 0 ? _b : "", (_c = match[5]) !== null && _c !== void 0 ? _c : "", (_d = match[7]) !== null && _d !== void 0 ? _d : "", (_e = match[9]) !== null && _e !== void 0 ? _e : "");
37
+ }
38
+ return result;
39
+ }
40
+ static from(components) {
41
+ return new Uri(components.scheme, components.authority, components.path, components.query, components.fragment);
42
+ }
43
+ }
44
+ Uri.regexp = /^(([^:/?#]+?):)?(\/\/([^/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?/;
45
+ const SCHEME_PATTERN = /^\w[\w\d+.-]*$/;
46
+ const SINGLE_SLASH_START = /^\//;
47
+ const DOUBLE_SLASH_START = /^\/\//;
48
+ function validateUri(uri, strict) {
49
+ if (!uri.scheme && strict) {
50
+ throw misuse(`Scheme is missing: {scheme: "", authority: "${uri.authority}", path: "${uri.path}", query: "${uri.query}", fragment: "${uri.fragment}"}`);
51
+ }
52
+ if (uri.scheme && !SCHEME_PATTERN.test(uri.scheme)) {
53
+ throw misuse("Scheme contains illegal characters.");
54
+ }
55
+ if (uri.path) {
56
+ if (uri.authority) {
57
+ if (!SINGLE_SLASH_START.test(uri.path)) {
58
+ throw misuse("If a URI contains an authority component, then the path component must either be empty or begin with a slash character ('/').");
59
+ }
60
+ }
61
+ else {
62
+ if (DOUBLE_SLASH_START.test(uri.path)) {
63
+ throw misuse("If a URI does not contain an authority component, then the path cannot begin with two slash characters ('//').");
64
+ }
65
+ }
66
+ }
67
+ }
@@ -7,6 +7,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
7
7
  step((generator = generator.apply(thisArg, _arguments || [])).next());
8
8
  });
9
9
  };
10
+ import { fatal, misuse } from "./Dbg.js";
10
11
  export class Utils {
11
12
  static freezeSet(obj) {
12
13
  if (obj instanceof Set) {
@@ -37,7 +38,7 @@ export class Utils {
37
38
  }
38
39
  }
39
40
  export function UNDEF(...args) {
40
- throw new Error("this method should never be called");
41
+ throw fatal(new Error("this method should never be called"));
41
42
  }
42
43
  export function all(promises) {
43
44
  return __awaiter(this, void 0, void 0, function* () {
@@ -63,7 +64,7 @@ export function proceedSyncOrAsync(result, success, failure) {
63
64
  }
64
65
  export function emitLetters(n) {
65
66
  if (n < 0)
66
- throw new Error(`emitLetters: argument (${n}) should not be negative or zero`);
67
+ throw misuse(`emitLetters: argument (${n}) should not be negative or zero`);
67
68
  let result = "";
68
69
  while (n >= 0) {
69
70
  const r = n % 26;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "reactronic",
3
- "version": "0.94.25030",
3
+ "version": "0.94.25031",
4
4
  "description": "Reactronic - Transactional Reactive State Management",
5
5
  "publisher": "Nezaboodka Software",
6
6
  "license": "Apache-2.0",