Summary
We encountered an empty Admin grid where data was successfully fetched by the datasource, but no column headers or rows were rendered. The uiRegistry confirmed the listing and datasource components were registered, but the columns component was missing (undefined). The root cause was a mismatch between the spinner configuration item and the name attribute of the <columns> XML node, combined with a missing or incorrect columns provider dependency in the listing configuration.
Root Cause
The immediate cause of the failure is that the Magento UI component processor cannot resolve the columns component instance because it is not correctly linked to the listing component’s configuration.
Specifically, in the provided XML:
- The
<argument name="data">block defines aspinnerkey with valuerefund_columns. - The
<columns>node defines anameattribute ofrefund_columns. - However, the
listingcomponent expects to find acolumnscomponent registered under a specific path (usuallymarket_refund_listing.market_refund_listing.columns). - Because the
spinnerlogic or thecolumnsprovider dependency is not explicitly defined or pointing to the correct component instance, thecolumnscomponent is never instantiated as a child of thelistingcomponent, resulting inuiRegistryreturningundefinedfor the columns path.
Why This Happens in Real Systems
Magento’s UI components rely on a strict Hierarchical Registry and Dependency Injection system.
- Dependency Resolution: The
listingcomponent (Magento_Ui/js/grid/listing) often initializes its children (like thecolumnscomponent) based on configuration dependencies defined injs_config. - Spinner/Columns Link: The
spinnerargument is used by the grid UI to show loading states. If the value provided tospinnerdoes not map correctly to the instantiated child component tree, the grid logic fails to locate the container for rendering headers and rows. - Asynchronous Loading: While the data source is independent, the structural components (columns) must be resolved synchronously during the RequireJS
defineandinitphases. If a dependency is missing inrequirejs-config.phporui_componentXML, the class definition for the columns is never loaded.
Real-World Impact
- Operational Blocker: Admin users cannot view, sort, filter, or edit data in the grid, effectively breaking backend management for that entity.
- Silent Failure: The page loads without JavaScript errors, making this difficult to debug for junior developers.
- Data Integrity Risk: Users might assume no data exists because the grid is empty, leading to duplicate record creation or missed refunds.
Example or Code
The problem lies in the configuration structure. Below is the corrected XML structure that ensures the columns component is instantiated and linked correctly.
market_refund_listing.market_refund_listing_data_source
market_refund_listing.market_refund_listing_data_source
refund_columns
full
text
asc
text
text
text
dateRange
How Senior Engineers Fix It
Senior engineers approach this by verifying the UI Component Tree and Dependencies:
- Inspect the Registry: Use
require('uiRegistry').get('market_refund_listing')to inspect the instantiated listing object. Check thechildrenproperty to see ifrefund_columnsorcolumnsexists. - Align
nameandspinner: Ensure thespinnerconfiguration item in thelistingargument matches thenameattribute of the<columns>XML node exactly. - Explicit
js_configdeps: If the columns component is not loading, explicitly add a dependency in the listing’s<argument name="data">...<js_config>...<deps>if available, or ensure thecolumnscomponent is defined as a sibling to thedataSourcewithin the<listing>tag. - Check Layout XML: Verify that the
uiComponentname in the Layout XML matches the file name and the rootnameattribute in the UI Component XML.
Why Juniors Miss It
- Focus on Data Source: Juniors often debug the PHP DataProvider endlessly because the data is not rendering, assuming the issue is backend.
- Missing “invisible” Dependencies: They assume that defining
<columns>in XML is sufficient. They miss that thespinnerorjs_configlinking acts as the “glue” that actually instantiates the columns object in the browser. - No Console Errors: Since the file loads and the data request succeeds, the browser console remains clean, providing false confidence that the code is correct.
- Copy-Paste Errors: Often, the
nameattribute in columns is changed (e.g., torefund_columns) but thespinnerargument in the main listing block is left as the defaultcolumnsor mismatched, breaking the link.