def _start_node_from_profile(self, master, hostname, pkg, binary, usr, cfg={}): try: args = [] restart = False # test for start or not node = master.getNode("/%s" % binary) if node: param = get_rosparam(binary, master.masteruri) if set(param.keys()) == set(cfg.keys()): for k, v in param.items(): if v != cfg[k]: restart = True master.stop_node(node[0], True) break else: restart = True if restart: delete_rosparam(binary, master.masteruri) for pname, pval in cfg.items(): args.append('_%s:=%s' % (pname, pval)) self._main_window._progress_queue.add2queue( utf8(uuid.uuid4()), 'start %s on %s' % (binary, hostname), nm.starter().runNodeWithoutConfig, (utf8(hostname), pkg, utf8(binary), utf8(binary), args, master.masteruri, False, False, usr)) self._main_window._progress_queue.start() except Exception as me: rospy.logwarn("Can not start %s for %s: %s" % (binary, master.masteruri, utf8(me)))
def run(self): ''' ''' if self._masteruri: service_names = interface_finder.get_refresh_service( self._masteruri, self._wait) err_msg = '' for service_name in service_names: rospy.logdebug("service 'refresh' found on %s as %s", self._masteruri, service_name) if self._wait: rospy.wait_for_service(service_name) socket.setdefaulttimeout(3) refreshMasters = rospy.ServiceProxy(service_name, std_srvs.srv.Empty) try: _ = refreshMasters() self.ok_signal.emit(self._masteruri) except rospy.ServiceException, e: rospy.logwarn("ERROR Service call 'refresh' failed: %s", utf8(e)) self.err_signal.emit( self._masteruri, "ERROR Service call 'refresh' failed: %s" % utf8(err_msg), True) finally: socket.setdefaulttimeout(None)
def run(self): ''' ''' try: if self._target is not None: if 'pqid' in self._target.func_code.co_varnames: self._target(*self._args, pqid=self._id) else: self._target(*self._args) self.finished_signal.emit(self._id) else: self.error_signal.emit(self._id, 'No target specified') except InteractionNeededError as ine: self.request_interact_signal.emit(self._id, self.descr, ine) except DetailedError as err: self.error_signal.emit(self._id, err.title, err.value, err.detailed_text) except Exception: import traceback # print traceback.print_exc() formatted_lines = traceback.format_exc(1).splitlines() last_line = formatted_lines[-1] index = 1 while not last_line and len(formatted_lines) > index: index += 1 last_line = formatted_lines[-index] self.error_signal.emit( self._id, 'Progress Job Error', "%s failed:\n%s" % (utf8(self.descr), utf8(last_line)), utf8(traceback.format_exc(4))) rospy.logwarn("%s failed:\n\t%s", utf8(self.descr), utf8(last_line))
def loadCache(self, history_file): ''' Loads the content of the given file and return it as cache. @param history_file: the name of the history file @type history_file: C{str} @return: the dictionary with arguments @rtype: C{dict(str(name):[str(value), ...], ...)} ''' result = {} historyFile = os.path.join(nm.settings().cfg_path, history_file) if os.path.isfile(historyFile): with codecs.open(historyFile, 'r', encoding='utf-8') as f: line = utf8(f.readline()) while line: if line: line = line.strip() if line: key, sep, value = line.partition(':=') if sep: if key not in result.keys(): result[key] = [value] elif len(result[key]) <= nm.settings( ).param_history_length: result[key].append(value) line = utf8(f.readline()) return result
def data(self, role): if role == self.NAME_ROLE: return self.topic.name elif role == self.NODENAMES_ROLE: return utf8(self.topic.publisherNodes) + utf8(self.topic.subscriberNodes) else: return QStandardItem.data(self, role)
def storeCache(self, history_file, cache, history_len): ''' Stores the cache to a file. @param history_file: the name of the history file @type history_file: C{str} @param cache: the dictionary with values @type cache: C{dict} @param history_len: the maximal count of value for a key @type history_len: C{int} ''' ignored = dict() with codecs.open(os.path.join(nm.settings().cfg_path, history_file), 'w', encoding='utf-8') as f: for key in cache.keys(): count = 0 for value in cache[key]: if count < history_len: try: f.write(''.join([key, ':=', utf8(value), '\n'])) except UnicodeEncodeError, e: ignored[key] = (value, utf8(e)) except Exception: import traceback rospy.logwarn("Storing history aborted: %s", traceback.format_exc(3)) count += 1 else: break
def _kill_wo(self, host, pid, auto_pw_request=False, user=None, pw=None): rospy.loginfo("kill %s on %s", utf8(pid), host) if nm.is_local(host): os.kill(pid, signal.SIGKILL) rospy.loginfo("kill: %s", utf8(pid)) else: # kill on a remote machine cmd = ['kill -9', str(pid)] _, stdout, stderr, ok = nm.ssh().ssh_exec(host, cmd, user, pw, False, close_stdin=True) if ok: output = stdout.read() error = stderr.read() stdout.close() stderr.close() if error: rospy.logwarn("ERROR while kill %s: %s", utf8(pid), error) raise StartException( utf8(''.join( ['The host "', host, '" reports:\n', error]))) if output: rospy.logdebug("STDOUT while kill %s on %s: %s", utf8(pid), host, output)
def _getSSH(self, host, user, pw=None, do_connect=True, auto_pw_request=False): ''' @return: the paramiko ssh client @rtype: U{paramiko.SSHClient<http://docs.paramiko.org/en/1.10/api/client.html>} @raise BadHostKeyException: - if the server's host key could not be verified @raise AuthenticationException: - if authentication failed @raise SSHException: - if there was any other error connecting or establishing an SSH session @raise socket.error: - if a socket error occurred while connecting ''' session = SSHhandler.SSH_SESSIONS.get(host, paramiko.SSHClient()) if session is None or (not session.get_transport() is None and (not session.get_transport().is_active() or session._transport.get_username() != user)): t = SSHhandler.SSH_SESSIONS.pop(host) del t if host in self.SSH_AUTH: del self.SSH_AUTH[host] session = SSHhandler.SSH_SESSIONS.get(host, paramiko.SSHClient()) if session._transport is None: session.set_missing_host_key_policy(paramiko.AutoAddPolicy()) while (session.get_transport() is None or not session.get_transport().authenticated) and do_connect: try: session.connect(host, username=user, password=pw, timeout=3, compress=True) self.SSH_AUTH[host] = user except Exception as e: if utf8(e) in [ 'Authentication failed.', 'No authentication methods available', 'Private key file is encrypted', 'No existing session' ]: if auto_pw_request: res, user, pw = self._requestPW(user, host) if not res: return None self.SSH_AUTH[host] = user else: raise AuthenticationRequest(user, host, utf8(e)) else: rospy.logwarn("ssh connection to %s failed: %s", host, utf8(e)) raise Exception(' '.join( ["ssh connection to", host, "failed:", utf8(e)])) else: SSHhandler.SSH_SESSIONS[host] = session if not session.get_transport() is None: session.get_transport().set_keepalive(10) return session
def __eq__(self, item): ''' Compares the value of parameter. ''' if isinstance(item, str) or isinstance(item, unicode): return utf8(self.value) == utf8(item) elif not (item is None): return utf8(self.value) == utf8(item.value) return False
def data(self, role): if role == self.NAME_ROLE: return self.name elif role == self.VALUE_ROLE: return utf8(self.value) elif role == self.TYPE_ROLE: return utf8(type(self.value).replace('<type \'').replace('\'>')) else: return QStandardItem.data(self, role)
def __eq__(self, item): ''' Compares the value of parameter. ''' if isstring(item): return utf8(self.value) == utf8(item) elif not (item is None): return utf8(self.value) == utf8(item.value) return False
def kill_screens(cls, node, grpc_url, auto_ok_request=True, user=None, pw=None): ''' Searches for the screen associated with the given node and kill this screens. :param str node: the name of the node those screen output to kill :param str grpc_url: the url of node manager daemon where the screen is running ''' if node is None or len(node) == 0: return False try: # get the available screens screens = nm.nmd().screen.get_screens(grpc_url, node) if screens: do_kill = True if auto_ok_request: from fkie_node_manager.detailed_msg_box import MessageBox result = MessageBox.question( None, "Kill SCREENs?", '\n'.join(list(screens.keys())), buttons=MessageBox.Ok | MessageBox.Cancel) if result == MessageBox.Ok: do_kill = True if do_kill: host = get_hostname(grpc_url) for sname, _nname in screens.items(): pid, _, _ = sname.partition('.') if pid: try: nm.nmd().monitor.kill_process( int(pid), grpc_url) # nm.starter()._kill_wo(host, int(pid), auto_ok_request, user, pw) except Exception: import traceback rospy.logwarn( "Error while kill screen (PID: %s) on host '%s': %s", utf8(pid), utf8(host), traceback.format_exc(1)) nm.nmd().screen.wipe_screens(grpc_url) # if nm.is_local(host): # SupervisedPopen([screen.SCREEN, '-wipe'], object_id='screen -wipe', description="screen: clean up the socket with -wipe") # else: # nm.ssh().ssh_exec(host, [screen.SCREEN, '-wipe'], close_stdin=True, close_stdout=True, close_stderr=True) except nm.AuthenticationRequest as e: raise nm.InteractionNeededError( e, cls.kill_screens, { 'node': node, 'grpc_url': grpc_url, 'auto_ok_request': auto_ok_request, 'user': user, 'pw': pw })
def _get_text(self, path): result = '' try: result = self._path_text[path] except KeyError: try: _, _, data = nm.nmd().file.get_file_content(path) result = utf8(data) except Exception as err: rospy.logwarn("can't get content: %s" % (utf8(err))) return result
def detect_version(package): ''' Try to detect the current version from git, installed VERSION/DATE files or package.xml ''' global VERSION global DATE if VERSION != 'unknown': return VERSION, DATE version = 'unknown' date = 'unknown' try: pkg_path = roslib.packages.get_pkg_dir(package) if pkg_path is not None and os.path.isfile("%s/VERSION" % pkg_path): try: with open("%s/VERSION" % pkg_path) as f: version = f.read() version = version.strip().decode('utf-8') with open("%s/DATE" % pkg_path) as f: datetag = f.read().split() if datetag: date = datetag[0].decode('utf-8') except Exception as err: sys.stderr.write("version detection error: %s" % utf8(err)) elif os.path.isdir("%s/../.git" % pkg_path): try: os.chdir(pkg_path) ps = SupervisedPopen(['git', 'describe', '--tags', '--dirty', '--always', '--abbrev=8'], stdout=subprocess.PIPE, object_id='get git version') output = ps.stdout.read().decode('utf-8') version = output.strip() ps = SupervisedPopen(['git', 'show', '-s', '--format=%ci'], stdout=subprocess.PIPE, object_id='get git date') output = ps.stdout.read().split() if output: date = output[0].decode('utf-8') except Exception as err: sys.stderr.write("version detection error: %s" % utf8(err)) else: ppath = roslib.packages.find_resource(package, 'package.xml') if ppath: doc = dom.parse(ppath[0]) version_tags = doc.getElementsByTagName("version") if version_tags: version = version_tags[0].firstChild.data version = version else: sys.stderr.write("version detection: no version tag in package.xml found!") else: sys.stderr.write("version detection: package.xml not found!") except Exception as err: sys.stderr.write("version detection error: %s" % utf8(err)) VERSION = version DATE = date return version, date
def _updateDisplay(self): self.display_clear_signal.emit() text = '<div style="font-family:Fixedsys,Courier,monospace; padding:10px;">\n' for index, addr_dict in self._discovered.items(): text += 'Network <b>%s</b>: <a href="%s">join</a><dl>' % ( utf8(index), utf8(index)) for addr, (hostname, ts) in addr_dict.items(): text += '<dt>%s <b><u>%s</u></b> %s, received messages: %s</dt>\n' % ( self._getTsStr(ts), utf8(hostname), utf8(addr), str(self._msg_counts[hostname])) text += '</dl><br>' text += '</div>' self.display_append_signal.emit(text)
def save(self, force=False): ''' Saves changes to the file. :return: saved, errors, msg :rtype: bool, bool, str ''' if self.isReadOnly(): return False, True, "Cannot save, the content was not loaded properly!" if force or self.document().isModified(): try: mtime = nm.nmd().file.save_file(self.filename, self.toPlainText().encode('utf-8'), 0 if force else self.file_mtime) self.file_mtime = mtime if mtime == 0: MessageBox.warning(self, "Warning", "File not saved and not error reported: %s" % os.path.basename(self.filename)) self.document().setModified(mtime == 0) ext = os.path.splitext(self.filename) # validate the xml structure of the launch files if ext[1] in self.CONTEXT_FILE_EXT: imported = False try: from lxml import etree imported = True parser = etree.XMLParser() etree.fromstring(self.toPlainText().encode('utf-8'), parser) except Exception as e: if imported: self.markLine(e.position[0]) return True, True, utf8(e) # validate the yaml structure of yaml files elif ext[1] in self.YAML_VALIDATION_FILES: try: import ruamel.yaml ruamel.yaml.load(self.toPlainText().encode('utf-8'), Loader=ruamel.yaml.Loader) except ruamel.yaml.MarkedYAMLError as e: return True, True, "YAML validation error: %s" % e return True, False, '' except IOError as ioe: if ioe.errno in [file_item.EFILE_CHANGED, file_item.EFILE_REMOVED]: result = MessageBox.question(self, "Changed file", "%s\n%s" % (utf8(ioe), "Save anyway?"), buttons=MessageBox.Yes | MessageBox.No) if result == MessageBox.Yes: return self.save(force=True) else: return False, True, utf8(ioe) except Exception as e: print(traceback.format_exc()) return False, True, utf8(e) return False, False, ''
def service_type_str(self): stype = '' try: stype = utf8(self.service.get_service_class(False)) except Exception: pass return stype
def on_heartbeat_received(self, msg, address, is_multicast): force_update = False with self.mutex: try: hostname = self._hosts[address[0]] except Exception: self.status_text_signal.emit("resolve %s" % address[0]) hostname = nm.nameres().hostname(utf8(address[0]), resolve=True) self._hosts[address[0]] = hostname try: (_version, _msg_tuple) = Discoverer.msg2masterState(msg, address) index = address[1] - self.default_port if index not in self._discovered: self._discovered[index] = dict() self._discovered[index][address] = (hostname, time.time()) if hostname not in self._msg_counts: self._msg_counts[hostname] = 0 self._msg_counts[hostname] += 1 self._received_msgs += 1 force_update = True except Exception: print(traceback.format_exc(1)) if force_update: self._updateDisplay()
def _requestPW(self, user, host): ''' Open the dialog to input the user name and password to open an SSH connection. ''' from python_qt_binding.QtCore import Qt from python_qt_binding import loadUi try: from python_qt_binding.QtGui import QDialog except Exception: from python_qt_binding.QtWidgets import QDialog result = False pw = None pwInput = QDialog() ui_file = os.path.join(os.path.dirname(os.path.realpath(__file__)), 'PasswordInput.ui') loadUi(ui_file, pwInput) pwInput.setWindowTitle(''.join(['Access for ', host])) pwInput.userLine.setText(utf8(user)) pwInput.pwLine.setText("") pwInput.pwLine.setFocus(Qt.OtherFocusReason) if pwInput.exec_(): result = True user = pwInput.userLine.text() pw = pwInput.pwLine.text() return result, user, pw
def delete_log(cls, nodename, grpc_uri, auto_pw_request=False, user=None, pw=None): ''' Deletes the log file associated with the given node. :param str nodename: the name of the node (with name space) :param str grpc_uri: uri of the node manager daemon where to delete log :raise Exception: on errors while resolving host :see: :meth:`fkie_node_manager.is_local()` ''' try: nm.nmd().screen.delete_log(grpc_uri, [nodename]) except Exception as err: rospy.logwarn("delete log using SSH because of error: %s" % utf8(err)) host = get_hostname(grpc_uri) if nm.is_local(host): screenLog = screen.get_logfile(node=nodename) pidFile = screen.get_pidfile(node=nodename) roslog = screen.get_ros_logfile(nodename) if os.path.isfile(screenLog): os.remove(screenLog) if os.path.isfile(pidFile): os.remove(pidFile) if os.path.isfile(roslog): os.remove(roslog) else: try: # output ignored: output, error, ok _, stdout, _, ok = nm.ssh().ssh_exec(host, [nm.settings().start_remote_script, '--delete_logs', nodename], user, pw, auto_pw_request, close_stdin=True, close_stdout=False, close_stderr=True) if ok: stdout.readlines() stdout.close() except nm.AuthenticationRequest as e: raise nm.InteractionNeededError(e, cls.delete_log, {'nodename': nodename, 'grpc_uri': host, 'auto_pw_request': auto_pw_request, 'user': user, 'pw': pw})
def _resolve_args(self, launch_node, resolve_args, path): ''' Load the content with xml parser, search for arg-nodes. :return: Dictionary with argument names and values :rtype: {name: value} ''' resolve_args_intern = dict(resolve_args) try: for child in launch_node.childNodes: if child.localName == 'arg' and child.hasAttributes(): aname = '' aval = '' for argi in range(child.attributes.length): arg_attr = child.attributes.item(argi) if arg_attr.localName == 'name': aname = arg_attr.value elif arg_attr.localName in ['value', 'default']: aval = arg_attr.value if aname and aname not in resolve_args_intern: for arg_key, args_val in resolve_args_intern.items(): aval = aval.replace('$(arg %s)' % arg_key, args_val) resolve_args_intern[aname] = aval except Exception as err: rospy.logwarn("%s in %s" % (utf8(err), path)) return resolve_args_intern
def ntpdate(cls, host, cmd, user=None, pw=None): ''' Opens the log file associated with the given node in a new terminal. :param str host: the host name or ip where the log file are :param str cmd: command to set the time :return: True, if a log file was found :rtype: bool :raise Exception: on errors while resolving host :see: :meth:`fkie_node_manager.is_local()` ''' mesg = "synchronize time on '%s' using '%s'" % (utf8(host), cmd) rospy.loginfo(mesg) title_opt = "ntpdate on %s" % str(host) # '%s on %s' % (cmd, host) if nm.is_local(host): cmd = nm.settings().terminal_cmd([cmd], title_opt, noclose=True) rospy.loginfo("EXEC: %s" % cmd) _ps = SupervisedPopen(shlex.split(cmd), object_id=cmd, description=mesg) else: _ps = nm.ssh().ssh_x11_exec(host, [ cmd, ';echo "";echo "this terminal will be closed in 10 sec...";sleep 10' ], title_opt, user) return False
def get_file_content(self, grpc_path='grpc://localhost:12321', force=False): file_size, file_mtime, file_content = (0, 0, '') try: if force: del self._cache_file_content[grpc_path] file_size, file_mtime, file_content = self._cache_file_content[ grpc_path] except KeyError: rospy.logdebug("get file content for %s:" % grpc_path) uri, path = nmdurl.split(grpc_path) fm, channel = self.get_file_manager(uri) try: file_size, file_mtime, file_content = fm.get_file_content(path) file_content = utf8(file_content) self._cache_file_content[grpc_path] = (file_size, file_mtime, file_content) except Exception as e: self.error.emit("get_file_content", "grpc://%s" % uri, grpc_path, e) raise e finally: self.close_channel(channel, uri) if hasattr(self, '_threads'): self._threads.finished("gfc_%s_%d" % (grpc_path, force)) self.file_content.emit(grpc_path, file_size, file_mtime, file_content) return file_size, file_mtime, file_content
def check_sensor(self): try: sensor_temps = psutil.sensors_temperatures() diag_level = 0 diag_vals = [] diag_msg = 'warn at >%.2f°C' % (self._cpu_temp_warn) warn_level = self._cpu_temp_warn if diag_level == DiagnosticStatus.WARN: warn_level = warn_level * 0.9 max_temp = 0 for sensor, shwtemps in sensor_temps.items(): if sensor == 'coretemp': for _label, current, hight, _critical in shwtemps: if hight is not None: self._cpu_temp_warn = hight if current > max_temp: max_temp = current if max_temp > warn_level: diag_msg = 'CPU Temperature: %.2f degree (warn level >%.2f)' % ( max_temp, self._cpu_temp_warn) diag_vals.append(KeyValue(key='Max [degree]', value=max_temp)) # Update status with self.mutex: self._ts_last = time.time() self._stat_msg.level = diag_level self._stat_msg.values = diag_vals self._stat_msg.message = diag_msg except Exception as error: import traceback print(traceback.format_exc()) rospy.logwarn( "Sensor temperatures are not checked because of error: %s" % utf8(error)) self._interval = 0
def run(self): ''' ''' if self._masteruri: found = False service_names = interface_finder.get_listmaster_service(self._masteruri, self._wait, check_host=self._check_host) err_msg = '' for service_name in service_names: rospy.logdebug("service 'list_masters' found on %s as %s", self._masteruri, service_name) if self._wait: rospy.wait_for_service(service_name) socket.setdefaulttimeout(3) discoverMasters = rospy.ServiceProxy(service_name, DiscoverMasters) try: resp = discoverMasters() except rospy.ServiceException as e: err_msg = "Service call 'list_masters' failed: %s" % utf8(e) rospy.logwarn(err_msg) self.err_signal.emit(self._masteruri, "Service call '%s' failed: %s" % (service_name, err_msg), False) else: if resp.masters: self.master_list_signal.emit(self._masteruri, service_name, resp.masters) found = True else: self.err_signal.emit(self._masteruri, "local 'master_discovery' reports empty master list, it seems he has a problem", False) finally: socket.setdefaulttimeout(None) if not found: self.err_signal.emit(self._masteruri, "no service 'list_masters' found on %s" % self._masteruri, False)
def find_default_args(self, path, inc_args): ''' Searches for args with default value not overwritten by including file. :param str path: file content or a launch file path :param dict(str,str) inc_args: a dictionary with arguments set while include the given path. :return: a dictinary with default arguments not overwriting while include. :rtype: dict(str: str) ''' not_set_args = {} if path and not (path.endswith('.launch') or path.find('.launch.') > 0): return not_set_args if rospy.is_shutdown(): return not_set_args try: # get file content _, _, data = nm.nmd().file.get_file_content(path) launch_node = None # create xml node xml_nodes = minidom.parseString(data.encode('utf-8')).getElementsByTagName('launch') if xml_nodes: launch_node = xml_nodes[-1] if launch_node is not None: # read XML content and get default arguments default_args = get_internal_args(data, only_default=True) for arg_in_file, arg_value in default_args.items(): if arg_in_file not in inc_args: not_set_args[arg_in_file] = arg_value except Exception as err: msg = "can't get default arguments for %s: %s" % (path, utf8(err)) self.error.emit(msg) rospy.logwarn(msg) return not_set_args
def get_profile_file(self): ''' Opens file manager dialog to save to select a new file for node manager profile. :return: path to profile file :rtype: str ''' # save the profile (path, _) = QFileDialog.getSaveFileName( self, "New profile file", nm.settings().current_dialog_path, "node manager profile files (*.nmprofile);;All files (*)" ) # _:=filter if path: if not path.endswith('.nmprofile'): path = "%s.nmprofile" % path nm.settings().current_dialog_path = os.path.dirname(path) try: # we need a grpc url for local node manager daemon nmd_url = nmdurl.nmduri() (pkg, _) = package_name( nmdurl.join(nmd_url, os.path.dirname(path))) # _:=pkg_path if pkg is None: ret = MessageBox.warning( self, "New File Error", 'The new file is not in a ROS package', buttons=MessageBox.Ok | MessageBox.Cancel) if ret == MessageBox.Cancel: return None return path except EnvironmentError as e: MessageBox.warning(self, "New File Error", 'Error while create a new file', utf8(e)) return None
def __init__(self, context): super(NodeManager, self).__init__(context) # Give QObjects reasonable names self.setObjectName('NodeManagerFKIE') # Process standalone plugin command-line arguments from argparse import ArgumentParser parser = ArgumentParser() # Add argument(s) to the parser. parser.add_argument("-q", "--quiet", action="store_true", dest="quiet", help="Put plugin in silent mode") args, unknowns = parser.parse_known_args(context.argv()) if not args.quiet: print('arguments: ', args) print('unknowns: ', unknowns) fkie_node_manager.init_settings() masteruri = fkie_node_manager.settings().masteruri() fkie_node_manager.init_globals(masteruri) # Create QWidget try: self._widget = MainWindow() # self._widget.read_view_history() except Exception, e: MessageBox.critical(None, "Node Manager", utf8(e)) raise
def _nmd_error(self, method, url, path, error): if method != 'list_path' or not self.is_current_nmd(url): return root = self.invisibleRootItem() while root.rowCount(): root.removeRow(0) self.pyqt_workaround.clear() self._add_path(self._current_path, PathItem.ROOT, 0, 0, '') detail_msg = utf8(error) if hasattr(error, 'details'): detail_msg = utf8(error.details()) path_item = PathItem.create_row_items( utf8("%s, please start node manager daemon" % detail_msg), PathItem.NOTHING, 0, 0, 'connecting to daemon...') root.appendRow(path_item) self.pyqt_workaround[path_item[0].name] = path_item[0] self.error_on_path.emit(nmdurl.join(url, path), error)
def data(self, role): if role == self.NAME_ROLE: return self.service.name elif role == self.TYPE_ROLE: return self.service_type_str elif role == self.NODENAMES_ROLE: return utf8(self.service.serviceProvider) else: return QStandardItem.data(self, role)