From d13c5349b668344e11d18df86775c0fb38ce8372 Mon Sep 17 00:00:00 2001 From: macneiln Date: Mon, 7 Sep 2020 19:48:31 +1200 Subject: [PATCH 1/3] Add hash_extension variable Add hash_extension variable to requires_signature function so URL _signature can be verified ignoring the given request extension. --- gluon/tools.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/gluon/tools.py b/gluon/tools.py index 9fafd48e..01095e05 100644 --- a/gluon/tools.py +++ b/gluon/tools.py @@ -3930,7 +3930,7 @@ class Auth(AuthAPI): return self.has_permission(name, table_name, record_id) return self.requires(has_permission, otherwise=otherwise) - def requires_signature(self, otherwise=None, hash_vars=True): + def requires_signature(self, otherwise=None, hash_vars=True, hash_extension=True): """ Decorator that prevents access to action if not logged in or if user logged in is not a member of group_id. @@ -3938,7 +3938,7 @@ class Auth(AuthAPI): group_id is calculated. """ def verify(): - return URL.verify(current.request, user_signature=True, hash_vars=hash_vars) + return URL.verify(current.request, user_signature=True, hash_vars=hash_vars, hash_extension=True) return self.requires(verify, otherwise) def accessible_query(self, name, table, user_id=None): From c23e95a9e2204a5b7701429dde74ca9e87e801c8 Mon Sep 17 00:00:00 2001 From: macneiln Date: Mon, 7 Sep 2020 19:55:59 +1200 Subject: [PATCH 2/3] Add hash_extension functionality Add hash_extension functionality so _signature can be verified regardless of the extension. --- gluon/html.py | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) diff --git a/gluon/html.py b/gluon/html.py index b4d597fd..9b8b52b0 100644 --- a/gluon/html.py +++ b/gluon/html.py @@ -190,7 +190,8 @@ def URL(a=None, port=None, encode_embedded_slash=False, url_encode=True, - language=None + language=None, + hash_extension=True ): """ generates a url '/a/c/f' corresponding to application a, controller c @@ -339,7 +340,8 @@ def URL(a=None, if '.' in function: function, extension = function.rsplit('.', 1) - function2 = '%s.%s' % (function, extension or 'html') + # only include the extension as part of the variables for the hash if requested + function2 = '%s.%s' % (function, extension or 'html') if hash_extension else function if not (application and controller and function): raise SyntaxError('not enough information to build the url (%s %s %s)' % (application, controller, function)) @@ -416,7 +418,7 @@ def URL(a=None, return url -def verifyURL(request, hmac_key=None, hash_vars=True, salt=None, user_signature=None): +def verifyURL(request, hmac_key=None, hash_vars=True, salt=None, user_signature=None, hash_extension=True): """ Verifies that a request's args & vars have not been tampered with by the user @@ -477,10 +479,19 @@ def verifyURL(request, hmac_key=None, hash_vars=True, salt=None, user_signature= # always include all of the args other = args and urllib_quote('/' + '/'.join([str(x) for x in args])) or '' + + # decide whether the extension should be part of the hash verification + h_extension = request.extension if hash_extension else '' + + # only add a period to the extension when it exists otherwise empty + # extensions will fail to validate + if h_extension: + h_extension = '.%s' % (h_extension) + h_args = '/%s/%s/%s.%s%s' % (request.application, request.controller, request.function, - request.extension, + h_extension, other) # but only include those vars specified (allows more flexibility for use with From d23a6e7b1be5de36f226f8535ed4b086a97af3bf Mon Sep 17 00:00:00 2001 From: macneiln Date: Mon, 7 Sep 2020 20:55:21 +1200 Subject: [PATCH 3/3] Remove missed period from h_args Update as part of adding hash_extension functionality. --- gluon/html.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gluon/html.py b/gluon/html.py index 9b8b52b0..49890fa6 100644 --- a/gluon/html.py +++ b/gluon/html.py @@ -488,7 +488,7 @@ def verifyURL(request, hmac_key=None, hash_vars=True, salt=None, user_signature= if h_extension: h_extension = '.%s' % (h_extension) - h_args = '/%s/%s/%s.%s%s' % (request.application, + h_args = '/%s/%s/%s%s%s' % (request.application, request.controller, request.function, h_extension,