from cmd import Cmd, (not working with class MyPrompt) - python

This is a helper command line in python, I was looking to add custom stuff for myself of course and was adding in a IP searcher. Have been getting this error for a while now, cant seem to figure it out and its critical to start my prompt. Any Tips appreciated, Good day.
from cmd import Cmd
import pyautogui as pag #Future#
import time #Debugging/Future#
import sys,os
clear = lambda : os.system('cls')
#############################################
from colorama import init
from ctypes.test.test_pickling import name
init(strip=not sys.stdout.isatty()) # strip colors if stdout is redirected
from termcolor import cprint
from pyfiglet import figlet_format
##############################################
class MyPrompt(Cmd):
#staticmethod
def do_lineage(self):
"""Switch to Lineage 2 Helper"""
print("Switching to Lineage 2 Helper....")
os.system(r"python C:\Users\David\eclipse-workspace\CMD\src\L2.py")
#staticmethod
def do_ip(self):
"""IP"""
print("Switching to IP stuff.... ")
os.system(r"python C:\Users\David\eclipse-workspace\CMD\src\Play.py")
#staticmethod
def do_quit(self):
"""Quits the program."""
print("Quitting...")
raise SystemExit
#staticmethod
def do_Movies(self,num):
"""1-3 different sites, or all for """
if num == 1:
print("https://genvideos.org")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=https://genvideos.org")
if num == 2:
print("https://www3.gomovies.sc")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=https://www3.gomovies.sc")
if num == 3:
print("https://vioozgo.org/")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=google.com")
if num == "all":
print("https://genvideos.org")
print("https://www3.gomovies.sc")
print("https://vioozgo.org/")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=google.com")
if __name__ == '__main__':
clear()
prompt = MyPrompt()
prompt.prompt = '> '
prompt.cmdloop(cprint(figlet_format('--------\nHelper\n--------', font='smslant'), "yellow"))
My error:
Traceback (most recent call last):
File "C:\Users\David\eclipse-workspace\CMD\src\Cmdd.py", line 1, in <module>
from cmd import Cmd
ImportError: cannot import name 'Cmd'
This was previously working, must of changed something. Where am I going wrong?

When I encounter an issue like this, I like drop myself into a debugger in the command line and start poking around.
To do this, I add import pdb; pdb.set_trace() near where the issue is happening, in this case at the top of the file. Once in debug mode, I starting looking at the object that is causing the issue. I'd probably start with changing the import statement to import the full cmd module, and then I would dir said module. You can print cmd.__file__ to see where it is coming from
import cmd
import pdb; pdb.set_trace()
# code stops here so you can start digging
# dir(cmd) will tell you what properties the module has
# cmd.__file__ will tell you the file path
from cmd import Cmd
import pyautogui as pag #Future#
import time #Debugging/Future#
import sys,os
clear = lambda : os.system('cls')
#############################################
from colorama import init
from ctypes.test.test_pickling import name
init(strip=not sys.stdout.isatty()) # strip colors if stdout is redirected
from termcolor import cprint
from pyfiglet import figlet_format
##############################################
class MyPrompt(Cmd):
#staticmethod
def do_lineage(self):
"""Switch to Lineage 2 Helper"""
print("Switching to Lineage 2 Helper....")
os.system(r"python C:\Users\David\eclipse-workspace\CMD\src\L2.py")
#staticmethod
def do_ip(self):
"""IP"""
print("Switching to IP stuff.... ")
os.system(r"python C:\Users\David\eclipse-workspace\CMD\src\Play.py")
#staticmethod
def do_quit(self):
"""Quits the program."""
print("Quitting...")
raise SystemExit
#staticmethod
def do_Movies(self,num):
"""1-3 different sites, or all for """
if num == 1:
print("https://genvideos.org")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=https://genvideos.org")
if num == 2:
print("https://www3.gomovies.sc")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=https://www3.gomovies.sc")
if num == 3:
print("https://vioozgo.org/")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=google.com")
if num == "all":
print("https://genvideos.org")
print("https://www3.gomovies.sc")
print("https://vioozgo.org/")
os.system("C:\Program Files (x86)\Google\Chrome\Application\chrome --app=google.com")
if __name__ == '__main__':
clear()
prompt = MyPrompt()
prompt.prompt = '> '
prompt.cmdloop(cprint(figlet_format('--------\nHelper\n--------', font='smslant'), "yellow"))

