Foo.cmd no generará líneas en proceso (en el sitio web)

Tengo un problema para entender las entradas y salidas de la clase ProcessStartInfo en .NET. Yo uso esta clase para ejecutar progtwigs .exe como FFmpeg sin ningún problema.

Pero cuando uso ProcessStartInfo para iniciar un progtwig .cmd como un simple foo.cmd que solo contiene @echo @echo Hello world , no genera nada.

  ProcessStartInfo oInfo = new ProcessStartInfo(@"C:\Program Files (x86)\itms\foo.cmd") { UseShellExecute = false, RedirectStandardError = true, RedirectStandardOutput = true, CreateNoWindow = true }; using (Process p = new Process()) { p.StartInfo = oInfo; p.OutputDataReceived += new DataReceivedEventHandler(transporter_OutputDataReceived); p.Start(); p.BeginOutputReadLine(); p.WaitForExit(); } private void transporter_OutputDataReceived(object sender, DataReceivedEventArgs e) { Response.Write(e.Data + " - line
"); }

He visto un montón de ejemplos, donde la gente usa cmd.exe para iniciar el progtwig .cmd y lo he intentado, pero sin éxito. El progtwig simplemente sigue cargando indefinidamente.

  ProcessStartInfo oInfo = new ProcessStartInfo("cmd", "/c start foo.cmd") { UseShellExecute = false, RedirectStandardError = true, RedirectStandardOutput = true, CreateNoWindow = true, WorkingDirectory = @"C:\Program Files (x86)\itms" }; 

El progtwig foo.cmd funciona y da buenos resultados cuando se usa una herramienta de línea de comandos en Windows y en Mac.

¿Podría alguien desmitificar esto por mí?

Gracias

EDITAR

El código se comporta correctamente cuando se ejecuta localmente. El problema surge cuando ejecuto el código en nuestro sitio web. O bien el progtwig no puede ejecutarse o la salida está deshabilitada de alguna manera.

Solo cmd.exe está devolviendo la salida “cmd”, “/ c dir” ´ es, por ejemplo, devolviendo información sobre el contenido de la carpeta actual.

¿Podría esto realmente ser un problema de permiso?

Encontré la respuesta y publicaré una solución para cualquier persona interesada.

El origen del problema es bastante difícil de depurar, porque el problema se originó en cómo IIS maneja los usuarios y los procesos.

Como pensé, no había nada malo con el código en sí.

Responder

En IIS, un sitio web se está ejecutando en un AppPool. A AppPool se le asigna una identidad de usuario. La identidad predeterminada es una cuenta virtual incorporada llamada ApplicationPoolIdentity . Este usuario no tiene el privilegio de llamar a ningún script de comandos / lotes externos (que yo sepa).

Proporcionar un nombre de usuario, contraseña y dominio para un usuario administrativo al iniciar un nuevo proceso, no me solucionó nada. Puede ser que simplemente haya entendido mal todo el concepto.

El uso de en webconfig tampoco resolvió nada. Aparentemente, esto se debe a que el usuario de AppPool asignado sigue siendo el autor de todos los procesos.

Lo que realmente me molestó fue que podía ejecutar archivos .exe, pero no archivos .cmd o .bat.

La solución para mí fue crear un nuevo usuario con privilegios para ejecutar scripts por lotes y seleccionar a ese usuario como el usuario de AppPool en IIS.

Edición: Como mencioné en los comentarios, el usuario con el que estoy trabajando se crea en un servidor de Active Directory ya que este servidor de archivos en particular está en un recurso compartido de red. El usuario forma parte del grupo de servidores locales IIS_IUSRS en mi servidor web y tiene privilegios de lectura / escritura / ejecución en la carpeta donde se almacenan los progtwigs ejecutables.

Edit2: La solución funciona para cuentas de usuarios locales y siempre que el usuario forme parte del grupo de servidores locales IIS_IUSRS y tenga privilegios de lectura / escritura / ejecución en la carpeta donde se almacenan los progtwigs ejecutables.

Este es un código ligeramente modificado pero debería darle una mejor idea sobre la clase

 ProcessStartInfo info = new ProcessStartInfo(); info.Arguments = "/CC:\Program Files (x86)\itms\foo.cmd"; info.WindowStyle = ProcessWindowStyle.Hidden; info.CreateNoWindow = true; info.FileName = "cmd.exe"; // or C:\Program Files (x86)\itms\foo.cmd with no info.Arguments info.UseShellExecute = false; info.RedirectStandardOutput = true; using (Process process = Process.Start(info)) { using (StreamReader reader = process.StandardOutput) { string result = reader.ReadToEnd(); Console.WriteLine(result); } } 

Esto redireccionará la salida de la ventana de cmd a la consola, solo ajuste según sea necesario.

necesitarás usarlo de esta manera

  using (Process p = Process.Start(oInfo)) { ..... 

El motivo se debe a que Process.Start () y Process.Star (startinfo) funcionan de forma ligeramente diferente

Process.Start () : inicia (o reutiliza) el recurso de proceso especificado por la propiedad StartInfo de este componente de proceso y lo asocia con el componente.

Valor de retorno

Escriba: System.Boolean true si se inicia un recurso de proceso; falso si no se inicia ningún nuevo recurso de proceso (por ejemplo, si se reutiliza un proceso existente).

Process.Start (StartInfo) : inicia el recurso de proceso especificado por el parámetro que contiene la información de inicio del proceso (por ejemplo, el nombre de archivo del proceso a iniciar) y asocia el recurso con un nuevo componente de proceso.

Valor de retorno

Tipo: System.Diagnostics.Process Un nuevo componente de proceso que está asociado con el recurso de proceso, o nulo si no se inicia ningún recurso de proceso (por ejemplo, si se reutiliza un proceso existente).