mirror of
https://github.com/go-task/task.git
synced 2026-06-11 09:51:50 +00:00
feat: recursive config search (#2166)
* refactor: experiments flags * refactor: args.Parse * feat: recursive search for taskrc files * feat: consolidate some code into new fsext package * feat: add tests for search and default dir * fix: linting issues
This commit is contained in:
8
taskrc/ast/taskrc.go
Normal file
8
taskrc/ast/taskrc.go
Normal file
@@ -0,0 +1,8 @@
|
||||
package ast
|
||||
|
||||
import "github.com/Masterminds/semver/v3"
|
||||
|
||||
type TaskRC struct {
|
||||
Version *semver.Version `yaml:"version"`
|
||||
Experiments map[string]int `yaml:"experiments"`
|
||||
}
|
||||
24
taskrc/node.go
Normal file
24
taskrc/node.go
Normal file
@@ -0,0 +1,24 @@
|
||||
package taskrc
|
||||
|
||||
import "github.com/go-task/task/v3/internal/fsext"
|
||||
|
||||
type Node struct {
|
||||
entrypoint string
|
||||
dir string
|
||||
}
|
||||
|
||||
func NewNode(
|
||||
entrypoint string,
|
||||
dir string,
|
||||
) (*Node, error) {
|
||||
dir = fsext.DefaultDir(entrypoint, dir)
|
||||
var err error
|
||||
entrypoint, dir, err = fsext.Search(entrypoint, dir, defaultTaskRCs)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return &Node{
|
||||
entrypoint: entrypoint,
|
||||
dir: dir,
|
||||
}, nil
|
||||
}
|
||||
79
taskrc/reader.go
Normal file
79
taskrc/reader.go
Normal file
@@ -0,0 +1,79 @@
|
||||
package taskrc
|
||||
|
||||
import (
|
||||
"os"
|
||||
|
||||
"gopkg.in/yaml.v3"
|
||||
|
||||
"github.com/go-task/task/v3/taskrc/ast"
|
||||
)
|
||||
|
||||
type (
|
||||
// DebugFunc is a function that can be called to log debug messages.
|
||||
DebugFunc func(string)
|
||||
// A ReaderOption is any type that can apply a configuration to a [Reader].
|
||||
ReaderOption interface {
|
||||
ApplyToReader(*Reader)
|
||||
}
|
||||
// A Reader will recursively read Taskfiles from a given [Node] and build a
|
||||
// [ast.TaskRC] from them.
|
||||
Reader struct {
|
||||
debugFunc DebugFunc
|
||||
}
|
||||
)
|
||||
|
||||
// NewReader constructs a new Taskfile [Reader] using the given Node and
|
||||
// options.
|
||||
func NewReader(opts ...ReaderOption) *Reader {
|
||||
r := &Reader{
|
||||
debugFunc: nil,
|
||||
}
|
||||
r.Options(opts...)
|
||||
return r
|
||||
}
|
||||
|
||||
// Options loops through the given [ReaderOption] functions and applies them to
|
||||
// the [Reader].
|
||||
func (r *Reader) Options(opts ...ReaderOption) {
|
||||
for _, opt := range opts {
|
||||
opt.ApplyToReader(r)
|
||||
}
|
||||
}
|
||||
|
||||
// WithDebugFunc sets the debug function to be used by the [Reader]. If set,
|
||||
// this function will be called with debug messages. This can be useful if the
|
||||
// caller wants to log debug messages from the [Reader]. By default, no debug
|
||||
// function is set and the logs are not written.
|
||||
func WithDebugFunc(debugFunc DebugFunc) ReaderOption {
|
||||
return &debugFuncOption{debugFunc: debugFunc}
|
||||
}
|
||||
|
||||
type debugFuncOption struct {
|
||||
debugFunc DebugFunc
|
||||
}
|
||||
|
||||
func (o *debugFuncOption) ApplyToReader(r *Reader) {
|
||||
r.debugFunc = o.debugFunc
|
||||
}
|
||||
|
||||
// Read will read the Task config defined by the [Reader]'s [Node].
|
||||
func (r *Reader) Read(node *Node) (*ast.TaskRC, error) {
|
||||
var config ast.TaskRC
|
||||
|
||||
if node == nil {
|
||||
return nil, os.ErrInvalid
|
||||
}
|
||||
|
||||
// Read the file
|
||||
b, err := os.ReadFile(node.entrypoint)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Parse the content
|
||||
if err := yaml.Unmarshal(b, &config); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &config, nil
|
||||
}
|
||||
6
taskrc/taskrc.go
Normal file
6
taskrc/taskrc.go
Normal file
@@ -0,0 +1,6 @@
|
||||
package taskrc
|
||||
|
||||
var defaultTaskRCs = []string{
|
||||
".taskrc.yml",
|
||||
".taskrc.yaml",
|
||||
}
|
||||
Reference in New Issue
Block a user