Quick Overview
Sometimes the :finish, qualifier (or its :finish-all & :finish-any counterparts for families) were used erroneously in Cylc 7 workflows where :succeed (or its :succeed-all & :succeed-any counterparts) would have been more appropriate.
This may cause validation failures when you try to upgrade to Cylc 8, similar to this one like this:
GraphParseError: Output foo:succeed can't be both required and optional
If you encounter errors like this where :finish triggers are present, consider whether you want to permit the task to fail and allow the workflow to move on to the next task.
If you don’t, then :finish was probably a mistake, switch it for :succeeded and the error will go away.
Otherwise have a look at the graph branching section of the migration guide for upgrade advice.
Full Explanation
:succeeded vs :finished
In Cylc graphs, if you don’t specify a qualifier, Cylc assumes you mean :succeed.
For example this:
foo => bar
Is shorthand for this:
foo:succeed => bar
There is a special qualifier called :finished which is shorthand for :succeed or :fail.
For example this:
foo:finished => bar
If equivalent to this:
foo:succeed | foo:fail => bar # | means "or"
The same goes for the :finished-all and :finished-any qualifiers which can be used with families.
Misconception
In Cylc 7, :finished was sometimes used by mistake in situations where :succeed would have been more appropriate. Especially with family triggers (e.g. FAMILY:finish-all) where the difference between :finish-all and :succeed-all might not have been so obvious to the person who wrote the workflow.
Issues Upgrading :finish to Cylc 8
Cylc 8 is smart enough to know that :succeed and :fail are opposite outcomes, so it doesn’t allow them to both be required.
For example this workflow:
foo:succeed => bar # foo must succeed
foo:failed => baz # foo must fail
Will fail validation:
$ cylc validate .
GraphParseError: Opposite outputs foo:succeeded and foo:failed must both be
optional if both are used
To fix the error, we put question marks after the outputs:
foo:succeed? => bar # foo may succeed
foo:failed? => baz # foo may fail
Putting a question mark after a task output tells Cylc that it is optional (i.e. this output may or may not be generated when the task runs).
At Cylc 8 :finish is equivalent to :succeed? | fail?, so this:
foo:finish => bar # foo may either succeed or fail
Is equivalent to:
foo:succeed? | foo:failed? => bar # | means "or"
Which means that this workflow:
foo:finish => bar # foo MAY either succeed or fail
foo => baz # foo MUST succeed
Will fail validation:
$ cylc validate .
GraphParseError: Output foo:succeed can't be both required and optional
Because one of the foo:succeed triggers has a question mark after it and the other doesn’t.
How To Fix Issues & Upgrade To Cylc 8
If you encounter this situation, there are two possible fixes.
-
If the
:finishtrigger was used by mistake, swap it for:succeed.foo => bar # foo must succeed foo => baz # foo must succeed -
If the
:finishtrigger was used purposefully, add question marks to allow the task to fail.foo:finished => bar # foo is permitted to fail foo? => baz # foo is permitted to failSee graph branching for more information about those question mark symbols and how to direct Cylc to take different paths through the graph according to runtime events.