def read_from_script(self): line = "" while self.running[0]: c = self.ch.stdout.read(1) if c == ",": c = "." if c == "": break line += c if c == "\n": line = line.strip(" \r\t\n%") if len(line) == 0: print "Read empty string from script" # TODO: Probably need another way of informing. TBD else: if line[0] == 'C': self.mtx.acquire() self.cpu = line[2:] self.mtx.release() elif line[0] == 'M': self.mtx.acquire() self.mem = line[2:] self.mtx.release() line = "" log_debug2( '%s:%s.read_from_script()' % (_this_file, self.__class__.__name__), 'WinLocalStats: line-"%s", cpu-"%s", mem-"%s"\n' % (line, self.cpu, self.mem))
def shutdown_event(self): self.poll_control = self.skip_poll if self.dbconn: self.dbconn.disconnect() self.dbconn = None self.poll_control = self.stopped log_debug2('%s:%s.shutdown_event()' % (_this_file, self.__class__.__name__), 'DBStatsDataSource shutdown. poll_control = %i\n' % self.poll_control)
def poll(self): if self.running[0] is False: self.ch.stdin.write("exit\r\n") self.ch.stdin.flush() return self.ch.stdin.write("cpu\r\n") self.ch.stdin.flush() self.ch.stdin.write("mem\r\n") self.ch.stdin.flush() value = self.get_mem() try: value = float(value) except ValueError: log_debug2('%s:%s.poll()' % (_this_file, self.__class__.__name__), 'Can not convert mem value "%r" to float\n' % value) value = None if value is not None: self.mem_widget[0].set_value(value) self.ctrl_be.uitask(self.mem_widget[0].set_description, "Mem: " + str(int(value)) + "%") value = self.get_cpu() try: value = float(value) except ValueError: value = None if value is not None: self.cpu_widget[0].set_value(value / 100) self.ctrl_be.uitask(self.cpu_widget[0].set_description, "CPU: " + str(int(value)) + "%")
def get_password_for( self, service_type ): # Raises OperationCancelledError if user cancels pwd dlg. force_reset = False if self.pwd_store.has_key(service_type): if self.pwd_store[service_type] is None: force_reset = True else: return self.pwd_store[service_type] details = self.get_password_parameters(service_type) if not details: # No password needed for this service_type return None # special case for UAC used in windows if details == "UAC": return "UAC" title, service, account = details grt.log_debug2( '%s:get_password_for()' % self.__class__.__name__, 'request password for "%s" => "%s", "%s", "%s"\n' % (service_type, title, service, account)) accepted, password = mforms.Utilities.find_or_ask_for_password( title, service, account, force_reset) if accepted: if not password: password = "" self.pwd_store[service_type] = password.encode("utf8") return password else: raise OperationCancelledError("Password input cancelled")
def server_started_event(self): self.poll_control = self.started if self.dbconn: self.dbconn.disconnect() self.dbconn = None self.dbconn = self.ctrl_be.get_new_sql_connection() self.poll_control = self.polling log_debug2('%s:%s.server_started_event()' % (_this_file, self.__class__.__name__), 'DBStatsDataSource server started. poll_control = %i\n' % self.poll_control)
def save_file_content_and_backup(self, path, content, backup_extension, as_admin = False, admin_password = None): # Check if dir, where config file will be stored is writable dirname, filename = splitpath(path) if not as_admin and not self.is_dir_writable(dirname.strip(" \r\t\n")): raise PermissionDeniedError("Cannot write to directory %s" % dirname) if self.ssh is not None: ## Get temp dir for using as tmpdir tmpdir, status = self.process_ops.get_cmd_output("echo %temp%") if type(tmpdir) is unicode: tmpdir = tmpdir.encode("utf8") if type(tmpdir) is str: tmpdir = tmpdir.strip(" \r\t\n") if tmpdir[1] == ":": tmpdir = tmpdir[2:] else: log_debug(_this_file, '%s: Temp directory path "%s" is not in expected form. The expected form is something like "C:\\Windows\\Temp"\n' % (self.__class__.__name__, tmpdir) ) tmpdir = None log_debug2(_this_file, '%s: Got temp dir: "%s"\n' % (self.__class__.__name__, tmpdir) ) else: tmpdir = None if not tmpdir: tmpdir = dirname tmpfilename = tmpdir + r"\workbench-temp-file.ini" log_debug(_this_file, '%s: Remotely writing contents to temporary file "%s"\n' % (self.__class__.__name__, tmpfilename) ) log_debug3(_this_file, '%s: %s\n' % (self.__class__.__name__, content) ) self.ssh.set_contents(tmpfilename, content) if backup_extension: log_debug(_this_file, '%s: Backing up "%s"\n' % (self.__class__.__name__, path) ) backup_cmd = "copy /y " + quote_path_win(path) + " " + quote_path_win(path+backup_extension) msg, code = self.process_ops.get_cmd_output(backup_cmd) if code != 0: print backup_cmd, "->", msg log_error(_this_file, '%s: Error backing up file: %s\n' % (self.__class__.__name__, backup_cmd+'->'+msg) ) raise RuntimeError("Error backing up file: %s" % msg) copy_to_dest = "copy /y " + quote_path_win(tmpfilename) + " " + quote_path_win(path) delete_tmp = "del " + quote_path_win(tmpfilename) log_debug(_this_file, '%s: Copying file to final destination: "%s"\n' % (self.__class__.__name__, copy_to_dest) ) msg, code = self.process_ops.get_cmd_output(copy_to_dest) if code != 0: print copy_to_dest, "->", msg log_error(_this_file, '%s: Error copying temporary file over destination file: %s\n%s to %s\n' % (self.__class__.__name__, msg, tmpfilename, path) ) raise RuntimeError("Error copying temporary file over destination file: %s\n%s to %s" % (msg, tmpfilename, path)) log_debug(_this_file, '%s: Deleting tmp file: "%s"\n' % (self.__class__.__name__, delete_tmp) ) msg, code = self.process_ops.get_cmd_output(delete_tmp) if code != 0: print "Could not delete temporary file %s: %s" % (tmpfilename, msg) log_info(_this_file, '%s: Could not delete temporary file "%s": %s\n' % (self.__class__.__name__, tmpfilename, msg) ) else: raise Exception("No SSH session active, cannot save file remotely")
def server_stopped_event(self): self.poll_control = self.skip_poll if self.dbconn: self.dbconn.disconnect() self.dbconn = None self.poll_control = self.stopped log_debug2( '%s:%s.server_stopped_event()' % (_this_file, self.__class__.__name__), 'SqlDataSource server stopped. poll_control = %i\n' % self.poll_control)
def __init__(self, sql, mon_be): DataSource.__init__(self, "sql_source", mon_be, None) self.sql = sql self.mon_be = mon_be self.sources = {} self.rev_sources = {} self.dbconn = None self.ctrl_be.add_me_for_event("server_started", self) self.ctrl_be.add_me_for_event("server_stopped", self) self.ctrl_be.add_me_for_event("shutdown", self) self.poll_control = self.stopped log_debug2('%s:%s.__init__()' % (_this_file, self.__class__.__name__), 'DBStatsDataSource created. poll_control = %i\n' % self.poll_control)
def get_password_for( self, service_type, cached_only=False ): # Raises OperationCancelledError if user cancels pwd dlg. force_reset = False password_type = self.get_password_type(service_type) if self.pwd_store.has_key(password_type): if self.pwd_store[password_type] is None: force_reset = True else: return self.pwd_store[password_type] details = self.get_password_parameters(service_type) if not details: # No password needed for this service_type return None # special case for UAC used in windows if details == "UAC": return "UAC" title, service, account = details grt.log_debug2( "%s:get_password_for()" % self.__class__.__name__, 'request password for "%s" => "%s", "%s", "%s"\n' % (service_type, title, service, account), ) if cached_only: found, password = mforms.Utilities.find_password(service, account) if found: return password return None else: accepted, password = mforms.Utilities.find_or_ask_for_password(title, service, account, force_reset) if accepted: if not password: password = "" self.pwd_store[password_type] = password.encode("utf8") return password else: raise OperationCancelledError("Password input cancelled")
def run(self): sys.stdout.write('Thread started\n') # sys.stdout.write is thread safe while print isn't log_debug2(_this_file,"SSH Tunel thread started\n") # Create a socket and pick a random port number for it: self._listen_sock = socket.socket() while True: local_port = random.randint(1024, 65535) try: self._listen_sock.bind(('127.0.0.1', local_port)) self._listen_sock.listen(2) with self.lock: self.local_port = local_port break except socket.error, exc: sys.stdout.write('Socket error: %s for port %d\n' % (exc, local_port) ) err, msg = exc.args if err == 22: continue # retry self.notify_exception_error('ERROR',"Error initializing server end of tunnel", sys.exc_info()) raise exc finally:
def save_file_content_and_backup(self, path, content, backup_extension, as_admin = False, admin_password = None): # Check if dir, where config file will be stored is writable dirname, filename = splitpath(path) if not as_admin and not self.is_dir_writable(dirname.strip(" \r\t\n")): raise PermissionDeniedError("Cannot write to directory %s" % dirname) if self.ssh is not None: ## Get home dir for using as tmpdir homedir, status = self.process_ops.get_cmd_output("echo ~") if type(homedir) is unicode: homedir = homedir.encode("utf8") if type(homedir) is str: homedir = homedir.strip(" \r\t\n") else: homedir = None log_debug2(_this_file, '%s: Got home dir: "%s"\n' % (self.__class__.__name__, homedir) ) if not homedir: raise Exception("Unable to get path for remote home directory") tmpfilename = homedir + "/.wba.temp" log_debug(_this_file, '%s: Remotely writing contents to temporary file "%s"\n' % (self.__class__.__name__, tmpfilename) ) log_debug3(_this_file, '%s: %s\n' % (self.__class__.__name__, content) ) self.ssh.set_contents(tmpfilename, content) if backup_extension: log_debug(_this_file, '%s: Backing up %s\n' % (self.__class__.__name__, path) ) backup_cmd = "/bin/cp " + quote_path(path) + " " + quote_path(path+backup_extension) self.process_ops.exec_cmd(backup_cmd, as_admin, admin_password) copy_to_dest = "/bin/cp " + quote_path(tmpfilename) + " " + quote_path(path) delete_tmp = "/bin/rm " + quote_path(tmpfilename) log_debug(_this_file, '%s: Copying file to final destination: "%s"\n' % (self.__class__.__name__, copy_to_dest) ) self.process_ops.exec_cmd(copy_to_dest, as_admin, admin_password) log_debug(_this_file, '%s: Deleting tmp file: "%s"\n' % (self.__class__.__name__, delete_tmp) ) self.process_ops.exec_cmd(delete_tmp) else: raise Exception("No SSH session active, cannot save file remotely")
def is_rdbms_migratable(rdbms): rev_eng_module = None migration_module = None db_module = None for mname in dir(grt.modules): mod = getattr(grt.modules, mname) if not hasattr(mod, "getTargetDBMSName") or mod.getTargetDBMSName() != rdbms.name: continue name = mod.__name__ if name.startswith("Db") and hasattr(mod, "reverseEngineer"): rev_eng_module = mod if name.startswith("Db") and hasattr(mod, "migrateCatalog"): migration_module = mod if name.startswith("Db") and hasattr(mod, "fullyQualifiedObjectName"): db_module = mod if not rev_eng_module: grt.log_debug2("Migration", "RDBMS %s cannot be a migration source because it's missing a RE module\n" % rdbms.name) if not migration_module: grt.log_debug2("Migration", "RDBMS %s cannot be a migration source because it's missing a Migration module\n" % rdbms.name) if not db_module: grt.log_debug2("Migration", "RDBMS %s cannot be a migration source because it's missing a Db information module\n" % rdbms.name) return rev_eng_module and migration_module and db_module
def notify(self, msg_type, msg_object): log_debug2(_this_file, "tunnel_%i: %s %s\n" % (self.local_port, msg_type, msg_object)) self.q.put((msg_type, msg_object))
def local_run_cmd_linux(command, as_admin=False, admin_password=None, sudo_prefix=default_sudo_prefix, output_handler=None): # pexpect used only in linux import pexpect # wrap cmd if as_admin: command = wrap_for_sudo(command, sudo_prefix) script = command.strip(" ") if script is None or len(script) == 0: return None script_to_log = script temp_file = tempfile.NamedTemporaryFile() script = script + " > " + temp_file.name + " 2>&1; echo CMDRESULT$? >> " + temp_file.name result = None if "'" in script: log_debug2(_this_file, "local_run_cmd_linux(): ' found in script:\n%s\n" % script ) raise Exception("WBA: Internal error, unexpected character in script to be executed") if not as_admin: result = pexpect.run("/bin/bash -c '" + script + "'", withexitstatus=True) else: child = pexpect.spawn("/bin/bash -c '" + script + "'") # script should already have sudo prefix try: child.expect('assword', timeout=10) if admin_password is not None: child.write(admin_password + '\n') else: child.write("\n"); except pexpect.TIMEOUT: #though we are not able to get the expected output, the password is fed anyway if admin_password is not None: child.write(admin_password + '\n') else: child.write("\n") except pexpect.EOF: #Nothing we can do, client is terminatd for some reason, try to read anything available log_debug2(_this_file,"local_run_cmd_linux(): Pipe from sudo is closed. script =\n%s\n" % script ) text = "" if child.isalive(): should_quit_read_loop = False while not should_quit_read_loop and child.isalive(): try: current_text = child.read_nonblocking(256, 30) if current_text.find('EnterPasswordHere') >= 0: try: child.close() except: pass temp_file.close() raise InvalidPasswordError("Incorrect password for sudo") else: text += current_text except pexpect.TIMEOUT: pass except pexpect.EOF: should_quit_read_loop = True else: #Try to read text = child.read() child.close(); text = temp_file.read() temp_file.close() idx = text.rfind("CMDRESULT") if (idx != -1): retcode = int(text[idx+9:].strip(" \r\t\n")) if output_handler: output_handler(text[0:idx]) result = retcode log_debug3(_this_file, 'local_run_cmd_linux(): script="%s", ret="%s", text="%s"' % (script_to_log, str(result), text[:16].replace('\n', '')) ) return result
def __init__(self, ctrl_be, server_profile, running, cpu_widget): self.ctrl_be = ctrl_be self.ssh = None self.cpu = 0 self.mtx = threading.Lock() self.running = running self.cpu_widget = cpu_widget self.settings = server_profile self.remote_admin_enabled = self.settings.uses_ssh if not self.remote_admin_enabled: return self.ctrl_be.add_me_for_event("shutdown", self) #upload script. Get local name, open ftp session and upload to the directory # where mysql.ini is. self.script = None self.ssh = ctrl_be.open_ssh_session_for_monitoring() (dirpath, code) = self.ssh.exec_cmd("cmd /C echo %USERPROFILE%") # %APPDATA% is n/a for LocalService # which is a user sshd can be run dirpath = dirpath.strip(" \r\t\n") if code == 0 and dirpath is not None and dirpath != "%USERPROFILE%": script_path = App.get().get_resource_path("mysql_system_status_rmt.vbs") filename = "\"" + dirpath + "\\mysql_system_status_rmt.vbs\"" log_debug('%s:%s.__init__()' % (_this_file, self.__class__.__name__), 'Script local path is "%s". Will be uploaded to "%s"\n' % (script_path, filename) ) if script_path is not None and script_path != "": #print "Uploading file to ", filename try: f = open(script_path) self.ssh.exec_cmd("cmd /C echo. > " + filename) maxsize = 1800 cmd = "" for line in f: line = line.strip("\r\n") tline = line.strip(" \t") if len(tline) > 0: if tline[0] != "'": if len(cmd) > maxsize: self.ssh.exec_cmd("cmd /C " + cmd.strip(" &")) self.ssh.exec_cmd("cmd /C echo " + line + " >> " + filename) cmd = "" else: cmd += "echo " + line + " >> " + filename cmd += " && " if len(cmd) > 0: self.ssh.exec_cmd("cmd /C " + cmd.strip(" &")) cmd = "" self.script = "cscript //NoLogo " + filename + " /DoStdIn" #run ssh in a thread log_debug2('%s:%s.__init__()' % (_this_file, self.__class__.__name__), 'About to run "%s"\n' % self.script) self.chan = None self.out = "" self.read_thread = threading.Thread(target=self.ssh.exec_cmd, args=(self.script, Users.CURRENT, None, self.reader, 1, self.save_channel)) self.read_thread.setDaemon(True) self.read_thread.start() except IOError, e: self.ssh.close() self.ssh = None raise e
def log_debug2(msg): tb = traceback.extract_stack(limit=2) grt.log_debug2("%s:%s:%s"%(os.path.basename(tb[-2][0]),tb[-2][2],tb[-2][1]), msg)