How to obtain project directory in init script when using daemon

I have a gradle initialization task (in a script in $GRADLE_HOME/init.d) that runs an exec process in the project directory.

The desired usage scenario from command line is: “cd myproject; gradle build”.

In my original init script, I had code like this:

exec {
workingDir new File(".").absolutePath
commandLine “$myCommand”.split()
standardOutput = stdout
}

It worked fined with 2.4 with disabled daemons, but if enabled, the initialization scripts will pick up the daemon launch directory instead of my project directory.

I can alias the gradle command to pass the launch directory as a system parameter, but this introduces more OS-dependence.

e.g.

to launch:
cd myproject; gradle -Dmydir=$PWD build


The init script code now has:


def myWDir

if ( System.properties[‘myDir’] ) {
myWDir = new File( System.properties[‘myDir’] ).absolutePath
} else {
myWDir = new File(".").absolutePath
}

exec {
workingDir myWDir
commandLine “$myCommand”.split()
standardOutput = stdout
}


Is there a way to accomplish this solely within gradle without the system parameter?

:Bob

You are not defining a task, you are running exec synchronously inside the init script, that’s why the directory is wrong (it’s the daemon’s working directory). You probably wanted to define an exec task in the root project:

rootProject {
  task someTask(type:Exec) {
    //configuration here
  }
  build.dependsOn(someTask)
}

Stefan – Thank you for the very quick reply. Amazing.

Right, I understand why the directory is wrong. Thank you for correcting my use of terms.

This exec should run only once before the configuration phase, so I prefer it runs during init. Also many tasks (in addition to build) depend on the output of this exec. I tried other things but had trouble guaranteeing that it would run before anything else.

I like your suggestion, but is there a way to guarantee that a particular rootProject task will run before any other tasks?

I gather there is no other practical way to pick up the project directory during initialization.

:Bob

If this exec needs to run during the configuration phase for some reason, you still need to do it in the rootProject to get the right directory:

rootProject {
  exec {
  }
}

If the exec is expensive and you’d rather have it run only during task execution, you can make all other tasks depend on it.

rootProject {
    task someTask(type:Exec) {
        //configuration here
    }
    tasks.all { t ->
        if( t != tasks.someTask ) {
            t.dependsOn( tasks.someTask )
        }
    }
}

Thank you for your patience!
I’ll refactor as you have suggested.

Chris -

I was thinking about how to implement this and you have handed it to me. I didn’t expect that! It feels slightly immoral, and may even be illegal in advanced civilizations, but you have saved me time, so thank you!