3

I am trying to make list of every command available on my linux (Lubuntu) machine. I would like to further work with that list in Python. Normally to list the commands in the console I would write "compgen -c" and it would print the results to stdout.

I would like to execute that command using Python subprocess library but it gives me an error and I don't know why.

Here is the code:

   #!/usr/bin/python

   import subprocess

   #get list of available linux commands
   l_commands = subprocess.Popen(['compgen', '-c'])

   print l_commands

Here is the error I'm getting:

   Traceback (most recent call last):
     File "commands.py", line 6, in <module>
       l_commands = subprocess.Popen(['compgen', '-c'])
     File "/usr/lib/python2.7/subprocess.py", line 679, in __init__
       errread, errwrite)
     File "/usr/lib/python2.7/subprocess.py", line 1249, in _execute_child
       raise child_exception
   OSError: [Errno 2] No such file or directory

I'm stuck. Could you guys help me with this? How to I execute the compgen command using subprocess?

Tim
  • 41,901
  • 18
  • 127
  • 145
xlogic
  • 1,509
  • 2
  • 11
  • 9

2 Answers2

3

compgen is a builtin bash command, run it in the shell:

from subprocess import check_output

output = check_output('compgen -c', shell=True, executable='/bin/bash')
commands = output.splitlines()

You could also write it as:

output = check_output(['/bin/bash', '-c', 'compgen -c'])

But it puts the essential part (compgen) last, so I prefer the first variant.

jfs
  • 399,953
  • 195
  • 994
  • 1,670
  • Thanks Sebastian, this works perfectly. I also found another solution based on the answer [here](http://stackoverflow.com/questions/5460923/run-bash-built-in-commands-in-python). You can also execute the command like this: `l_commands = Popen(["bash -c 'compgen -c'"], shell = True, stdin=PIPE, stdout=PIPE, stderr=STDOUT)` – xlogic May 08 '14 at 20:12
  • @user3573032: do not mix a list argument and `shell=True`. Also `shell=True` is redundant if you use `bash` in the command. I've updated the answer – jfs May 08 '14 at 21:38
0

I'm not sure what compgen is, but that path needs to be absolute. When I use subprocess, I spell out the exact page /absolute/path/to/compgen

Chris Hawkes
  • 11,923
  • 6
  • 58
  • 68
  • It's strange but when I try to locate compgen by 'which compgen', the output is null. But when I run 'compgen -c' in the terminal it gives me the list of available commands. – xlogic May 08 '14 at 19:33
  • 1
    @user3573032: `compgen` might be a shell function. Run in the shell: `type compgen` – jfs May 08 '14 at 19:41
  • I run `type compgen` and it is indeed a shell builtin. Knowing this, is there any way I can execute it with subprocess? – xlogic May 08 '14 at 19:51