import { Callback , AsyncCallbackFn , CallbackFn , GraphMode , NodeFilterFn , NodeType , PartialConfig , PositionType , TraversalMode } from "./types" ; import { walk , walkAsync , walkAsyncStep , walkStep } from "./walk" ; import { WalkNode } from "./node" ; class CallbacksBuilder < T extends CallbackFn , TUpper extends BaseWalkBuilder < T > > { private readonly callback : Callback < T > ; constructor ( private cbs , private source ) { this . callback = { callback : ( ( ( ) => { } ) as unknown as T ) } ; } withExecutionOrder ( order ) { this . callback . executionOrder = order ; return this ; } withFilter ( fn ) { return this . withFilters ( fn ) ; } withFilters ( ... fn ) { this . callback . filters = fn ; return this ; } filteredByNodeTypes ( ... types ) { this . callback . nodeTypeFilters = types ; return this ; } filteredByKeys ( ... keys ) { this . callback . keyFilters = keys ; return this ; } filteredByPosition ( position ) { this . callback . positionFilter = position ; return this ; } done ( ) { return this . source . withCallbacks ( ... this . cbs . map ( cb => ( { ... this . callback , callback : cb } ) ) ) ; } } abstract class BaseWalkBuilder < T extends CallbackFn > { protected _config : PartialConfig < T > = { } ; private globalFilters : NodeFilterFn [ ] = [ ] ; resetConfig ( ) { this . _config = { } ; return this ; } withConfig ( config ) { this . _config = { ... this . _config , ... config } ; return this ; } withTraversalMode ( traversalMode ) { this . _config . traversalMode = traversalMode ; return this ; } withGraphMode ( graphMode ) { this . _config . graphMode = graphMode ; return this ; } withRootObjectCallbacks ( val ) { this . _config . rootObjectCallbacks = val ; return this ; } withRunningCallbacks ( val ) { this . _config . runCallbacks = val ; return this ; } withConfiguredCallbacks ( ... callbacks ) { return new CallbacksBuilder ( callbacks , this ) ; } withConfiguredCallback ( callback ) { return this . withConfiguredCallbacks ( callback ) ; } withCallback ( callback ) { return this . withCallbacks ( callback ) ; } withGlobalFilter ( fn ) { this . globalFilters . push ( fn ) ; return this ; } withCallbacks ( ... callbacks ) { if ( ! this . _config . callbacks ) this . _config . callbacks = [ ] ; this . _config . callbacks . push ( ... callbacks ) ; return this ; } getCurrentConfig ( ) { return { ... this . _config , callbacks : this . _config . callbacks ?. map ( cb => ( { ... cb , filters : [ ... ( ! cb . filters ? [ ] : Array . isArray ( cb . filters ) ? cb . filters : [ cb . filters ] ) , ... this . globalFilters ] } ) ) } ; } } export class WalkBuilder extends BaseWalkBuilder < CallbackFn > { walk ( target ) { walk ( target , this . getCurrentConfig ( ) ) ; } * walkStep ( target ) { return walkStep ( target , this . getCurrentConfig ( ) ) ; } withSimpleCallback ( callback ) { return this . withSimpleCallbacks ( callback ) ; } withSimpleCallbacks ( ... callbacks ) { return this . withCallbacks ( ... ( callbacks . map ( c => ( { callback : c } ) ) ) ) ; } } export class AsyncWalkBuilder extends BaseWalkBuilder < AsyncCallbackFn > { async walk ( target ) { return walkAsync ( target , this . getCurrentConfig ( ) ) ; } async * walkStep ( target ) { return walkAsyncStep ( target , this . getCurrentConfig ( ) ) ; } withParallelizeAsyncCallbacks ( val ) { this . _config . parallelizeAsyncCallbacks = val ; return this ; } withSimpleCallback ( callback ) { return this . withSimpleCallbacks ( callback ) ; } withSimpleCallbacks ( ... callbacks ) { return this . withCallbacks ( ... ( callbacks . map ( c => ( { callback : c } ) ) ) ) ; } }