grafana/grafana · error · Error
Path "${path}" does not point to a row
Error message
Path "${path}" does not point to a row What it means
Thrown by REMOVE_ROW when resolveLayoutPath succeeds but the resolved .item is not a RowItem. The path must point at a row for removal; pointing it at a tab or root fails. Returned as { success: false, error }.
Source
Thrown at public/app/features/dashboard-scene/mutation-api/commands/removeRow.ts:43
payloadSchema: payloads.removeRow,
permission: requiresNewDashboardLayouts,
readOnly: false,
handler: async (payload, context) => {
const { scene } = context;
enterEditModeIfNeeded(scene);
try {
const { path, moveContentTo } = payload;
if (moveContentTo === path) {
throw new Error(`moveContentTo cannot be the same path as the row being removed`);
}
// Resolve the row to remove
const resolved = resolveLayoutPath(scene.state.body, path);
if (!(resolved.item instanceof RowItem)) {
throw new Error(`Path "${path}" does not point to a row`);
}
const { parent, segment } = resolveParentPath(scene.state.body, path);
if (!(parent instanceof RowsLayoutManager)) {
throw new Error(`Parent of "${path}" is not a RowsLayoutManager`);
}
if (moveContentTo) {
const panels = resolved.item.state.layout.getVizPanels();
if (panels.length > 0) {
const targetResolved = resolveLayoutPath(scene.state.body, moveContentTo);
movePanelsToLayout(panels, targetResolved.layoutManager);
}
}
// Remove the row
const currentRows = [...parent.state.rows];
currentRows.splice(segment.index, 1);View on GitHub (pinned to ae3104e369)
Solutions
- Re-fetch the layout via GET_LAYOUT and use a path ending in /rows/<index>.
- If the target is actually a tab, use REMOVE_TAB instead.
- If the target no longer exists, treat removal as already complete.
Example fix
// before: path points at a tab
mutationApi.execute('REMOVE_ROW', { path: '/tabs/0' });
// after: remove the actual tab, or re-target a row
mutationApi.execute('REMOVE_TAB', { path: '/tabs/0' }); Defensive patterns
Strategy: validation
Validate before calling
// Validate path is a row path before REMOVE_ROW
function isRowPath(p) {
return /^\/([a-z]+\/\d+)*\/rows\/\d+$/.test(p);
}
if (!isRowPath(path)) {
throw new Error(`Expected a row path ending in /rows/<index>, got: ${path}`);
} Type guard
null
Try / catch
const res = await mutationApi.execute('REMOVE_ROW', { path, moveContentTo });
if (!res.success && res.error.includes('does not point to a row')) {
if (path.includes('/tabs/')) {
await mutationApi.execute('REMOVE_TAB', { path });
}
} Prevention
- Use GET_LAYOUT to obtain valid row paths.
- Ensure the path's terminal segment is 'rows' for REMOVE_ROW.
- If the target is a tab, use REMOVE_TAB instead.
When it happens
Trigger: Calling REMOVE_ROW with a path resolving to a TabItem (e.g. "/tabs/0") or the root layout. Occurs when row and tab paths are confused or the layout was restructured since the path was obtained.
Common situations: Stale path after an UPDATE_LAYOUT converted rows to tabs; LLM tool used a tab path for a row removal; path assembled with wrong segment type.
Related errors
- Path "${path}" does not point to a row
- Path "${path}" does not point to a tab
- moveContentTo cannot be the same path as the row being remov
- Parent of "${path}" is not a RowsLayoutManager
- Path "${path}" does not point to a tab
AI-assisted analysis of grafana/grafana@ae3104e369 (2026-08-12).
Data as JSON: /api/errors/e9295a158b9ee4da.
Report an issue: GitHub.