VIEW THIS AS

Auto mode follows the Route Engine until you choose a viewpoint.

YOU ARE HERE

ROUTE CHECK

CONNECTED TO

WHAT NEXT

Use the canonical route for this room, or HELP if you are unsure.

The Gold Standard of Websites | Tracing SuppressedError Chains When Work and Cleanup Both Fail

A cleanup failure should not erase the failure that brought execution to scope exit. DisposeResources carries the incoming completion through reverse cleanup. When another cleanup throws, it places the new failure in error and retains the earlier thrown value in suppressed, producing a nested chain when several cleanup steps fail.

This specialist guide belongs to the Websites root. It also connects to The Gold Standard of Education | Learning That Transfers into Life and the How X Works hub. The worked cases are original teaching examples; their numbers are stipulated so that the reasoning can be checked.

eduKateSG · Websites

Find your next learning step

Trace reverse cleanup after a body failure and reconstruct nested SuppressedError error and suppressed links without losing earlier evidence.

ROUTE 1 · CHAPTERS 1–3

Build the resource model

Identify the registered value, cleanup method, stack state and initiating operation.

ROUTE 2 · CHAPTERS 4–6

Trace normal cleanup

Follow registration, reverse order, receiver binding and returned values in sequence.

ROUTE 3 · CHAPTERS 7–9

Change one condition

Rebuild the trace when ownership, method availability, scope completion or timing changes.

ROUTE 4 · CHAPTERS 10–12

Handle failures and limits

Track abrupt completion, error precedence, repeated requests and bounded claims.

ROUTE 5 · CHAPTERS 13–15

Test and explain

Design decisive fixtures, review code and transfer the reasoning to another resource.

Full chapter contents · Websites subject guide

Chapter contents

Build the resource model · Chapters 1–3

1. Start with the incoming completion

2. Process resources newest first

3. Promote the first cleanup failure after normal work

Trace normal cleanup · Chapters 4–6

4. Combine a cleanup failure with a body failure

5. Nest multiple cleanup failures

6. Read error and suppressed in the correct direction

Change one condition · Chapters 7–9

7. Keep cleanup running after a throw

8. Distinguish explicit constructor use from disposal wrapping

9. Inspect non-enumerable error fields

Handle failures and limits · Chapters 10–12

10. Preserve arbitrary thrown values

11. Trace return and break completions carefully

12. Compare synchronous and asynchronous cleanup chains

Test and explain · Chapters 13–15

13. Catch without losing the chain

14. Design a three-failure fixture

15. Explain precedence without saying errors vanish

CHAPTER 1 OF 15 · Build the resource model

1. Start with the incoming completion

Back to contents

DisposeResources begins with the completion produced by the protected work, which may already be normal or throwing. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. A using scope throws bodyError before cleanup begins; record bodyError as the initial output completion. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Let the body finish normally and compare how the first cleanup failure becomes the output. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Cleanup error precedence cannot be explained without naming the incoming completion. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Next chapter

CHAPTER 2 OF 15 · Build the resource model

2. Process resources newest first

Back to contents

Every cleanup record is still visited in reverse order while the current output completion is carried forward. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Register A then B; B cleanup throws bError before A cleanup is attempted. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Reverse registration and observe which error arrives first. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Error nesting follows cleanup order, not alphabetical resource names or source-line order of catch clauses. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 3 OF 15 · Build the resource model

3. Promote the first cleanup failure after normal work

Back to contents

If work completed normally, the first throwing cleanup replaces that normal completion. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Body returns normally, B throws, A succeeds; the scope throws bError directly. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Make B succeed and A throw so aError becomes the direct result. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. SuppressedError is not required when there is only one thrown completion in the trace. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 4 OF 15 · Trace normal cleanup

4. Combine a cleanup failure with a body failure

Back to contents

When outputCompletion is already throwing and a cleanup also throws, the new cleanup error becomes error and the earlier failure becomes suppressed. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Body throws bodyError and B cleanup throws bError; final value is SuppressedError with error bError and suppressed bodyError. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Make B succeed and bodyError remains the direct thrown value. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. The property names describe precedence, not moral importance. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 5 OF 15 · Trace normal cleanup

5. Nest multiple cleanup failures

Back to contents

Each later processed cleanup failure wraps the current thrown completion in another SuppressedError. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Body throws, B throws, then A throws; outer error is aError and outer suppressed is the B/body chain. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Make A succeed and inspect the shorter one-level chain. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. The chain is nested; it is not specified as an array of peer errors. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 6 OF 15 · Trace normal cleanup

6. Read error and suppressed in the correct direction

Back to contents

For each wrapper, error stores the newly encountered cleanup failure and suppressed stores the completion that was already being carried. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Walk outer.error, outer.suppressed.error and outer.suppressed.suppressed to reconstruct A, B, body. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Reverse cleanup order and rebuild the path from the new event ledger. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Printing only error.message can hide the earlier work failure entirely. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 7 OF 15 · Change one condition

7. Keep cleanup running after a throw

Back to contents

A throwing newer cleanup does not prevent older registered resources from receiving their cleanup calls. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. B throws, A logs success, and the final thrown value still records B. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Make A throw too and observe wrapping rather than skipped cleanup. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Continuation through cleanup is specified, but a process crash or host termination lies outside the fixture. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 8 OF 15 · Change one condition

8. Distinguish explicit constructor use from disposal wrapping

Back to contents

User code can construct SuppressedError directly, while DisposeResources creates instances and defines error and suppressed properties during combination. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Construct one manually and compare observable fields with a disposal-produced wrapper. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Add a message to the manual constructor and note that disposal combination does not supply that message step. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Similar objects do not prove they arose from the same control-flow mechanism. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 9 OF 15 · Change one condition

