Jacob Overgaard 1694e3bad2 Tree: Fix incorrect error notification when deleting last child (closes #20977) (#20985)
* Fix infinite recursion and incorrect error notifications in tree children loading

This commit addresses two critical issues in the tree item children manager:

1. **Infinite recursion vulnerability**: The #resetChildren() method called
   loadChildren(), which could recursively call #resetChildren() again if
   the underlying issue persisted, creating an infinite loop.

2. **Inappropriate error messages**: The "Menu loading failed" notification
   was shown even in legitimate scenarios, such as when deleting the last
   child of a node, where an empty tree is the expected outcome.

Changes made:

- Add ResetReason type ('error' | 'empty' | 'fallback') to differentiate
  between error states and expected empty states

- Extract #loadChildrenWithOffsetPagination() as a terminal fallback method
  that uses only offset pagination and never calls #resetChildren(),
  structurally preventing recursion

- Update #resetChildren() to:
  - Accept a reason parameter to determine whether to show error notification
  - Reset all retry counters (#loadChildrenRetries, #loadPrevItemsRetries,
    #loadNextItemsRetries) to ensure clean state
  - Call #loadChildrenWithOffsetPagination() instead of loadChildren()
  - Only show error notification when reason is 'error'

- Update all call sites of #resetChildren() with appropriate reasons:
  - 'error' when retries are exhausted (actual failures)
  - 'empty' or 'fallback' when no new target is found (may be expected,
    e.g., after deleting items)

The fix makes infinite recursion structurally impossible by creating a
one-way flow: target-based loading can fall back to #resetChildren(),
which calls offset-only loading that never recurses back.

* Fix undefined items array causing tree to break after deletion

This fixes the root cause of issue #20977 where deleting a document type
would cause the tree to "forever load" with a JavaScript error.

The error occurred in #getTargetResultHasValidParents() which called .every()
on data without checking if it was undefined. When the API returned undefined
items (e.g., after deleting the last child), this caused:

TypeError: can't access property "every", e is undefined

The fix adds a guard to check if data is undefined before calling .every(),
returning false in that case to trigger the proper error handling flow.

* Address code review feedback on terminal fallback method

- Change error throwing to silent return for graceful failure handling
- Remove target pagination state updates from offset-only loading method
- Update JSDoc to clarify that method does not throw errors
2025-12-01 20:12:23 +01:00
2025-10-31 11:13:45 +01:00
2025-11-24 12:06:03 +01:00
2024-12-10 10:25:50 +01:00
2022-09-27 14:22:34 +02:00
2024-11-11 13:02:33 +01:00
2025-04-01 11:52:32 +02:00
2025-09-24 23:31:14 +02:00
2025-11-28 10:58:04 +09:00

Umbraco CMS

GitHub license NuGet Version Build status PRs Welcome Forum Chat about Umbraco on Discord Mastodon Follow

Umbraco is a free and open source .NET content management system. Our mission is to help you deliver delightful digital experiences by making Umbraco friendly, simpler and social.

Learn more at umbraco.com

Umbraco Logo

Looking to install Umbraco?

You can get started using the following commands on Windows, Linux and MacOS (after installing the .NET Runtime and SDK):

dotnet new install Umbraco.Templates
dotnet new umbraco --name MyProject
cd MyProject
dotnet run

Documentation

Our comprehensive documentation takes you from the fundamentals on how to start with Umbraco to deploying it to production.

Some important documentation links to get you started:

Get help

If you need a bit of feedback while building your Umbraco projects, we are chatty on Discord. Our Discord server serves as a social space for all Umbracians. If you have any questions or need some help with a problem, head over to our dedicated forum where the Umbraco Community will be happy to help.

Looking to contribute back to Umbraco?

You came to the right place! Our GitHub repository is available for all kinds of contributions:

Umbraco is contribution-focused and community-driven. If you want to contribute back to the Umbraco source code, please check out our guide to contributing.

Tip: You should not run Umbraco from source code found here. Umbraco is extremely extensible and can do whatever you need. Instead, install Umbraco as noted above and then extend it any way you want to.

Description
Umbraco is a free and open source .NET content management system helping you deliver delightful digital experiences.
Readme 448 MiB
Languages
C# 59.5%
TypeScript 39.9%
JavaScript 0.3%
HTML 0.2%