Выполнить команду promt обработать asnyc и получить результат

#.net #vb.net #winforms #asynchronous #process

#.net #vb.net #winforms #асинхронный #процесс

Вопрос:

Мне нужно выполнить процесс commandpromt асинхронно и получить результат выполнения. в настоящее время у меня есть этот код

 Public Function ExecuteCommandSync(ByVal command As Object) As String
    Dim result As String = Nothing
    Try
        Dim procStartInfo As New System.Diagnostics.ProcessStartInfo("cmd", "/c " amp; Convert.ToString(command))
        procStartInfo.RedirectStandardOutput = True
        procStartInfo.UseShellExecute = False
        procStartInfo.CreateNoWindow = True
        Dim proc As New System.Diagnostics.Process()
        proc.StartInfo = procStartInfo
        proc.Start()
        result = proc.StandardOutput.ReadToEnd()
        Console.WriteLine(result)
    Catch objException As Exception
    End Try
    Return result
End Function
  

Пожалуйста, помогите мне преобразовать это в async без использования потока. возможно ли это?

Спасибо

Ответ №1:

Ниже приведен класс, который, я полагаю, достигает того, что вы ищете.

Процесс уже запущен асинхронно, я считаю, что то, что вы ищете, управляется событиями и скрыто. По какой-то причине вы специально хотите блокирующий вызов или боитесь многопоточности?

Если я не нахожусь на базе, и вы хотите, чтобы он блокировался, дайте мне знать, что мы тоже можем это сделать, хотя я не могу себе представить, почему.

По сути, это позволяет вам создавать командную оболочку и незаметно взаимодействовать с ней.

 #Region " Imports "

Imports System.Threading
Imports System.ComponentModel

#End Region

Namespace Common

    Public Class CmdShell

#Region " Variables "

        Private WithEvents ShellProcess As Process

#End Region

#Region " Events "

        ''' <summary>
        ''' Event indicating an asyc read of the command process's StdOut pipe has occured.
        ''' </summary>
        Public Event DataReceived As EventHandler(Of CmdShellDataReceivedEventArgs)

#End Region

#Region " Public Methods "

        Public Sub New()
            ThreadPool.QueueUserWorkItem(AddressOf ShellLoop, Nothing)
            Do Until Not ShellProcess Is Nothing : Loop
        End Sub

        ''' <param name="Value">String value to write to the StdIn pipe of the command process, (CRLF not required).</param>
        Public Sub Write(ByVal value As String)
            ShellProcess.StandardInput.WriteLine(value)
        End Sub

#End Region

#Region " Private Methods "

        Private Sub ShellLoop(ByVal state As Object)
            Try
                Dim SI As New ProcessStartInfo("cmd.exe")
                With SI
                    .Arguments = "/k"
                    .RedirectStandardInput = True
                    .RedirectStandardOutput = True
                    .RedirectStandardError = True
                    .UseShellExecute = False
                    .CreateNoWindow = True
                    .WorkingDirectory = Environ("windir")
                End With
                Try
                    ShellProcess = Process.Start(SI)
                    With ShellProcess
                        .BeginOutputReadLine()
                        .BeginErrorReadLine()
                        .WaitForExit()
                    End With
                Catch ex As Exception
                    With ex
                        Trace.WriteLine(.Message)
                        Trace.WriteLine(.Source)
                        Trace.WriteLine(.StackTrace)
                    End With
                End Try
            Catch ex As Exception
                With ex
                    Trace.WriteLine(.Message)
                    Trace.WriteLine(.Source)
                    Trace.WriteLine(.StackTrace)
                End With
            End Try
        End Sub

        Private Sub ShellProcess_ErrorDataReceived(ByVal sender As Object, ByVal e As System.Diagnostics.DataReceivedEventArgs) Handles ShellProcess.ErrorDataReceived
            If Not e.Data Is Nothing Then RaiseEvent DataReceived(Me, New CmdShellDataReceivedEventArgs(e.Data))
        End Sub

        Private Sub ShellProcess_OutputDataReceived(ByVal sender As Object, ByVal e As System.Diagnostics.DataReceivedEventArgs) Handles ShellProcess.OutputDataReceived
            If Not e.Data Is Nothing Then RaiseEvent DataReceived(Me, New CmdShellDataReceivedEventArgs(e.Data amp; Environment.NewLine))
        End Sub

#End Region

    End Class

    <EditorBrowsable(EditorBrowsableState.Never)> _
       Public Class CmdShellDataReceivedEventArgs : Inherits EventArgs
        Private _Value As String

        Public Sub New(ByVal value As String)
            _Value = value
        End Sub

        Public ReadOnly Property Value() As String
            Get
                Return _Value
            End Get
        End Property

    End Class

End Namespace