mirror of
https://github.com/go-task/task.git
synced 2025-11-29 22:48:03 +02:00
feat: improve unmarshal error handling and use v3 yaml interface everywhere (#959)
This commit is contained in:
143
taskfile/cmd.go
143
taskfile/cmd.go
@@ -1,5 +1,11 @@
|
|||||||
package taskfile
|
package taskfile
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"gopkg.in/yaml.v3"
|
||||||
|
)
|
||||||
|
|
||||||
// Cmd is a task command
|
// Cmd is a task command
|
||||||
type Cmd struct {
|
type Cmd struct {
|
||||||
Cmd string
|
Cmd string
|
||||||
@@ -16,68 +22,93 @@ type Dep struct {
|
|||||||
Vars *Vars
|
Vars *Vars
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler interface
|
func (c *Cmd) UnmarshalYAML(node *yaml.Node) error {
|
||||||
func (c *Cmd) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
switch node.Kind {
|
||||||
var cmd string
|
|
||||||
if err := unmarshal(&cmd); err == nil {
|
case yaml.ScalarNode:
|
||||||
|
var cmd string
|
||||||
|
if err := node.Decode(&cmd); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
c.Cmd = cmd
|
c.Cmd = cmd
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
case yaml.MappingNode:
|
||||||
|
|
||||||
|
// A command with additional options
|
||||||
|
var cmdStruct struct {
|
||||||
|
Cmd string
|
||||||
|
Silent bool
|
||||||
|
IgnoreError bool `yaml:"ignore_error"`
|
||||||
|
}
|
||||||
|
if err := node.Decode(&cmdStruct); err == nil && cmdStruct.Cmd != "" {
|
||||||
|
c.Cmd = cmdStruct.Cmd
|
||||||
|
c.Silent = cmdStruct.Silent
|
||||||
|
c.IgnoreError = cmdStruct.IgnoreError
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// A deferred command
|
||||||
|
var deferredCmd struct {
|
||||||
|
Defer string
|
||||||
|
}
|
||||||
|
if err := node.Decode(&deferredCmd); err == nil && deferredCmd.Defer != "" {
|
||||||
|
c.Defer = true
|
||||||
|
c.Cmd = deferredCmd.Defer
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// A deferred task call
|
||||||
|
var deferredCall struct {
|
||||||
|
Defer Call
|
||||||
|
}
|
||||||
|
if err := node.Decode(&deferredCall); err == nil && deferredCall.Defer.Task != "" {
|
||||||
|
c.Defer = true
|
||||||
|
c.Task = deferredCall.Defer.Task
|
||||||
|
c.Vars = deferredCall.Defer.Vars
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// A task call
|
||||||
|
var taskCall struct {
|
||||||
|
Task string
|
||||||
|
Vars *Vars
|
||||||
|
}
|
||||||
|
if err := node.Decode(&taskCall); err == nil && taskCall.Task != "" {
|
||||||
|
c.Task = taskCall.Task
|
||||||
|
c.Vars = taskCall.Vars
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
return fmt.Errorf("yaml: line %d: invalid keys in command", node.Line)
|
||||||
}
|
}
|
||||||
var cmdStruct struct {
|
|
||||||
Cmd string
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into command", node.Line, node.ShortTag())
|
||||||
Silent bool
|
|
||||||
IgnoreError bool `yaml:"ignore_error"`
|
|
||||||
}
|
|
||||||
if err := unmarshal(&cmdStruct); err == nil && cmdStruct.Cmd != "" {
|
|
||||||
c.Cmd = cmdStruct.Cmd
|
|
||||||
c.Silent = cmdStruct.Silent
|
|
||||||
c.IgnoreError = cmdStruct.IgnoreError
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
var deferredCmd struct {
|
|
||||||
Defer string
|
|
||||||
}
|
|
||||||
if err := unmarshal(&deferredCmd); err == nil && deferredCmd.Defer != "" {
|
|
||||||
c.Defer = true
|
|
||||||
c.Cmd = deferredCmd.Defer
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
var deferredCall struct {
|
|
||||||
Defer Call
|
|
||||||
}
|
|
||||||
if err := unmarshal(&deferredCall); err == nil && deferredCall.Defer.Task != "" {
|
|
||||||
c.Defer = true
|
|
||||||
c.Task = deferredCall.Defer.Task
|
|
||||||
c.Vars = deferredCall.Defer.Vars
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
var taskCall struct {
|
|
||||||
Task string
|
|
||||||
Vars *Vars
|
|
||||||
}
|
|
||||||
if err := unmarshal(&taskCall); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
c.Task = taskCall.Task
|
|
||||||
c.Vars = taskCall.Vars
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler interface
|
func (d *Dep) UnmarshalYAML(node *yaml.Node) error {
|
||||||
func (d *Dep) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
switch node.Kind {
|
||||||
var task string
|
|
||||||
if err := unmarshal(&task); err == nil {
|
case yaml.ScalarNode:
|
||||||
|
var task string
|
||||||
|
if err := node.Decode(&task); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
d.Task = task
|
d.Task = task
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
case yaml.MappingNode:
|
||||||
|
var taskCall struct {
|
||||||
|
Task string
|
||||||
|
Vars *Vars
|
||||||
|
}
|
||||||
|
if err := node.Decode(&taskCall); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
d.Task = taskCall.Task
|
||||||
|
d.Vars = taskCall.Vars
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
var taskCall struct {
|
|
||||||
Task string
|
return fmt.Errorf("cannot unmarshal %s into dependency", node.ShortTag())
|
||||||
Vars *Vars
|
|
||||||
}
|
|
||||||
if err := unmarshal(&taskCall); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
d.Task = taskCall.Task
|
|
||||||
d.Vars = taskCall.Vars
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
package taskfile
|
package taskfile
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"errors"
|
|
||||||
"fmt"
|
"fmt"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
|
|
||||||
@@ -32,24 +31,26 @@ type IncludedTaskfiles struct {
|
|||||||
|
|
||||||
// UnmarshalYAML implements the yaml.Unmarshaler interface.
|
// UnmarshalYAML implements the yaml.Unmarshaler interface.
|
||||||
func (tfs *IncludedTaskfiles) UnmarshalYAML(node *yaml.Node) error {
|
func (tfs *IncludedTaskfiles) UnmarshalYAML(node *yaml.Node) error {
|
||||||
if node.Kind != yaml.MappingNode {
|
switch node.Kind {
|
||||||
return errors.New("task: includes is not a map")
|
|
||||||
}
|
|
||||||
|
|
||||||
// NOTE(@andreynering): on this style of custom unmarsheling,
|
case yaml.MappingNode:
|
||||||
// even number contains the keys, while odd numbers contains
|
// NOTE(@andreynering): on this style of custom unmarshalling,
|
||||||
// the values.
|
// even number contains the keys, while odd numbers contains
|
||||||
for i := 0; i < len(node.Content); i += 2 {
|
// the values.
|
||||||
keyNode := node.Content[i]
|
for i := 0; i < len(node.Content); i += 2 {
|
||||||
valueNode := node.Content[i+1]
|
keyNode := node.Content[i]
|
||||||
|
valueNode := node.Content[i+1]
|
||||||
|
|
||||||
var v IncludedTaskfile
|
var v IncludedTaskfile
|
||||||
if err := valueNode.Decode(&v); err != nil {
|
if err := valueNode.Decode(&v); err != nil {
|
||||||
return err
|
return err
|
||||||
|
}
|
||||||
|
tfs.Set(keyNode.Value, v)
|
||||||
}
|
}
|
||||||
tfs.Set(keyNode.Value, v)
|
return nil
|
||||||
}
|
}
|
||||||
return nil
|
|
||||||
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into included taskfiles", node.Line, node.ShortTag())
|
||||||
}
|
}
|
||||||
|
|
||||||
// Len returns the length of the map
|
// Len returns the length of the map
|
||||||
@@ -92,33 +93,40 @@ func (tfs *IncludedTaskfiles) Range(yield func(key string, includedTaskfile Incl
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler interface
|
func (it *IncludedTaskfile) UnmarshalYAML(node *yaml.Node) error {
|
||||||
func (it *IncludedTaskfile) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
switch node.Kind {
|
||||||
var str string
|
|
||||||
if err := unmarshal(&str); err == nil {
|
case yaml.ScalarNode:
|
||||||
|
var str string
|
||||||
|
if err := node.Decode(&str); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
it.Taskfile = str
|
it.Taskfile = str
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
case yaml.MappingNode:
|
||||||
|
var includedTaskfile struct {
|
||||||
|
Taskfile string
|
||||||
|
Dir string
|
||||||
|
Optional bool
|
||||||
|
Internal bool
|
||||||
|
Aliases []string
|
||||||
|
Vars *Vars
|
||||||
|
}
|
||||||
|
if err := node.Decode(&includedTaskfile); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
it.Taskfile = includedTaskfile.Taskfile
|
||||||
|
it.Dir = includedTaskfile.Dir
|
||||||
|
it.Optional = includedTaskfile.Optional
|
||||||
|
it.Internal = includedTaskfile.Internal
|
||||||
|
it.Aliases = includedTaskfile.Aliases
|
||||||
|
it.AdvancedImport = true
|
||||||
|
it.Vars = includedTaskfile.Vars
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
var includedTaskfile struct {
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into included taskfile", node.Line, node.ShortTag())
|
||||||
Taskfile string
|
|
||||||
Dir string
|
|
||||||
Optional bool
|
|
||||||
Internal bool
|
|
||||||
Aliases []string
|
|
||||||
Vars *Vars
|
|
||||||
}
|
|
||||||
if err := unmarshal(&includedTaskfile); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
it.Taskfile = includedTaskfile.Taskfile
|
|
||||||
it.Dir = includedTaskfile.Dir
|
|
||||||
it.Optional = includedTaskfile.Optional
|
|
||||||
it.Internal = includedTaskfile.Internal
|
|
||||||
it.Aliases = includedTaskfile.Aliases
|
|
||||||
it.AdvancedImport = true
|
|
||||||
it.Vars = includedTaskfile.Vars
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// DeepCopy creates a new instance of IncludedTaskfile and copies
|
// DeepCopy creates a new instance of IncludedTaskfile and copies
|
||||||
|
|||||||
@@ -2,6 +2,8 @@ package taskfile
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
|
"gopkg.in/yaml.v3"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Output of the Task output
|
// Output of the Task output
|
||||||
@@ -17,28 +19,35 @@ func (s *Output) IsSet() bool {
|
|||||||
return s.Name != ""
|
return s.Name != ""
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler
|
func (s *Output) UnmarshalYAML(node *yaml.Node) error {
|
||||||
// It accepts a scalar node representing the Output.Name or a mapping node representing the OutputGroup.
|
switch node.Kind {
|
||||||
func (s *Output) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
|
||||||
var name string
|
case yaml.ScalarNode:
|
||||||
if err := unmarshal(&name); err == nil {
|
var name string
|
||||||
|
if err := node.Decode(&name); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
s.Name = name
|
s.Name = name
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
case yaml.MappingNode:
|
||||||
|
var tmp struct {
|
||||||
|
Group *OutputGroup
|
||||||
|
}
|
||||||
|
if err := node.Decode(&tmp); err != nil {
|
||||||
|
return fmt.Errorf("task: output style must be a string or mapping with a \"group\" key: %w", err)
|
||||||
|
}
|
||||||
|
if tmp.Group == nil {
|
||||||
|
return fmt.Errorf("task: output style must have the \"group\" key when in mapping form")
|
||||||
|
}
|
||||||
|
*s = Output{
|
||||||
|
Name: "group",
|
||||||
|
Group: *tmp.Group,
|
||||||
|
}
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
var tmp struct {
|
|
||||||
Group *OutputGroup
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into output", node.Line, node.ShortTag())
|
||||||
}
|
|
||||||
if err := unmarshal(&tmp); err != nil {
|
|
||||||
return fmt.Errorf("task: output style must be a string or mapping with a \"group\" key: %w", err)
|
|
||||||
}
|
|
||||||
if tmp.Group == nil {
|
|
||||||
return fmt.Errorf("task: output style must have the \"group\" key when in mapping form")
|
|
||||||
}
|
|
||||||
*s = Output{
|
|
||||||
Name: "group",
|
|
||||||
Group: *tmp.Group,
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// OutputGroup is the style options specific to the Group style.
|
// OutputGroup is the style options specific to the Group style.
|
||||||
|
|||||||
@@ -3,6 +3,8 @@ package taskfile
|
|||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
|
"gopkg.in/yaml.v3"
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@@ -17,29 +19,33 @@ type Precondition struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler interface.
|
// UnmarshalYAML implements yaml.Unmarshaler interface.
|
||||||
func (p *Precondition) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
func (p *Precondition) UnmarshalYAML(node *yaml.Node) error {
|
||||||
var cmd string
|
switch node.Kind {
|
||||||
|
|
||||||
if err := unmarshal(&cmd); err == nil {
|
case yaml.ScalarNode:
|
||||||
|
var cmd string
|
||||||
|
if err := node.Decode(&cmd); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
p.Sh = cmd
|
p.Sh = cmd
|
||||||
p.Msg = fmt.Sprintf("`%s` failed", cmd)
|
p.Msg = fmt.Sprintf("`%s` failed", cmd)
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
case yaml.MappingNode:
|
||||||
|
var sh struct {
|
||||||
|
Sh string
|
||||||
|
Msg string
|
||||||
|
}
|
||||||
|
if err := node.Decode(&sh); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
p.Sh = sh.Sh
|
||||||
|
p.Msg = sh.Msg
|
||||||
|
if p.Msg == "" {
|
||||||
|
p.Msg = fmt.Sprintf("%s failed", sh.Sh)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
var sh struct {
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into precondition", node.Line, node.ShortTag())
|
||||||
Sh string
|
|
||||||
Msg string
|
|
||||||
}
|
|
||||||
|
|
||||||
if err := unmarshal(&sh); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
p.Sh = sh.Sh
|
|
||||||
p.Msg = sh.Msg
|
|
||||||
if p.Msg == "" {
|
|
||||||
p.Msg = fmt.Sprintf("%s failed", sh.Sh)
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|||||||
127
taskfile/task.go
127
taskfile/task.go
@@ -1,5 +1,11 @@
|
|||||||
package taskfile
|
package taskfile
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"gopkg.in/yaml.v3"
|
||||||
|
)
|
||||||
|
|
||||||
// Tasks represents a group of tasks
|
// Tasks represents a group of tasks
|
||||||
type Tasks map[string]*Task
|
type Tasks map[string]*Task
|
||||||
|
|
||||||
@@ -39,67 +45,80 @@ func (t *Task) Name() string {
|
|||||||
return t.Task
|
return t.Task
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *Task) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
func (t *Task) UnmarshalYAML(node *yaml.Node) error {
|
||||||
var cmd Cmd
|
switch node.Kind {
|
||||||
if err := unmarshal(&cmd); err == nil && cmd.Cmd != "" {
|
|
||||||
|
// Shortcut syntax for a task with a single command
|
||||||
|
case yaml.ScalarNode:
|
||||||
|
var cmd Cmd
|
||||||
|
if err := node.Decode(&cmd); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
t.Cmds = append(t.Cmds, &cmd)
|
t.Cmds = append(t.Cmds, &cmd)
|
||||||
return nil
|
return nil
|
||||||
}
|
|
||||||
|
|
||||||
var cmds []*Cmd
|
// Shortcut syntax for a simple task with a list of commands
|
||||||
if err := unmarshal(&cmds); err == nil && len(cmds) > 0 {
|
case yaml.SequenceNode:
|
||||||
|
var cmds []*Cmd
|
||||||
|
if err := node.Decode(&cmds); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
t.Cmds = cmds
|
t.Cmds = cmds
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
// Full task object
|
||||||
|
case yaml.MappingNode:
|
||||||
|
var task struct {
|
||||||
|
Cmds []*Cmd
|
||||||
|
Deps []*Dep
|
||||||
|
Label string
|
||||||
|
Desc string
|
||||||
|
Summary string
|
||||||
|
Aliases []string
|
||||||
|
Sources []string
|
||||||
|
Generates []string
|
||||||
|
Status []string
|
||||||
|
Preconditions []*Precondition
|
||||||
|
Dir string
|
||||||
|
Vars *Vars
|
||||||
|
Env *Vars
|
||||||
|
Dotenv []string
|
||||||
|
Silent bool
|
||||||
|
Interactive bool
|
||||||
|
Internal bool
|
||||||
|
Method string
|
||||||
|
Prefix string
|
||||||
|
IgnoreError bool `yaml:"ignore_error"`
|
||||||
|
Run string
|
||||||
|
}
|
||||||
|
if err := node.Decode(&task); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
t.Cmds = task.Cmds
|
||||||
|
t.Deps = task.Deps
|
||||||
|
t.Label = task.Label
|
||||||
|
t.Desc = task.Desc
|
||||||
|
t.Summary = task.Summary
|
||||||
|
t.Aliases = task.Aliases
|
||||||
|
t.Sources = task.Sources
|
||||||
|
t.Generates = task.Generates
|
||||||
|
t.Status = task.Status
|
||||||
|
t.Preconditions = task.Preconditions
|
||||||
|
t.Dir = task.Dir
|
||||||
|
t.Vars = task.Vars
|
||||||
|
t.Env = task.Env
|
||||||
|
t.Dotenv = task.Dotenv
|
||||||
|
t.Silent = task.Silent
|
||||||
|
t.Interactive = task.Interactive
|
||||||
|
t.Internal = task.Internal
|
||||||
|
t.Method = task.Method
|
||||||
|
t.Prefix = task.Prefix
|
||||||
|
t.IgnoreError = task.IgnoreError
|
||||||
|
t.Run = task.Run
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
var task struct {
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into task", node.Line, node.ShortTag())
|
||||||
Cmds []*Cmd
|
|
||||||
Deps []*Dep
|
|
||||||
Label string
|
|
||||||
Desc string
|
|
||||||
Summary string
|
|
||||||
Aliases []string
|
|
||||||
Sources []string
|
|
||||||
Generates []string
|
|
||||||
Status []string
|
|
||||||
Preconditions []*Precondition
|
|
||||||
Dir string
|
|
||||||
Vars *Vars
|
|
||||||
Env *Vars
|
|
||||||
Dotenv []string
|
|
||||||
Silent bool
|
|
||||||
Interactive bool
|
|
||||||
Internal bool
|
|
||||||
Method string
|
|
||||||
Prefix string
|
|
||||||
IgnoreError bool `yaml:"ignore_error"`
|
|
||||||
Run string
|
|
||||||
}
|
|
||||||
if err := unmarshal(&task); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
t.Cmds = task.Cmds
|
|
||||||
t.Deps = task.Deps
|
|
||||||
t.Label = task.Label
|
|
||||||
t.Desc = task.Desc
|
|
||||||
t.Aliases = task.Aliases
|
|
||||||
t.Summary = task.Summary
|
|
||||||
t.Sources = task.Sources
|
|
||||||
t.Generates = task.Generates
|
|
||||||
t.Status = task.Status
|
|
||||||
t.Preconditions = task.Preconditions
|
|
||||||
t.Dir = task.Dir
|
|
||||||
t.Vars = task.Vars
|
|
||||||
t.Env = task.Env
|
|
||||||
t.Dotenv = task.Dotenv
|
|
||||||
t.Silent = task.Silent
|
|
||||||
t.Interactive = task.Interactive
|
|
||||||
t.Internal = task.Internal
|
|
||||||
t.Method = task.Method
|
|
||||||
t.Prefix = task.Prefix
|
|
||||||
t.IgnoreError = task.IgnoreError
|
|
||||||
t.Run = task.Run
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// DeepCopy creates a new instance of Task and copies
|
// DeepCopy creates a new instance of Task and copies
|
||||||
|
|||||||
@@ -3,6 +3,8 @@ package taskfile
|
|||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
|
"gopkg.in/yaml.v3"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Taskfile represents a Taskfile.yml
|
// Taskfile represents a Taskfile.yml
|
||||||
@@ -21,50 +23,52 @@ type Taskfile struct {
|
|||||||
Interval string
|
Interval string
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler interface
|
func (tf *Taskfile) UnmarshalYAML(node *yaml.Node) error {
|
||||||
func (tf *Taskfile) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
switch node.Kind {
|
||||||
var taskfile struct {
|
|
||||||
Version string
|
case yaml.MappingNode:
|
||||||
Expansions int
|
var taskfile struct {
|
||||||
Output Output
|
Version string
|
||||||
Method string
|
Expansions int
|
||||||
Includes *IncludedTaskfiles
|
Output Output
|
||||||
Vars *Vars
|
Method string
|
||||||
Env *Vars
|
Includes *IncludedTaskfiles
|
||||||
Tasks Tasks
|
Vars *Vars
|
||||||
Silent bool
|
Env *Vars
|
||||||
Dotenv []string
|
Tasks Tasks
|
||||||
Run string
|
Silent bool
|
||||||
Interval string
|
Dotenv []string
|
||||||
|
Run string
|
||||||
|
Interval string
|
||||||
|
}
|
||||||
|
if err := node.Decode(&taskfile); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tf.Version = taskfile.Version
|
||||||
|
tf.Expansions = taskfile.Expansions
|
||||||
|
tf.Output = taskfile.Output
|
||||||
|
tf.Method = taskfile.Method
|
||||||
|
tf.Includes = taskfile.Includes
|
||||||
|
tf.Vars = taskfile.Vars
|
||||||
|
tf.Env = taskfile.Env
|
||||||
|
tf.Tasks = taskfile.Tasks
|
||||||
|
tf.Silent = taskfile.Silent
|
||||||
|
tf.Dotenv = taskfile.Dotenv
|
||||||
|
tf.Run = taskfile.Run
|
||||||
|
tf.Interval = taskfile.Interval
|
||||||
|
if tf.Expansions <= 0 {
|
||||||
|
tf.Expansions = 2
|
||||||
|
}
|
||||||
|
if tf.Vars == nil {
|
||||||
|
tf.Vars = &Vars{}
|
||||||
|
}
|
||||||
|
if tf.Env == nil {
|
||||||
|
tf.Env = &Vars{}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := unmarshal(&taskfile); err != nil {
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into taskfile", node.Line, node.ShortTag())
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
tf.Version = taskfile.Version
|
|
||||||
tf.Expansions = taskfile.Expansions
|
|
||||||
tf.Output = taskfile.Output
|
|
||||||
tf.Method = taskfile.Method
|
|
||||||
tf.Includes = taskfile.Includes
|
|
||||||
tf.Vars = taskfile.Vars
|
|
||||||
tf.Env = taskfile.Env
|
|
||||||
tf.Tasks = taskfile.Tasks
|
|
||||||
tf.Silent = taskfile.Silent
|
|
||||||
tf.Dotenv = taskfile.Dotenv
|
|
||||||
tf.Run = taskfile.Run
|
|
||||||
tf.Interval = taskfile.Interval
|
|
||||||
|
|
||||||
if tf.Expansions <= 0 {
|
|
||||||
tf.Expansions = 2
|
|
||||||
}
|
|
||||||
if tf.Vars == nil {
|
|
||||||
tf.Vars = &Vars{}
|
|
||||||
}
|
|
||||||
if tf.Env == nil {
|
|
||||||
tf.Env = &Vars{}
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ParsedVersion returns the version as a float64
|
// ParsedVersion returns the version as a float64
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
package taskfile
|
package taskfile
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"errors"
|
"fmt"
|
||||||
|
|
||||||
"golang.org/x/exp/slices"
|
"golang.org/x/exp/slices"
|
||||||
"gopkg.in/yaml.v3"
|
"gopkg.in/yaml.v3"
|
||||||
@@ -13,26 +13,27 @@ type Vars struct {
|
|||||||
Mapping map[string]Var
|
Mapping map[string]Var
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements the yaml.Unmarshaler interface.
|
|
||||||
func (vs *Vars) UnmarshalYAML(node *yaml.Node) error {
|
func (vs *Vars) UnmarshalYAML(node *yaml.Node) error {
|
||||||
if node.Kind != yaml.MappingNode {
|
switch node.Kind {
|
||||||
return errors.New("task: vars is not a map")
|
|
||||||
}
|
|
||||||
|
|
||||||
// NOTE(@andreynering): on this style of custom unmarsheling,
|
case yaml.MappingNode:
|
||||||
// even number contains the keys, while odd numbers contains
|
// NOTE(@andreynering): on this style of custom unmarshalling,
|
||||||
// the values.
|
// even number contains the keys, while odd numbers contains
|
||||||
for i := 0; i < len(node.Content); i += 2 {
|
// the values.
|
||||||
keyNode := node.Content[i]
|
for i := 0; i < len(node.Content); i += 2 {
|
||||||
valueNode := node.Content[i+1]
|
keyNode := node.Content[i]
|
||||||
|
valueNode := node.Content[i+1]
|
||||||
|
|
||||||
var v Var
|
var v Var
|
||||||
if err := valueNode.Decode(&v); err != nil {
|
if err := valueNode.Decode(&v); err != nil {
|
||||||
return err
|
return err
|
||||||
|
}
|
||||||
|
vs.Set(keyNode.Value, v)
|
||||||
}
|
}
|
||||||
vs.Set(keyNode.Value, v)
|
return nil
|
||||||
}
|
}
|
||||||
return nil
|
|
||||||
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into variables", node.Line, node.ShortTag())
|
||||||
}
|
}
|
||||||
|
|
||||||
// DeepCopy creates a new instance of Vars and copies
|
// DeepCopy creates a new instance of Vars and copies
|
||||||
@@ -116,20 +117,27 @@ type Var struct {
|
|||||||
Dir string
|
Dir string
|
||||||
}
|
}
|
||||||
|
|
||||||
// UnmarshalYAML implements yaml.Unmarshaler interface.
|
func (v *Var) UnmarshalYAML(node *yaml.Node) error {
|
||||||
func (v *Var) UnmarshalYAML(unmarshal func(interface{}) error) error {
|
switch node.Kind {
|
||||||
var str string
|
|
||||||
if err := unmarshal(&str); err == nil {
|
case yaml.ScalarNode:
|
||||||
|
var str string
|
||||||
|
if err := node.Decode(&str); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
v.Static = str
|
v.Static = str
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
|
case yaml.MappingNode:
|
||||||
|
var sh struct {
|
||||||
|
Sh string
|
||||||
|
}
|
||||||
|
if err := node.Decode(&sh); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
v.Sh = sh.Sh
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
var sh struct {
|
return fmt.Errorf("yaml: line %d: cannot unmarshal %s into variable", node.Line, node.ShortTag())
|
||||||
Sh string
|
|
||||||
}
|
|
||||||
if err := unmarshal(&sh); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
v.Sh = sh.Sh
|
|
||||||
return nil
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user