Related

from multithreading.decorators import measure_time - Why thet dont works?

import time
Pycharm for some reason highlights the .decorators, but I install all
from multithreading.decorators import measure_time # <-- Problem with thet line
def tick():
print('tick')
time.sleep(1)
print('tock')
#measure_time
def main():
for _ in range(3):
tick()
if __name__ == '__main__':
main()
image
why decorators and measure_time are underlined

Python subprocess.Popen not stop when using kill()

I am trying to restart a python process, when file changes are made.
Dir Structure
/root
|_ test.py
|_ main.py
main.py
import os
import sys
import shutil
import _thread
import subprocess
from watchdog.observers import Observer
from watchdog.events import FileSystemEventHandler, FileSystemEvent
cwd = os.getcwd()
pj = os.path.join
exists = os.path.exists
class Reloader(FileSystemEventHandler):
def __init__(self, openProc: subprocess.Popen = None, cmd=""):
super().__init__()
self.__cmd = cmd
self.openProc = openProc if openProc else subprocess.Popen(self.__cmd, cwd=cwd, shell=True)
def on_any_event(self, event):
if event.is_directory:
return
_, ext = os.path.splitext(event.src_path)
if ext[1:] in ["py", "cpp", "c", "h", "hpp"]:
print(":: CHANGES DETECTED, RELOADING ::")
print("--changed file '{}'--".format(event.src_path))
self.killProc()
def killProc(self):
self.openProc.kill()
def getInput():
global cwd
cwd = os.getcwd()
return input("⚡>" + cwd + ">")
if __name__ == "__main__":
while True:
userInput = getInput()
split = userInput.split(" ")
print("Starting CMD Command With Reloader...")
while True:
try:
event_handler = Reloader(cmd=split)
observer = Observer()
observer.schedule(event_handler, cwd, recursive=True)
observer.start()
while event_handler.openProc.poll() is None:
pass
observer.stop()
except KeyboardInterrupt:
break
test.py
import time
c = 0
while True:
c+=1
print(c)
time.sleep(1)
When I run that:
E:\electrocli>py main.py
⚡>E:\electrocli>py test.py
Starting CMD Command With Reloader...
1
2
3
4
:: CHANGES DETECTED, RELOADING ::
--changed file 'E:\electrocli\test.py'--
:: CHANGES DETECTED, RELOADING ::
--changed file 'E:\electrocli\test.py'--
5
1
6
2
7
3
This shows that, the older process, whis should be revoked by subprocess.Popen.kill has not ended. I want to kill the old process, and start the new one. Is there any way to do that? Or, is there any mistake in my code?

Send file pointer to python thread and update file pointer

I have a python program with a thread and the thread should write into a file. I will spawn a thread from the main program. Now on new day trigger I will change the file pointer in the main program and I want the thread also to take the new file to write the data to the file.
I have a code which will take global variable and do this task. But is there any other better way of doing this?
#!/usr/bin/env python
import sys
import threading
import time
filePtr = None
import time
def fileWriteTh():
global filePtr
time.sleep(2)
filePtr.write("from the thrread this should in file 2")
def main():
global filePtr
filePtr = open("test1.txt","ab")
fileThread = threading.Thread(target=fileWriteTh)
fileThread.start()
if new_day_trigger:
filePtr.close()
filePtr = open("test2.txt","ab")
fileThread.join()
if __name__ == "__main__":
main()
This is the new code that is written:
#!/usr/bin/env python
import sys
import threading
import time
class SendPacket(object):
fileDesc = None
def __init__(self, fd):
super(SendPacket, self).__init__()
SendPacket.fileDesc = fd
def printFromInstance(self,var):
print var
SendPacket.fileDesc.write(var)
time.sleep(3)
print var
SendPacket.fileDesc.write(var)
def startabc(self, someVar):
self.printFromInstance(someVar)
#classmethod
def printVar(cls, printStr):
print printStr
cls.fileDesc.write(printStr)
#classmethod
def changeClsFile(cls, newFd):
cls.fileDesc = newFd
def main():
filePtr = open("test1.txt","ab")
sendPack_inst = SendPacket(filePtr)
fileThread = threading.Thread(target=sendPack_inst.startabc, args=("test1",))
fileThread.start()
time.sleep(2)
filePtr.close()
filePtr = open("test2.txt","ab")
SendPacket.changeClsFile(filePtr)
fileThread.join()
filePtr.close()
if __name__ == "__main__":
main()
Like this:
#!/usr/bin/env python
import sys
import thread
import time
class _fileACT :
def __init__(self):
self.trigger = 0
self.flag = True
self.msg = ""
self.files = (open("test1.txt","ab"),open("test2.txt","ab"))
def run(self,pssrg):
while self.flag :
if self.msg != "" :
self.files[self.trigger].write(self.msg)
self.msg = ""
def test(self,pssrg):
for i in range(20):
time.sleep(1)
if i %2 != 0 :
self.trigger = 0
elif i %2 != 1:
self.trigger = 1
self.msg = "%0.3d test-1,asdasdasd\n"%i
time.sleep(0.5)
print "wait..."
self.flag = False
for e in self.files : e.close()
print "can exit !"
if __name__ == "__main__":
fileACT = _fileACT()
thread.start_new_thread(fileACT.run,(None,))
thread.start_new_thread(fileACT.test,(None,))
We have three variables, filename, last opened file name and message. Two files, only False and True will be sufficient (of course you can use index for multiple files). We've written a test function into the class because we don't want our main cycle to freeze. The file selection is done with ' trigger ', but the previous and next file name is not the same, the previous closes.
The important point in the thread is that the time delay is strictly unavailable! The time delay is always applied to the trigger. The time delay cannot be placed in the main loop. An instance of access from outside the class is also attached. I hope it helps.

