Fri, 08 Mar 2024 15:30:23 +0100
Corrected some issues and improved some existing code with respect to eric-ide server use.
--- a/src/eric7/DataViews/PyCoverageDialog.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/DataViews/PyCoverageDialog.py Fri Mar 08 15:30:23 2024 +0100 @@ -80,10 +80,13 @@ self.resultList.setContextMenuPolicy(Qt.ContextMenuPolicy.CustomContextMenu) self.resultList.customContextMenuRequested.connect(self.__showContextMenu) - # eric-ide server interface + # eric-ide server interfaces self.__serverCoverageInterface = ( ericApp().getObject("EricServer").getServiceInterface("Coverage") ) + self.__remotefsInterface = ( + ericApp().getObject("EricServer").getServiceInterface("FileSystem") + ) def __format_lines(self, lines): """
--- a/src/eric7/Debugger/DebugUI.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Debugger/DebugUI.py Fri Mar 08 15:30:23 2024 +0100 @@ -2565,6 +2565,14 @@ scriptName = self.lastDebuggedFile else: scriptName = "" + if ( + scriptName + and FileSystemUtilities.isRemoteFileName(scriptName) + and not self.ui.isEricServerConnected() + ): + self.__showNotConnectedWarning(title=cap, name=scriptName) + return + dlg = StartDialog( cap, self.lastUsedVenvName, @@ -2661,7 +2669,7 @@ FileSystemUtilities.isRemoteFileName(fn) and not self.ui.isEricServerConnected() ): - self.__showNotConnectedWarning(title=cap) + self.__showNotConnectedWarning(title=cap, name=fn) return # save the filename for use by the restart method @@ -3205,18 +3213,20 @@ """ return self.debugServer.getProjectEnvironmentString() - def __showNotConnectedWarning(self, title): + def __showNotConnectedWarning(self, title, name=""): """ Private method to show a warning about a not connected eric-ide server. @param title title for the dialog @type str + @param name name of the file (defaults to "") + @type str (optional) """ EricMessageBox.warning( None, title, self.tr( - "<p>The selected file is located on an eric-ide server but no such" - " server is connected. Aborting...</p>" - ), + "<p>The selected file <b>{0}</b> is located on an eric-ide server but" + " no such server is connected. Aborting...</p>" + ).format(name), )
--- a/src/eric7/Debugger/DebuggerInterfaceNone.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Debugger/DebuggerInterfaceNone.py Fri Mar 08 15:30:23 2024 +0100 @@ -46,6 +46,7 @@ originalPathString, workingDir=None, configOverride=None, + startRemote=False, ): """ Public method to start a remote Python interpreter. @@ -64,6 +65,9 @@ @param configOverride dictionary containing the global config override data @type dict + @param startRemote flag indicating to start the client via an eric-ide server + (defaults to False) + @type bool (optional) @return client process object, a flag to indicate a network connection and the name of the interpreter in case of a local execution @rtype tuple of (QProcess, bool, str) @@ -78,6 +82,7 @@ originalPathString, workingDir=None, configOverride=None, + startRemote=False, ): """ Public method to start a remote Python interpreter for a project. @@ -96,6 +101,9 @@ @param configOverride dictionary containing the global config override data @type dict + @param startRemote flag indicating to start the client via an eric-ide server + (defaults to False) + @type bool (optional) @return client process object, a flag to indicate a network connection and the name of the interpreter in case of a local execution @rtype tuple of (QProcess, bool, str)
--- a/src/eric7/Debugger/DebuggerInterfacePython.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Debugger/DebuggerInterfacePython.py Fri Mar 08 15:30:23 2024 +0100 @@ -231,7 +231,7 @@ # TODO change this once server environment definitions are supported startRemote = True venvName = self.debugServer.getEricServerEnvironmentString() - interpreter = "" + interpreter = "" # use the interpreter of the server else: if not venvName: venvName = Preferences.getDebugger("Python3VirtualEnv") @@ -501,8 +501,6 @@ and the name of the interpreter in case of a local execution @rtype tuple of (QProcess, bool, str) """ - # TODO: 'startRemoteForProject()' - implement the 'startRemote' logic like - # for 'startRemote'. global origPathEnv project = ericApp().getObject("Project") @@ -525,21 +523,36 @@ else "" ) - if venvName and venvName != self.debugServer.getProjectEnvironmentString(): - venvManager = ericApp().getObject("VirtualEnvManager") - interpreter = venvManager.getVirtualenvInterpreter(venvName) - execPath = venvManager.getVirtualenvExecPath(venvName) + if ( + startRemote is True + or ( + startRemote is None + and ( + venvName == self.debugServer.getEricServerEnvironmentString() + or self.__ericServerDebugging + ) + ) + ) and ericApp().getObject("EricServer").isServerConnected(): + # TODO change this once server environment definitions are supported + startRemote = True + venvName = self.debugServer.getEricServerEnvironmentString() + interpreter = "" # use the interpreter of the server else: - venvName = project.getProjectVenv() - execPath = project.getProjectExecPath() - interpreter = project.getProjectInterpreter() - if interpreter == "": - EricMessageBox.critical( - None, - self.tr("Start Debugger"), - self.tr("""<p>No suitable Python3 environment configured.</p>"""), - ) - return None, self.__isNetworked, "" + if venvName and venvName != self.debugServer.getProjectEnvironmentString(): + venvManager = ericApp().getObject("VirtualEnvManager") + interpreter = venvManager.getVirtualenvInterpreter(venvName) + execPath = venvManager.getVirtualenvExecPath(venvName) + else: + venvName = project.getProjectVenv() + execPath = project.getProjectExecPath() + interpreter = project.getProjectInterpreter() + if interpreter == "": + EricMessageBox.critical( + None, + self.tr("Start Debugger"), + self.tr("""<p>No suitable Python3 environment configured.</p>"""), + ) + return None, self.__isNetworked, "" self.__inShutdown = False @@ -603,6 +616,27 @@ return None, self.__isNetworked, "" # TODO: add server debugging for projects + elif startRemote and self.__ericServerDebuggerInterface is not None: + # debugging via an eric-ide server + self.translate = self.__ericServerTranslation + self.__ericServerDebugging = True + + args = [] + if noencoding: + args.append(noencoding) + if multiprocessEnabled: + args.append(multiprocessEnabled) + if callTraceOptimization: + args.append(callTraceOptimization) + self.__ericServerDebuggerInterface.startClient( + interpreter, + originalPathString, + args, + workingDir=workingDir, + ) + self.__startedVenv = venvName + + return None, self.__isNetworked, "" else: # local debugging code below
--- a/src/eric7/Debugger/StartDialog.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Debugger/StartDialog.py Fri Mar 08 15:30:23 2024 +0100 @@ -16,6 +16,7 @@ from eric7 import Preferences from eric7.EricWidgets.EricApplication import ericApp from eric7.EricWidgets.EricPathPicker import EricPathPickerModes +from eric7.SystemUtilities import FileSystemUtilities from .Ui_StartDialog import Ui_StartDialog @@ -203,6 +204,13 @@ self.scriptnamePicker.addItems(scriptsList) self.scriptnamePicker.setText(scriptName) + self.scriptnamePicker.setRemote( + FileSystemUtilities.isRemoteFileName(scriptName) + ) + self.workdirPicker.setRemote( + FileSystemUtilities.isRemoteFileName(scriptName) + ) + if dialogMode == StartDialogMode.Debug: enableMultiprocessGlobal = Preferences.getDebugger("MultiProcessEnabled") self.tracePythonCheckBox.setChecked(tracePython)
--- a/src/eric7/EricWidgets/EricPathPickerDialog.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/EricWidgets/EricPathPickerDialog.py Fri Mar 08 15:30:23 2024 +0100 @@ -78,6 +78,15 @@ """ self.__pathPicker.setMode(mode) + def setPickerRemote(self, remote): + """ + Public method to set the remote mode of the path picker. + + @param remote flag indicating the remote mode + @type bool + """ + self.__pathPicker.setRemote(remote) + def setPickerFilters(self, filters): """ Public method to set the filters of the path picker. @@ -134,6 +143,7 @@ strPath=None, defaultDirectory=None, filters=None, + remote=False, ): """ Function to get a file or directory path from the user. @@ -153,6 +163,8 @@ @type str (optional) @param filters list of file filters (defaults to None) @type list of str (optional) + @param remote flag indicating the remote mode (defaults to False) + @type bool (optional) @return tuple containing the entered path and a flag indicating that the user pressed the OK button @rtype tuple of (str, bool) @@ -164,6 +176,7 @@ if label: dlg.setLabelText(label) dlg.setPickerMode(mode) + dlg.setPickerRemote(remote) if strPath: dlg.setPickerPath(strPath) if defaultDirectory:
--- a/src/eric7/Plugins/CheckerPlugins/CodeStyleChecker/CodeStyleCheckerDialog.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Plugins/CheckerPlugins/CodeStyleChecker/CodeStyleCheckerDialog.py Fri Mar 08 15:30:23 2024 +0100 @@ -1579,7 +1579,7 @@ return if item.parent(): - fn = os.path.abspath(item.data(0, self.filenameRole)) + fn = item.data(0, self.filenameRole) lineno = item.data(0, self.lineRole) position = item.data(0, self.positionRole) message = item.data(0, self.messageRole) @@ -1621,7 +1621,7 @@ for index in selectedIndexes: itm = self.resultList.topLevelItem(index) if itm.data(0, self.filenameRole) is not None: - fn = os.path.abspath(itm.data(0, self.filenameRole)) + fn = itm.data(0, self.filenameRole) vm.openSourceFile(fn, 1) editor = vm.getOpenEditor(fn) editor.clearStyleWarnings() @@ -1639,7 +1639,7 @@ errorFiles = [] for index in range(self.resultList.topLevelItemCount()): itm = self.resultList.topLevelItem(index) - errorFiles.append(os.path.abspath(itm.data(0, self.filenameRole))) + errorFiles.append(itm.data(0, self.filenameRole)) for file in openFiles: if file not in errorFiles: editor = vm.getOpenEditor(file)
--- a/src/eric7/Plugins/CheckerPlugins/SyntaxChecker/SyntaxCheckerDialog.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Plugins/CheckerPlugins/SyntaxChecker/SyntaxCheckerDialog.py Fri Mar 08 15:30:23 2024 +0100 @@ -298,18 +298,35 @@ @param fn file or list of files or directory to be checked @type str or list of str """ + isdir = isinstance(fn, str) and ( + self.__remotefsInterface.isdir(fn) + if FileSystemUtilities.isRemoteFileName(fn) + else os.path.isdir(fn) + ) + if isinstance(fn, list): files = fn - elif os.path.isdir(fn): - files = FileSystemUtilities.direntries( - fn, - filesonly=True, - pattern=[ - "*{0}".format(ext) - for ext in self.syntaxCheckService.getExtensions() - ], - followsymlinks=False, - ) + elif isdir: + if FileSystemUtilities.isRemoteFileName(fn): + files = self.__remotefsInterface.direntries( + fn, + filesonly=True, + pattern=[ + "*{0}".format(ext) + for ext in self.syntaxCheckService.getExtensions() + ], + followsymlinks=False, + ) + else: + files = FileSystemUtilities.direntries( + fn, + filesonly=True, + pattern=[ + "*{0}".format(ext) + for ext in self.syntaxCheckService.getExtensions() + ], + followsymlinks=False, + ) else: files = [fn] @@ -364,13 +381,25 @@ self.checkProgress.setVisible(True) QApplication.processEvents() + isdir = isinstance(fn, str) and ( + self.__remotefsInterface.isdir(fn) + if FileSystemUtilities.isRemoteFileName(fn) + else os.path.isdir(fn) + ) + if isinstance(fn, list): self.files = fn - elif os.path.isdir(fn): + elif isdir: self.files = [] for ext in self.syntaxCheckService.getExtensions(): self.files.extend( - FileSystemUtilities.direntries(fn, True, "*{0}".format(ext), 0) + self.__remotefsInterface.direntries( + fn, True, "*{0}".format(ext), False + ) + if FileSystemUtilities.isRemoteFileName(fn) + else FileSystemUtilities.direntries( + fn, True, "*{0}".format(ext), False + ) ) else: self.files = [fn] @@ -468,8 +497,8 @@ try: source = ( - self.__remotefsInterface.readEncodedFile(self.filename)[0] - if FileSystemUtilities.isRemoteFileName(self.filename) + self.__remotefsInterface.readEncodedFile(filename)[0] + if FileSystemUtilities.isRemoteFileName(filename) else Utilities.readEncodedFile(filename)[0] ) source = Utilities.normalizeCode(source) @@ -699,7 +728,7 @@ vm = ericApp().getObject("ViewManager") if itm.parent(): - fn = os.path.abspath(itm.data(0, self.filenameRole)) + fn = itm.data(0, self.filenameRole) lineno = itm.data(0, self.lineRole) index = itm.data(0, self.indexRole) error = itm.data(0, self.errorRole) @@ -712,7 +741,7 @@ else: editor.toggleSyntaxError(lineno, index, True, error, show=True) else: - fn = os.path.abspath(itm.data(0, self.filenameRole)) + fn = itm.data(0, self.filenameRole) vm.openSourceFile(fn) editor = vm.getOpenEditor(fn) for index in range(itm.childCount()): @@ -744,7 +773,7 @@ for index in selectedIndexes: itm = self.resultList.topLevelItem(index) if itm.data(0, self.filenameRole) is not None: - fn = os.path.abspath(itm.data(0, self.filenameRole)) + fn = itm.data(0, self.filenameRole) vm.openSourceFile(fn, 1) editor = vm.getOpenEditor(fn) editor.clearSyntaxError() @@ -764,7 +793,7 @@ errorFiles = [] for index in range(self.resultList.topLevelItemCount()): itm = self.resultList.topLevelItem(index) - errorFiles.append(os.path.abspath(itm.data(0, self.filenameRole))) + errorFiles.append(itm.data(0, self.filenameRole)) for fn in vm.getOpenFilenames(): if fn not in errorFiles: editor = vm.getOpenEditor(fn)
--- a/src/eric7/Plugins/PluginCodeStyleChecker.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/Plugins/PluginCodeStyleChecker.py Fri Mar 08 15:30:23 2024 +0100 @@ -476,7 +476,6 @@ if menuName == "Checks": if self.__editorAct not in menu.actions(): menu.addAction(self.__editorAct) - # TODO: disable the action for eric-ide server files self.__editorAct.setEnabled(editor.isPyFile()) def __editorCodeStyleCheck(self):
--- a/src/eric7/QScintilla/Shell.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/QScintilla/Shell.py Fri Mar 08 15:30:23 2024 +0100 @@ -34,6 +34,7 @@ from eric7.EricWidgets import EricFileDialog, EricMessageBox from eric7.EricWidgets.EricApplication import ericApp from eric7.EricWidgets.EricSimpleHelpDialog import EricSimpleHelpDialog +from eric7.SystemUtilities import FileSystemUtilities from eric7.UI.SearchWidget import SearchWidget from . import Lexers @@ -2628,8 +2629,12 @@ Private slot to start the shell for the opened project. """ if Preferences.getProject("RestartShellForProject"): + ppath = self.__project.getProjectPath() self.dbs.startClient( - False, forProject=True, workingDir=self.__project.getProjectPath() + False, + forProject=True, + workingDir=ppath, + startRemote=FileSystemUtilities.isRemoteFileName(ppath) ) self.__currentWorkingDirectory = self.__project.getProjectPath() self.__getBanner()
--- a/src/eric7/RemoteServer/EricServer.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/RemoteServer/EricServer.py Fri Mar 08 15:30:23 2024 +0100 @@ -73,7 +73,6 @@ self.__coverageRequestHandler.handleRequest, ) - # TODO: 'Project' handler not implemented yet # TODO: implement an 'EditorConfig' handler (?) self.__address = ("", port) @@ -203,7 +202,7 @@ return {} jsonStr = data.decode("utf8", "backslashreplace") - # - print("Eric Server Receive:", jsonStr) # for debugging + print("Eric Server Receive:", jsonStr) # for debugging try: return json.loads(jsonStr.strip()) except (TypeError, ValueError) as err: @@ -281,8 +280,10 @@ self.__socket.listen(0) self.__socket.setblocking(False) - print(f"Listening for 'eric-ide' connections on {self.__socket.getsockname()}") - # noqa: M801 + address = self.__socket.getsockname() + print( # noqa: M801 + f"Listening for 'eric-ide' connections on {address[0]}, port {address[1]}" + ) data = types.SimpleNamespace( name="server", acceptHandler=self.__acceptIdeConnection ) @@ -320,10 +321,10 @@ """ connection, address = sock.accept() # Should be ready to read if self.__connection is None: - print(f"'eric-ide' connection from {address[0]}, port {address[1]}") + print(f"'eric-ide' connection from {address[0]}, port {address[1]}") # noqa: M801 self.__connection = connection - self.__connection.setblocking(False) + ##self.__connection.setblocking(False) data = types.SimpleNamespace( name="eric-ide", address=address, handler=self.__serviceIdeConnection ) @@ -333,7 +334,7 @@ self.__unregisterIdeSocket() else: print( # noqa: M801 - f"'eric-ide' connection from {address[0]}, port {address[1]} rejected" + f"'eric-ide' connection from {address[0]}, port {address[1]} rejected" ) connection.close() @@ -347,9 +348,9 @@ if self.__connection is not None: self.__selector.unregister(self.__connection) try: + address = self.__connection.getpeername() print( # noqa: M801 - f"Closing 'eric-ide' connection to" - f" {self.__connection.getpeername()}." + f"Closing 'eric-ide' connection to {address[0]}, port {address[1]}." ) self.__connection.shutdown(socket.SHUT_RDWR) self.__connection.close()
--- a/src/eric7/RemoteServer/EricServerCoverageRequestHandler.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/RemoteServer/EricServerCoverageRequestHandler.py Fri Mar 08 15:30:23 2024 +0100 @@ -125,7 +125,6 @@ @return dictionary containing the reply data @rtype dict """ - # TODO: not implemented yet if self.__cover is None: return { "ok": False, @@ -152,7 +151,6 @@ @return dictionary containing the reply data @rtype dict """ - # TODO: not implemented yet if self.__cover is None: return { "ok": False,
--- a/src/eric7/RemoteServer/EricServerDebuggerRequestHandler.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/RemoteServer/EricServerDebuggerRequestHandler.py Fri Mar 08 15:30:23 2024 +0100 @@ -47,6 +47,9 @@ address = ("127.0.0.1", 0) self.__socket = socket.create_server(address, family=socket.AF_INET) + self.__originalPathString = os.getenv("PATH") + + def initServerSocket(self): """ Public method to initialize the server socket listening for debug client @@ -55,9 +58,10 @@ # listen on the debug server socket self.__socket.listen() self.__socket.setblocking(False) + address = self.__socket.getsockname() print( # noqa: M801 - f"Listening for 'debug client' connections on" - f" {self.__socket.getsockname()}" + f"Listening for 'Debug Client' connections on" + f" {address[0]}, port {address[1]}" ) data = types.SimpleNamespace( name="server", acceptHandler=self.__acceptDbgClientConnection @@ -106,7 +110,7 @@ @type socket.socket """ connection, address = sock.accept() # Should be ready to read - print(f"'Debug client' connection from {address[0]}, port {address[1]}") + print(f"'Debug Client' connection from {address[0]}, port {address[1]}") # noqa: M801 connection.setblocking(False) self.__pendingConnections.append(connection) @@ -173,6 +177,11 @@ """ self.__server.getSelector().unregister(sock) + address = sock.getpeername() + print( + f"'Debug Client' connection from {address[0]}, port {address[1]} closed." + ) + # noqa: M801 for debuggerId in list(self.__connections): if self.__connections[debuggerId] is sock: del self.__connections[debuggerId] @@ -291,8 +300,18 @@ args.extend(params["arguments"]) args.extend([str(port), "True", ipaddr]) + workingDir = params["working_dir"] if params["working_dir"] else None + + clientEnv = os.environ.copy() + if self.__originalPathString: + clientEnv["PATH"] = self.__originalPathString + self.__client = subprocess.Popen( - args, stdout=subprocess.PIPE, stderr=subprocess.PIPE + args, + stdout=subprocess.PIPE, + stderr=subprocess.PIPE, + cwd=workingDir, + env=clientEnv, ) def __stopClient(self, params): # noqa: U100 @@ -327,9 +346,9 @@ for sock in self.__connections.values(): self.__server.sendJsonCommand(jsonStr, sock) else: - try: + try: # noqa: Y105 sock = self.__connections[debuggerId] self.__server.sendJsonCommand(jsonStr, sock) except KeyError: - print(f"Command for unknown debugger ID '{debuggerId}' received.") - # noqa: M801 + pass + # - print(f"Command for unknown debugger ID '{debuggerId}' received.")
--- a/src/eric7/RemoteServer/EricServerFileSystemRequestHandler.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/RemoteServer/EricServerFileSystemRequestHandler.py Fri Mar 08 15:30:23 2024 +0100 @@ -140,23 +140,7 @@ directory = os.getcwd() try: - listing = [] - for dirEntry in os.scandir(directory): - filestat = dirEntry.stat() - entry = { - "name": dirEntry.name, - "path": dirEntry.path, - "is_dir": dirEntry.is_dir(), - "is_file": dirEntry.is_file(), - "is_link": dirEntry.is_symlink(), - "mode": filestat.st_mode, - "mode_str": stat.filemode(filestat.st_mode), - "size": filestat.st_size, - "mtime": time.strftime( - "%Y-%m-%d %H:%M:%S", time.localtime(filestat.st_mtime) - ), - } - listing.append(entry) + listing = self.__scanDirectory(directory, params["recursive"]) return { "ok": True, @@ -170,6 +154,43 @@ "error": str(err), } + def __scanDirectory(self, directory, recursive, withHidden=False): + """ + Private method to scan a given directory. + + @param directory path of the directory to be scanned + @type str + @param recursive flag indicating a recursive scan + @type bool + @param withHidden flag indicating to list hidden files and directories + as well (defaults to False) + @type bool (optional) + """ + listing = [] + for dirEntry in os.scandir(directory): + filestat = dirEntry.stat() + if withHidden or not dirEntry.name.startswith("."): + entry = { + "name": dirEntry.name, + "path": dirEntry.path, + "is_dir": dirEntry.is_dir(), + "is_file": dirEntry.is_file(), + "is_link": dirEntry.is_symlink(), + "mode": filestat.st_mode, + "mode_str": stat.filemode(filestat.st_mode), + "size": filestat.st_size, + "mtime": filestat.st_mtime, + "mtime_str": time.strftime( + "%Y-%m-%d %H:%M:%S", time.localtime(filestat.st_mtime) + ), + } + listing.append(entry) + + if entry["is_dir"] and recursive: + listing += self.__scanDirectory(dirEntry.path, recursive) + + return listing + def __stat(self, params): """ Private method to get the status of a file. @@ -327,8 +348,9 @@ with open(filename, "wb"): pass + newline = None if params["newline"] == "<<none>>" else params["newline"] try: - with open(filename, "rb") as f: + with open(filename, "rb", newline=newline) as f: data = f.read() return { "ok": True, @@ -369,8 +391,9 @@ os.rename(filename, backupFilename) # 2. write the data to the file and reset the permissions + newline = None if params["newline"] == "<<none>>" else params["newline"] try: - with open(filename, "wb") as f: + with open(filename, "wb", newline=newline) as f: f.write(data) if params["with_backup"] and perms_valid: os.chmod(filename, permissions)
--- a/src/eric7/RemoteServerInterface/EricServerFileDialog.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/RemoteServerInterface/EricServerFileDialog.py Fri Mar 08 15:30:23 2024 +0100 @@ -122,9 +122,7 @@ self.treeCombo.currentTextChanged.connect(self.setDirectory) - if self.__fsInterface.isfile(directory): - directory = self.__fsInterface.dirname(directory) - self.setDirectory(FileSystemUtilities.plainFileName(directory)) + self.setDirectory(directory) def acceptMode(self): """ @@ -488,6 +486,11 @@ self.__filenameCache.clear() self.__directoryCache.clear() + if self.__fsInterface.isfile(directory): + directory, basename = self.__fsInterface.split(directory) + else: + basename = "" + try: directory, sep, dirListing = self.__fsInterface.listdir(directory) @@ -528,7 +531,9 @@ sizeStr = dataString(dirEntry["size"], QLocale.system()) self.__filenameCache.append(dirEntry["name"]) itm = QTreeWidgetItem( - self.listing, [dirEntry["name"], sizeStr, type_, dirEntry["mtime"]] + self.listing, [ + dirEntry["name"], sizeStr, type_, dirEntry["mtime_str"] + ] ) itm.setIcon(0, EricPixmapCache.getIcon(iconName)) itm.setTextAlignment(1, Qt.AlignmentFlag.AlignRight) @@ -555,7 +560,10 @@ ) # 4. update some dependent states - self.nameEdit.clear() + if basename: + self.nameEdit.setText(basename) + else: + self.nameEdit.clear() self.__updateUpButton() @pyqtSlot(QPoint)
--- a/src/eric7/RemoteServerInterface/EricServerInterface.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/RemoteServerInterface/EricServerInterface.py Fri Mar 08 15:30:23 2024 +0100 @@ -111,7 +111,7 @@ try: return self.__serviceInterfaces[lname] except KeyError: - if lname not in ("coverage", "debugger", "filesystem", "project"): + if lname not in ("coverage", "debugger", "filesystem"): raise ValueError(f"no such service supported ({name})") else: # instantiate the service interface @@ -135,9 +135,6 @@ ) self.__serviceInterfaces[lname] = EricServerCoverageInterface(self) - elif lname == "project": - # TODO: 'Project Interface' not implemented yet - pass return self.__serviceInterfaces[lname]
--- a/src/eric7/UI/UserInterface.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/UI/UserInterface.py Fri Mar 08 15:30:23 2024 +0100 @@ -592,13 +592,17 @@ ) self.__ericServerInterface.connectionStateChanged.connect( + self.project.remoteConnectionChanged + ) + self.__ericServerInterface.connectionStateChanged.connect( self.viewmanager.remoteConnectionChanged ) self.__ericServerInterface.connectionStateChanged.connect( self.shell.remoteConnectionChanged ) - self.__ericServerInterface.connectionStateChanged.connect( - self.project.remoteConnectionChanged + + self.__ericServerInterface.aboutToDisconnect.connect( + self.project.closeProject ) self.__ericServerInterface.aboutToDisconnect.connect( self.viewmanager.closeRemoteEditors
--- a/src/eric7/ViewManager/ViewManager.py Tue Feb 27 15:05:53 2024 +0100 +++ b/src/eric7/ViewManager/ViewManager.py Fri Mar 08 15:30:23 2024 +0100 @@ -6122,7 +6122,7 @@ if fn is not None and fn not in filenames: # only return names of existing files exists = ( - self.__remotefsInterface.exists(fn) + True if FileSystemUtilities.isRemoteFileName(fn) else os.path.exists(fn) )