versiones guia espaƱol descargar actualizar python logging subprocess

python - guia - Ejecutar subproceso e imprimir salida al registro



qgis manual (2)

Estoy seguro de que existe la forma de hacerlo sin crear un archivo temporal para almacenar la salida del proceso

Simplemente debe verificar la documentación de Popen , en particular sobre stdout y stderr :

stdin , stdout y stderr especifican la entrada estándar del programa ejecutado, la salida estándar y los identificadores de archivo de error estándar, respectivamente. Los valores válidos son PIPE , un descriptor de archivo existente (un entero positivo), un objeto de archivo existente y None . PIPE indica que se debe crear una nueva canalización para el hijo. Con la configuración predeterminada de None , no se producirá ninguna redirección; los manejadores de archivos del niño serán heredados de los padres. Además, stderr puede ser STDOUT , lo que indica que los datos stderr del proceso hijo deben capturarse en el mismo identificador de archivo que para stdout .

Así que puede ver que puede usar un objeto de archivo o el valor PIPE . Esto le permite utilizar el método de communicate() para recuperar la salida:

from StringIO import StringIO process = subprocess.Popen(arguments, stdout=subprocess.PIPE, stderr=subprocess.STDOUT) output, error = process.communicate() log_subprocess_output(StringIO(output))

Reescribiría tu código como:

import shlex import logging import subprocess from StringIO import StringIO def run_shell_command(command_line): command_line_args = shlex.split(command_line) logging.info(''Subprocess: "'' + command_line + ''"'') try: command_line_process = subprocess.Popen( command_line_args, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, ) process_output, _ = command_line_process.communicate() # process_output is now a string, not a file, # you may want to do: # process_output = StringIO(process_output) log_subprocess_output(process_output) except (OSError, CalledProcessError) as exception: logging.info(''Exception occured: '' + str(exception)) logging.info(''Subprocess failed'') return False else: # no exception was raised logging.info(''Subprocess finished'') return True

Estoy buscando la manera de llamar shell scripts desde python y escribir su stdout y stderr a un archivo utilizando el registro. Aquí está mi código:

import logging import tempfile import shlex import os def run_shell_command(command_line): command_line_args = shlex.split(command_line) logging.info(''Subprocess: /"'' + command_line + ''/"'') process_succeeded = True try: process_output_filename = tempfile.mktemp(suffix = ''subprocess_tmp_file_'') process_output = open(process_output_filename, ''w'') command_line_process = subprocess.Popen(command_line_args,/ stdout = process_output,/ stderr = process_output) command_line_process.wait() process_output.close() process_output = open(process_output_filename, ''r'') log_subprocess_output(process_output) process_output.close() os.remove(process_output_filename) except: exception = sys.exc_info()[1] logging.info(''Exception occured: '' + str(exception)) process_succeeded = False if process_succeeded: logging.info(''Subprocess finished'') else: logging.info(''Subprocess failed'') return process_succeeded

Y estoy seguro de que existe la forma de hacerlo sin crear un archivo temporal para almacenar la salida del proceso. ¿Algunas ideas?


Puede intentar pasar la tubería directamente sin almacenar en memoria intermedia toda la salida del subproceso en la memoria:

from subprocess import Popen, PIPE, STDOUT process = Popen(command_line_args, stdout=PIPE, stderr=STDOUT) with process.stdout: log_subprocess_output(process.stdout) exitcode = process.wait() # 0 means success

donde log_subprocess_output() podría verse así:

def log_subprocess_output(pipe): for line in iter(pipe.readline, b''''): # b''/n''-separated lines logging.info(''got line from subprocess: %r'', line)