Replace Fillable interface with a concrete wrapper

Signed-off-by: Solomon Hykes <sh.github.6811@hykes.org>
This commit is contained in:
Solomon Hykes 2021-01-21 16:49:25 -08:00
parent 2ee27e83f3
commit eab6028b70
6 changed files with 35 additions and 29 deletions

View File

@ -52,7 +52,7 @@ func (c *Component) ComputeScript() (*Script, error) {
// 1. Always start with an empty fs state (Execute may receive any state as input)
// 2. Always solve at the end (Execute is lazy)
//
func (c *Component) Compute(ctx context.Context, s Solver, out Fillable) (FS, error) {
func (c *Component) Compute(ctx context.Context, s Solver, out *Fillable) (FS, error) {
fs, err := c.Execute(ctx, s.Scratch(), out)
if err != nil {
return fs, err
@ -67,7 +67,7 @@ func (c *Component) Compute(ctx context.Context, s Solver, out Fillable) (FS, er
// A component implements the Executable interface by returning its
// compute script.
// See Value.Executable().
func (c *Component) Execute(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (c *Component) Execute(ctx context.Context, fs FS, out *Fillable) (FS, error) {
script, err := c.ComputeScript()
if err != nil {
// If the component has no script, then do not fail.

View File

@ -43,7 +43,7 @@ func NewEnv(ctx context.Context, s Solver, bootsrc, inputsrc string) (*Env, erro
if err != nil {
return nil, errors.Wrap(err, "compile boot script")
}
bootfs, err := boot.Execute(ctx, s.Scratch(), Discard())
bootfs, err := boot.Execute(ctx, s.Scratch(), nil)
if err != nil {
return nil, errors.Wrap(err, "execute boot script")
}
@ -81,7 +81,7 @@ func NewEnv(ctx context.Context, s Solver, bootsrc, inputsrc string) (*Env, erro
// Compute missing values in env configuration, and write them to state.
func (env *Env) Compute(ctx context.Context) error {
output, err := env.Walk(ctx, func(ctx context.Context, c *Component, out Fillable) error {
output, err := env.Walk(ctx, func(ctx context.Context, c *Component, out *Fillable) error {
lg := log.Ctx(ctx)
lg.
@ -119,7 +119,7 @@ func (env *Env) Export(fs FS) (FS, error) {
return fs, nil
}
type EnvWalkFunc func(context.Context, *Component, Fillable) error
type EnvWalkFunc func(context.Context, *Component, *Fillable) error
// Walk components and return any computed values
func (env *Env) Walk(ctx context.Context, fn EnvWalkFunc) (*Value, error) {
@ -195,7 +195,7 @@ func (env *Env) Walk(ctx context.Context, fn EnvWalkFunc) (*Value, error) {
return nil, err
}
return cueflow.RunnerFunc(func(t *cueflow.Task) error {
return fn(ctx, c, t)
return fn(ctx, c, NewFillable(t))
}), nil
}
// Orchestrate execution with cueflow

View File

@ -30,7 +30,7 @@ func (mnt *Mount) LLB(ctx context.Context, s Solver) (llb.RunOption, error) {
if err != nil {
return nil, errors.Wrap(err, "from")
}
fromFS, err := from.Execute(ctx, s.Scratch(), Discard())
fromFS, err := from.Execute(ctx, s.Scratch(), nil)
if err != nil {
return nil, err
}

View File

@ -14,7 +14,7 @@ type Op struct {
v *Value
}
func (op *Op) Execute(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Execute(ctx context.Context, fs FS, out *Fillable) (FS, error) {
action, err := op.Action()
if err != nil {
return fs, err
@ -50,7 +50,7 @@ func (op *Op) Walk(ctx context.Context, fn func(*Op) error) error {
return fn(op)
}
type Action func(context.Context, FS, Fillable) (FS, error)
type Action func(context.Context, FS, *Fillable) (FS, error)
func (op *Op) Action() (Action, error) {
// An empty struct is allowed as a no-op, to be
@ -88,7 +88,7 @@ func (op *Op) Validate(defs ...string) error {
return op.v.Validate(defs...)
}
func (op *Op) Copy(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Copy(ctx context.Context, fs FS, out *Fillable) (FS, error) {
// Decode copy options
src, err := op.Get("src").String()
if err != nil {
@ -103,7 +103,7 @@ func (op *Op) Copy(ctx context.Context, fs FS, out Fillable) (FS, error) {
return fs, errors.Wrap(err, "from")
}
// Compute source component or script, discarding fs writes & output value
fromFS, err := from.Execute(ctx, fs.Solver().Scratch(), Discard())
fromFS, err := from.Execute(ctx, fs.Solver().Scratch(), nil)
if err != nil {
return fs, err
}
@ -123,10 +123,10 @@ func (op *Op) Copy(ctx context.Context, fs FS, out Fillable) (FS, error) {
}), nil // lazy solve
}
func (op *Op) Nothing(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Nothing(ctx context.Context, fs FS, out *Fillable) (FS, error) {
return fs, nil
}
func (op *Op) Local(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Local(ctx context.Context, fs FS, out *Fillable) (FS, error) {
dir, err := op.Get("dir").String()
if err != nil {
return fs, err
@ -138,7 +138,7 @@ func (op *Op) Local(ctx context.Context, fs FS, out Fillable) (FS, error) {
return fs.Set(llb.Local(dir, llb.FollowPaths(include))), nil // lazy solve
}
func (op *Op) Exec(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Exec(ctx context.Context, fs FS, out *Fillable) (FS, error) {
opts := []llb.RunOption{}
var cmd struct {
Args []string
@ -187,7 +187,7 @@ func (op *Op) Exec(ctx context.Context, fs FS, out Fillable) (FS, error) {
}), nil // lazy solve
}
func (op *Op) Export(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Export(ctx context.Context, fs FS, out *Fillable) (FS, error) {
source, err := op.Get("source").String()
if err != nil {
return fs, err
@ -232,26 +232,26 @@ func (op *Op) Export(ctx context.Context, fs FS, out Fillable) (FS, error) {
return fs, nil
}
func (op *Op) Load(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) Load(ctx context.Context, fs FS, out *Fillable) (FS, error) {
from, err := op.Get("from").Executable()
if err != nil {
return fs, errors.Wrap(err, "load")
}
fromFS, err := from.Execute(ctx, fs.Solver().Scratch(), Discard())
fromFS, err := from.Execute(ctx, fs.Solver().Scratch(), nil)
if err != nil {
return fs, errors.Wrap(err, "load: compute source")
}
return fs.Set(fromFS.LLB()), nil
}
func (op *Op) FetchContainer(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) FetchContainer(ctx context.Context, fs FS, out *Fillable) (FS, error) {
ref, err := op.Get("ref").String()
if err != nil {
return fs, err
}
return fs.Set(llb.Image(ref)), nil
}
func (op *Op) FetchGit(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (op *Op) FetchGit(ctx context.Context, fs FS, out *Fillable) (FS, error) {
remote, err := op.Get("remote").String()
if err != nil {
return fs, err

View File

@ -25,7 +25,7 @@ func (s *Script) Value() *Value {
}
// Run a dagger script
func (s *Script) Execute(ctx context.Context, fs FS, out Fillable) (FS, error) {
func (s *Script) Execute(ctx context.Context, fs FS, out *Fillable) (FS, error) {
err := s.v.RangeList(func(idx int, v *Value) error {
// If op not concrete, interrupt without error.
// This allows gradual resolution:

View File

@ -2,25 +2,31 @@ package dagger
import (
"context"
cueflow "cuelang.org/go/tools/flow"
)
// Implemented by Component, Script, Op
type Executable interface {
Execute(context.Context, FS, Fillable) (FS, error)
Execute(context.Context, FS, *Fillable) (FS, error)
Walk(context.Context, func(*Op) error) error
}
// Something which can be filled in-place with a cue value
type Fillable interface {
Fill(interface{}) error
type Fillable struct {
t *cueflow.Task
}
func Discard() Fillable {
return discard{}
func NewFillable(t *cueflow.Task) *Fillable {
return &Fillable{
t: t,
}
}
type discard struct{}
func (d discard) Fill(x interface{}) error {
return nil
func (f *Fillable) Fill(x interface{}) error {
// Use a nil pointer receiver to discard all values
if f == nil {
return nil
}
return f.t.Fill(x)
}