Using subprocess.run python module with different languages

Question:

i’m building tester for programs in different languages, but I’m not able to get C program working, currently the command is called like this:

codeResult = subprocess.run(self.createRunCommand(currLanguage, file),
                                        input = codeToTest,
                                        shell = True, 
                                        timeout = TIMEOUT, 
                                        capture_output=True)

and createRunCommand() returns:

def createRunCommand(self, language, file):
    if language == '.py':
        command = f'python {file}'
    elif language == '.c':
        if not os.path.exists(f'C:/<myPath>/{file}.out'):
            command = f'gcc -std=c11 {file} -o C:/<myPath>/{file}.out 
                        ./C:/<myPath>/{file}.out'
        else:
            command = f'./C:/<myPath>/{file}.out'
    elif language == '.java':
        command = f''
    elif language == '.cpp':
        command = f''    

    return command

the input and test itself is good, as it runs correctly with a python program, but I cannot figure out how to setup C (and probably other compiled first languages).

Asked By: KubaJ

||

Answers:

You’ll need multiple command invocations for (e.g.) C/C++, so have your createRunCommand return multiple.

I also changed things up here to

  1. automatically figure out the language from the extension of the filename
  2. use a list of arguments instead of a string; it’s safer
  3. use sys.executable for the current Python interpreter, and shutil.which("gcc") to find gcc.
import os
import shlex
import shutil
import subprocess
import sys


def get_commands(file):
    """
    Get commands to (compile and) execute `file`, as a list of subprocess arguments.
    """
    ext = os.path.splitext(file)[1].lower()
    if ext == ".py":
        return [(sys.executable, file)]
    if ext in (".c", ".cpp"):
        exe_file = f"{file}.exe"
        return [
            (shutil.which("gcc"), "-std=c11", file, "-o", exe_file),
            (exe_file,),
        ]
    raise ValueError(f"Unsupported file type: {ext}")


filename = "foo.py"

for command in get_commands(filename):
    print(f"Running: {shlex.join(command)}")
    code_result = subprocess.run(command, capture_output=True)
Answered By: AKX
Categories: questions Tags: , ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.