Calling the main function after running explorer (python) - python

I wrote a app that restarts explorer.exe but the problem is that after i re-open explorer.exe it should call the main function again, but it doesn't.
The 'funny' stuff that i found is that if i dont open explorer.exe, the main function will be called as it should.
import os
def sendCmd(command):
return os.system(command)
# Main function
def Main():
sendCmd('cls')
q = input() # Checks for input
if q == "1": # If the option 1 is selected
sendCmd("taskkill /f /im explorer.exe") # Kills explorer
sendCmd("explorer.exe") # Opens explorer
Main()
Thanks!

nice question, my guess is that python uses the main thread when explorer.exe is open so it is not going forward to the Main() function and does not do that command. try to close explorer.exe manually and check if the program calls the main function.
Anyway, To solve that you can call the sendCmd("explorer.exe") in another thread and your program will continue to the Main() line (I would use while True in this case instead of recursion https://www.geeksforgeeks.org/difference-between-recursion-and-iteration/)
th = threading.Thread(target=sendCmd, args=('explorer.exe', ))
# Start the thread
th.start()

Related

Python file that recursively executes itself

I want to make my program recursively call itself, so I tried this. However, for some reason even though the code does execute I get the desired effect only in Pycharms debugger. Any ideas?
os.execv(sys.executable, [sys.executable, file] + sys.argv)
Note: I don't really need to pass any arguments to the new iteration
In my code I have an object called mcp. When this objects internal state changes to restart I need to start the main function all over again. Note that the internal state of the system is correct. I managed to work around it by using os.system("")
if __name__ == "__main__":
mcp = Mcp()
mcp.start()
while mcp.internal_state == State.Running.value:
time.sleep(1)
if mcp.internal_state == State.ShutDown.value or mcp.internal_state == State.Restart.value:
mcp.wait()
if mcp.internal_state == State.Restart.value:
#os.execv(sys.executable, [sys.executable, __file__] + sys.argv)
os.system("Python rinzler.py")

Re-run script in Python 3.5

How do I get main to run again without executing the whole script again?
import sys #importing module that is used to exit the script
def main ():
#doing stuff
main ()
#Re-run the script - looking for a cleaner way to do this!
def restart ():
restart = input("Press any key + Enter to start again, or x + Enter to exit.")
if(restart != "x"):
exec(open("./calc.py").read())
# not sure how to run main() again without calling out the script name again?
else:
print ("Exiting!")
sys.exit ((main))
restart ()
#End of Program
You can re-run the main module-method as many times as you want by directly calling main() sequentially:
def main( ):
# Code goes here...
return;
main();
main();
main();
However, if you want the user-interaction like your restart method has, you might want to consider defining main with an optional parameter (one that has a default value) that controls whether you ask to re-run the method or not.
def main( argv, AskRestart= True ):
# Main code goes here....
if ( AskRestart ):
# User interaction code goes here ...
return;
Also, you can look into the atexit package in Python 3.5.1 to see how you can assign a method to be run only when exiting the interpreter:
https://docs.python.org/3.5/library/atexit.html
That would allow you to do whatever you want and then when everything is done, give someone the option of restarting the entire module. This would remove the reliance on the exec call, and be a more coherent and simpler approach to getting the exact same expected functionality.
In addition to Tommy's great advice, (I'm not sure of your goal in continually restarting main() as main is an empty function that doesn't do anything yet, but..) one way to have main continually repeat until the user enters x may be to use a while True loop:
import sys #importing module that is used to exit the script
def main ():
#doing stuff
restart() # <-- use main to restart()
#Re-run the script - looking for a cleaner way to do this!
def restart ():
restart = raw_input("Press any key + Enter to start again, or x + Enter to exit.")
while True: # <-- key to continually restart main() function
if(restart != "x"):
exec(open("./calc.py").read())
# not sure how to run main() again without calling out the script name again?
main() # <-- restart main
else:
print ("Exiting!")
sys.exit ((main))
restart ()
#End of Program
Hope this also helps!

How do I abort reading a user's input in Python 3.x?

I have a thread that monitors user input which looks like this:
def keyboard_monitor(temp): #temp is sys.stdin
global flag_exit
while True:
keyin = temp.readline().rstrip().lower()
if keyin == "exit":
flag_exit = True
print("Stopping...")
if flag_exit == True:
break
If I type exit the flag is properly set and all the other threads terminate. If another one of my threads sets the flag, this thread refuses to finish because it's hanging on the user input. I have to input something to get it to finish. How do I change this code so that the program finishes when the flag is set externally?
Its hard to tell exactly what is going wrong without more of your code, but as an easy solution you could rather exit() which is a python built in. This should reliably terminate the application, also sys.exit()
From wim's comment:
You can use the atexit module to register clean up handlers
import atexit
def cleanup():
pass
# TODO cleanup
atexit.register(cleanup)

How to interrupt a program while it's running?

I wrote a program that reads a text file and runs an .exe for every line in the text file. This results in opening a new command line window for every time i run the .exe. The windows do close on their own once the current task is finished, but the problem is as follows:
If i have 100 lines in the text file, this means that i call the .exe file 100 times. My problem with that is if i want to cancel the run after it already started, i have to click on the red "X" to close every window one after the another.
What i am trying to do is have some sort of a command interrupt the running program and either close all upcoming windows or just stop the for loop from running.
Is it possible to write into the console a command to interrupt the current running code?
Would it be better to use some sort of a key event listener? If so, are there any built-in key listeners in Python? I can't seem to find any. Does that mean that i have to install Pygame just so i can use a key event listener?
Maybe i should try to listen to the command line and detect an exit code on one of the windows that i manually close and that way end the for loop?
There are a few ways you could go about this. But pretty much you have one main issue - you need some sort of flag that can be switched such that the code will know it must stop. For instance, if the code is working in a while-loop, it should check at the start of this loop if the flag is valid, or if the flag is telling the loop to stop...
while flag:
# do code
There are a few ways to implement this flagging like operation for your needs. I will discuss the threading option. First, you need to understand how threading works, and then you need to mold your script such that instead of "running an executable" for each line of the text file, you would read the text file, and put all the lines into a queue, then you would have a few threads that read from that queue, and perform the desired action (like running an executable) but instead of running an external executable, you should mimick this with Python, this thread should be a daemon thread.. and it should have a main loop which checks if a flag that exists in the parent thread is turned on...
Below is an example:
from threading import Thread
from Queue import Queue
import sys
import time
class Performer():
def __init__(self):
self.active = False
self.queue = Queue()
def action(self, line):
pass # your code should be here
def operate(self, text_file, threads=5):
with open(text_file) as f:
for line in f:
self.queue.put(line)
self.active = True
thread_pool = []
for i in range(threads):
t = Thread(target=self.__thread, name=('worker-%d' % i))
t.daemon = True
t.start()
thread_pool.append(t)
while self.active:
try:
if self.queue.empty():
break
except KeyboardInterrupt:
self.active = False
sys.exit('user + keyboard = byebye')
else:
time.sleep(1)
def __thread(self):
while self.active:
if not self.queue.empty():
try:
self.action(self.queue.get())
except Exception:
pass # do something here

run a python program on a new thread

I have two programs
program1.py is like commandline interface which takes command from user
program2.py has the program which runs the relevant program as per the command.
Program 1 has also has an quit_program() module
In our simple universe.. lets say I have just one command and just one program
So lets say...
program1.py
def main():
while True:
try:
command = raw_input('> ')
if command == "quit" :
return
if command == '':
continue
except KeyboardInterrupt:
exit()
parseCommand(command)
And then I have:
if commmand == "hi":
say_hi()
Now program2 has
def say_hi():
#do something..
Now there can be two cases...
Either say_hi() completes in which case no issue...
But what i want is that if user enters a command (say: end)
then this say_hi() is terminated in between..
But my current implementation is very sequential.. I mean I dont get to type anything on my terminal untill the execution is completed..
Somethng tells me that the say_hi() should be running on another thread?
I am not able to think straight about this.
Any suggestions?
Thanks
The threading module is what you are looking for.
import threading
t = threading.Thread(target=target_function,name=name,args=(args))
t.daemon = True
t.start()
The .daemon option makes it so you don't have to explicitly kill threads when your app exits... Threads can be quite nasty otherwise
Specific to this question and the question in the comments, the say_hi function can be called in another thread as such:
import threading
if commmand == "hi":
t = threading.Thread(target=say_hi, name='Saying hi') #< Note that I did not actually call the function, but instead sent it as a parameter
t.daemon = True
t.start() #< This actually starts the thread execution in the background
As a side note, you must make sure you are using thread safe functions inside of threads. In the example of saying hi, you would want to use the logging module instead of print()
import logging
logging.info('I am saying hi in a thread-safe manner')
You can read more in the Python Docs.

Categories

Resources