import Branch from './branch' ; import StackNode from './stack_node' ; export default class Stack { source : StackNode ; constructor ( source ) { this . source = source ; } public branches ( ) { let branches = [ this . source . branch ] ; this . source . children . forEach ( ( c ) => { branches = branches . concat ( new Stack ( c ) . branches ( ) ) ; } ) ; return branches ; } public toPromptChoices ( indent = 0 ) { let choices = [ { title : `${ '  ' . repeat ( indent ) }↳ (${ this . source . branch . name })` , value : this . source . branch . name , } , ] ; this . source . children . forEach ( ( c ) => { choices = choices . concat ( new Stack ( c ) . toPromptChoices ( indent + 1 ) ) ; } ) ; return choices ; } public toString ( ) { const indentMultilineString = ( lines ) => lines . split ( '\n' ) . map ( ( l ) => '  ' + l ) . join ( '\n' ) ; return [ `↳ (${ this . source . branch . name })` ] . concat ( this . source . children . map ( ( c ) => new Stack ( c ) . toString ( ) ) . map ( indentMultilineString ) ) . join ( '\n' ) ; } public toDictionary ( ) { return this . source . toDictionary ( ) ; } public equals ( other ) { return this . base ( ) . equals ( other . base ( ) ) ; } private base ( ) { let base = this . source ; while ( base . parent ) { base = base . parent ; } return base ; } static fromMap ( map ) { if ( Object . keys ( map ) . length != 1 ) { throw Error ( `Map must have only only top level branch name` ) ; } const sourceBranchName = Object . keys ( map ) [ 0 ] as string ; const sourceNode = new StackNode ( { branch : new Branch ( sourceBranchName ) , parent : undefined , children : [ ] , } ) ; sourceNode . children = StackNode . childrenNodesFromMap ( sourceNode , map [ sourceBranchName ] ) ; return new Stack ( sourceNode ) ; } }