fix: only enable built-in core utils by default on windows

Andrey Nering created

Or we risk making them failing on other platforms due to
incompatibilities.

Fixes #1341

Change summary

internal/shell/coreutils.go | 19 +++++++++++++++++++
internal/shell/shell.go     | 12 +++++++++++-
2 files changed, 30 insertions(+), 1 deletion(-)

Detailed changes

internal/shell/coreutils.go 🔗

@@ -0,0 +1,19 @@
+package shell
+
+import (
+	"os"
+	"runtime"
+	"strconv"
+)
+
+var useGoCoreUtils bool
+
+func init() {
+	// If CRUSH_CORE_UTILS is set to either true or false, respect that.
+	// By default, enable on Windows only.
+	if v, err := strconv.ParseBool(os.Getenv("CRUSH_CORE_UTILS")); err == nil {
+		useGoCoreUtils = v
+	} else {
+		useGoCoreUtils = runtime.GOOS == "windows"
+	}
+}

internal/shell/shell.go 🔗

@@ -241,7 +241,7 @@ func (s *Shell) execPOSIX(ctx context.Context, command string) (string, string,
 		interp.Interactive(false),
 		interp.Env(expand.ListEnviron(s.env...)),
 		interp.Dir(s.cwd),
-		interp.ExecHandlers(s.blockHandler(), coreutils.ExecHandler),
+		interp.ExecHandlers(s.execHandlers()...),
 	)
 	if err != nil {
 		return "", "", fmt.Errorf("could not run command: %w", err)
@@ -257,6 +257,16 @@ func (s *Shell) execPOSIX(ctx context.Context, command string) (string, string,
 	return stdout.String(), stderr.String(), err
 }
 
+func (s *Shell) execHandlers() []func(next interp.ExecHandlerFunc) interp.ExecHandlerFunc {
+	handlers := []func(next interp.ExecHandlerFunc) interp.ExecHandlerFunc{
+		s.blockHandler(),
+	}
+	if useGoCoreUtils {
+		handlers = append(handlers, coreutils.ExecHandler)
+	}
+	return handlers
+}
+
 // IsInterrupt checks if an error is due to interruption
 func IsInterrupt(err error) bool {
 	return errors.Is(err, context.Canceled) ||