Reputation: 55
I have an issue with Tkinter, I'm running this script "index.py" after clicking the button, the script starts running, but I do not get an output anywhere, any remarks?
from tkinter import *
import threading
import subprocess
root = Tk()
frame = Frame(root, width=300, height=300)
frame.pack()
def myClick():
t = threading.Thread(target=run())
t.start()
def run():
arg = "python index.py"
process = subprocess.check_output(arg)
lab = Label(frame, text=process)
lab.pack()
myButton = Button(root, text="run", padx=40, pady=10, command=myClick)
myButton.pack(pady=40)
root.mainloop()
Upvotes: 0
Views: 160
Reputation: 43495
The way you are starting a subprocess
does not work on all platforms.
As acw1668 commented, it works fine on ms-windows. But it does not work on POSIX platforms like macOS, Linux or *BSD:
> python
Python 3.9.13 (main, May 31 2022, 12:56:40)
[Clang 13.0.0 ([email protected]:llvm/llvm-project.git llvmorg-13.0.0-0-gd7b669b3a on freebsd13
Type "help", "copyright", "credits" or "license" for more information.
>>> import subprocess
>>> arg = "python index.py"
>>> process = subprocess.check_output(arg)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/local/lib/python3.9/subprocess.py", line 424, in check_output
return run(*popenargs, stdout=PIPE, timeout=timeout, check=True,
File "/usr/local/lib/python3.9/subprocess.py", line 505, in run
with Popen(*popenargs, **kwargs) as process:
File "/usr/local/lib/python3.9/subprocess.py", line 951, in __init__
self._execute_child(args, executable, preexec_fn, close_fds,
File "/usr/local/lib/python3.9/subprocess.py", line 1821, in _execute_child
raise child_exception_type(errno_num, err_msg, err_filename)
FileNotFoundError: [Errno 2] No such file or directory: 'python index.py'
>>>
This is due to the different way that process creation works on different platforms.
Look closely at the last line of the error message.
You have told subprocess
to execute a file named python<space>index.py
, which of course doesn't exist.
Convert arg
into a list of strings, and it will work:
>>> arg = ["python", "index.py"]
>>> process = subprocess.check_output(arg)
>>> print(process)
b'Hello from index.py\n'
The following code should work everywhere:
def run():
arg = ["python", "index.py"]
process = subprocess.check_output(arg)
lab = Label(frame, text=process)
lab.pack()
EDIT1:
IDE's can do weird things with the standard output of your programs. And they might interact with scripts using subprocess
, multiprocessing
or threading
in non-inuitive ways. When in doubt, first run your program from a command prompt. If it works there, it is an IDE problem.
In general, if you have any problem with a python script in an IDE or interactive environment, try saving it to a file and running it from a command prompt first.
Upvotes: 1
Reputation: 5694
I dont know what you are trying to achieve exactly, but the issue is with the process line
.
So this correction works:
import threading
import subprocess
from tkinter import *
root = Tk()
frame = Frame(root, width=300, height=300)
frame.pack()
def myClick():
t = threading.Thread(target=run())
t.start()
def run():
arg = "python index.py"
# process = subprocess.check_output(arg) # <--- error is here
lab = Label(frame, text='hello') # <--- this works
lab.pack()
myButton = Button(root, text="run", padx=40, pady=10, command=myClick)
myButton.pack(pady=40)
root.mainloop()
So the result looks like this:
Every time you click it says "hello".
Upvotes: 0