Replies: 13 comments
-
@shykes The problem @grouville is facing (if I understand correctly) is: how does this work with higher level packages? Let's say you want The problem in dagger mainstream is you have no idea which fields are the output of tasks (e.g. can be used as It's worse when a package contains a set of tasks. How do you wait on all of them to complete? |
Beta Was this translation helpful? Give feedback.
-
I see. What if we made it a convention to expose an
@helderco had the exact same request :) I will update the design proposal based on this, thanks! |
Beta Was this translation helpful? Give feedback.
This comment has been hidden.
This comment has been hidden.
-
This makes me think any reference is valid.
But this says it's not. How does the go implementation know to follow a CUE reference as a dependency? Do tasks need to reference other tasks somehow (through the higher level abstractions)? |
Beta Was this translation helpful? Give feedback.
-
Reading on cue flow... |
Beta Was this translation helpful? Give feedback.
-
At first glance I like how the if option reads for a simple case, but soon I hit some limitations.
Taking inspiration from Salt, which I'm used to, every state has a name (aka id) and some global requisites. These are powerful, here's some I like:
As a global, every task would have to follow a convention, but looks cleaner when used (no need for wrapping):
Example usage:
And in user-land:
Copying all requisites like this doesn't look good, but maybe there's a simpler way to implement? So... for me, either this (option 3?) or option 1, with some notes:
|
Beta Was this translation helpful? Give feedback.
-
I don't have a strong opinion on all these alternatives, but I like the UX of the third option (@helderco's one) the most (even though his current example isn't fully functional atm [theoritically]). From what I understand, helderco's proposition might be possible with your The second option seems more "risky" because it relies on Cue to expose subfields in the scope of the Having a
Btw, these directives are indeed very powerful and could bring a lot of potential use-cases. They may all fit your
Curious to know your opinion on the subject |
Beta Was this translation helpful? Give feedback.
-
Duplicate of #940 |
Beta Was this translation helpful? Give feedback.
-
Picking this up.
|
Beta Was this translation helpful? Give feedback.
This comment has been hidden.
This comment has been hidden.
-
I'm look forward to this new feature |
Beta Was this translation helpful? Give feedback.
-
Engineering wise, the option 1 makes more sense, but I don't really like the syntax/implementation presented. |
Beta Was this translation helpful? Give feedback.
-
@aluzzardi you mentioned a possible |
Beta Was this translation helpful? Give feedback.
-
Overview
This proposes a design in Dagger 0.2 to solve #940.
Problem
Most of the time, dependencies between Dagger tasks are implicit, thanks to the magic of CUE references. If a config value for task
foo
is referenced by a config value for taskbar
, Dagger implicitely knows thatfoo
must run beforebar
.But sometimes,
foo
must run beforebar
even though there is no dependency between their configurations. For example,foo
might upload an artifact at a known URL, whichbar
must later download. In this case, developers need a way to control dependencies between tasks explicitly.Currently this is achieved by various hacks (cc @grouville who is carrying the oppressive weight of these soul-destroying hacks on his shoulders).
Solution
Instead of hacks, there should be a reliable and intuitive API to achieve this with minimal effort. There are 3 design options being considered:
#Wait
+id
engine
engine.#Wait & { target: foo , completed: { …}}
engine.#Wait & { targets: [foo, bar] }
id: #ID
(can be#Wait
on multiple sub-tasks)if
+status
if (foo.status == “completed”) { … }
if (foo.status == “completed”) && (bar.status == “completed”) { … }
status: #Status
(can be CUE expression combining status of multiple sub-tasks)require: foo
require: [foo, bar]
require
,require_any
,onfail
,onfail_any
See below for details on each option.
Option 1:
#Wait
+id
conventionSpec:
Example usage:
User-defined actions can also be waited on: they simply need to implement the
id: #TaskID
interface.For example
docker.#Run
would do:Option 2:
if
+status
conventionThis option requires the CUE
if
statement to be a reliable synchronization primitive.All tasks have a
status
field filled by the runtime:Then waiting for a task is as simple as:
High-level actions could also be waited on, by implementing the
status: engine.#Status
convention. For example:Option 3: Salt-style convention
Copied from @helderco’s comment below
Beta Was this translation helpful? Give feedback.
All reactions