[Checkins] SVN: z3c.password/branches/jw-noraise-for-irrelevant-requests/src/z3c/password/principal.py check for relevancy as early as possible. this prevents account locked errors raised for things like resources.

Jan-Wijbrand Kolman janwijbrand at gmail.com
Thu Feb 4 06:08:56 EST 2010


Log message for revision 108749:
  check for relevancy as early as possible. this prevents account locked errors raised for things like resources.

Changed:
  U   z3c.password/branches/jw-noraise-for-irrelevant-requests/src/z3c/password/principal.py

-=-
Modified: z3c.password/branches/jw-noraise-for-irrelevant-requests/src/z3c/password/principal.py
===================================================================
--- z3c.password/branches/jw-noraise-for-irrelevant-requests/src/z3c/password/principal.py	2010-02-04 11:07:44 UTC (rev 108748)
+++ z3c.password/branches/jw-noraise-for-irrelevant-requests/src/z3c/password/principal.py	2010-02-04 11:08:55 UTC (rev 108749)
@@ -81,6 +81,30 @@
         #hook to facilitate testing and easier override
         return datetime.datetime.now()
 
+    def _isIrrelevantRequest(self, RELEVANT=False, IRRELEVANT=True):
+        fac = self._failedAttemptCheck()
+        if fac is None:
+            return RELEVANT
+
+        if fac == interfaces.TML_CHECK_ALL:
+            return RELEVANT
+
+        interaction = getInteraction()
+        try:
+            request = interaction.participations[0]
+        except IndexError:
+            return RELEVANT # no request, we regard that as relevant.
+
+        if fac == interfaces.TML_CHECK_NONRESOURCE:
+            if '/@@/' in request.getURL():
+                return IRRELEVANT
+            return RELEVANT
+
+        if fac == interfaces.TML_CHECK_POSTONLY:
+            if request.method == 'POST':
+                return RELEVANT
+            return IRRELEVANT
+
     def checkPassword(self, pwd, ignoreExpiration=False, ignoreFailures=False):
         # keep this as fast as possible, because it will be called (usually)
         # for EACH request
@@ -88,6 +112,11 @@
         # Check the password
         same = super(PrincipalMixIn, self).checkPassword(pwd)
 
+        # Do not try to record failed attempts or raise account locked
+        # errors for requests that are irrelevant in this regard.
+        if self._isIrrelevantRequest():
+            return same
+
         if not ignoreFailures and self.lastFailedAttempt is not None:
             if self.tooManyLoginFailures():
                 locked = self.accountLocked()
@@ -118,7 +147,9 @@
             add = 0
         else:
             #failed attempt, record it, increase counter
-            add = self.checkFailedAttempt()
+            self.failedAttempts += 1
+            self.lastFailedAttempt = self.now()
+            add = 1
 
         # If the maximum amount of failures has been reached notify the
         # system by raising an error.
@@ -133,45 +164,6 @@
 
         return same
 
-    def _getRequest(self):
-        interaction = getInteraction()
-        try:
-            return interaction.participations[0]
-        except IndexError:
-            return None
-
-    def checkFailedAttempt(self):
-        #failed attempt, record it, increase counter (in case we have to)
-        validRequest = True
-        fac = self._failedAttemptCheck()
-        if fac == interfaces.TML_CHECK_ALL:
-            validRequest = True
-        else:
-            request = self._getRequest()
-            if request is None:
-                validRequest = True
-            else:
-                if fac == interfaces.TML_CHECK_NONRESOURCE:
-                    url = request.getURL()
-                    if '/@@/' in url:
-                        #this is a resource
-                        validRequest = False
-                    else:
-                        validRequest = True
-                elif fac == interfaces.TML_CHECK_POSTONLY:
-                    if request.method == 'POST':
-                        #this is a POST request
-                        validRequest = True
-                    else:
-                        validRequest = False
-
-        if validRequest:
-            self.failedAttempts += 1
-            self.lastFailedAttempt = self.now()
-            return 1
-        else:
-            return 0
-
     def tooManyLoginFailures(self, add = 0):
         attempts = self._maxFailedAttempts()
         #this one needs to be >=, because... data just does not



More information about the checkins mailing list