diff --git a/AutoDuck/makedfromi.py b/AutoDuck/makedfromi.py index 53edf0111a..adb2fdfd13 100644 --- a/AutoDuck/makedfromi.py +++ b/AutoDuck/makedfromi.py @@ -83,9 +83,8 @@ def make_doc_summary(inFile, outFile): curMethod[1].append("// " + doc + "\n") else: extra_tags.append("// " + doc + "\n") - except: - _, msg, _ = sys.exc_info() - print("Line %d is badly formed - %s" % (lineNo, msg)) + except Exception as msg: + print(f"Line {lineNo} is badly formed - {msg}") lineNo += 1 @@ -150,10 +149,9 @@ def doit(): elif o == "-o": outName = a msg = " ".join(args) - except getopt.error: - _, msg, _ = sys.exc_info() + except getopt.error as msg: print(msg) - print("Usage: %s [-o output_name] [-p com_parent] filename" % sys.argv[0]) + print(f"Usage: {sys.argv[0]} [-o output_name] [-p com_parent] filename") return inName = args[0] diff --git a/Pythonwin/pywin/Demos/app/basictimerapp.py b/Pythonwin/pywin/Demos/app/basictimerapp.py index 6a21715de1..5fa4c15d05 100644 --- a/Pythonwin/pywin/Demos/app/basictimerapp.py +++ b/Pythonwin/pywin/Demos/app/basictimerapp.py @@ -127,12 +127,10 @@ def OnTimer(self, id, timeVal): try: exec(self.dlg.doWork) print("The last operation completed successfully.") - except: - t, v, tb = sys.exc_info() - str = f"Failed: {t}: {v!r}" + except Exception as error: + str = f"Failed: {type(error)}: {error!r}" print(str) self.oldErr.write(str) - tb = None # Prevent cycle finally: self.ReleaseOutput() self.dlg.butOK.EnableWindow() diff --git a/Pythonwin/pywin/Demos/cmdserver.py b/Pythonwin/pywin/Demos/cmdserver.py index cb751f0847..e1023edcda 100644 --- a/Pythonwin/pywin/Demos/cmdserver.py +++ b/Pythonwin/pywin/Demos/cmdserver.py @@ -83,10 +83,7 @@ def ServerThread(myout, cmd, title, bCloseOnEnd): if bOK: print("Command terminated without errors.") else: - t, v, tb = sys.exc_info() - print(t, ": ", v) - traceback.print_tb(tb) - tb = None # prevent a cycle + traceback.print_exc() print("Command terminated with an unhandled exception") writer.unregister() if bOK and bCloseOnEnd: @@ -94,10 +91,7 @@ def ServerThread(myout, cmd, title, bCloseOnEnd): # Unhandled exception of any kind in a thread kills the gui! except: - t, v, tb = sys.exc_info() - print(t, ": ", v) - traceback.print_tb(tb) - tb = None + traceback.print_exc() print("Thread failed") diff --git a/Pythonwin/pywin/debugger/debugger.py b/Pythonwin/pywin/debugger/debugger.py index 72b9cf2dc4..81ccfe25f6 100644 --- a/Pythonwin/pywin/debugger/debugger.py +++ b/Pythonwin/pywin/debugger/debugger.py @@ -478,10 +478,8 @@ def RespondDebuggerState(self, state): val = repr(eval(text, globs, locs)) except SyntaxError: val = "Syntax Error" - except: - t, v, tb = sys.exc_info() - val = traceback.format_exception_only(t, v)[0].strip() - tb = None # prevent a cycle. + except Exception as error: + val = traceback.format_exception_only(type(error), error)[0].strip() self.SetItemText(i, 1, val) diff --git a/Pythonwin/pywin/debugger/fail.py b/Pythonwin/pywin/debugger/fail.py index 0afc70eb37..babb39fb53 100644 --- a/Pythonwin/pywin/debugger/fail.py +++ b/Pythonwin/pywin/debugger/fail.py @@ -5,7 +5,6 @@ # It does nothing useful, and it even doesn't do that! -import sys import time import pywin.debugger @@ -15,9 +14,9 @@ def a(): a = 1 try: b() - except: + except Exception as error: # Break into the debugger with the exception information. - pywin.debugger.post_mortem(sys.exc_info()[2]) + pywin.debugger.post_mortem(error.__traceback__) a = 1 a = 2 a = 3 diff --git a/Pythonwin/pywin/framework/app.py b/Pythonwin/pywin/framework/app.py index 931a007871..2ef02b98a0 100644 --- a/Pythonwin/pywin/framework/app.py +++ b/Pythonwin/pywin/framework/app.py @@ -213,10 +213,10 @@ def OnHelp(self, id, code): from . import help help.OpenHelpFile(helpFile, helpCmd) - except: - t, v, tb = sys.exc_info() - win32ui.MessageBox(f"Internal error in help file processing\r\n{t}: {v}") - tb = None # Prevent a cycle + except Exception as error: + win32ui.MessageBox( + f"Internal error in help file processing\r\n{type(error)}: {error}" + ) def DoLoadModules(self, modules): # XXX - this should go, but the debugger uses it :-( @@ -280,23 +280,23 @@ def OnDropFiles(self, msg): # but handles errors slightly better. # It all still works, tho, so if you need similar functionality, you can use it. # Therefore I haven't deleted this code completely! - # def CallbackManager( self, ob, args = () ): - # """Manage win32 callbacks. Trap exceptions, report on them, then return 'All OK' - # to the frame-work. """ - # import traceback - # try: - # ret = apply(ob, args) - # return ret - # except: - # # take copies of the exception values, else other (handled) exceptions may get - # # copied over by the other fns called. - # win32ui.SetStatusText('An exception occured in a windows command handler.') - # t, v, tb = sys.exc_info() - # traceback.print_exception(t, v, tb.tb_next) - # try: - # sys.stdout.flush() - # except (NameError, AttributeError): - # pass + # def CallbackManager(self, ob, args=()): + # """Manage win32 callbacks. Trap exceptions, report on them, then return 'All OK' + # to the frame-work.""" + # try: + # ret = apply(ob, args) + # return ret + # except Exception as error: + # import traceback + # + # # take copies of the exception values, else other (handled) exceptions may get + # # copied over by the other fns called. + # win32ui.SetStatusText("An exception occurred in a windows command handler.") + # traceback.print_exception(type(error), error, error.__traceback__.tb_next) + # try: + # sys.stdout.flush() + # except (NameError, AttributeError): + # pass # Command handlers. def OnFileMRU(self, id, code): diff --git a/Pythonwin/pywin/framework/editor/__init__.py b/Pythonwin/pywin/framework/editor/__init__.py index f237244924..73595f9352 100644 --- a/Pythonwin/pywin/framework/editor/__init__.py +++ b/Pythonwin/pywin/framework/editor/__init__.py @@ -29,37 +29,41 @@ def LoadDefaultEditor(): pass - -## prefModule = GetDefaultEditorModuleName() -## restorePrefModule = None -## mod = None -## if prefModule: -## try: -## mod = __import__(prefModule) -## except 'xx': -## msg = "Importing your preferred editor ('%s') failed.\n\nError %s: %s\n\nAn attempt will be made to load the default editor.\n\nWould you like this editor disabled in the future?" % (prefModule, sys.exc_info()[0], sys.exc_info()[1]) -## rc = win32ui.MessageBox(msg, "Error importing editor", win32con.MB_YESNO) -## if rc == win32con.IDNO: -## restorePrefModule = prefModule -## WriteDefaultEditorModule("") -## del rc -## -## try: -## # Try and load the default one - don't catch errors here. -## if mod is None: -## prefModule = "pywin.framework.editor.color.coloreditor" -## mod = __import__(prefModule) -## -## # Get at the real module. -## mod = sys.modules[prefModule] -## -## # Do a "from mod import *" -## globals().update(mod.__dict__) -## -## finally: -## # Restore the users default editor if it failed and they requested not to disable it. -## if restorePrefModule: -## WriteDefaultEditorModule(restorePrefModule) + # prefModule = GetDefaultEditorModuleName() + # restorePrefModule = None + # mod = None + # if prefModule: + # try: + # mod = __import__(prefModule) + # except Exception as error: + # msg = ( + # f"Importing your preferred editor ('{prefModule}') failed." + # + f"\n\nError {type(error)}: {error}" + # + "\n\nAn attempt will be made to load the default editor." + # + "\n\nWould you like this editor disabled in the future?" + # ) + # rc = win32ui.MessageBox(msg, "Error importing editor", win32con.MB_YESNO) + # if rc == win32con.IDNO: + # restorePrefModule = prefModule + # WriteDefaultEditorModule("") + # del rc + # + # try: + # # Try and load the default one - don't catch errors here. + # if mod is None: + # prefModule = "pywin.framework.editor.color.coloreditor" + # mod = __import__(prefModule) + # + # # Get at the real module. + # mod = sys.modules[prefModule] + # + # # Do a "from mod import *" + # globals().update(mod.__dict__) + # + # finally: + # # Restore the users default editor if it failed and they requested not to disable it. + # if restorePrefModule: + # WriteDefaultEditorModule(restorePrefModule) def GetEditorOption(option, defaultValue, min=None, max=None): diff --git a/Pythonwin/pywin/framework/editor/vss.py b/Pythonwin/pywin/framework/editor/vss.py index c357c58a4b..4c18ce387e 100644 --- a/Pythonwin/pywin/framework/editor/vss.py +++ b/Pythonwin/pywin/framework/editor/vss.py @@ -17,7 +17,6 @@ import os -import sys import traceback import win32api @@ -96,9 +95,7 @@ def CheckoutFile(fileName): ok = 1 except pythoncom.com_error as exc: win32ui.MessageBox(exc.strerror, "Error checking out file") - except: - typ, val, tb = sys.exc_info() + except Exception as error: traceback.print_exc() - win32ui.MessageBox(f"{typ} - {val}", "Error checking out file") - tb = None # Cleanup a cycle + win32ui.MessageBox(f"{type(error)} - {error}", "Error checking out file") return ok diff --git a/Pythonwin/pywin/framework/intpydde.py b/Pythonwin/pywin/framework/intpydde.py index 4b2365ab57..d9f33dbded 100644 --- a/Pythonwin/pywin/framework/intpydde.py +++ b/Pythonwin/pywin/framework/intpydde.py @@ -5,7 +5,6 @@ # is open. Strange, but true. If you have problems with this, close all Command Prompts! -import sys import traceback import win32ui @@ -29,10 +28,9 @@ def Exec(self, data): # print("Executing", cmd) self.app.OnDDECommand(data) except: - t, v, tb = sys.exc_info() # The DDE Execution failed. print("Error executing DDE command.") - traceback.print_exception(t, v, tb) + traceback.print_exc() return 0 diff --git a/Pythonwin/pywin/framework/scriptutils.py b/Pythonwin/pywin/framework/scriptutils.py index abf5a40c13..6e5dc85f16 100644 --- a/Pythonwin/pywin/framework/scriptutils.py +++ b/Pythonwin/pywin/framework/scriptutils.py @@ -603,7 +603,7 @@ def JumpToDocument(fileName, lineno=0, col=1, nChars=0, bScrollToTop=0): def _HandlePythonFailure(what, syntaxErrorPathName=None): - typ, details, tb = sys.exc_info() + details = sys.exc_info()[1] if isinstance(details, SyntaxError): try: msg, (fileName, line, col, text) = details @@ -616,7 +616,6 @@ def _HandlePythonFailure(what, syntaxErrorPathName=None): else: traceback.print_exc() win32ui.SetStatusText(f"Failed to {what} - {details}") - tb = None # Clean up a cycle. # Find the Python TabNanny in either the standard library or the Python Tools/Scripts directory. diff --git a/Pythonwin/pywin/scintilla/view.py b/Pythonwin/pywin/scintilla/view.py index 0d73382c3e..6b298a57e5 100644 --- a/Pythonwin/pywin/scintilla/view.py +++ b/Pythonwin/pywin/scintilla/view.py @@ -506,9 +506,9 @@ def _AutoComplete(self): self._UpdateWithITypeInfo(items_dict, typeInfo) except: pass - except: + except Exception as error: win32ui.SetStatusText( - f"Error attempting to get object attributes - {sys.exc_info()[0]!r}" + f"Error attempting to get object attributes - {type(error)!r}" ) items = [ diff --git a/Pythonwin/pywin/tools/browser.py b/Pythonwin/pywin/tools/browser.py index b5629dc065..8025329926 100644 --- a/Pythonwin/pywin/tools/browser.py +++ b/Pythonwin/pywin/tools/browser.py @@ -5,7 +5,6 @@ # >>> browser.Browse() # or # >>> browser.Browse(your_module) -import sys import types import __main__ @@ -340,10 +339,8 @@ def OnInitDialog(self): self.edit = self.GetDlgItem(win32ui.IDC_EDIT1) try: strval = str(self.object) - except: - t, v, tb = sys.exc_info() - strval = f"Exception getting object value\n\n{t}:{v}" - tb = None + except Exception as error: + strval = f"Exception getting object value\n\n{type(error)}:{error}" strval = re.sub(r"\n", "\r\n", strval) self.edit.ReplaceSel(strval) diff --git a/adodbapi/adodbapi.py b/adodbapi/adodbapi.py index 8f590c4668..d403f6a8b2 100644 --- a/adodbapi/adodbapi.py +++ b/adodbapi/adodbapi.py @@ -33,7 +33,6 @@ import copy import decimal import os -import sys import weakref from . import ado_consts as adc, apibase as api, process_connect_string @@ -335,7 +334,7 @@ def close(self): try: self._closeAdoConnection() # v2.1 Rose except Exception as e: - self._raiseConnectionError(sys.exc_info()[0], sys.exc_info()[1]) + self._raiseConnectionError(type(e), e) self.connector = None # v2.4.2.2 fix subtle timeout bug # per M.Hammond: "I expect the benefits of uninitializing are probably fairly small, @@ -855,7 +854,6 @@ def _buildADOparameterList(self, parameters, sproc=False): except api.Error: if verbose: print("ADO Parameter Refresh failed") - pass else: if len(parameters) != self.cmd.Parameters.Count - 1: raise api.ProgrammingError( diff --git a/adodbapi/apibase.py b/adodbapi/apibase.py index 40aeb9447f..7190541897 100644 --- a/adodbapi/apibase.py +++ b/adodbapi/apibase.py @@ -551,9 +551,8 @@ def __getitem__(self, key): # used for row[key] type of value access return self._getValue( self.rows.columnNames[key.lower()] ) # extension row[columnName] designation - except (KeyError, TypeError): - er, st, tr = sys.exc_info() - raise er(f'No such key as "{key!r}" in {self!r}').with_traceback(tr) + except (KeyError, TypeError) as er: + raise type(er)(f'No such key as "{key!r}" in {self!r}') from er def __iter__(self): return iter(self.__next__()) diff --git a/com/win32com/client/gencache.py b/com/win32com/client/gencache.py index 4012cb2a58..c42fc70680 100644 --- a/com/win32com/client/gencache.py +++ b/com/win32com/client/gencache.py @@ -766,12 +766,8 @@ def Rebuild(verbose=1): print("Checking", GetGeneratedFileName(*info)) try: AddModuleToCache(iid, lcid, major, minor, verbose, 0) - except: - print( - "Could not add module {} - {}: {}".format( - info, sys.exc_info()[0], sys.exc_info()[1] - ) - ) + except Exception as error: + print(f"Could not add module {info} - {type(error)}: {error}") if verbose and len(infos): # Don't bother reporting this when directory is empty! print("Done.") _SaveDicts() diff --git a/com/win32com/client/makepy.py b/com/win32com/client/makepy.py index 8d23c9a171..a30038acd6 100644 --- a/com/win32com/client/makepy.py +++ b/com/win32com/client/makepy.py @@ -229,10 +229,8 @@ def GetTypeLibsForSpec(arg): spec.lcid = attr[1] typelibs.append((tlb, spec)) return typelibs - except pythoncom.com_error: - t, v, tb = sys.exc_info() + except pythoncom.com_error as v: sys.stderr.write(f"Unable to load type library from '{arg}' - {v}\n") - tb = None # Storing tb in a local is a cycle! sys.exit(1) diff --git a/com/win32com/test/testall.py b/com/win32com/test/testall.py index 991dbdf6c8..a9ee8dd60a 100644 --- a/com/win32com/test/testall.py +++ b/com/win32com/test/testall.py @@ -202,8 +202,8 @@ def get_test_mod_and_func(test_name, import_failures): try: __import__(fq_mod_name) mod = sys.modules[fq_mod_name] - except: - import_failures.append((mod_name, sys.exc_info()[:2])) + except Exception as error: + import_failures.append((mod_name, error.__traceback__)) return None, None func = None if func_name is None else getattr(mod, func_name) return mod, func @@ -238,8 +238,8 @@ def make_test_suite(test_level=1): for mod_name in unittest_other_modules[i]: try: __import__(mod_name) - except: - import_failures.append((mod_name, sys.exc_info()[:2])) + except Exception as error: + import_failures.append((mod_name, error.__traceback__)) continue mod = sys.modules[mod_name] diff --git a/com/win32comext/axdebug/expressions.py b/com/win32comext/axdebug/expressions.py index 401b9a5996..cd4c71928c 100644 --- a/com/win32comext/axdebug/expressions.py +++ b/com/win32comext/axdebug/expressions.py @@ -1,5 +1,4 @@ import io -import sys import traceback from pprint import pprint @@ -58,10 +57,8 @@ def Start(self, callback): exec(self.code, self.frame.f_globals, self.frame.f_locals) self.result = "" self.hresult = 0 - except: - l = traceback.format_exception_only( - sys.exc_info()[0], sys.exc_info()[1] - ) + except Exception as error: + l = traceback.format_exception_only(type(error), error) # l is a list of strings with trailing "\n" self.result = "\n".join(s[:-1] for s in l) self.hresult = winerror.E_FAIL diff --git a/com/win32comext/axdebug/util.py b/com/win32comext/axdebug/util.py index b1b560e40e..e52eaeb822 100644 --- a/com/win32comext/axdebug/util.py +++ b/com/win32comext/axdebug/util.py @@ -80,19 +80,15 @@ def _Invoke_(self, dispid, lcid, wFlags, args): ) # print("Invoke of", dispid, "returning", rc) return rc - except COMException: - t, v, tb = sys.exc_info() - tb = None # A cycle - scode = v.scode + except COMException as v: try: desc = f" ({v.description})" except AttributeError: desc = "" - print(f"*** Invoke of {dispid} raised COM exception 0x{scode:x}{desc}") + print(f"*** Invoke of {dispid} raised COM exception 0x{v.scode:x}{desc}") except: print(f"*** Invoke of {dispid} failed:") - typ, val, tb = sys.exc_info() import traceback - traceback.print_exception(typ, val, tb) + traceback.print_exc() raise diff --git a/com/win32comext/axscript/client/framework.py b/com/win32comext/axscript/client/framework.py index 69e8cc5543..8ed22d8445 100644 --- a/com/win32comext/axscript/client/framework.py +++ b/com/win32comext/axscript/client/framework.py @@ -763,13 +763,9 @@ def SetScriptSite(self, site): "Debugging extensions (axdebug) module does not exist - debugging is disabled.." ) self.debugManager = None - except: + except Exception as error: traceback.print_exc() - trace( - "*** Debugger Manager could not initialize - {}: {}".format( - sys.exc_info()[0], sys.exc_info()[1] - ) - ) + trace(f"*** Debugger Manager could not initialize - {type(error)}: {error}") self.debugManager = None try: @@ -1197,11 +1193,11 @@ def EvalInScriptedSection(self, codeBlock, globals, locals=None): def HandleException(self, codeBlock: AXScriptCodeBlock | None) -> NoReturn: """Never returns - raises a ComException""" - exc_type, exc_value, *_ = sys.exc_info() + exc_value = sys.exc_info()[1] # If a SERVER exception, re-raise it. If a client side COM error, it is # likely to have originated from the script code itself, and therefore # needs to be reported like any other exception. - if IsCOMServerException(exc_type): + if IsCOMServerException(type(exc_value)): # Ensure the traceback doesn't cause a cycle. raise # It could be an error by another script. diff --git a/isapi/install.py b/isapi/install.py index aa861bbfc5..2d1bcc0e43 100644 --- a/isapi/install.py +++ b/isapi/install.py @@ -563,16 +563,14 @@ def RemoveDirectory(params, options): # Be robust should IIS get upset about unloading. try: directory.AppUnLoad() - except: - exc_val = sys.exc_info()[1] + except Exception as exc_val: log(2, f"AppUnLoad() for {params.Name} failed: {exc_val}") # Continue trying to delete it. try: parent = GetObject(directory.Parent) parent.Delete(directory.Class, directory.Name) log(1, f"Deleted Virtual Directory: {params.Name}") - except: - exc_val = sys.exc_info()[1] + except Exception as exc_val: log(1, f"Failed to remove directory {params.Name}: {exc_val}") diff --git a/isapi/threaded_extension.py b/isapi/threaded_extension.py index a7fd17ff39..84bb78f980 100644 --- a/isapi/threaded_extension.py +++ b/isapi/threaded_extension.py @@ -156,7 +156,6 @@ def HandleDispatchError(self, ecb): ecb.HttpStatusCode = isapicon.HSE_STATUS_ERROR # control_block.LogData = "we failed!" exc_typ, exc_val, exc_tb = sys.exc_info() - limit = None try: try: import html @@ -166,9 +165,9 @@ def HandleDispatchError(self, ecb): ) print(file=ecb) print("
{}{}".format(
@@ -187,7 +186,4 @@ def HandleDispatchError(self, ecb):
print("ORIGINAL extension error:")
traceback.print_exception(exc_typ, exc_val, exc_tb)
finally:
- # holding tracebacks in a local of a frame that may itself be
- # part of a traceback used to be evil and cause leaks!
- exc_tb = None
ecb.DoneWithSession()
diff --git a/win32/Lib/pywin32_testutil.py b/win32/Lib/pywin32_testutil.py
index e2b1b8b3ab..a897b878d4 100644
--- a/win32/Lib/pywin32_testutil.py
+++ b/win32/Lib/pywin32_testutil.py
@@ -1,12 +1,19 @@
-# Utilities for the pywin32 tests
+"""Utilities for the pywin32 tests"""
+
+from __future__ import annotations
+
import gc
import os
import site
import sys
import unittest
+from typing import TYPE_CHECKING
import winerror
+if TYPE_CHECKING:
+ from _typeshed import OptExcInfo
+
##
## unittest related stuff
##
@@ -214,7 +221,7 @@ def __init__(self, *args, **kw):
super().__init__(*args, **kw)
self.skips = {} # count of skips for each reason.
- def addError(self, test, err):
+ def addError(self, test, err: OptExcInfo) -> None:
"""Called when an error has occurred. 'err' is a tuple of values as
returned by sys.exc_info().
"""
diff --git a/win32/scripts/setup_d.py b/win32/scripts/setup_d.py
index 6fcb730d93..29fe352cd2 100644
--- a/win32/scripts/setup_d.py
+++ b/win32/scripts/setup_d.py
@@ -59,9 +59,9 @@ def _docopy(src, dest):
shutil.copy(src, dest)
print(f"Copied {src} -> {dest}")
return 1
- except:
+ except Exception as error:
print(f"Error copying '{src}' -> '{dest}'")
- print(sys.exc_info()[1])
+ print(error)
usage_and_die(3)