On May 11, 2009, at 12:27 AM, Adam Murdoch wrote:
<snip>
Together with (b) that might simplify the API in a very nice way.
Another thing I'm wondering is, whether onlyIf should follow the
specification pattern (http://en.wikipedia.org/wiki/Specification_pattern
).
Yes. You should be able to call onlyIf() with either a closure or a
Spec<Task>. You should be able to make multiple calls to onlyIf(),
and the task is enabled only if all such predicates are true.
AND looks like a natural operation for this in most of the cases. One
problem with our Spec's at the moment, is that Groovy does not allow
for anonymous inner classes (this is planned for 1.7). You can use
interface coercion to make things works but the syntax is not nice. It
would be nice to have a Groovy Spec builder at some point.
Right now skipping a task means not executing its actions. I think
a nicer solution might be to exclude the task from the DAG. In this
case we might also change the terminology from 'skipping a task' to
'excluding a task'. Excluding would make it easier to follow and
work with the execution of a build. For example when looking at the
console output or when working with the dependency graph.
This works for tasks skipped from the command-line. I'm not sure it
works when tasks need to be skipped because their input and output
artifacts are up to date.
That makes sense.
For the up-to-date case, you can exclude a task from the DAG only
if, at the point in time when it would normally execute, its input
artifacts haven't changed since last time it was run, and its output
artifacts still exist unmodified. The problem is that you can't know
this in a general way when the DAG is assembled. You can know it
sometimes. For example, you know the answer when all the
dependencies of the task are also excluded, or when they declare
that they won't touch the input or output files.
What this mean, in practise, is that every task has to do up-to-date
checking. A task deep in the DAG which does not do any checking
effectively means that nothing will ever be treated as up-to-date.
And so, every task defined in a build file would have to have an
onlyIf predicate which checks that its input and output files are up
to date. Which is really a big step backwards as far as usability
goes: Firstly I have to do the work of declaring all this stuff for
every task (including, somehow, tasks which simply configure the
project in some way), and secondly, it is extremely easy to break
the up to date checking of the build as a whole, by forgetting to do
this for a single task.
So, I think we want a solution which provides some way for a task to
declare that it shouldn't be executed, at 2 different points in time
- when the DAG is being assembled, and when the task is about to be
executed.
Some options:
- Evaluate onlyIf twice: once when the DAG is assembled, and again
just before executing the task. False means 'do not execute' and
true means 'maybe - keep going and I'll let you know later'
- Have 2 different properties, say, skipWhen and excludeWhen (bad
names, I know, but you get the idea)
I think I prefer the second approach as it makes the two different
concepts clearer. And some rules will only make sense for either of
them.
Were we to have a more artifact-centric way of declaring task
dependencies, then Gradle can take care of figuring this stuff out
on behalf of the tasks.
Yep.
- Hans
As an alternative a StopExecutionException would still be available
(no smart skipping, no exclusion from the graph).
Would it makes sense to provide a skipping API also to actions?
I don't think we should. Tasks should be our atomic units of
scheduling. Actions should simply be chunks of code that get
executed as part of a task. If you need to skip some actions and not
others, you can use the if statement, or throw a
StopExecutionException, or split the task up, or implement a custom
task which does this.
Adam
---------------------------------------------------------------------
To unsubscribe from this list, please visit:
http://xircles.codehaus.org/manage_email
--
Hans Dockter
Gradle Project lead
http://www.gradle.org
---------------------------------------------------------------------
To unsubscribe from this list, please visit:
http://xircles.codehaus.org/manage_email