Каков правильный порядок вызова класса процесса с WaitForExit? - PullRequest
0 голосов
/ 11 апреля 2011

У меня проблемы с расшифровкой документации msdn.

Я хочу вызвать класс процесса.Если процесс, который вызывает класс процесса, завершается, я хочу, чтобы мой код завершился, но я хочу, чтобы "StandardOutput" и "StandardError" были записаны в файл журнала.

Если процесс, который вызывает класс процесса, зависает(и не завершается) Я хочу, чтобы мой код завершил работу по таймауту и ​​закрыл процесс после определенного времени ожидания, но я все еще хочу, чтобы "StandardOutput" и "StandardError" были записаны в файл журнала.

ИтакУ меня есть это как мой код:

using (Process p = new Process())
{
    p.StartInfo.FileName = exePathArg;
    p.StartInfo.RedirectStandardOutput = true;
    p.StartInfo.RedirectStandardError = true;
    p.StartInfo.Arguments = argumentsArg;
    p.StartInfo.UseShellExecute = false;
    p.StartInfo.CreateNoWindow = true;

    try
    {
        p.Start();
        p.WaitForExit(timeToWaitForProcessToExit);

        StreamReader standardOutput = p.StandardOutput;
        StreamReader standardError = p.StandardError;

        retDirects.Add("StandardOutput", standardOutput.ReadToEnd());
        retDirects.Add("StandardError", standardError.ReadToEnd());    
    }
    catch (Exception ex)
    {
        //nothing to do with this yet
    }
    finally
    {
        try
        {
            p.Kill();
        }
        catch { }
    }
}

Это правильный способ делать вещи?

1 Ответ

0 голосов
/ 11 апреля 2011

Не совсем, вам нужен таймер для установки времени ожидания. Этот код может помочь вам:

Process process = Process.Start(startInfo);

process.EnableRaisingEvents = true;

bool execTimeout = false;

// this call back will be called when timer ticks, Timeout for process.
TimerCallback callBack = (_process) =>
{
    // if the process didn't finish exexuting
    // and the timeout has reached 
    // then kill the process.
    if (!(_process as Process).HasExited)
    {
        execTimeout = true;
        (_process as Process).Kill();
    }
};

int timeout = 4000; // 4 seconds
System.Threading.Timer timer = new System.Threading.Timer(callBack, 
                                     process, timeout, Timeout.Infinite);

// block untill finishing executing [Sync calling]
process.WaitForExit();

// Disable the timer. because the process has finished executing.
timer.Change(Timeout.Infinite, Timeout.Infinite);

// if the process has finished by timeout [The timer which declared above]
// or finished normally [success or failed].
if (execTimeout)
{
    // Write in log here
}
else
{
    string standardOutput = process.StandardOutput.ReadToEnd();
    string standardError = process.StandardError.ReadToEnd();
}

Удачи!

...