@angular/core 21.0.0-next.0 → 21.0.0-next.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.
- package/fesm2022/_attribute-chunk.mjs +12 -0
- package/fesm2022/_attribute-chunk.mjs.map +1 -0
- package/fesm2022/_debug_node-chunk.mjs +18469 -0
- package/fesm2022/_debug_node-chunk.mjs.map +1 -0
- package/fesm2022/_effect-chunk.mjs +423 -0
- package/fesm2022/_effect-chunk.mjs.map +1 -0
- package/fesm2022/_effect-chunk2.mjs +2951 -0
- package/fesm2022/_effect-chunk2.mjs.map +1 -0
- package/fesm2022/_not_found-chunk.mjs +39 -0
- package/fesm2022/_not_found-chunk.mjs.map +1 -0
- package/fesm2022/_resource-chunk.mjs +378 -0
- package/fesm2022/_resource-chunk.mjs.map +1 -0
- package/fesm2022/_untracked-chunk.mjs +96 -0
- package/fesm2022/_untracked-chunk.mjs.map +1 -0
- package/fesm2022/_weak_ref-chunk.mjs +10 -0
- package/fesm2022/_weak_ref-chunk.mjs.map +1 -0
- package/fesm2022/core.mjs +2499 -4185
- package/fesm2022/core.mjs.map +1 -1
- package/fesm2022/primitives-di.mjs +23 -0
- package/fesm2022/primitives-di.mjs.map +1 -0
- package/fesm2022/primitives-event-dispatch.mjs +788 -0
- package/fesm2022/primitives-event-dispatch.mjs.map +1 -0
- package/fesm2022/primitives-signals.mjs +187 -0
- package/fesm2022/primitives-signals.mjs.map +1 -0
- package/fesm2022/rxjs-interop.mjs +210 -308
- package/fesm2022/rxjs-interop.mjs.map +1 -1
- package/fesm2022/testing.mjs +2309 -3170
- package/fesm2022/testing.mjs.map +1 -1
- package/package.json +18 -12
- package/resources/best-practices.md +56 -0
- package/schematics/bundles/add-bootstrap-context-to-server-main.cjs +117 -0
- package/schematics/bundles/application-config-core.cjs +84 -0
- package/schematics/bundles/{apply_import_manager-DR9xXCle.cjs → apply_import_manager-1Zs_gpB6.cjs} +4 -5
- package/schematics/bundles/bootstrap-options-migration.cjs +598 -0
- package/schematics/bundles/cleanup-unused-imports.cjs +9 -13
- package/schematics/bundles/common-to-standalone-migration.cjs +381 -0
- package/schematics/bundles/{compiler_host-BXBP7CE2.cjs → compiler_host-DBwYMlTo.cjs} +10 -11
- package/schematics/bundles/control-flow-migration.cjs +122 -119
- package/schematics/bundles/{imports-CIX-JgAN.cjs → imports-DP72APSx.cjs} +6 -1
- package/schematics/bundles/{index-CfTQUOiz.cjs → index-B7I9sIUx.cjs} +36 -39
- package/schematics/bundles/inject-migration.cjs +148 -70
- package/schematics/bundles/leading_space-D9nQ8UQC.cjs +1 -1
- package/schematics/bundles/{migrate_ts_type_references-6NtAj-Wk.cjs → migrate_ts_type_references-UGIUl7En.cjs} +500 -24
- package/schematics/bundles/ng_component_template-Dsuq1Lw7.cjs +185 -0
- package/schematics/bundles/{ng_decorators-B5HCqr20.cjs → ng_decorators-DSFlWYQY.cjs} +2 -2
- package/schematics/bundles/ngclass-to-class-migration.cjs +542 -0
- package/schematics/bundles/ngstyle-to-style-migration.cjs +487 -0
- package/schematics/bundles/nodes-B16H9JUd.cjs +1 -1
- package/schematics/bundles/output-migration.cjs +16 -19
- package/schematics/bundles/parse_html-8VLCL37B.cjs +132 -0
- package/schematics/bundles/{project_paths-DcaODbky.cjs → project_paths-DvD50ouC.cjs} +14 -247
- package/schematics/bundles/project_tsconfig_paths-CDVxT6Ov.cjs +90 -0
- package/schematics/bundles/property_name-BBwFuqMe.cjs +1 -1
- package/schematics/bundles/route-lazy-loading.cjs +54 -26
- package/schematics/bundles/router-current-navigation.cjs +7 -18
- package/schematics/bundles/router-last-successful-navigation.cjs +7 -18
- package/schematics/bundles/router-testing-module-migration.cjs +502 -0
- package/schematics/bundles/self-closing-tags-migration.cjs +17 -216
- package/schematics/bundles/signal-input-migration.cjs +93 -29
- package/schematics/bundles/signal-queries-migration.cjs +22 -25
- package/schematics/bundles/signals.cjs +10 -13
- package/schematics/bundles/standalone-migration.cjs +135 -102
- package/schematics/bundles/{symbol-VPWguRxr.cjs → symbol-BObKoqes.cjs} +3 -2
- package/schematics/collection.json +23 -0
- package/schematics/migrations/common-to-standalone-migration/schema.json +14 -0
- package/schematics/migrations/ngclass-to-class-migration/schema.json +20 -0
- package/schematics/migrations/ngstyle-to-style-migration/schema.json +20 -0
- package/schematics/migrations/router-testing-module-migration/schema.json +14 -0
- package/schematics/migrations.json +16 -2
- package/{api.d.d.ts → types/_api-chunk.d.ts} +9 -6
- package/{chrome_dev_tools_performance.d.d.ts → types/_chrome_dev_tools_performance-chunk.d.ts} +26 -31
- package/{discovery.d.d.ts → types/_discovery-chunk.d.ts} +135 -98
- package/{signal.d.d.ts → types/_effect-chunk.d.ts} +14 -5
- package/{event_dispatcher.d.d.ts → types/_event_dispatcher-chunk.d.ts} +2 -2
- package/{graph.d.d.ts → types/_formatter-chunk.d.ts} +40 -7
- package/{weak_ref.d.d.ts → types/_weak_ref-chunk.d.ts} +2 -2
- package/{index.d.ts → types/core.d.ts} +233 -305
- package/{primitives/di/index.d.ts → types/primitives-di.d.ts} +2 -2
- package/{primitives/event-dispatch/index.d.ts → types/primitives-event-dispatch.d.ts} +4 -4
- package/{primitives/signals/index.d.ts → types/primitives-signals.d.ts} +7 -8
- package/{rxjs-interop/index.d.ts → types/rxjs-interop.d.ts} +8 -6
- package/{testing/index.d.ts → types/testing.d.ts} +7 -7
- package/fesm2022/attribute.mjs +0 -24
- package/fesm2022/attribute.mjs.map +0 -1
- package/fesm2022/debug_node.mjs +0 -31833
- package/fesm2022/debug_node.mjs.map +0 -1
- package/fesm2022/not_found.mjs +0 -56
- package/fesm2022/not_found.mjs.map +0 -1
- package/fesm2022/primitives/di.mjs +0 -23
- package/fesm2022/primitives/di.mjs.map +0 -1
- package/fesm2022/primitives/event-dispatch.mjs +0 -1622
- package/fesm2022/primitives/event-dispatch.mjs.map +0 -1
- package/fesm2022/primitives/signals.mjs +0 -89
- package/fesm2022/primitives/signals.mjs.map +0 -1
- package/fesm2022/resource.mjs +0 -633
- package/fesm2022/resource.mjs.map +0 -1
- package/fesm2022/root_effect_scheduler.mjs +0 -4007
- package/fesm2022/root_effect_scheduler.mjs.map +0 -1
- package/fesm2022/signal.mjs +0 -560
- package/fesm2022/signal.mjs.map +0 -1
- package/fesm2022/untracked.mjs +0 -117
- package/fesm2022/untracked.mjs.map +0 -1
- package/fesm2022/weak_ref.mjs +0 -12
- package/fesm2022/weak_ref.mjs.map +0 -1
- package/schematics/bundles/index-esqfDjNB.cjs +0 -22074
- package/schematics/bundles/project_tsconfig_paths-CS-eSeHC.cjs +0 -51062
|
@@ -1,349 +1,251 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* @license Angular v21.0.0-next.
|
|
3
|
-
* (c) 2010-2025 Google LLC. https://angular.
|
|
2
|
+
* @license Angular v21.0.0-next.10
|
|
3
|
+
* (c) 2010-2025 Google LLC. https://angular.dev/
|
|
4
4
|
* License: MIT
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
7
|
import { Observable, ReplaySubject } from 'rxjs';
|
|
8
8
|
import { takeUntil } from 'rxjs/operators';
|
|
9
|
-
import { assertInInjectionContext, inject, DestroyRef, RuntimeError, Injector, assertNotInReactiveContext, signal, PendingTasks } from './
|
|
10
|
-
import { getOutputDestroyRef,
|
|
11
|
-
import './
|
|
12
|
-
import './
|
|
9
|
+
import { assertInInjectionContext, inject, DestroyRef, RuntimeError, Injector, effect, assertNotInReactiveContext, signal, PendingTasks } from './_effect-chunk2.mjs';
|
|
10
|
+
import { getOutputDestroyRef, untracked, computed, resource, encapsulateResourceError } from './_resource-chunk.mjs';
|
|
11
|
+
import './_effect-chunk.mjs';
|
|
12
|
+
import './_not_found-chunk.mjs';
|
|
13
13
|
import '@angular/core/primitives/signals';
|
|
14
14
|
import '@angular/core/primitives/di';
|
|
15
|
-
import './
|
|
15
|
+
import './_untracked-chunk.mjs';
|
|
16
16
|
|
|
17
|
-
/**
|
|
18
|
-
* Operator which completes the Observable when the calling context (component, directive, service,
|
|
19
|
-
* etc) is destroyed.
|
|
20
|
-
*
|
|
21
|
-
* @param destroyRef optionally, the `DestroyRef` representing the current context. This can be
|
|
22
|
-
* passed explicitly to use `takeUntilDestroyed` outside of an [injection
|
|
23
|
-
* context](guide/di/dependency-injection-context). Otherwise, the current `DestroyRef` is injected.
|
|
24
|
-
*
|
|
25
|
-
* @publicApi 19.0
|
|
26
|
-
*/
|
|
27
17
|
function takeUntilDestroyed(destroyRef) {
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
18
|
+
if (!destroyRef) {
|
|
19
|
+
ngDevMode && assertInInjectionContext(takeUntilDestroyed);
|
|
20
|
+
destroyRef = inject(DestroyRef);
|
|
21
|
+
}
|
|
22
|
+
const destroyed$ = new Observable(subscriber => {
|
|
23
|
+
if (destroyRef.destroyed) {
|
|
24
|
+
subscriber.next();
|
|
25
|
+
return;
|
|
31
26
|
}
|
|
32
|
-
const
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
return unregisterFn;
|
|
39
|
-
});
|
|
40
|
-
return (source) => {
|
|
41
|
-
return source.pipe(takeUntil(destroyed$));
|
|
42
|
-
};
|
|
27
|
+
const unregisterFn = destroyRef.onDestroy(subscriber.next.bind(subscriber));
|
|
28
|
+
return unregisterFn;
|
|
29
|
+
});
|
|
30
|
+
return source => {
|
|
31
|
+
return source.pipe(takeUntil(destroyed$));
|
|
32
|
+
};
|
|
43
33
|
}
|
|
44
34
|
|
|
45
|
-
/**
|
|
46
|
-
* Implementation of `OutputRef` that emits values from
|
|
47
|
-
* an RxJS observable source.
|
|
48
|
-
*
|
|
49
|
-
* @internal
|
|
50
|
-
*/
|
|
51
35
|
class OutputFromObservableRef {
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
'Unexpected subscription to destroyed `OutputRef`. ' +
|
|
65
|
-
'The owning directive/component is destroyed.');
|
|
66
|
-
}
|
|
67
|
-
// Stop yielding more values when the directive/component is already destroyed.
|
|
68
|
-
const subscription = this.source.pipe(takeUntilDestroyed(this.destroyRef)).subscribe({
|
|
69
|
-
next: (value) => callbackFn(value),
|
|
70
|
-
});
|
|
71
|
-
return {
|
|
72
|
-
unsubscribe: () => subscription.unsubscribe(),
|
|
73
|
-
};
|
|
36
|
+
source;
|
|
37
|
+
destroyed = false;
|
|
38
|
+
destroyRef = inject(DestroyRef);
|
|
39
|
+
constructor(source) {
|
|
40
|
+
this.source = source;
|
|
41
|
+
this.destroyRef.onDestroy(() => {
|
|
42
|
+
this.destroyed = true;
|
|
43
|
+
});
|
|
44
|
+
}
|
|
45
|
+
subscribe(callbackFn) {
|
|
46
|
+
if (this.destroyed) {
|
|
47
|
+
throw new RuntimeError(953, ngDevMode && 'Unexpected subscription to destroyed `OutputRef`. ' + 'The owning directive/component is destroyed.');
|
|
74
48
|
}
|
|
49
|
+
const subscription = this.source.pipe(takeUntilDestroyed(this.destroyRef)).subscribe({
|
|
50
|
+
next: value => callbackFn(value)
|
|
51
|
+
});
|
|
52
|
+
return {
|
|
53
|
+
unsubscribe: () => subscription.unsubscribe()
|
|
54
|
+
};
|
|
55
|
+
}
|
|
75
56
|
}
|
|
76
|
-
/**
|
|
77
|
-
* Declares an Angular output that is using an RxJS observable as a source
|
|
78
|
-
* for events dispatched to parent subscribers.
|
|
79
|
-
*
|
|
80
|
-
* The behavior for an observable as source is defined as followed:
|
|
81
|
-
* 1. New values are forwarded to the Angular output (next notifications).
|
|
82
|
-
* 2. Errors notifications are not handled by Angular. You need to handle these manually.
|
|
83
|
-
* For example by using `catchError`.
|
|
84
|
-
* 3. Completion notifications stop the output from emitting new values.
|
|
85
|
-
*
|
|
86
|
-
* @usageNotes
|
|
87
|
-
* Initialize an output in your directive by declaring a
|
|
88
|
-
* class field and initializing it with the `outputFromObservable()` function.
|
|
89
|
-
*
|
|
90
|
-
* ```ts
|
|
91
|
-
* @Directive({..})
|
|
92
|
-
* export class MyDir {
|
|
93
|
-
* nameChange$ = <some-observable>;
|
|
94
|
-
* nameChange = outputFromObservable(this.nameChange$);
|
|
95
|
-
* }
|
|
96
|
-
* ```
|
|
97
|
-
*
|
|
98
|
-
* @publicApi 19.0
|
|
99
|
-
*/
|
|
100
57
|
function outputFromObservable(observable, opts) {
|
|
101
|
-
|
|
102
|
-
|
|
58
|
+
ngDevMode && assertInInjectionContext(outputFromObservable);
|
|
59
|
+
return new OutputFromObservableRef(observable);
|
|
103
60
|
}
|
|
104
61
|
|
|
105
|
-
/**
|
|
106
|
-
* Converts an Angular output declared via `output()` or `outputFromObservable()`
|
|
107
|
-
* to an observable.
|
|
108
|
-
*
|
|
109
|
-
* You can subscribe to the output via `Observable.subscribe` then.
|
|
110
|
-
*
|
|
111
|
-
* @publicApi 19.0
|
|
112
|
-
*/
|
|
113
62
|
function outputToObservable(ref) {
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
unregisterOnDestroy?.();
|
|
124
|
-
};
|
|
125
|
-
});
|
|
63
|
+
const destroyRef = getOutputDestroyRef(ref);
|
|
64
|
+
return new Observable(observer => {
|
|
65
|
+
const unregisterOnDestroy = destroyRef?.onDestroy(() => observer.complete());
|
|
66
|
+
const subscription = ref.subscribe(v => observer.next(v));
|
|
67
|
+
return () => {
|
|
68
|
+
subscription.unsubscribe();
|
|
69
|
+
unregisterOnDestroy?.();
|
|
70
|
+
};
|
|
71
|
+
});
|
|
126
72
|
}
|
|
127
73
|
|
|
128
|
-
/**
|
|
129
|
-
* Exposes the value of an Angular `Signal` as an RxJS `Observable`.
|
|
130
|
-
*
|
|
131
|
-
* The signal's value will be propagated into the `Observable`'s subscribers using an `effect`.
|
|
132
|
-
*
|
|
133
|
-
* `toObservable` must be called in an injection context unless an injector is provided via options.
|
|
134
|
-
*
|
|
135
|
-
* @publicApi 20.0
|
|
136
|
-
*/
|
|
137
74
|
function toObservable(source, options) {
|
|
138
|
-
|
|
139
|
-
|
|
75
|
+
if (ngDevMode && !options?.injector) {
|
|
76
|
+
assertInInjectionContext(toObservable);
|
|
77
|
+
}
|
|
78
|
+
const injector = options?.injector ?? inject(Injector);
|
|
79
|
+
const subject = new ReplaySubject(1);
|
|
80
|
+
const watcher = effect(() => {
|
|
81
|
+
let value;
|
|
82
|
+
try {
|
|
83
|
+
value = source();
|
|
84
|
+
} catch (err) {
|
|
85
|
+
untracked(() => subject.error(err));
|
|
86
|
+
return;
|
|
140
87
|
}
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
}
|
|
152
|
-
untracked(() => subject.next(value));
|
|
153
|
-
}, { injector, manualCleanup: true });
|
|
154
|
-
injector.get(DestroyRef).onDestroy(() => {
|
|
155
|
-
watcher.destroy();
|
|
156
|
-
subject.complete();
|
|
157
|
-
});
|
|
158
|
-
return subject.asObservable();
|
|
88
|
+
untracked(() => subject.next(value));
|
|
89
|
+
}, {
|
|
90
|
+
injector,
|
|
91
|
+
manualCleanup: true
|
|
92
|
+
});
|
|
93
|
+
injector.get(DestroyRef).onDestroy(() => {
|
|
94
|
+
watcher.destroy();
|
|
95
|
+
subject.complete();
|
|
96
|
+
});
|
|
97
|
+
return subject.asObservable();
|
|
159
98
|
}
|
|
160
99
|
|
|
161
|
-
/**
|
|
162
|
-
* Get the current value of an `Observable` as a reactive `Signal`.
|
|
163
|
-
*
|
|
164
|
-
* `toSignal` returns a `Signal` which provides synchronous reactive access to values produced
|
|
165
|
-
* by the given `Observable`, by subscribing to that `Observable`. The returned `Signal` will always
|
|
166
|
-
* have the most recent value emitted by the subscription, and will throw an error if the
|
|
167
|
-
* `Observable` errors.
|
|
168
|
-
*
|
|
169
|
-
* With `requireSync` set to `true`, `toSignal` will assert that the `Observable` produces a value
|
|
170
|
-
* immediately upon subscription. No `initialValue` is needed in this case, and the returned signal
|
|
171
|
-
* does not include an `undefined` type.
|
|
172
|
-
*
|
|
173
|
-
* By default, the subscription will be automatically cleaned up when the current [injection
|
|
174
|
-
* context](guide/di/dependency-injection-context) is destroyed. For example, when `toSignal` is
|
|
175
|
-
* called during the construction of a component, the subscription will be cleaned up when the
|
|
176
|
-
* component is destroyed. If an injection context is not available, an explicit `Injector` can be
|
|
177
|
-
* passed instead.
|
|
178
|
-
*
|
|
179
|
-
* If the subscription should persist until the `Observable` itself completes, the `manualCleanup`
|
|
180
|
-
* option can be specified instead, which disables the automatic subscription teardown. No injection
|
|
181
|
-
* context is needed in this configuration as well.
|
|
182
|
-
*/
|
|
183
100
|
function toSignal(source, options) {
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
}
|
|
203
|
-
|
|
204
|
-
// If an initial value was passed, use it. Otherwise, use `undefined` as the initial value.
|
|
205
|
-
state = signal({ kind: 1 /* StateKind.Value */, value: options?.initialValue }, { equal });
|
|
206
|
-
}
|
|
207
|
-
let destroyUnregisterFn;
|
|
208
|
-
// Note: This code cannot run inside a reactive context (see assertion above). If we'd support
|
|
209
|
-
// this, we would subscribe to the observable outside of the current reactive context, avoiding
|
|
210
|
-
// that side-effect signal reads/writes are attribute to the current consumer. The current
|
|
211
|
-
// consumer only needs to be notified when the `state` signal changes through the observable
|
|
212
|
-
// subscription. Additional context (related to async pipe):
|
|
213
|
-
// https://github.com/angular/angular/pull/50522.
|
|
214
|
-
const sub = source.subscribe({
|
|
215
|
-
next: (value) => state.set({ kind: 1 /* StateKind.Value */, value }),
|
|
216
|
-
error: (error) => {
|
|
217
|
-
state.set({ kind: 2 /* StateKind.Error */, error });
|
|
218
|
-
destroyUnregisterFn?.();
|
|
219
|
-
},
|
|
220
|
-
complete: () => {
|
|
221
|
-
destroyUnregisterFn?.();
|
|
222
|
-
},
|
|
223
|
-
// Completion of the Observable is meaningless to the signal. Signals don't have a concept of
|
|
224
|
-
// "complete".
|
|
101
|
+
typeof ngDevMode !== 'undefined' && ngDevMode && assertNotInReactiveContext(toSignal, 'Invoking `toSignal` causes new subscriptions every time. ' + 'Consider moving `toSignal` outside of the reactive context and read the signal value where needed.');
|
|
102
|
+
const requiresCleanup = !options?.manualCleanup;
|
|
103
|
+
if (ngDevMode && requiresCleanup && !options?.injector) {
|
|
104
|
+
assertInInjectionContext(toSignal);
|
|
105
|
+
}
|
|
106
|
+
const cleanupRef = requiresCleanup ? options?.injector?.get(DestroyRef) ?? inject(DestroyRef) : null;
|
|
107
|
+
const equal = makeToSignalEqual(options?.equal);
|
|
108
|
+
let state;
|
|
109
|
+
if (options?.requireSync) {
|
|
110
|
+
state = signal({
|
|
111
|
+
kind: 0
|
|
112
|
+
}, {
|
|
113
|
+
equal
|
|
114
|
+
});
|
|
115
|
+
} else {
|
|
116
|
+
state = signal({
|
|
117
|
+
kind: 1,
|
|
118
|
+
value: options?.initialValue
|
|
119
|
+
}, {
|
|
120
|
+
equal
|
|
225
121
|
});
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
122
|
+
}
|
|
123
|
+
let destroyUnregisterFn;
|
|
124
|
+
const sub = source.subscribe({
|
|
125
|
+
next: value => state.set({
|
|
126
|
+
kind: 1,
|
|
127
|
+
value
|
|
128
|
+
}),
|
|
129
|
+
error: error => {
|
|
130
|
+
state.set({
|
|
131
|
+
kind: 2,
|
|
132
|
+
error
|
|
133
|
+
});
|
|
134
|
+
destroyUnregisterFn?.();
|
|
135
|
+
},
|
|
136
|
+
complete: () => {
|
|
137
|
+
destroyUnregisterFn?.();
|
|
229
138
|
}
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
139
|
+
});
|
|
140
|
+
if (options?.requireSync && state().kind === 0) {
|
|
141
|
+
throw new RuntimeError(601, (typeof ngDevMode === 'undefined' || ngDevMode) && '`toSignal()` called with `requireSync` but `Observable` did not emit synchronously.');
|
|
142
|
+
}
|
|
143
|
+
destroyUnregisterFn = cleanupRef?.onDestroy(sub.unsubscribe.bind(sub));
|
|
144
|
+
return computed(() => {
|
|
145
|
+
const current = state();
|
|
146
|
+
switch (current.kind) {
|
|
147
|
+
case 1:
|
|
148
|
+
return current.value;
|
|
149
|
+
case 2:
|
|
150
|
+
throw current.error;
|
|
151
|
+
case 0:
|
|
152
|
+
throw new RuntimeError(601, (typeof ngDevMode === 'undefined' || ngDevMode) && '`toSignal()` called with `requireSync` but `Observable` did not emit synchronously.');
|
|
153
|
+
}
|
|
154
|
+
}, {
|
|
155
|
+
equal: options?.equal
|
|
156
|
+
});
|
|
247
157
|
}
|
|
248
158
|
function makeToSignalEqual(userEquality = Object.is) {
|
|
249
|
-
|
|
159
|
+
return (a, b) => a.kind === 1 && b.kind === 1 && userEquality(a.value, b.value);
|
|
250
160
|
}
|
|
251
161
|
|
|
252
|
-
/**
|
|
253
|
-
* Operator which makes the application unstable until the observable emits, completes, errors, or is unsubscribed.
|
|
254
|
-
*
|
|
255
|
-
* Use this operator in observables whose subscriptions are important for rendering and should be included in SSR serialization.
|
|
256
|
-
*
|
|
257
|
-
* @param injector The `Injector` to use during creation. If this is not provided, the current injection context will be used instead (via `inject`).
|
|
258
|
-
*
|
|
259
|
-
* @developerPreview 20.0
|
|
260
|
-
*/
|
|
261
162
|
function pendingUntilEvent(injector) {
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
};
|
|
163
|
+
if (injector === undefined) {
|
|
164
|
+
ngDevMode && assertInInjectionContext(pendingUntilEvent);
|
|
165
|
+
injector = inject(Injector);
|
|
166
|
+
}
|
|
167
|
+
const taskService = injector.get(PendingTasks);
|
|
168
|
+
return sourceObservable => {
|
|
169
|
+
return new Observable(originalSubscriber => {
|
|
170
|
+
const removeTask = taskService.add();
|
|
171
|
+
let cleanedUp = false;
|
|
172
|
+
function cleanupTask() {
|
|
173
|
+
if (cleanedUp) {
|
|
174
|
+
return;
|
|
175
|
+
}
|
|
176
|
+
removeTask();
|
|
177
|
+
cleanedUp = true;
|
|
178
|
+
}
|
|
179
|
+
const innerSubscription = sourceObservable.subscribe({
|
|
180
|
+
next: v => {
|
|
181
|
+
originalSubscriber.next(v);
|
|
182
|
+
cleanupTask();
|
|
183
|
+
},
|
|
184
|
+
complete: () => {
|
|
185
|
+
originalSubscriber.complete();
|
|
186
|
+
cleanupTask();
|
|
187
|
+
},
|
|
188
|
+
error: e => {
|
|
189
|
+
originalSubscriber.error(e);
|
|
190
|
+
cleanupTask();
|
|
191
|
+
}
|
|
192
|
+
});
|
|
193
|
+
innerSubscription.add(() => {
|
|
194
|
+
originalSubscriber.unsubscribe();
|
|
195
|
+
cleanupTask();
|
|
196
|
+
});
|
|
197
|
+
return innerSubscription;
|
|
198
|
+
});
|
|
199
|
+
};
|
|
300
200
|
}
|
|
301
201
|
|
|
302
202
|
function rxResource(opts) {
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
if (resolve) {
|
|
337
|
-
send({
|
|
338
|
-
error: new RuntimeError(991 /* ɵRuntimeErrorCode.RESOURCE_COMPLETED_BEFORE_PRODUCING_VALUE */, ngDevMode && 'Resource completed before producing a value'),
|
|
339
|
-
});
|
|
340
|
-
}
|
|
341
|
-
params.abortSignal.removeEventListener('abort', onAbort);
|
|
342
|
-
},
|
|
343
|
-
});
|
|
344
|
-
return promise;
|
|
203
|
+
if (ngDevMode && !opts?.injector) {
|
|
204
|
+
assertInInjectionContext(rxResource);
|
|
205
|
+
}
|
|
206
|
+
return resource({
|
|
207
|
+
...opts,
|
|
208
|
+
loader: undefined,
|
|
209
|
+
stream: params => {
|
|
210
|
+
let sub;
|
|
211
|
+
const onAbort = () => sub?.unsubscribe();
|
|
212
|
+
params.abortSignal.addEventListener('abort', onAbort);
|
|
213
|
+
const stream = signal({
|
|
214
|
+
value: undefined
|
|
215
|
+
});
|
|
216
|
+
let resolve;
|
|
217
|
+
const promise = new Promise(r => resolve = r);
|
|
218
|
+
function send(value) {
|
|
219
|
+
stream.set(value);
|
|
220
|
+
resolve?.(stream);
|
|
221
|
+
resolve = undefined;
|
|
222
|
+
}
|
|
223
|
+
const streamFn = opts.stream ?? opts.loader;
|
|
224
|
+
if (streamFn === undefined) {
|
|
225
|
+
throw new RuntimeError(990, ngDevMode && `Must provide \`stream\` option.`);
|
|
226
|
+
}
|
|
227
|
+
sub = streamFn(params).subscribe({
|
|
228
|
+
next: value => send({
|
|
229
|
+
value
|
|
230
|
+
}),
|
|
231
|
+
error: error => {
|
|
232
|
+
send({
|
|
233
|
+
error: encapsulateResourceError(error)
|
|
234
|
+
});
|
|
235
|
+
params.abortSignal.removeEventListener('abort', onAbort);
|
|
345
236
|
},
|
|
346
|
-
|
|
237
|
+
complete: () => {
|
|
238
|
+
if (resolve) {
|
|
239
|
+
send({
|
|
240
|
+
error: new RuntimeError(991, ngDevMode && 'Resource completed before producing a value')
|
|
241
|
+
});
|
|
242
|
+
}
|
|
243
|
+
params.abortSignal.removeEventListener('abort', onAbort);
|
|
244
|
+
}
|
|
245
|
+
});
|
|
246
|
+
return promise;
|
|
247
|
+
}
|
|
248
|
+
});
|
|
347
249
|
}
|
|
348
250
|
|
|
349
251
|
export { outputFromObservable, outputToObservable, pendingUntilEvent, rxResource, takeUntilDestroyed, toObservable, toSignal };
|