--- a/Debugger/DebugServer.py Sat Mar 02 11:17:15 2019 +0100 +++ b/Debugger/DebugServer.py Fri Apr 05 19:06:39 2019 +0200 @@ -69,8 +69,8 @@ detected on the client side @signal clientSignal(signal) emitted after a signal has been generated on the client side - @signal clientExit(int) emitted with the exit status after the client has - exited + @signal clientExit(int, str, bool) emitted after the client has exited + giving the exit status, an exit message and an indication to be quiet @signal clientClearBreak(filename, lineno) emitted after the debug client has decided to clear a temporary breakpoint @signal clientBreakConditionError(fn, lineno) emitted after the client has @@ -94,6 +94,8 @@ unplanned) @signal clientInterpreterChanged(str) emitted to signal a change of the client interpreter + @signal utDiscovered(testCases, exc_type, exc_value) emitted after the + client has performed a test case discovery action @signal utPrepared(nrTests, exc_type, exc_value) emitted after the client has loaded a unittest suite @signal utFinished() emitted after the client signalled the end of the @@ -134,7 +136,7 @@ clientException = pyqtSignal(str, str, list) clientSyntaxError = pyqtSignal(str, str, int, int) clientSignal = pyqtSignal(str, str, int, str, str) - clientExit = pyqtSignal(int, str) + clientExit = pyqtSignal(int, str, bool) clientBreakConditionError = pyqtSignal(str, int) clientWatchConditionError = pyqtSignal(str) clientRawInput = pyqtSignal(str, bool) @@ -142,6 +144,7 @@ clientCapabilities = pyqtSignal(int, str, str) clientCompletionList = pyqtSignal(list, str) clientInterpreterChanged = pyqtSignal(str) + utDiscovered = pyqtSignal(list, str, str) utPrepared = pyqtSignal(int, str, str) utStartTest = pyqtSignal(str, str) utStopTest = pyqtSignal() @@ -1311,26 +1314,91 @@ @param text the text to be completed (string) """ self.debuggerInterface.remoteCompletion(text) - + + def remoteUTDiscover(self, clientType, forProject, venvName, syspath, + workdir, discoveryStart): + """ + Public method to perform a test case discovery. + + @param clientType client type to be used + @type str + @param forProject flag indicating a project related action + @type bool + @param venvName name of a virtual environment + @type str + @param syspath list of directories to be added to sys.path on the + remote side + @type list of str + @param workdir path name of the working directory + @type str + @param discoveryStart directory to start auto-discovery at + @type str + """ + if clientType and clientType not in self.getSupportedLanguages(): + # a not supported client language was requested + E5MessageBox.critical( + None, + self.tr("Start Debugger"), + self.tr( + """<p>The debugger type <b>{0}</b> is not supported""" + """ or not configured.</p>""").format(clientType) + ) + return + + # Restart the client if there is already a program loaded. + try: + if clientType: + self.__setClientType(clientType) + except KeyError: + self.__setClientType('Python3') # assume it is a Python3 file + self.startClient(False, forProject=forProject, venvName=venvName) + + self.debuggerInterface.remoteUTDiscover( + syspath, workdir, discoveryStart) + def remoteUTPrepare(self, fn, tn, tfn, failed, cov, covname, coverase, - clientType=""): + clientType="", forProject=False, venvName="", + syspath=None, workdir="", discover=False, + discoveryStart="", testCases=None, debug=False): """ Public method to prepare a new unittest run. - @param fn the filename to load (string) - @param tn the testname to load (string) - @param tfn the test function name to load tests from (string) + @param fn the filename to load + @type str + @param tn the testname to load + @type str + @param tfn the test function name to load tests from + @type str @param failed list of failed test, if only failed test should be run - (list of strings) + @type list of str @param cov flag indicating collection of coverage data is requested - (boolean) + @type bool @param covname filename to be used to assemble the coverage caches - filename (string) + filename + @type str @param coverase flag indicating erasure of coverage data is requested - (boolean) - @keyparam clientType client type to be used (string) + @type bool + @param clientType client type to be used + @type str + @param forProject flag indicating a project related action + @type bool + @param venvName name of a virtual environment + @type str + @param syspath list of directories to be added to sys.path on the + remote side + @type list of str + @param workdir path name of the working directory + @type str + @param discover flag indicating to discover the tests automatically + @type bool + @param discoveryStart directory to start auto-discovery at + @type str + @param testCases list of test cases to be loaded + @type list of str + @param debug flag indicating to run unittest with debugging + @type bool """ - if clientType not in self.getSupportedLanguages(): + if clientType and clientType not in self.getSupportedLanguages(): # a not supported client language was requested E5MessageBox.critical( None, @@ -1350,18 +1418,27 @@ self.__findLanguageForExtension(os.path.splitext(fn)[1])) except KeyError: self.__setClientType('Python3') # assume it is a Python3 file - self.startClient(False) + self.startClient(False, forProject=forProject, venvName=venvName) self.debuggerInterface.remoteUTPrepare( - fn, tn, tfn, failed, cov, covname, coverase) - self.debugging = False + fn, tn, tfn, failed, cov, covname, coverase, syspath, workdir, + discover, discoveryStart, testCases, debug) self.running = True + self.debugging = debug + if debug: + self.__restoreBreakpoints() + self.__restoreWatchpoints() - def remoteUTRun(self): + def remoteUTRun(self, debug=False, failfast=False): """ Public method to start a unittest run. + + @param debug flag indicating to run unittest with debugging + @type bool + @param failfast flag indicating to stop at the first error + @type bool """ - self.debuggerInterface.remoteUTRun() + self.debuggerInterface.remoteUTRun(debug, failfast) def remoteUTStop(self): """ @@ -1500,7 +1577,7 @@ """ if self.passive: self.__passiveShutDown() - self.clientExit.emit(int(status), message) + self.clientExit.emit(int(status), message, False) if Preferences.getDebugger("AutomaticReset") or (self.running and not self.debugging): self.debugging = False @@ -1613,6 +1690,19 @@ isCall, fromFile, fromLine, fromFunction, toFile, toLine, toFunction) + def clientUtDiscovered(self, testCases, exceptionType, exceptionValue): + """ + Public method to process the client unittest discover info. + + @param testCases list of detected test cases + @type str + @param exceptionType exception type + @type str + @param exceptionValue exception message + @type str + """ + self.utDiscovered.emit(testCases, exceptionType, exceptionValue) + def clientUtPrepared(self, result, exceptionType, exceptionValue): """ Public method to process the client unittest prepared info. @@ -1687,12 +1777,19 @@ """ self.utTestSucceededUnexpected.emit(testname, testId) - def clientUtFinished(self): + def clientUtFinished(self, status): """ Public method to process the client unit test finished info. + + @param status exit status of the unit test + @type int """ self.utFinished.emit() + self.clientExit.emit(int(status), "", True) + self.debugging = False + self.running = False + def passiveStartUp(self, fn, exc): """ Public method to handle a passive debug connection.