From: Mike Bayer Date: Thu, 11 Jun 2020 18:31:57 +0000 (-0400) Subject: Add version token to error URL X-Git-Tag: rel_1_4_0b1~270 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=dbaf82d258cc12d92ef28de4677d147fdb7808fd;p=thirdparty%2Fsqlalchemy%2Fsqlalchemy.git Add version token to error URL the sqlalche.me redirector now supports the numerical version code in the URL, e.g. /13/, /14/, /20/, etc., so that we can redirect to the error codes for the appropriate version of SQLAlchemy in use without going through the catch-all "latest" link. If a particular version of the docs is no longer on the site, the redirect will revert to falling through the "latest" link (which ultimately lands on the current release version, /13/ at the time of this writing). Change-Id: I3bb463fd6fb6c8767c95a57f3699aba715a9a72d --- diff --git a/lib/sqlalchemy/__init__.py b/lib/sqlalchemy/__init__.py index 27e9fd1c0b..d52393d0b1 100644 --- a/lib/sqlalchemy/__init__.py +++ b/lib/sqlalchemy/__init__.py @@ -142,5 +142,9 @@ def __go(lcls): _sa_util.preloaded.import_prefix("sqlalchemy") + from . import exc + + exc._version_token = "".join(__version__.split(".")[0:2]) + __go(locals()) diff --git a/lib/sqlalchemy/exc.py b/lib/sqlalchemy/exc.py index 92322fb903..491dde7b21 100644 --- a/lib/sqlalchemy/exc.py +++ b/lib/sqlalchemy/exc.py @@ -15,6 +15,8 @@ raised as a result of DBAPI exceptions are all subclasses of from .util import compat +_version_token = None + class SQLAlchemyError(Exception): """Generic error class.""" @@ -33,7 +35,7 @@ class SQLAlchemyError(Exception): else: return ( "(Background on this error at: " - "http://sqlalche.me/e/%s)" % (self.code,) + "http://sqlalche.me/e/%s/%s)" % (_version_token, self.code,) ) def _message(self, as_unicode=compat.py3k): diff --git a/test/base/test_except.py b/test/base/test_except.py index be8c85a643..7ef0776590 100644 --- a/test/base/test_except.py +++ b/test/base/test_except.py @@ -47,6 +47,17 @@ class SpecificIntegrityError(WrongNameError): class WrapTest(fixtures.TestBase): + def test_version_token(self): + assert sa_exceptions._version_token in ( + "13", + "14", + "15", + "16", + "20", + "21", + "22", + ) + def _translating_dialect_fixture(self): d = default.DefaultDialect() d.dbapi_exception_translation_map = { @@ -72,7 +83,8 @@ class WrapTest(fixtures.TestBase): str(exc), "(test.base.test_except.OperationalError) \n" "[SQL: this is a message]\n" - "(Background on this error at: http://sqlalche.me/e/e3q8)", + "(Background on this error at: http://sqlalche.me/e/%s/e3q8)" + % sa_exceptions._version_token, ) def test_tostring_with_newlines(self): @@ -89,7 +101,8 @@ class WrapTest(fixtures.TestBase): "(test.base.test_except.OperationalError) \n" "[SQL: this is a message\nthis is the next line\n" "the last line]\n" - "(Background on this error at: http://sqlalche.me/e/e3q8)", + "(Background on this error at: http://sqlalche.me/e/%s/e3q8)" + % sa_exceptions._version_token, ) def test_statement_error_no_code(self): @@ -122,7 +135,8 @@ class WrapTest(fixtures.TestBase): "(sqlalchemy.exc.InvalidRequestError) hello\n" "[SQL: select * from table]\n" "[parameters: [{'x': 1}]]\n" - "(Background on this error at: http://sqlalche.me/e/abcd)", + "(Background on this error at: http://sqlalche.me/e/%s/abcd)" + % sa_exceptions._version_token, ) eq_(err.args, ("(sqlalchemy.exc.InvalidRequestError) hello",)) @@ -133,7 +147,8 @@ class WrapTest(fixtures.TestBase): eq_( str(orig), "(2006, 'Test raise operational error')\n" - "(Background on this error at: http://sqlalche.me/e/dbapi)", + "(Background on this error at: http://sqlalche.me/e/%s/dbapi)" + % sa_exceptions._version_token, ) def test_wrap_unicode_arg(self): @@ -144,7 +159,7 @@ class WrapTest(fixtures.TestBase): compat.text_type(orig), compat.u( "méil\n(Background on this error at: " - "http://sqlalche.me/e/dbapi)" + "http://sqlalche.me/e/%s/dbapi)" % sa_exceptions._version_token ), ) eq_(orig.args, (u("méil"),)) @@ -217,7 +232,8 @@ class WrapTest(fixtures.TestBase): "[SQL: this is a message]\n" "[parameters: [{1: 1}, {1: 1}, {1: 1}, {1: 1}, {1: 1}," " {1: 1}, {1: 1}, {1: 1}, {1: 1}, {1: 1}]]\n" - "(Background on this error at: http://sqlalche.me/e/e3q8)", + "(Background on this error at: http://sqlalche.me/e/%s/e3q8)" + % sa_exceptions._version_token, ) eq_( exc.args, @@ -252,7 +268,8 @@ class WrapTest(fixtures.TestBase): "{1: 1}, {1: 1}, {1: 1}, {1: 1}, {1: 1}, " "{1: 1}, {1: 1} ... displaying 10 of 11 total " "bound parameter sets ... {1: 1}, {1: 1}]]\n" - "(Background on this error at: http://sqlalche.me/e/e3q8)", + "(Background on this error at: http://sqlalche.me/e/%s/e3q8)" + % sa_exceptions._version_token, ) try: raise sa_exceptions.DBAPIError.instance( @@ -269,7 +286,8 @@ class WrapTest(fixtures.TestBase): "[SQL: this is a message]\n" "[parameters: [(1,), " "(1,), (1,), (1,), (1,), (1,), (1,), (1,), (1,), (1,)]]\n" - "(Background on this error at: http://sqlalche.me/e/e3q8)", + "(Background on this error at: http://sqlalche.me/e/%s/e3q8)" + % sa_exceptions._version_token, ) try: raise sa_exceptions.DBAPIError.instance( @@ -300,7 +318,8 @@ class WrapTest(fixtures.TestBase): "(1,), (1,), (1,), (1,), (1,), (1,), (1,) " "... displaying 10 of 11 total bound " "parameter sets ... (1,), (1,)]]\n" - "(Background on this error at: http://sqlalche.me/e/e3q8)", + "(Background on this error at: http://sqlalche.me/e/%s/e3q8)" + % sa_exceptions._version_token, ) def test_db_error_busted_dbapi(self):