rust-lang/rust-analyzer · error

this node should have an ast id

Error message

this node should have an ast id

What it means

While building the AstIdMap, every remaining node in the traversal is expected to have an AST id computable via ErasedFileAstId::ast_id_for. If a node cannot be assigned an id the expect panics with 'this node should have an ast id'. It guards the invariant that the map is total over the file's syntax tree.

Source

Thrown at crates/span/src/ast_id.rs:721

                                            }) && anc.next().is_some_and(|it| {
                                                it.kind() == SyntaxKind::EXPR_STMT
                                                    || it.kind() == SyntaxKind::STMT_LIST
                                            })
                                        }))
                                {
                                    let parent = parent_of(parent_idx, &res);
                                    let block_ast_id =
                                        block_expr_ast_id(last_block_node, &mut index_map, parent)
                                            .expect("not a BlockExpr");
                                    res.arena
                                        .alloc((SyntaxNodePtr::new(last_block_node), block_ast_id));
                                    *already_allocated = ContainsItems::Yes;
                                }

                                let parent = parent_of(parent_idx, &res);
                                let ast_id =
                                    ErasedFileAstId::ast_id_for(&node, &mut index_map, parent)
                                        .expect("this node should have an ast id");
                                let idx = res.arena.alloc((SyntaxNodePtr::new(&node), ast_id));

                                next_layer.extend(node.children().map(|child| (child, Some(idx))));
                                preorder.skip_subtree();
                            }
                        }
                        syntax::WalkEvent::Leave(node) => {
                            if ast::BlockExpr::can_cast(node.kind()) {
                                let block = blocks.pop();
                                debug_assert_eq!(
                                    block.map(|it| it.0),
                                    Some(node),
                                    "left a BlockExpr we never entered"
                                );
                            }
                        }
                    }
                }

View on GitHub (pinned to e8f7e90aa3)

Solutions

  1. Update all rust-analyzer crates together (parser, syntax, span, hir) so node-kind enums match.
  2. If you added a new syntax node kind, extend ErasedFileAstId::ast_id_for to handle it.
  3. Reduce the failing input to a minimal example and file an upstream issue.
  4. Verify no version skew: cargo update / consistent lockfile across the workspace.

Example fix

// before (new node kind missing from ast_id_for)
match node.kind() { ... } // no arm for the new kind
// after
match node.kind() {
    SyntaxKind::MY_NEW_NODE => ...map it...,
    ...
}
Defensive patterns

Strategy: fallback

Try / catch

match ErasedFileAstId::ast_id_for(&node, &mut index_map, parent) {
    Some(id) => ..., // proceed
    None => { /* skip node or report diagnostic instead of panicking */ }
}

Prevention

When it happens

Trigger: from_source encounters a syntax node kind that ast_id_for cannot map — typically after parser changes, new/unknown node kinds from macro expansion, or a hand-constructed tree missing expected structure while processing top-level/item nodes in the arena traversal.

Common situations: rust-analyzer development: adding a new AST node kind without extending ast_id_for; synching the syntax crate versions across crates (span vs parser mismatch); fuzzed inputs producing novel tree shapes.

Related errors


AI-assisted analysis of rust-lang/rust-analyzer@e8f7e90aa3 (2026-09-03). Data as JSON: /api/errors/5641e9b9af5f34e8. Report an issue: GitHub.