handsontable/handsontable · warning
The "data" setting is ignored when "hasExternalDataSource" r
Error message
The "data" setting is ignored when "hasExternalDataSource" returns `true`.
What it means
When a hook/callback named hasExternalDataSource returns true, Handsontable treats data loading as delegated to an external data provider (server-backed), so any static data setting in the same payload cannot be used — it is ignored and this warning tells you why your data array never reached the grid.
Source
Thrown at handsontable/src/core.ts:3625
themeObject = registerTheme(settings.theme);
} else {
themeObject = settings.theme as ThemeBuilder;
}
instance.themeManager!.update(themeObject);
instance.useTheme(instance.themeManager!.getClassName());
}
}
}
const themeOverridesChanged = applyThemeOverrides(settings, init);
// Load data or create data map
if (instance.runHooks('hasExternalDataSource') === true) {
// When dataProvider is a complete server-backed config, ignore static data, the plugin loads rows.
if (settings.data) {
warn('The "data" setting is ignored when "hasExternalDataSource" returns `true`.');
}
// Replace the in-memory placeholder only when the update touches init, `data`, or `dataProvider`. Otherwise
// `updateData([], …)` would empty the grid without a refetch, because DataProvider runs `updatePlugin` only when
// `dataProvider` is present in this payload.
const shouldSyncExternalPlaceholderData = init ||
hasOwnProperty(settings, 'data') ||
hasOwnProperty(settings, 'dataProvider');
if (shouldSyncExternalPlaceholderData) {
dataUpdateFunction([], 'updateSettings');
} else if (settings.columns !== undefined) {
datamap.createMap();
instance.initIndexMappers();
}
} else if (settings.data === undefined && tableMeta.data === undefined) {
dataUpdateFunction(null as unknown as unknown[], 'updateSettings'); // data source created just nowView on GitHub (pinned to 2c365a3291)
Solutions
- Remove the data setting from init/updateSettings/updateData when the external data source is active
- Or return false from (or remove) the hasExternalDataSource hook if you actually want static data
- Keep the static data path and the provider path mutually exclusive in your component logic
Example fix
// before
hot.updateSettings({ data: localRows }); // hook returns true, so ignored
// after
hot.updateData([], { dataProvider }); // or return false from hasExternalDataSource and pass data normally Defensive patterns
Strategy: validation
Validate before calling
const external = hot.runHooks('hasExternalDataSource') === true;
if (external && settings.data) {
delete settings.data; // would be ignored anyway
} Prevention
- Make data and hasExternalDataSource mutually exclusive in your grid factory
- When introducing a data provider, remove the static data prop in the same change
- Log a dev-time assertion when both are present in a settings payload
When it happens
Trigger: Registering a hasExternalDataSource hook returning true (or a DataProvider config that implies it) while also passing data: [...] in init or updateSettings/updateData.
Common situations: Switching a grid from static data to a server-backed data provider but leaving the old data array in the settings object; wrapper components that always pass a data prop while a parent wires up external data loading.
Related errors
- The `colorScheme` and `density` options require the theme en
- The "${themeName}" theme is enabled, but its stylesheets are
- Both `rowHeights` and `minRowHeights` are defined in your co
- Both `theme` and `themeName` are defined in your configurati
- "${focusMode}" is not a valid focus mode.
AI-assisted analysis of handsontable/handsontable@2c365a3291 (2026-09-01).
Data as JSON: /api/errors/f79c515a652e6227.
Report an issue: GitHub.