facebook/lexical · error

Cell not found in table.

Error message

Cell not found in table.

What it means

TableNode.getCordsFromCell (or the method containing this throw) converts a TableCellNode into (x, y) coordinates by scanning the table's rows/cells; when the given cell is not found anywhere in the table it throws 'Cell not found in table.'. This means the caller passed a TableCellNode that is not a descendant of this TableNode, or the table's cached structure is stale.

Source

Thrown at packages/lexical-table/src/LexicalTableNode.ts:722

      if (row == null) {
        continue;
      }

      for (let x = 0; x < row.length; x++) {
        const cell = row[x];
        if (cell == null) {
          continue;
        }
        const {elem} = cell;
        const cellNode = $getNearestTableCellInTableFromDOMNode(this, elem);
        if (cellNode !== null && tableCellNode.is(cellNode)) {
          return {x, y};
        }
      }
    }

    throw new Error('Cell not found in table.');
  }

  getDOMCellFromCords(
    x: number,
    y: number,
    table: TableDOMTable,
  ): null | TableDOMCell {
    const {domRows} = table;

    const row = domRows[y];

    if (row == null) {
      return null;
    }

    const index = x < row.length ? x : row.length - 1;

    const cell = row[index];

View on GitHub (pinned to 76a22dcba9)

Solutions

  1. Confirm the TableCellNode is actually a descendant of this TableNode (walk parents via $isParentElement before the call)
  2. Re-read the cell inside the same update context instead of reusing cached node references
  3. Look up the cell through the selection or DOM cell (getDOMCellFromCords) rather than assuming membership

Example fix

// before
const cell = $getNodeByKey(someKey);
table.getCordsFromCell(cell); // throws if cell not in this table

// after
const cell = $getNodeByKey(someKey);
if ($isTableCellNode(cell) && cell.getParentOrThrow().getParentOrThrow().is(table)) {
  const {x, y} = table.getCordsFromCell(cell);
}
Defensive patterns

Strategy: type-guard

Validate before calling

function isCellInTable(table: TableNode, cell: LexicalNode | null | undefined): boolean {
  let parent = cell?.getParent();
  while (parent) {
    if (parent.is(table)) return true;
    parent = parent.getParent();
  }
  return false;
}
// guard: if (!isCellInTable(table, cellNode)) return;

Type guard

function isTableCellOf(node: LexicalNode | null, table: TableNode): node is TableCellNode {
  return $isTableCellNode(node) && isCellInTable(table, node);
}

Try / catch

try {
  const {x, y} = table.getCordsFromCell(cellNode);
} catch (e) {
  if (String(e).includes('Cell not found in table')) {
    // cell belongs to another/detached table — re-resolve within current update
  } else { throw e; }
}

Prevention

When it happens

Trigger: Calling getCordsFromCell(tableCellNode) on a TableNode while passing a cell that belongs to a different table, a detached cell, or a cell whose parent linkage was mutated mid-update.

Common situations: Selection code iterating cells across table boundaries; custom plugins storing TableCellNode references across update boundaries (stale keys resolve incorrectly); mergeCells/insert operations running transforms that detach the cell before coordinate lookup.

Related errors


AI-assisted analysis of facebook/lexical@76a22dcba9 (2026-08-31). Data as JSON: /api/errors/aadea3d93317b837. Report an issue: GitHub.