Sergey Alaev
Sergey Alaev

Reputation: 3972

How to implement custom watch task in sbt?

I am unsatisfied with ~ ;task1; task2; so I want to implement my very own task that watches for changes and executes tasks. I.e. I need an sbt task that watches for some files and runs some tasks depending on what is changed.

e.g.

val task1: Initialize[Task[Int]] = ....
val task2: Initialize[Task[Int]] = ....

myTask := {
    log.info("Press Enter to stop watching...")
    while(isEnterNotPressedYet) {
        if (someFilesChanged)
            execute(task1) //start task1 and wait for its termination
        else if (someOtherFilesChanged)
            execute(task2)
        Thread.sleep(watchDuration.value)
    }
}

task1.value will not work because it will execute task1 BEFORE the body and only once. dynTask will not work because I want to execute tasks multiple times and without leaving the loop. Precisely, question is how to implement following:

def execute[T](task: Initialize[Task[T]]): T
def isEnterNotPressedYet: Boolean

Background:

I have web application that uses JS, Scala, sbt-revolver. Some resources support hot reloading (but still require compilation!), some does not. I.e. if *.js files change, I want to invoke compileJs task. If .scala files change, I want to invoke re-start task. But sbt watch has only one set of watched resources per project...

Upvotes: 1

Views: 187

Answers (1)

Sergey Alaev
Sergey Alaev

Reputation: 3972

Had to dive into SBT sources and implement it on my own. There are quite a bit workarounds around strange SBT behavior but it works!

https://github.com/scf37/sbt-overwatch

Upvotes: 2

Related Questions