diff --git a/cmd/config/.golangci.yml b/cmd/config/.golangci.yml index 26827c174..fc4b84297 100644 --- a/cmd/config/.golangci.yml +++ b/cmd/config/.golangci.yml @@ -19,7 +19,7 @@ linters: # - gochecknoinits # - goconst # - gocritic - - gocyclo +# - gocyclo - gofmt - goimports # - golint diff --git a/cmd/config/internal/commands/run-fns.go b/cmd/config/internal/commands/run-fns.go index 4dfbc3e05..83a3ca7aa 100644 --- a/cmd/config/internal/commands/run-fns.go +++ b/cmd/config/internal/commands/run-fns.go @@ -42,14 +42,17 @@ func GetRunFnRunner(name string) *RunFnRunner { &r.Image, "image", "", "run this image as a function instead of discovering them.") r.Command.Flags().BoolVar( - &r.EnableStar, "enable-star", false, "enable support for starlark functions.") - r.Command.Flags().MarkHidden("enable-star") + &r.EnableExec, "enable-exec", false, "enable support for exec functions. (Alpha)") r.Command.Flags().StringVar( - &r.StarPath, "star-path", "", "run a starlark script as a function.") - r.Command.Flags().MarkHidden("star-path") + &r.ExecPath, "exec-path", "", "run an executable as a function. (Alpha)") + r.Command.Flags().StringArrayVar( + &r.ExecArgs, "exec-arg", nil, "arg for executable function. (Alpha)") + r.Command.Flags().BoolVar( + &r.EnableStar, "enable-star", false, "enable support for starlark functions. (Alpha)") r.Command.Flags().StringVar( - &r.StarName, "star-name", "", "name of starlark program.") - r.Command.Flags().MarkHidden("star-name") + &r.StarPath, "star-path", "", "run a starlark script as a function. (Alpha)") + r.Command.Flags().StringVar( + &r.StarName, "star-name", "", "name of starlark program. (Alpha)") r.Command.Flags().StringVar( &r.ResultsDir, "results-dir", "", "write function results to this dir") @@ -79,6 +82,9 @@ type RunFnRunner struct { EnableStar bool StarPath string StarName string + EnableExec bool + ExecPath string + ExecArgs []string RunFns runfn.RunFns ResultsDir string Network bool @@ -94,14 +100,13 @@ func (r *RunFnRunner) runE(c *cobra.Command, args []string) error { // Functions to run. func (r *RunFnRunner) getContainerFunctions(c *cobra.Command, args, dataItems []string) ( []*yaml.RNode, error) { - if r.Image == "" && r.StarPath == "" { + if r.Image == "" && r.StarPath == "" && r.ExecPath == "" { return nil, nil } var fn *yaml.RNode var err error - // if image isn't specified, then Functions is empty if r.Image != "" { // create the function spec to set as an annotation fn, err = yaml.Parse(`container: {}`) @@ -143,8 +148,29 @@ func (r *RunFnRunner) getContainerFunctions(c *cobra.Command, args, dataItems [] if err != nil { return nil, err } - } else { - return nil, nil + } else if r.EnableExec && r.ExecPath != "" { + // create the function spec to set as an annotation + fn, err = yaml.Parse(`exec: {}`) + if err != nil { + return nil, err + } + + err = fn.PipeE( + yaml.Lookup("exec"), + yaml.SetField("path", yaml.NewScalarRNode(r.ExecPath))) + if err != nil { + return nil, err + } + + // add the arguments + for _, a := range r.ExecArgs { + err = fn.PipeE( + yaml.LookupCreate(yaml.SequenceNode, "exec", "args"), + yaml.Append(yaml.NewScalarRNode(a).YNode())) + if err != nil { + return nil, err + } + } } // create the function config @@ -221,8 +247,12 @@ func (r *RunFnRunner) preRunE(c *cobra.Command, args []string) error { return errors.Errorf("must specify --enable-star with --star-path") } + if !r.EnableExec && r.ExecPath != "" { + return errors.Errorf("must specify --enable-exec with --exec-path") + } + if c.ArgsLenAtDash() >= 0 && r.Image == "" && - !(r.EnableStar && r.StarPath != "") { + !(r.EnableStar && r.StarPath != "") && !(r.EnableExec && r.ExecPath != "") { return errors.Errorf("must specify --image") } @@ -270,6 +300,7 @@ func (r *RunFnRunner) preRunE(c *cobra.Command, args []string) error { Network: r.Network, NetworkName: r.NetworkName, EnableStarlark: r.EnableStar, + EnableExec: r.EnableExec, StorageMounts: storageMounts, ResultsDir: r.ResultsDir, } diff --git a/kyaml/fn/runtime/runtimeutil/functiontypes.go b/kyaml/fn/runtime/runtimeutil/functiontypes.go index 2bec8786f..634adaec5 100644 --- a/kyaml/fn/runtime/runtimeutil/functiontypes.go +++ b/kyaml/fn/runtime/runtimeutil/functiontypes.go @@ -30,10 +30,19 @@ type FunctionSpec struct { // Starlark is the spec for running a function as a starlark script Starlark StarlarkSpec `json:"starlark,omitempty" yaml:"starlark,omitempty"` + // ExecSpec is the spec for running a function as an executable + Exec ExecSpec `json:"exec,omitempty" yaml:"exec,omitempty"` + // Mounts are the storage or directories to mount into the container StorageMounts []StorageMount `json:"mounts,omitempty" yaml:"mounts,omitempty"` } +type ExecSpec struct { + Path string `json:"path,omitempty" yaml:"path,omitempty"` + + Args []string `json:"args,omitempty" yaml:"args,omitempty"` +} + // ContainerSpec defines a spec for running a function as a container type ContainerSpec struct { // Image is the container image to run diff --git a/kyaml/runfn/runfn.go b/kyaml/runfn/runfn.go index 4f5ed7f91..d5f27faed 100644 --- a/kyaml/runfn/runfn.go +++ b/kyaml/runfn/runfn.go @@ -15,6 +15,7 @@ import ( "sigs.k8s.io/kustomize/kyaml/errors" "sigs.k8s.io/kustomize/kyaml/fn/runtime/container" + "sigs.k8s.io/kustomize/kyaml/fn/runtime/exec" "sigs.k8s.io/kustomize/kyaml/fn/runtime/runtimeutil" "sigs.k8s.io/kustomize/kyaml/fn/runtime/starlark" "sigs.k8s.io/kustomize/kyaml/kio" @@ -64,6 +65,9 @@ type RunFns struct { // EnableStarlark will enable functions run as starlark scripts EnableStarlark bool + // EnableExec will enable exec functions + EnableExec bool + // DisableContainers will disable functions run as containers DisableContainers bool @@ -333,16 +337,14 @@ func (r *RunFns) init() { // ffp provides function filters func (r *RunFns) ffp(spec runtimeutil.FunctionSpec, api *yaml.RNode) (kio.Filter, error) { + var resultsFile string + if r.ResultsDir != "" { + resultsFile = filepath.Join(r.ResultsDir, fmt.Sprintf( + "results-%v.yaml", r.resultsCount)) + atomic.AddUint32(&r.resultsCount, 1) + } if !r.DisableContainers && spec.Container.Image != "" { - var resultsFile string // TODO: Add a test for this behavior - - if r.ResultsDir != "" { - resultsFile = filepath.Join(r.ResultsDir, fmt.Sprintf( - "results-%v.yaml", r.resultsCount)) - atomic.AddUint32(&r.resultsCount, 1) - } - cf := &container.Filter{ Image: spec.Container.Image, Network: spec.Network, @@ -372,11 +374,24 @@ func (r *RunFns) ffp(spec runtimeutil.FunctionSpec, api *yaml.RNode) (kio.Filter } p = path.Join(r.Path, path.Dir(p), spec.Starlark.Path) - return &starlark.Filter{ - Name: spec.Starlark.Name, - Path: p, - FunctionFilter: runtimeutil.FunctionFilter{FunctionConfig: api}, - }, nil + sf := &starlark.Filter{Name: spec.Starlark.Name, Path: p} + + sf.FunctionConfig = api + sf.GlobalScope = r.GlobalScope + sf.ResultsFile = resultsFile + sf.DeferFailure = spec.DeferFailure + return sf, nil } + + if r.EnableExec && spec.Exec.Path != "" { + ef := &exec.Filter{Path: spec.Exec.Path, Args: spec.Exec.Args} + + ef.FunctionConfig = api + ef.GlobalScope = r.GlobalScope + ef.ResultsFile = resultsFile + ef.DeferFailure = spec.DeferFailure + return ef, nil + } + return nil, nil }