Python cmd module - Resume prompt after asynchronous event

I am maintaining an operator terminal based on cmd. The customer asked for an alerting behavior. e.g. a message shown onscreen when some asynchronous event occurs. I made a thread that periodically checks for alerts, and when it finds some, it just prints them to stdout.
This seems to work OK, but it doesn't seem very elegant, and it has a problem:
Because cmd doesn't know an alert happened, the message is followed onscreen by blank. The command prompt is not reprinted, and any user input is left pending.
Is there a better way to do asynchronous alerts during Python cmd? With the method as-is, can I interrupt cmd and get it to redraw its prompt?
I tried from my thread to poke a newline in stdin using StringIO, but this is not ideal, and I haven't gotten it work right.
Example code:
import cmd, sys
import threading, time
import io
import sys
class MyShell(cmd.Cmd):
intro = '*** Terminal ***\nType help or ? to list commands.\n'
prompt = '> '
file = None
def alert(self):
time.sleep(5)
print ('\n\n*** ALERT!\n')
sys.stdin = io.StringIO("\n")
def do_bye(self, arg):
'Stop recording, close the terminal, and exit: BYE'
print('Exiting.')
sys.exit(0)
return True
def do_async(self, arg):
'Set a five second timer to pop an alert.'
threading.Thread(target=self.alert).start()
def emptyline(self):
pass
def parse(arg):
'Convert a series of zero or more numbers to an argument tuple'
return tuple(map(int, arg.split()))
if __name__ == '__main__':
MyShell().cmdloop()
I ended up overriding Cmd.cmdloop with my own version, replacing the readlines() with my own readlines that use non-blocking terminal IO.
Non-Blocking terminal IO info here:
Non-Blocking terminal IO
Unfortunately, this opens another can trouble in that it is messy and breaks auto-completion and command history. Fortunately, the customer was OK with having to push Enter to redo the prompt, so I don't need to worry about it anymore.
Incomplete example code showing the non-blocking terminal input approach:
import cmd, sys
import threading, time
import io
import os
if os.name=='nt':
import msvcrt
def getAnyKey():
if msvcrt.kbhit():
return msvcrt.getch()
return None
else:
import sys
import select
import tty
import termios
import atexit
def isData():
return select.select([sys.stdin], [], [], 0) == ([sys.stdin], [], [])
old_settings = termios.tcgetattr(sys.stdin)
def restoreSettings():
global old_settings
termios.tcsetattr(sys.stdin, termios.TCSADRAIN, old_settings)
atexit.register(restoreSettings)
def getAnyKey():
try:
if isData():
return sys.stdin.read(1)
return None
except:
pass
return None
class MyShell(cmd.Cmd):
prompt = '> '
file = None
realstdin = sys.stdin
mocking=False
breakReadLine=False
def alert(self):
time.sleep(5)
print ('\n\n*** ALERT!\n')
self.breakReadLine=True
# ----- basic commands -----
def do_bye(self, arg):
'Stop recording, close the terminal, and exit: BYE'
print('Exiting.')
sys.exit(0)
return True
def do_async(self, arg):
'Set a five second timer to pop an alert.'
threading.Thread(target=self.alert).start()
def emptyline(self):
pass
def myReadLine(self):
sys.stdout.flush()
self.breakReadLine=False
line=''
while not self.breakReadLine:
c=getAnyKey()
if not c is None:
c=c.decode("utf-8")
if c=='\x08' and len(line):
line=line[0:-1]
elif c in ['\r','\n']:
print('\n')
return line
else:
line+=c
print(c,end='')
sys.stdout.flush()
def mycmdloop(self, intro=None):
"""Repeatedly issue a prompt, accept input, parse an initial prefix
off the received input, and dispatch to action methods, passing them
the remainder of the line as argument.
"""
self.preloop()
if self.use_rawinput and self.completekey:
try:
import readline
self.old_completer = readline.get_completer()
readline.set_completer(self.complete)
readline.parse_and_bind(self.completekey+": complete")
except ImportError:
pass
try:
if intro is not None:
self.intro = intro
if self.intro:
self.stdout.write(str(self.intro)+"\n")
stop = None
while not stop:
if self.cmdqueue:
line = self.cmdqueue.pop(0)
else:
if self.use_rawinput:
try:
print(self.prompt,end='')
line = self.myReadLine()#input(self.prompt)
except EOFError:
line = 'EOF'
else:
self.stdout.write(self.prompt)
self.stdout.flush()
line = self.myReadLine()#self.stdin.readline()
if not line is None:
line = line.rstrip('\r\n')
line = self.precmd(line)
stop = self.onecmd(line)
stop = self.postcmd(stop, line)
self.postloop()
finally:
if self.use_rawinput and self.completekey:
try:
import readline
readline.set_completer(self.old_completer)
except ImportError:
pass
def cmdloop_with_keyboard_interrupt(self, intro):
doQuit = False
while doQuit != True:
try:
if intro!='':
cintro=intro
intro=''
self.mycmdloop(cintro)
else:
self.intro=''
self.mycmdloop()
doQuit = True
except KeyboardInterrupt:
sys.stdout.write('\n')
def parse(arg):
'Convert a series of zero or more numbers to an argument tuple'
return tuple(map(int, arg.split()))
if __name__ == '__main__':
#MyShell().cmdloop()
MyShell().cmdloop_with_keyboard_interrupt('*** Terminal ***\nType help or ? to list commands.\n')

