Nested effects are a way to manage the lifetime of effects created for an imperative instance—not a built-in Angular API or a general solution for copying signal state. In Miha Mulec’s September 30, 2026 article, the nestedEffect helper from @mmstack/primitives/core associates child effects with the current run of a parent effect, so the parent can clean them up when that run is replaced.
How do nested effects work in Angular?
Angular’s effect API does not itself define this nested ownership pattern. Mulec’s nestedEffect helper, also re-exported by @mmstack/primitives, provides it: a child created while a parent’s effect body is running is registered to that parent run. When the parent runs again or is destroyed, the helper disposes of the children belonging to the old run.
That makes the pattern useful when a parent owns an imperative instance and separate child effects synchronize independent values into it. For example, a chart instance might be recreated when its container changes, while child effects update its theme, locale, and data. A data update need not reapply the theme.
The helper models ownership and cleanup; it does not make effects synchronous or eliminate Angular’s effect scheduling. Component effects run as part of Angular synchronization, while root effects run as microtasks and are not connected to the component tree. See Angular’s effect API documentation for the current distinction and injection-context requirements.
Do these 3 things before closing this tab:
1Scan for outdated or missing drivers - takes under a minute2Clear out junk files and repair common Windows errors3Fix the driver behind crashes, sound loss and screen glitches#1 Best Overall
Choose derivation or synchronization first
Before adding an effect, decide whether the value belongs in Angular’s signal state graph or must be sent to something imperative. Angular’s effect guide recommends computed() for derived read-only values and linkedSignal() when derived state also needs to be manually writable. Effects are best reserved for synchronization with APIs outside that graph, such as a chart library, editor, canvas, storage, or logging.
| Need | Prefer | Why |
|---|---|---|
| Read-only value derived from other signals | computed() |
Keeps derivation in the signal graph rather than copying values through a scheduled side effect. |
| Derived value that users or other code can also update | linkedSignal() |
Represents writable derived state directly. |
| Send one signal value to an imperative API | Plain effect() |
A nested lifetime structure may be unnecessary for a single synchronization. |
| Manage an imperative instance with several independently changing inputs | Parent effect plus nested child effects | Separates instance creation and disposal from individual updates. |
Mulec’s concise rule is: “For a single value passed to a library I’d still use a plain effect.” Nesting is for the case where several updates have distinct dependencies and share an instance lifetime.
What a parent rerun means for its children
A parent rerun destroys its old children and creates new ones only if the new execution reaches their creation points. A branch that no longer runs therefore does not leave its former child effect alive. This is a useful lifetime boundary, but it also means the parent’s dependencies should be relatively stable: if a frequently changing signal is read by the parent, every change can tear down and rebuild the instance and its children.
Rank #2
Put stable setup inputs in the parent and read high-frequency update signals in children. For a chart, container identity may belong to the parent; streaming data belongs in a child. For a connection, enabled state and URL may govern the parent lifetime, while outgoing messages belong in a child.
Example: connection and chart lifetimes
Connection with hot message updates
A parent can open a connection while an enabled signal is true and reconnect when its URL changes. A child effect can read outgoing messages and send them through that connection. When the parent reruns because the URL changes—or exits because the connection is disabled—the child must be destroyed before the old connection is closed if its cleanup needs that connection.
Chart with independent settings
A parent can create a chart for a particular container. Child effects can then apply theme, locale, and data changes independently. If the container changes, the parent disposes the descendants and old chart before creating a replacement. Data streaming need only update the chart’s data child rather than reapplying unrelated settings.
Rank #3
Nested lifetimes for editors and mapped items
Editor, model, and language
An editor integration can use an outer effect for the editor instance, a child for the selected text model, and a nested child for that model’s language. Switching models replaces the language effect associated with the old model, while destroying the editor scope cleans up descendants. Text models may be shared, so disposing one editor view should not dispose a model that another editor may use; model ownership belongs to the caller.
Effects inside mapped collections
Lazy mapped collections need deliberate ownership. If a mapped row’s update effect is owned by whichever effect happens to read the mapper, a rerun of that reader can destroy the row effect even though the mapped entry remains. If the mapper does not recreate that stable row, its updates stop. Mulec’s library supports choosing an explicit owner for these effects.
Key entries by identity when a widget should follow an item through reordering; positional mapping instead follows slots. Those are different semantics, so choose based on whether the effect belongs to the item or to its current position.
Rank #4
Pause work without tracking skipped inputs
A pause condition can be read first, followed by an early return while paused. In that execution, the effect tracks the pause signal but not the signals used in the skipped work. When the pause signal changes back, the effect runs again and establishes those dependencies as it proceeds. Angular’s Signals guide explains that dependency tracking is synchronous: reads after an asynchronous boundary such as await are not tracked. Read dependencies before awaiting, and use untracked for incidental reads that should not create dependencies.
Cleanup, scheduling, and scope limits
Dispose dependents before their resources
Cleanup order is a correctness requirement when a child uses a resource created by its parent. Destroy the child effects before closing a connection or disposing a chart instance they may still access. Angular’s effect cleanup callback, onCleanup, runs before the next execution or when the effect is destroyed; the helper’s parent-run cleanup must likewise preserve resource ordering.
The ownership frame is synchronous
The helper’s ownership stack exists during synchronous execution of the effect body. An effect created later from a timer callback is outside that frame and will not automatically become its child. Such creation needs an injector or an established injection context, as Angular’s effect API describes.
What the helper implementation does—and does not—guarantee
The article’s simplified implementation uses a stack of frames containing an injector and child EffectRefs. A nested call uses the current frame’s injector and wraps child construction in untracked, preventing setup reads from accidentally subscribing the parent. Each parent execution gets a fresh frame; its cleanup invokes registered callbacks and destroys its child effects. A top-level call relies on Angular’s injector cleanup, while nested calls use manual disposal because the helper assumes responsibility for their lifetime.
The production package adds effect options, explicit frame ownership, repeated-destroy protection, and guarded cleanup callbacks. Those protections should not be assumed to exist in the simplified sketch. Nor does nesting change Angular’s scheduling model: effects track signal reads dynamically and run at least once, but they are not a synchronous substitute for deriving a value with computed().
For DOM work that must happen after Angular updates the DOM, Angular documents afterRenderEffect as an integration option in its effect guide.
Quick Recap
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.
Quick wins for a faster PC:
Scan for outdated or missing drivers - takes under a minuteDriver Scan →Repair Windows errors before they cause bigger problemsFix Now →Fix the driver behind crashes, sound loss and screen glitchesFind Drivers →




