public static async Task RunShellCommandAsync()

in src/common/details/helpers/process_helpers.cs [125:208]


        public static async Task<ProcessOutput> RunShellCommandAsync(string command, string arguments, Dictionary<string, string>? addToEnvironment = null, Action<string>? stdOutHandler = null, Action<string>? stdErrHandler = null, Action<string>? mergedOutputHandler = null, bool captureOutput = true)
        {
            SHELL_DEBUG_TRACE($"COMMAND: {command} {arguments} {DictionaryToString(addToEnvironment)}");

            var redirectOutput = captureOutput || stdOutHandler != null || stdErrHandler != null || mergedOutputHandler != null;

            var outDoneSignal = new ManualResetEvent(false);
            var errDoneSignal = new ManualResetEvent(false);
            var sbOut = new StringBuilder();
            var sbErr = new StringBuilder();
            var sbMerged = new StringBuilder();

            var stdOutReceived = (string? data) => {
                if (data != null)
                {
                    sbOut.AppendLine(data);
                    sbMerged.AppendLine(data);
                    if (stdOutHandler != null) stdOutHandler(data);
                    if (mergedOutputHandler != null) mergedOutputHandler(data);
                }
                else
                {
                    outDoneSignal.Set();
                }
            };
            var stdErrReceived = (string? data) => {
                if (data != null)
                {
                    sbErr.AppendLine(data);
                    sbMerged.AppendLine(data);
                    if (stdErrHandler != null) stdErrHandler(data);
                    if (mergedOutputHandler != null) mergedOutputHandler(data);
                }
                else
                {
                    errDoneSignal.Set();
                }
            };

            Process? process;
            try
            {
                process = StartShellCommandProcess(command, arguments, addToEnvironment, redirectOutput);
            }
            catch (Exception processException)
            {
                SHELL_DEBUG_TRACE($"ERROR: {processException}");
                return new ProcessOutput()
                {
                    ExitCode = -1,
                    StdError = processException.ToString()
                };
            }

            if (process != null)
            {
                if (redirectOutput)
                {
                    process.OutputDataReceived += (sender, e) => stdOutReceived(e.Data);
                    process.ErrorDataReceived += (sender, e) => stdErrReceived(e.Data);
                    process.BeginOutputReadLine();
                    process.BeginErrorReadLine();
                }

                await process.WaitForExitAsync();

                if (redirectOutput)
                {
                    outDoneSignal.WaitOne();
                    errDoneSignal.WaitOne();
                }
            }

            var output = new ProcessOutput();
            output.StdOutput = sbOut.ToString().Trim(' ', '\r', '\n');
            output.StdError = sbErr.ToString().Trim(' ', '\r', '\n');
            output.MergedOutput = sbMerged.ToString().Trim(' ', '\r', '\n');
            output.ExitCode = process?.ExitCode ?? -1;

            if (!string.IsNullOrEmpty(output.StdOutput)) SHELL_DEBUG_TRACE($"---\nSTDOUT\n---\n{output.StdOutput}");
            if (!string.IsNullOrEmpty(output.StdError)) SHELL_DEBUG_TRACE($"---\nSTDERR\n---\n{output.StdError}");

            return output;
        }