9. Inspect non-enumerable error fields

Back to contents

The disposal algorithm creates error and suppressed as non-enumerable data properties. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Use Object.keys and direct property access on a produced wrapper; keys omit fields that direct access reveals. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Inspect property descriptors to verify enumerability rather than relying on console formatting. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Developer tools may display non-enumerable fields even when ordinary enumeration skips them. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 10 OF 15 · Handle failures and limits

10. Preserve arbitrary thrown values

Back to contents

JavaScript throw completions can carry values that are not Error objects, and suppression stores those values without normalizing them. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Body throws “body”, B throws 42; inspect error===42 and suppressed===”body”. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Replace both with Error instances and compare stack traces and messages. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Application guidance may prefer Error objects, but the language mechanism does not require them. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 11 OF 15 · Handle failures and limits

11. Trace return and break completions carefully

Back to contents

Abrupt control flow such as return can be replaced by a cleanup throw even though it is not itself an error to suppress. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. A function prepares return 7, then cleanup throws; caller observes the cleanup error rather than 7. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Make cleanup succeed and return 7 reaches the caller. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. SuppressedError wrapping specifically requires two throw completions; other abrupt completions follow their own completion rules. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 12 OF 15 · Handle failures and limits

12. Compare synchronous and asynchronous cleanup chains

Back to contents

Both sync and async disposal use DisposeResources, while async steps await cleanup results before deciding whether they threw. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. An async cleanup rejects after B; older A then rejects and the final chain reflects settlement order under reverse traversal. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Change B to fulfil and inspect the shorter result. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Promise timing does not change reverse record order, though user code inside cleanup can schedule additional work. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 13 OF 15 · Test and explain

13. Catch without losing the chain

Back to contents

A useful handler inspects SuppressedError recursively while preserving unknown thrown values. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Write a small walker that records each error link and the final suppressed value, then rethrow or report according to policy. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Use a handler that logs only the outer message and compare the lost evidence. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. A diagnostic walker should avoid assuming every value has name, message or stack. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 14 OF 15 · Test and explain

14. Design a three-failure fixture

Back to contents

A decisive fixture uses a body error and two cleanup errors with unique identities and a separate call-order log. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Assert B then A calls, outer.error A, nested.error B and deepest suppressed body. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Make exactly one cleanup succeed and predict which wrapper disappears. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Snapshotting a console string is weaker than identity and descriptor assertions. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Next chapter

CHAPTER 15 OF 15 · Test and explain

15. Explain precedence without saying errors vanish

Back to contents

A complete account states the incoming completion, reverse cleanup calls and every wrapper edge. Name the resource value, the cleanup function actually stored, the stack state before the step and the operation that initiates cleanup. That ledger prevents a familiar final log from concealing earlier validation or ownership transfer.

Worked case. Report that bodyError was retained as suppressed, bError wrapped it, and later aError became the outer error. Write the event ledger before predicting the result: registration, method lookup, callback creation, state change, cleanup call, thrown value and caller observation all get separate entries.

Follow the specified order. Identify the first step that selects this branch, then mark which records remain on the stack and which completion is carried forward. The final exception or return value makes sense only after those intermediate facts are visible.

Changed-context check. Changed report: normal body and one failing cleanup produce the cleanup error directly. Rebuild the ledger from the changed premise. Compare registration effects, reverse-order calls, receivers, promise settlement and the state of both old and new stacks wherever the mechanism makes them observable.

Limit and misconception check. Suppression means retained behind a newer failure, not ignored, swallowed or erased. Keep the claim tied to the fixture. A logging object cannot by itself prove behaviour for proxies, host resources, re-entrant cleanup, implementation bugs or APIs whose release methods have undocumented side effects.

For a practical evidence check, instrument every cleanup method or adapter, record this and arguments, expose the disposed getter where relevant and assert the complete ordered log. A test that checks only the last error can pass even when ownership or cleanup order is wrong.

A useful review separates three layers. The resource decides what its cleanup function does; the stack or declaration decides when and in what order to call it; the surrounding code observes normal completion, a thrown value or Promise settlement. Mixing those layers creates false causal stories.

Transfer the chapter into a compact explanation: state the starting state, the decisive algorithm step, the observed result and one caveat. Then change one condition and predict the first point where the new trace diverges. This turns one example into a reusable resource-lifecycle model.

Contents · Previous chapter · Return to Websites

Trace stack registration and reverse cleanup

Trace stack registration and reverse cleanup. Read the root route that groups explicit resource-management specialists.

Compare Promise.finally cleanup failure

Compare Promise.finally cleanup failure. See another mechanism in which cleanup changes the outcome observed by the caller.

Review iterator disposal failure timing

Review iterator disposal failure timing. Contrast one direct cleanup hook with a multi-resource suppression chain.

Frequently asked questions

When is SuppressedError created?

When a cleanup throws while the carried completion is already a throw completion.

Which value is error?

The newly encountered cleanup failure.

Which value is suppressed?

The earlier throw completion already being carried.

Do older resources still clean up after one throws?

Yes. Reverse traversal continues.

Are multiple failures stored in an array?

No. They form nested SuppressedError objects.

Must thrown values be Error objects?

No. JavaScript can throw arbitrary values, and the chain preserves them.

Authoritative sources and further reading

ECMAScript: DisposeResources. Normative reverse cleanup and SuppressedError construction.

ECMAScript: SuppressedError objects. Constructor, prototype and instance properties.

TC39 explicit resource management proposal. Motivation and examples for retaining cleanup failures with earlier failures.

Return to the Websites subject guide, The Gold Standard of Education, or the How X Works hub.