2010-11-23 15 views
123

en mi máquina local que ejecuta un script en Python que contiene esta líneala ejecución de comandos Bash en Python

bashCommand = "cwm --rdf test.rdf --ntriples > test.nt" 
os.system(bashCommand) 

Esto funciona bien.

Luego ejecutar el mismo código en un servidor y me sale el siguiente mensaje de error

'import site' failed; use -v for traceback 
Traceback (most recent call last): 
File "/usr/bin/cwm", line 48, in <module> 
from swap import diag 
ImportError: No module named swap 

Así que lo que hice es entonces me inserta un "bashCommand de impresión" que me imprime entonces el comando en el terminal antes lo ejecuta con os.system().

Obvio que vuelvo a tener el error (causado por os.system (bashCommand)) pero antes de ese error imprime el comando en el terminal. Entonces me acaba de copiar lo que la producción y pegar una copia en el terminal y pulsa enter y funciona ...

¿Alguien tiene una idea de lo que está pasando :(?

+1

Parece que hay una diferencia en el medio ambiente en función de cómo ejecutar 'cwm'. Tal vez tiene alguna configuración en su '.bashrc' que configura el entorno para el uso interactivo de bash. –

+0

¿Intentó ejecutar el comando desde la línea de comando cuando inició sesión en el servidor? Tu publicación solo dice que "pegaste [it] en la terminal". –

+0

@Sven: sí Quise decir que ejecuté el comando directamente en la terminal del servidor – mkn

Respuesta

30

llama con subproceso

import subprocess 
subprocess.Popen("cwm --rdf test.rdf --ntriples > test.nt") 

el error que está recibiendo parece deberse a que no existe ningún módulo de intercambio en el servidor, debe instalar intercambio en el servidor y ejecute el guión de nuevo

+2

El módulo 'swap' obviamente está allí, porque funciona el comando desde el shell. –

+1

No en el servidor, cuando lo ejecuta en el servidor, hay un error de importación. –

+0

@mkn: "Entonces simplemente copié esa salida e hice una copia pegada en la terminal y presioné enter y funciona ..."- ¿Probé esto en el servidor o en su máquina? –

168

no utilice os.system. se ha desaprobado en favor de subprocess. De docs: "Este módulo tiene la intención de reemplazar varios módulos y funciones anteriores: os.system, os.spawn".

Al igual que en su caso:

bashCommand = "cwm --rdf test.rdf --ntriples > test.nt" 
import subprocess 
process = subprocess.Popen(bashCommand.split(), stdout=subprocess.PIPE) 
output, error = process.communicate() 
+6

Esto no hizo lo que yo quería cuando neede d para hacer un 'cd 'path \ to \ somewhere'' seguido de otro comando bash que se debe ejecutar en algún lugar. @ user225312 – AWrightIV

+1

puedes simplemente configurar el comando como este "nano /home/you/path/a.txt" o el comando que quieras, incluso puedes | & – icebox19

+10

@AWrightIV Si necesita que su subproceso se ejecute en un directorio de trabajo particular, puede usar el argumento 'cwd' para Popen: ' subprocess.Popen (..., cwd = 'path \ to \ somewhere') ' – waterproof

8

De acuerdo con el error se echa en falta un paquete llamado de intercambio en el servidor. Esto /usr/bin/cwm lo requiere. Si está en Ubuntu/Debian, instale python-swap usando aptitude.

+0

pero funciona cuando lo ejecuto directamente en el terminal ... entonces el intercambio debe estar allí, ¿no? – mkn

+0

hay dos opciones. o bien no puede encontrar 'swap' o no debería haberlo importado en primer lugar. ¿puedes 'importar swap' manualmente? ¿Funciona? – kichik

+0

hm No puedo. Si comienzo python con tipear python en el terminal y luego escribo el intercambio de importación, entonces aparece el error "ImportError: ningún módulo llamado swap". Lo extraño es que funciona cuando ejecuto el comando cwm directamente en la terminal del servidor – mkn

11

Es posible que utilice el programa bash, con el parámetro -c para ejecutar los comandos:

bashCommand = "cwm --rdf test.rdf --ntriples > test.nt" 
output = subprocess.check_output(['bash','-c', bashCommand]) 
+0

'subprocess.check_output (bashCommand, shell = True)' hace lo mismo. Si su comando es una cadena estática, intente analizarla en una lista usted mismo y evite el 'shell = True'; aunque en este caso necesita el shell para la redirección de todos modos, de lo contrario tendrá que refactorizarlo a Python puro - 'con open ('test.nt', 'w') como dest: output = subprocess.check_output ([ 'cwm', '- rdf', 'test.rdf', '--ntriples'], stdout = dest, shell = False) ' – tripleee

5

Puede utilizar 'subproceso', pero siempre me sentí que no era una forma 'Pythonic' de hacerlo Así que creé Sultan (plug sin vergüenza) que hace que sea fácil ejecutar funciones de línea de comandos.

https://github.com/aeroxis/sultan

+1

¡Bien hecho! Mucho más limpio y más intuitivo que el subproceso. – mjd2

+0

¡Muchas gracias! ¡Estoy feliz de escucharlo! –

Cuestiones relacionadas