* Get the containment hierarchy for a node (ancestors) * * @param nodeId - ID of the node * @returns Array of ancestor nodes from immediate parent to root
(nodeId: string)
| 680 | * @returns Array of ancestor nodes from immediate parent to root |
| 681 | */ |
| 682 | getAncestors(nodeId: string): Node[] { |
| 683 | const ancestors: Node[] = []; |
| 684 | const visited = new Set<string>(); |
| 685 | let currentId = nodeId; |
| 686 | |
| 687 | while (true) { |
| 688 | if (visited.has(currentId)) { |
| 689 | break; |
| 690 | } |
| 691 | visited.add(currentId); |
| 692 | |
| 693 | // Look for 'contains' edges pointing to this node |
| 694 | const containingEdges = this.queries.getIncomingEdges(currentId, ['contains']); |
| 695 | |
| 696 | const firstEdge = containingEdges[0]; |
| 697 | if (!firstEdge) { |
| 698 | break; |
| 699 | } |
| 700 | |
| 701 | // Typically there should be at most one containing parent |
| 702 | const parentNode = this.queries.getNodeById(firstEdge.source); |
| 703 | if (parentNode) { |
| 704 | ancestors.push(parentNode); |
| 705 | currentId = parentNode.id; |
| 706 | } else { |
| 707 | break; |
| 708 | } |
| 709 | } |
| 710 | |
| 711 | return ancestors; |
| 712 | } |
| 713 | |
| 714 | /** |
| 715 | * Get immediate children of a node |
no test coverage detected