@cascateer/core 2.1.14 → 2.1.15
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 +1 -1
- package/src/api.ts +37 -48
- package/src/observable/ProxyObservable.ts +9 -1
- package/src/observable/Signal.ts +3 -8
- package/src/observable/index.ts +0 -1
- package/src/terminal.ts +8 -9
- package/src/types.ts +24 -33
- package/src/observable/AsyncObservable.ts +0 -33
package/package.json
CHANGED
package/src/api.ts
CHANGED
|
@@ -5,12 +5,12 @@ import {
|
|
|
5
5
|
isEqual,
|
|
6
6
|
isFunction,
|
|
7
7
|
memoize,
|
|
8
|
+
thru,
|
|
8
9
|
} from "lodash";
|
|
9
10
|
import objectHash from "object-hash";
|
|
10
11
|
import {
|
|
11
12
|
BehaviorSubject,
|
|
12
13
|
combineLatest,
|
|
13
|
-
defer,
|
|
14
14
|
filter,
|
|
15
15
|
finalize,
|
|
16
16
|
lastValueFrom,
|
|
@@ -20,11 +20,12 @@ import {
|
|
|
20
20
|
repeat,
|
|
21
21
|
shareReplay,
|
|
22
22
|
Subject,
|
|
23
|
+
tap,
|
|
23
24
|
UnaryFunction,
|
|
24
25
|
} from "rxjs";
|
|
25
26
|
import { asObservable, ExtendableDictionary, property } from "./lib";
|
|
26
|
-
import {
|
|
27
|
-
import { Action,
|
|
27
|
+
import { ProxyObservable } from "./observable";
|
|
28
|
+
import { Action, MaybeArray, MaybeObservable, ProxyEffect } from "./types";
|
|
28
29
|
|
|
29
30
|
interface TagsConstructor<Args, Result> {
|
|
30
31
|
(args: Args, result: Result): string[];
|
|
@@ -39,7 +40,7 @@ class Memoizable<Args, Result> {
|
|
|
39
40
|
predicate: UnaryFunction<Args, Observable<Result>>;
|
|
40
41
|
tags: TagsConstructor<Args, Result>;
|
|
41
42
|
|
|
42
|
-
subscribe: UnaryFunction<Observable<string[]>,
|
|
43
|
+
subscribe: UnaryFunction<Observable<string[]>, ProxyEffect<Args, Result>>;
|
|
43
44
|
|
|
44
45
|
share: UnaryFunction<NextObserver<string[]>, Action<Args, Result>>;
|
|
45
46
|
|
|
@@ -49,52 +50,40 @@ class Memoizable<Args, Result> {
|
|
|
49
50
|
this.tags = isFunction(tags) ? tags : constant([tags ?? []].flat());
|
|
50
51
|
|
|
51
52
|
this.subscribe = (invalidatedTags) => {
|
|
52
|
-
const memoizedEffect:
|
|
53
|
-
(args) =>
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
),
|
|
78
|
-
invalidatedTags,
|
|
79
|
-
]).pipe(
|
|
80
|
-
filter(([tags, invalidatedTags]) =>
|
|
81
|
-
isEqual(
|
|
82
|
-
tags,
|
|
83
|
-
intersectionWith(tags, invalidatedTags),
|
|
84
|
-
),
|
|
53
|
+
const memoizedEffect: ProxyEffect<Args, Result> = memoize(
|
|
54
|
+
(args) =>
|
|
55
|
+
thru(
|
|
56
|
+
new BehaviorSubject(false),
|
|
57
|
+
(pending) =>
|
|
58
|
+
new ProxyObservable(
|
|
59
|
+
this.predicate(args),
|
|
60
|
+
(source) =>
|
|
61
|
+
source.pipe(
|
|
62
|
+
tap({
|
|
63
|
+
subscribe: () => pending.next(true),
|
|
64
|
+
}),
|
|
65
|
+
finalize(() => pending.next(false)),
|
|
66
|
+
repeat({
|
|
67
|
+
delay: () =>
|
|
68
|
+
combineLatest([
|
|
69
|
+
memoizedEffect(args).pipe(
|
|
70
|
+
map((result) => this.tags(args, result)),
|
|
71
|
+
),
|
|
72
|
+
invalidatedTags,
|
|
73
|
+
]).pipe(
|
|
74
|
+
filter(([tags, invalidatedTags]) =>
|
|
75
|
+
isEqual(
|
|
76
|
+
tags,
|
|
77
|
+
intersectionWith(tags, invalidatedTags),
|
|
85
78
|
),
|
|
86
79
|
),
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
)
|
|
80
|
+
),
|
|
81
|
+
}),
|
|
82
|
+
shareReplay({ bufferSize: 1, refCount: false }),
|
|
90
83
|
),
|
|
91
|
-
|
|
92
|
-
)
|
|
93
|
-
|
|
94
|
-
this.pending = pending;
|
|
95
|
-
}
|
|
96
|
-
})(this.predicate(args), this.tags);
|
|
97
|
-
},
|
|
84
|
+
pending,
|
|
85
|
+
),
|
|
86
|
+
),
|
|
98
87
|
(args) => objectHash(args ?? null),
|
|
99
88
|
);
|
|
100
89
|
|
|
@@ -108,7 +97,7 @@ class Memoizable<Args, Result> {
|
|
|
108
97
|
}
|
|
109
98
|
}
|
|
110
99
|
|
|
111
|
-
export interface ApiEffect<Args, Result> extends
|
|
100
|
+
export interface ApiEffect<Args, Result> extends ProxyEffect<Args, Result> {}
|
|
112
101
|
|
|
113
102
|
type ApiAdapterPropertyConstructor<Source, Type extends "effect" | "action"> = {
|
|
114
103
|
[T in Type]: <Args, Result>(
|
|
@@ -6,9 +6,17 @@ export interface ProxyObservableHandler<T, U> {
|
|
|
6
6
|
}
|
|
7
7
|
|
|
8
8
|
export class ProxyObservable<T, U = T> extends Observable<U> {
|
|
9
|
-
|
|
9
|
+
pending: Observable<boolean>;
|
|
10
|
+
|
|
11
|
+
constructor(
|
|
12
|
+
target: Observable<T>,
|
|
13
|
+
handler: ProxyObservableHandler<T, U>,
|
|
14
|
+
pending: Observable<boolean>,
|
|
15
|
+
) {
|
|
10
16
|
handler = once(handler);
|
|
11
17
|
|
|
12
18
|
super((subscriber) => handler(target).subscribe(subscriber));
|
|
19
|
+
|
|
20
|
+
this.pending = pending;
|
|
13
21
|
}
|
|
14
22
|
}
|
package/src/observable/Signal.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { clone, identity, isEqual, memoize } from "lodash";
|
|
2
2
|
import { distinctUntilChanged, map, Observable, of, UnaryFunction } from "rxjs";
|
|
3
|
-
import {
|
|
3
|
+
import { ProxyObservable } from ".";
|
|
4
4
|
import {
|
|
5
5
|
asEnumerable,
|
|
6
6
|
EnumerableItem,
|
|
@@ -33,12 +33,7 @@ class SignalReflector<T> {
|
|
|
33
33
|
new SignalReflector((transform) => this.predicate(lift(transform)));
|
|
34
34
|
}
|
|
35
35
|
|
|
36
|
-
export class Signal<T>
|
|
37
|
-
extends ProxyObservable<T>
|
|
38
|
-
implements AsyncObservable<T>
|
|
39
|
-
{
|
|
40
|
-
pending = of(false);
|
|
41
|
-
|
|
36
|
+
export class Signal<T> extends ProxyObservable<T> {
|
|
42
37
|
clone(): Signal<T> {
|
|
43
38
|
return this;
|
|
44
39
|
}
|
|
@@ -59,7 +54,7 @@ export class Signal<T>
|
|
|
59
54
|
enumerator?: SignalEnumerator<T>;
|
|
60
55
|
reflector?: SignalReflector<T>;
|
|
61
56
|
}) {
|
|
62
|
-
super(value, identity);
|
|
57
|
+
super(value, identity, of(false));
|
|
63
58
|
|
|
64
59
|
this.enumerator = enumerator;
|
|
65
60
|
this.reflector = reflector;
|
package/src/observable/index.ts
CHANGED
package/src/terminal.ts
CHANGED
|
@@ -6,13 +6,13 @@ import { ComputedSignal } from "./observable";
|
|
|
6
6
|
import { asStoreEffects, StoreAdapter, StoreEffects } from "./store";
|
|
7
7
|
import {
|
|
8
8
|
Action,
|
|
9
|
-
AsyncEffect,
|
|
10
|
-
AsyncEffectInterceptor,
|
|
11
|
-
AsyncEffects,
|
|
12
9
|
Effect,
|
|
10
|
+
ProxyEffect,
|
|
11
|
+
ProxyEffectInterceptor,
|
|
12
|
+
ProxyEffects,
|
|
13
13
|
} from "./types";
|
|
14
14
|
|
|
15
|
-
export interface TerminalEffect<Args, Result> extends
|
|
15
|
+
export interface TerminalEffect<Args, Result> extends ProxyEffect<
|
|
16
16
|
Args,
|
|
17
17
|
Result
|
|
18
18
|
> {}
|
|
@@ -64,10 +64,10 @@ export class ExtendableTerminalAdapter<
|
|
|
64
64
|
effects: StoreEffects<StoreSignals>;
|
|
65
65
|
};
|
|
66
66
|
api: {
|
|
67
|
-
effects:
|
|
67
|
+
effects: ProxyEffects<ApiEffects>;
|
|
68
68
|
};
|
|
69
69
|
terminal: {
|
|
70
|
-
effects:
|
|
70
|
+
effects: ProxyEffects<Effects>;
|
|
71
71
|
};
|
|
72
72
|
},
|
|
73
73
|
Effect<Args, Result>
|
|
@@ -80,7 +80,7 @@ export class ExtendableTerminalAdapter<
|
|
|
80
80
|
return new ExtendableTerminalAdapter(
|
|
81
81
|
this.context,
|
|
82
82
|
this.extendableEffects.extend((currentEffects) => () => {
|
|
83
|
-
const interceptor = new
|
|
83
|
+
const interceptor = new ProxyEffectInterceptor();
|
|
84
84
|
const source = {
|
|
85
85
|
store: {
|
|
86
86
|
effects: asStoreEffects(this.context.store.signals),
|
|
@@ -94,8 +94,7 @@ export class ExtendableTerminalAdapter<
|
|
|
94
94
|
};
|
|
95
95
|
|
|
96
96
|
return effects({
|
|
97
|
-
effect: (constructor) =>
|
|
98
|
-
interceptor.toAsyncEffect(constructor(source)),
|
|
97
|
+
effect: (constructor) => interceptor.proxy(constructor(source)),
|
|
99
98
|
});
|
|
100
99
|
}),
|
|
101
100
|
this.extendableActions,
|
package/src/types.ts
CHANGED
|
@@ -10,7 +10,7 @@ import {
|
|
|
10
10
|
} from "rxjs";
|
|
11
11
|
import { Observable } from "rxjs/internal/Observable";
|
|
12
12
|
import { ObservableInput } from "rxjs/internal/types";
|
|
13
|
-
import {
|
|
13
|
+
import { ProxyObservable } from "./observable";
|
|
14
14
|
import { concat } from "./operators";
|
|
15
15
|
|
|
16
16
|
export interface Effect<Args, Result> extends UnaryFunction<
|
|
@@ -18,59 +18,50 @@ export interface Effect<Args, Result> extends UnaryFunction<
|
|
|
18
18
|
Observable<Result>
|
|
19
19
|
> {}
|
|
20
20
|
|
|
21
|
-
export interface
|
|
21
|
+
export interface ProxyEffect<Args, Result> extends UnaryFunction<
|
|
22
22
|
Args,
|
|
23
|
-
|
|
23
|
+
ProxyObservable<Result>
|
|
24
24
|
> {}
|
|
25
25
|
|
|
26
|
-
export type
|
|
26
|
+
export type ProxyEffects<Effects extends Dictionary<ProxyEffect<any, any>>> = {
|
|
27
27
|
[K in keyof Effects]: ReturnType<
|
|
28
28
|
<
|
|
29
|
-
Args extends Effects[K] extends
|
|
29
|
+
Args extends Effects[K] extends ProxyEffect<infer Args, infer _>
|
|
30
30
|
? Args
|
|
31
31
|
: never,
|
|
32
|
-
Result extends Effects[K] extends
|
|
32
|
+
Result extends Effects[K] extends ProxyEffect<infer _, infer Result>
|
|
33
33
|
? Result
|
|
34
34
|
: never,
|
|
35
|
-
>() =>
|
|
35
|
+
>() => ProxyEffect<Args, Result>
|
|
36
36
|
>;
|
|
37
37
|
};
|
|
38
38
|
|
|
39
|
-
export class
|
|
40
|
-
|
|
39
|
+
export class ProxyEffectInterceptor extends ReplaySubject<
|
|
40
|
+
ProxyObservable<any>
|
|
41
41
|
> {
|
|
42
|
-
intercept<Effects extends Dictionary<
|
|
42
|
+
intercept<Effects extends Dictionary<ProxyEffect<any, any>>>(
|
|
43
43
|
effects: Effects,
|
|
44
|
-
):
|
|
44
|
+
): ProxyEffects<Effects> {
|
|
45
45
|
return mapValues(
|
|
46
46
|
effects,
|
|
47
47
|
(effect) => (args) => tap(effect(args), (source) => this.next(source)),
|
|
48
48
|
);
|
|
49
49
|
}
|
|
50
50
|
|
|
51
|
-
|
|
52
|
-
effect: Effect<Args, Result>,
|
|
53
|
-
): AsyncEffect<Args, Result> {
|
|
51
|
+
proxy<Args, Result>(effect: Effect<Args, Result>): ProxyEffect<Args, Result> {
|
|
54
52
|
return (args) =>
|
|
55
|
-
new (
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
switchMap((sources) =>
|
|
68
|
-
combineLatest(sources.map((source) => source.pending)),
|
|
69
|
-
),
|
|
70
|
-
map((values) => values.some(Boolean)),
|
|
71
|
-
);
|
|
72
|
-
}
|
|
73
|
-
})(this);
|
|
53
|
+
new ProxyObservable(
|
|
54
|
+
effect(args),
|
|
55
|
+
identity,
|
|
56
|
+
this.pipe(
|
|
57
|
+
distinct(),
|
|
58
|
+
concat(),
|
|
59
|
+
switchMap((sources) =>
|
|
60
|
+
combineLatest(sources.map((source) => source.pending)),
|
|
61
|
+
),
|
|
62
|
+
map((values) => values.some(Boolean)),
|
|
63
|
+
),
|
|
64
|
+
);
|
|
74
65
|
}
|
|
75
66
|
}
|
|
76
67
|
|
|
@@ -1,33 +0,0 @@
|
|
|
1
|
-
import { constant } from "lodash";
|
|
2
|
-
import {
|
|
3
|
-
BehaviorSubject,
|
|
4
|
-
defer,
|
|
5
|
-
finalize,
|
|
6
|
-
isObservable,
|
|
7
|
-
Observable,
|
|
8
|
-
UnaryFunction,
|
|
9
|
-
} from "rxjs";
|
|
10
|
-
import { ProxyObservable } from "./ProxyObservable";
|
|
11
|
-
|
|
12
|
-
export interface AsyncObservable<T> {
|
|
13
|
-
pending: Observable<boolean>;
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
export class AsyncObservable<T> extends ProxyObservable<T> {
|
|
17
|
-
constructor(
|
|
18
|
-
source: Observable<T> | UnaryFunction<() => void, Observable<T>>,
|
|
19
|
-
) {
|
|
20
|
-
const pending = new BehaviorSubject(false);
|
|
21
|
-
const complete = () => pending.next(false);
|
|
22
|
-
|
|
23
|
-
if (isObservable(source)) {
|
|
24
|
-
source = constant(source);
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
super(source(complete), (source) =>
|
|
28
|
-
defer(() => (pending.next(true), source)).pipe(finalize(complete)),
|
|
29
|
-
);
|
|
30
|
-
|
|
31
|
-
this.pending = pending;
|
|
32
|
-
}
|
|
33
|
-
}
|