package Ġorg . us first . f rc . team 4 3 2 2 . command v 2 Ċ Ċ import Ġkotlinx . coroutines .* Ċ import Ġkotlinx . coroutines . select s . select ĊĊ Ċ interface ĠElement Ġ{ ĊĠĠĠ Ġoperator Ġfun Ġinvoke ( sc : ĠCor outine Scope Ġ= ĠGlobal Scope ): ĠDeferred < Unit > Ċ } Ċ Ċ class ĠGroup Ġ: ĠCommand Set () Ċ Ċ @ Dsl Marker Ċ annotation Ġclass ĠCommand Marker Ċ Ċ enum Ġclass ĠLocation Ġ{ ĊĠĠĠ ĠChildren , ĊĠĠĠ ĠCommands Ċ } Ċ Ċ /** Ċ Ġ* Ġuses Ġa Ġblock Ġto Ġdetermine Ġwhat Ġcommand Ġto Ġrun . ĠE asi est Ġway Ġto Ġinclude Ġcondition als Ġinto Ġa Ġ[ Group ]. Ċ Ġ*/ Ċ internal Ġclass ĠRouter ( private Ġval Ġblock : Ġ() Ġ-> ĠCommand ) Ġ{ ĊĠĠĠ Ġfun Ġroute (): ĠCommand Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġblock () ĊĠĠĠ Ġ} Ċ } ĊĊ Ċ @ Command Marker Ċ abstract Ġclass ĠCommand Set Ġ: ĠElement Ġ{ ĊĠĠĠ Ġprotected Ġval Ġchildren Ġ= Ġarray ListOf < Element >() ĊĠĠĠ Ġprotected Ġval Ġorder Ġ= Ġarray ListOf < Pair < Location , ĠInt >>() ĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠCreates Ġa Ġblock Ġof Ġcommands Ġthat Ġrun Ġin Ġparallel . ĠThis Ġblock Ġwill Ġrun Ġuntil Ġall Ġit 's Ġmembers Ġterminate . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġparallel ( init : ĠParallel . () Ġ-> ĠUnit ) Ġ= Ġinit Tag ( Parallel (), Ġinit ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠCreates Ġa Ġblock Ġof Ġcommands Ġthat Ġrun Ġse quent ially . ĠThis Ġblock Ġwill Ġrun Ġuntil Ġall Ġit 's Ġmembers Ġterminate . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġsequential ( init : ĠSequential . () Ġ-> ĠUnit ) Ġ= Ġinit Tag ( Sequential (), Ġinit ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠCreates Ġa Ġblock Ġof Ġcommands Ġthat Ġrun Ġin Ġparallel . ĠThis Ġblock Ġwill Ġrun Ġuntil Ġany Ġof Ġit 's Ġmembers Ġterminate . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġfirst ( init : ĠFirst . () Ġ-> ĠUnit ) Ġ= Ġinit Tag ( First (), Ġinit ) ĊĊĠĠĠ Ġprivate Ġfun Ġ< T Ġ: ĠElement > Ġinit Tag ( tag : ĠT , Ġinit : ĠT . () Ġ-> ĠUnit ): ĠT Ġ{ ĊĠĠĠĠĠĠĠ Ġtag . init () ĊĠĠĠĠĠĠĠ Ġchildren . add ( tag ) ĊĠĠĠĠĠĠĠ Ġorder . add ( Pair ( Location . Children , Ġchildren . size Ġ- Ġ 1 )) ĊĠĠĠĠĠĠĠ Ġreturn Ġtag ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoverride Ġoperator Ġfun Ġinvoke ( sc : ĠCor outine Scope ): ĠDeferred < Unit > Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġsc . async ( start Ġ= ĠCor outine Start . LA ZY ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( child Ġin Ġchildren ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġchild ( sc ). await () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} Ċ } Ċ Ċ abstract Ġclass ĠSub Set Ġ: ĠCommand Set () Ġ{ ĊĠĠĠ Ġval Ġcommands Ġ= Ġarray ListOf < Any >() ĊĠĠĠ Ġoperator Ġfun ĠCommand . unary Plus () Ġ{ ĊĠĠĠĠĠĠĠ Ġadd ( this ) ĊĠĠĠĠĠĠĠ Ġthis . parent ed Ġ= Ġtrue ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun Ġrouter ( route : Ġ() Ġ-> ĠCommand ) Ġ{ ĊĠĠĠĠĠĠĠ Ġadd ( Router ( route )) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun Ġlambda ( fn : Ġ() Ġ-> ĠUnit ): ĠCommand Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn ĠCommand . lambda ( fn ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun Ġlambda ( subsystem : ĠSub system , Ġfn : Ġ() Ġ-> ĠUnit ): ĠCommand Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn ĠCommand . lambda ( subsystem , Ġfn ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun ĠwaitFor ( cond : Ġ() Ġ-> ĠBoolean ) Ġ{ ĊĠĠĠĠĠĠĠ Ġadd ( Command . waitFor ( cond )) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġprivate Ġfun Ġadd ( op : ĠAny ) Ġ{ ĊĠĠĠĠĠĠĠ Ġcommands . add ( op ) ĊĠĠĠĠĠĠĠ Ġorder . add ( Pair ( Location . Commands , Ġcommands . size Ġ- Ġ 1 )) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġoperator Ġfun ĠCommand Set . unary Plus () Ġ{ ĊĠĠĠĠĠĠĠ Ġthis @ Sub Set . add ( this ) ĊĠĠĠ Ġ} Ċ } ĊĊ Ċ class ĠFirst Ġ: ĠSub Set () Ġ{ ĊĠĠĠ Ġoverride Ġoperator Ġfun Ġinvoke ( sc : ĠCor outine Scope ): ĠDeferred < Unit > Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġsc . async Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġtasks Ġ= Ġmutable ListOf < Deferred < Unit >>() ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( entry Ġin Ġorder ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( entry . first ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLocation . Commands Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġcommand Ġ= Ġcommands [ entry . second ] ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( command ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġis ĠCommand Ġ-> Ġtasks . add ( command ( sc )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġis ĠRouter Ġ-> Ġtasks . add ( command . route ()( sc )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLocation . Children Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġtasks . add ( children [ entry . second ]( sc )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġfirst Job Ġ= Ġselect < Deferred < Unit >> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġtasks . forEach Ġ{ Ġjob Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġjob . on Await Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġjob ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġtasks . forEach Ġ{ Ġtask Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( task Ġ!= Ġfirst Job ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġtask . cancel () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} Ċ } Ċ Ċ class ĠParallel Ġ: ĠSub Set () Ġ{ ĊĠĠĠ Ġoverride Ġoperator Ġfun Ġinvoke ( sc : ĠCor outine Scope ): ĠDeferred < Unit > Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġsc . async Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġtasks Ġ= Ġmutable ListOf < Deferred < Unit >>() ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( entry Ġin Ġorder ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( entry . first ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLocation . Children Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġtasks . add ( children [ entry . second ]( sc )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLocation . Commands Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġcommand Ġ= Ġcommands [ entry . second ] ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( command ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġis ĠRouter Ġ-> Ġtasks . add ( command . route ()( sc )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġis ĠCommand Ġ-> Ġtasks . add ( command ( sc )) ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġtasks . forEach Ġ{ Ġit . await () Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} Ċ } ĊĊ Ċ class ĠSequential Ġ: ĠSub Set () Ġ{ ĊĠĠĠ Ġoverride Ġoperator Ġfun Ġinvoke ( sc : ĠCor outine Scope ): ĠDeferred < Unit > Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġsc . async Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġfor Ġ( entry Ġin Ġorder ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( entry . first ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLocation . Children Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġchildren [ entry . second ]( sc ). await () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ ĠLocation . Commands Ġ-> Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġval Ġcommand Ġ= Ġcommands [ entry . second ] ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwhen Ġ( command ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġis ĠRouter Ġ-> Ġcommand . route ()( sc ). await () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġis ĠCommand Ġ-> Ġcommand ( sc ). await () ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} Ċ } ĊĊ Ċ /** Ċ Ġ* ĠStarts Ġa ĠCommand Set ĠDSL . ĠIn side Ġthe ĠDSL , Ġcommands Ġmay Ġbe Ġplaced Ġin Ġ[ Command Set . sequential ] Ġand Ġ[ Command Set . parallel ] Ġblocks . Ċ Ġ* ĠCommands Ġare Ġadded Ġto Ġblocks Ġvia Ġputting Ġa Ġplus Ġsymbol Ġahead Ġof Ġtheir Ġdeclaration . Ċ Ġ*/ Ċ fun Ġgroup ( init : ĠGroup . () Ġ-> ĠUnit ): ĠCommand Ġ{ ĊĠĠĠ Ġval Ġset Ġ= ĠGroup () ĊĠĠĠ Ġset . init () ĊĠĠĠ Ġreturn Ġobject Ġ: ĠCommand () Ġ{ ĊĠĠĠĠĠĠĠ Ġoverride Ġoperator Ġfun Ġinvoke ( coroutine Scope : ĠCor outine Scope ): ĠDeferred < Unit > Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġjob Ġ= Ġset () ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn Ġjob !! ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġoverride Ġfun Ġis Finished (): ĠBoolean Ġ= Ġjob !!. is Completed ĊĠĠĠ Ġ} Ċ } Ċ Ċ /** Ċ Ġ* ĠShort cut Ġfor Ġmaking Ġa ĠCommand Set Ġconsisting Ġof Ġsole ly Ġa Ġrouter . Ċ Ġ*/ Ċ fun Ġrouter ( route : Ġ() Ġ-> ĠCommand ): ĠCommand Ġ{ ĊĠĠĠ Ġreturn Ġgroup Ġ{ ĊĠĠĠĠĠĠĠ Ġsequential Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġrouter ( route ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠ Ġ} Ċ }