unist-utils-core
Version:
A collection of commonly used (albeit enhanced) algorithms based on unist and unist-util-xxx
95 lines (94 loc) • 5.46 kB
TypeScript
import { Node, Parent } from './nodes';
import { Test } from './test';
/**
* Continue traversing as normal.
*/
export declare const CONTINUE = true;
/**
* Do not traverse this node’s children
*/
export declare const SKIP = "skip";
/**
* Stop traversing immediately
*/
export declare const EXIT = false;
/**
* Union of the action types
*/
export type Action = true | false | 'skip';
/**
* Move to the sibling at index next (after node itself is completely traversed).
* Useful if mutating the tree, such as removing the node the visitor is currently on,
* or any of its previous siblings (or next siblings, in case of reverse)
* Results less than 0 or greater than or equal to children.length stop traversing the parent
*/
export type Index = number;
/**
* List with one or two values, the first an action, the second an index.
*/
export type ActionTuple = [Action, Index];
export type VisitorResult = void | Action | Index | ActionTuple;
/**
* Invoked when a node (matching test, if given) is found.
* Visitors are free to transform node. They can also transform the parent of node (the last of ancestors).
* Replacing node itself, if visit.SKIP is not returned, still causes its descendants to be visited.
* If adding or removing previous siblings (or next siblings, in case of reverse) of node, visitor should return a new index (number) to specify the sibling to traverse after node is traversed.
* Adding or removing next siblings of node (or previous siblings, in case of reverse) is handled as expected without needing to return a new index.
* Removing the children property of an ancestor still results in them being traversed.
*
* @param node The active Node
* @param index Index of Node within it's Parent's list of children.
* @param parents Ancestors of node (parent of node will be parents[parents.length-1])
* @param ctx Whatever was originally provided to @see VisitOptions.context
* @returns The return value can have the following forms:
* index (number) — Treated as a tuple of [CONTINUE, index]
* Move to the sibling at index next (after node itself is completely traversed).
* Useful if mutating the tree, such as removing the node the visitor is currently on, or any of its previous siblings (or next siblings, in case of reverse)
* Results less than 0 or greater than or equal to children.length stop traversing the parent
* action (*) — Treated as a tuple of [action]
* CONTINUE: Continue traversing as normal (same behaviour as not returning anything)
* SKIP: Do not traverse this node’s children (continue with the specified index)
* EXIT: Stop traversing immediately
* tuple (Array.<*>) — List with one or two values, the first an action, the second and index.
* Note that passing a tuple only makes sense if the action is SKIP. If the action is EXIT, that action can be returned. If the action is CONTINUE, index can be returned.
*/
export type Visitor<T extends Node, P extends Parent, C extends any = never> = (node: T, index: number, parents: P[], ctx: C) => VisitorResult;
/**
* Options for more control over visitation.
*/
export interface VisitOptions<C extends any = never> {
/**
* When false, the tree is traversed in preorder (NLR), visiting the node itself, then its head, etc.
* When true, the tree is traversed in reverse preorder (NRL): the node itself is visited, then its tail, etc.
* (default: false)
*/
reverse?: boolean;
/**
* When true, the Visitor will be called once for every Node which has children, before those children are visited.
* The Visitor will be invoked as:
* Visitor(undefined, PreTraversalIndex (aka Number.MIN_SAFE_INTEGER), parents);
* NOTE: parents[parents.length-1] will be the Node whose children are about to be visited.
* (default: false)
*/
preTraverse?: boolean;
/**
* When true, the Visitor will be called once for every Node which has children, after those children have been visited.
* The Visitor will be invoked as:
* Visitor(undefined, PostTraversalIndex (aka Number.MAX_SAFE_INTEGER), parents);
* NOTE: parents[parents.length-1] will be the Node whose children have just been visited
* (default: false)
*/
postTraverse?: boolean;
/**
* Caller defined context that will be passed to every invocation of the @see Visitor.
*/
context?: C;
}
export declare const PreTraversalIndex: number;
export declare const PostTraversalIndex: number;
export declare function visitorResultToTuple(value: any): any;
export declare const vistorResultToTuple: typeof visitorResultToTuple;
export declare function visit<T extends Node<any>, P extends Parent<T>, C extends any = never>(tree: T | T[], visitor: Visitor<T, P, C>): any;
export declare function visit<T extends Node<any>, P extends Parent<T>, C extends any = never>(tree: T | T[], visitor: Visitor<T, P, C>, options: boolean | VisitOptions<C>): any;
export declare function visit<T extends Node<any>, P extends Parent<T>, C extends any = never>(tree: T | T[], tst: Test<T>, visitor: Visitor<T, P, C>): any;
export declare function visit<T extends Node<any>, P extends Parent<T>, C extends any = never>(tree: T | T[], tst: Test<T>, visitor: Visitor<T, P, C>, options: boolean | VisitOptions<C>): any;