Import module containing input/output

I have a python module file (func.py) and a unit test file (f_test.py):
# func.py
def f(x):
return x + 1
x = input("Enter x: "))
print("f(x): " + str(f(x)))
and
# f_test.py
import unittest
from func import f
class MyTest(unittest.TestCase):
def test(self):
self.assertEqual(f(1), 2)
When I run f_test.py I expect the test suite to be executed (successfully).
Instead however I see the following input:
Finding files... done.
Importing test modules ... Enter x:
If I comment out the input/output lines from func.py then I get the expected behaviour.
How do I achieve it without modifying func.py?
When you import func, all the code inside is run. Running the definition def f(x)... is what creates the function f.
You can distinguish between importing and running a file by using if __name__=='__main__'.
For instance:
# func.py
def f(x):
return x + 1
if __name__ == '__main__':
x = input("Enter x: "))
print("f(x): " + str(f(x)))
When you run func.py, __name__=='__main__' will be true. When you import it, it will be false (__name__ will be 'func' instead).
Of course, the correct answer is to modify func.py. If you absolutely, positively, won't modify func.py, then you could redirect standard input:
# f_test.py
import os
import sys
import unittest
oldstdin, sys.stdin = sys.stdin, StringIO.StringIO('7')
try:
from func import f
finally:
sys.stdin = oldstdin
class MyTest(unittest.TestCase):
def test(self):
self.assertEqual(f(1), 2)
You need to add to the bottom of f_test.py:
if __name__ == '__main__':
unittest.main()
This way the tests will be executed when the file is run (I forget this more times than I would like to admit).

Categories