Fix null reference error in Virtualize component#65207
Fix null reference error in Virtualize component#65207
Conversation
When a Virtualize component is rapidly shown/hidden (e.g., in an autocomplete dropdown), the JS interop call to initialize the virtualize observers may arrive after the component has been removed from the DOM. This causes a 'Cannot read properties of null (reading parentElement)' error. This fix adds null checks at three points in Virtualize.ts: 1. Early return in init() if spacerBefore or spacerAfter are null 2. Check spacer.isConnected in mutation observer callback 3. Check spacerBefore.isConnected and spacerAfter.isConnected in intersection callback Fixes #65139
|
This is a Copilot PR that directly prevents the null error reported in the issue. The question is if the spacer reference being null could indicate a deeper problem in logic of the Virtualize component or if it is really due to an otherwise harmless race condition. @ilonatommy @dariatiurina @javiercn I'll appreciate your thoughts since you know the Virtualize component better. |
|
The right thing to do here is to ask it to write a test or to do some validation in a deterministic way. Something like this: "Before you attempt a fix. Write a sample that uses a mutation observer to keep track of the dom changes and logs information to the console. Modify init on virtualize so that it also prints to the console logs. Use some javascript to cause the virtualized list to appear and disappear quickly and then read the console logs to see what is happening" |
I think it is a natural consequence of how rendering works (async rendering and DOM interop overlap). The fix looks good. +1 to ask copilot to make a side branch with test and without the fix. |
Description
When a
Virtualizecomponent is rapidly shown/hidden (e.g., in an autocomplete dropdown), the JS interop call to initialize the virtualize observers may arrive after the component has been removed from the DOM. This causes aCannot read properties of null (reading 'parentElement')error in the browser console.Investigation Summary
The issue occurs in
Virtualize.tswhen:Blazor._internal.Virtualize.init()init()function receives null element references or references to disconnected elementsparentElementon null/disconnected elementsFix
This PR adds null/disconnected element checks at three points in
Virtualize.ts:init(): IfspacerBeforeorspacerAfterare null, return immediately to avoid errorsspacer.isConnectedbefore processing mutationsspacerBefore.isConnectedandspacerAfter.isConnectedbefore processing intersectionsFixes #65139