Exemplo n.º 1
0
    def extractCredentials(self, request, overrides=None):
        """Extracts credentials from a session if they exist."""

        if not IHTTPRequest.providedBy(request):
            return None

        session = ISession(request)
        sessionData = session.get('zope.app.authentication.browserplugins')

        (login, password, domain, ip) = (None, None, None, None)
        credentials = None
        logging_in = False

        if overrides:
            login = overrides.get('login', None)
            password = overrides.get('password', None)
            ip = overrides.get('ip', None)
            domain = overrides.get('domain', None)

        login = login or request.get(self.loginfield, None)
        password = password or request.get(self.passwordfield, None)
        domain = domain or request.get(self.domainfield, None)
        ip = ip or request.environment.get('HTTP_X_FORWARDED_FOR', None)
        ip = ip or request.environment.get('REMOTE_ADDR', None)

        if login and password:
            credentials = SessionCredentials(
                login,
                password,
                ip=ip,
                domain=domain,
                request_annotations=request.annotations,
                passwordManager=self.passwordManager)
            if IHTTPRequest.providedBy(request):
                self._update_cookie(request, credentials)
            logging_in = True

        elif not sessionData:
            return None
        sessionData = session['zope.app.authentication.browserplugins']
        if credentials:
            sessionData['credentials'] = credentials
        else:
            credentials = sessionData.get('credentials', None)
            if not credentials:
                return None
            if credentials.isExpired(self.idleExpiry):
                return None
        return {
            'login': credentials.getLogin(),
            'password': credentials.getPassword(),
            'ip': credentials.getIP(),
            'domain': credentials.getDomain(),
            'logging_in': logging_in,
            'request-annotations': credentials.getRequestAnnotations(),
            'extractTime': credentials.getExtractTime(),
            'accessTime': credentials.getAccessTime(),
            'passwordManager': credentials.getPasswordManager(),
        }
Exemplo n.º 2
0
 def logout(self, request):
     if not IHTTPRequest.providedBy(request):
         return
     request.response.expireCookie(self.cookie_name, path="/")
     session = ISession(request, None)
     if session is not None:
         session.delete()
Exemplo n.º 3
0
 def extractCredentials(self, request):
     if not IHTTPRequest.providedBy(request):
         return None
     login = request.get(self.loginfield, None)
     password = request.get(self.passwordfield, None)
     session = ISession(request)
     sessionData = session.get('zope.pluggableauth.browserplugins')
     traversalStack = request.getTraversalStack()
     authMethod = 'standard'
     credentials = None
     if sessionData:
         credentials = sessionData.get('credentials')
         if isinstance(sessionData, TwoFactorSessionCredentials):
             authMethod = '2factor'
     if (authMethod == 'standard' and 
             traversalStack and traversalStack[-1].startswith('++auth++')):
         authMethod = traversalStack[-1][8:]
     viewAnnotations = request.annotations.setdefault('loops.view', {})
     viewAnnotations['auth_method'] = authMethod
     #log.info('authentication method: %s.' % authMethod)
     if authMethod == 'standard':
         return self.extractStandardCredentials(
                         request, login, password, session, credentials)
     elif authMethod == '2factor':
         return self.extract2FactorCredentials(
                         request, login, password, session, credentials)
     else:
         return None
Exemplo n.º 4
0
def get_request_language():
    request = common.get_request()
    if IHTTPRequest.providedBy(request):
        lang = request.locale.getLocaleID()
    else:
        lang = capi.default_language
    return lang
Exemplo n.º 5
0
    def extractCredentials(self, request):
        """Extracts credentials from a session if they exist."""
        if not IHTTPRequest.providedBy(request):
            return None
        session = ISession(request, None)
        sessionData = session.get('z3c.authenticator.credential.session')
        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        # support z3c.form prefixes
        for prefix in self.prefixes:
            login = request.get(prefix + self.loginfield, login)
            password = request.get(prefix + self.passwordfield, password)
        credentials = None

        if login and password:
            credentials = SessionCredentials(login, password)
        elif not sessionData:
            return None
        sessionData = session['z3c.authenticator.credential.session']
        if credentials:
            sessionData['credentials'] = credentials
        else:
            credentials = sessionData.get('credentials', None)
        if not credentials:
            return None
        return {'login': credentials.getLogin(),
                'password': credentials.getPassword()}
Exemplo n.º 6
0
    def extractCredentials(self, request):
        if not IHTTPRequest.providedBy( request ):
            return None
        
        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        cookie = request.get(self.cookie_name, None)

        # login attempt 
        if login and password:
            # verify the credentials and then setup token, needs a double login for
            # initial login attempts
            creds = {'login': login, 'password':password }
            # does assume a pluggable authentication utility
            for auth_name, auth in getUtility( IAuthentication ).getAuthenticatorPlugins():
                if auth.authenticateCredentials( creds ):
                    self.setupTokenSession( login, request )                    
                    break
            return creds

        # check for token
        if not self.cookie_name in request:
            return None

        # extract token
        try:
            return { 'token': binascii.a2b_base64(request.get(self.cookie_name)) }
        except binascii.Error:
            # If we have a cookie which is not properly base64 encoded it
            # can not be ours.
            return None
Exemplo n.º 7
0
 def extractCredentials(self, request):
     if not IHTTPRequest.providedBy(request):
         return None
     login = request.get(self.loginfield, None)
     password = request.get(self.passwordfield, None)
     session = ISession(request)
     sessionData = session.get('zope.pluggableauth.browserplugins')
     traversalStack = request.getTraversalStack()
     authMethod = 'standard'
     credentials = None
     if sessionData:
         credentials = sessionData.get('credentials')
         if isinstance(sessionData, TwoFactorSessionCredentials):
             authMethod = '2factor'
     if (authMethod == 'standard' and traversalStack
             and traversalStack[-1].startswith('++auth++')):
         authMethod = traversalStack[-1][8:]
     viewAnnotations = request.annotations.setdefault('loops.view', {})
     viewAnnotations['auth_method'] = authMethod
     #log.info('authentication method: %s.' % authMethod)
     if authMethod == 'standard':
         return self.extractStandardCredentials(request, login, password,
                                                session, credentials)
     elif authMethod == '2factor':
         return self.extract2FactorCredentials(request, login, password,
                                               session, credentials)
     else:
         return None
Exemplo n.º 8
0
 def getLanguage(self):
     try:
         request = get_request()
         if request and IHTTPRequest.providedBy(request):
             return request.getCookies().get(I18N_COOKIE_NAME)
     except zope.security.interfaces.NoInteraction:
         return None
Exemplo n.º 9
0
def get_request_language():
    request = common.get_request()
    if IHTTPRequest.providedBy(request):
        lang = request.locale.getLocaleID()
    else:
        lang = capi.default_language
    return lang
Exemplo n.º 10
0
    def extractCredentials(self, request):
        """Extracts credentials from a session if they exist."""
        if not IHTTPRequest.providedBy(request):
            return None
        session = ISession(request)
        sessionData = session.get(
            'zope.pluggableauth.browserplugins')
        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        credentials = None

        if login and password:
            credentials = self._makeCredentials(login, password)
        elif not sessionData:
            return None
        sessionData = session[
            'zope.pluggableauth.browserplugins']
        if credentials:
            sessionData['credentials'] = credentials
        else:
            credentials = sessionData.get('credentials', None)
        if not credentials:
            return None
        return {'login': credentials.getLogin(),
                'password': credentials.getPassword()}
Exemplo n.º 11
0
def solrSearchResults(request=None, **keywords):
    """ perform a query using solr after translating the passed in
        parameters with portal catalog semantics """
    site = getSite()
    search = queryUtility(ISearch, context=site)
    config = queryUtility(ISolrConnectionConfig, context=site)

    if request is None:
        # try to get a request instance, so that flares can be adapted to
        # ploneflares and urls can be converted into absolute ones etc;
        # however, in this case any arguments from the request are ignored
        args = deepcopy(keywords)
        request = getattr(site, 'REQUEST', None)
    elif IHTTPRequest.providedBy(request):
        args = deepcopy(request.form)
        args.update(keywords)  # keywords take precedence
    else:
        assert isinstance(request, dict), request
        args = deepcopy(request)
        args.update(keywords)  # keywords take precedence
        # if request is a dict, we need the real request in order to
        # be able to adapt to plone flares
        request = getattr(site, 'REQUEST', args)

    if 'path' in args and 'navtree' in args['path']:
        raise FallBackException     # we can't handle navtree queries yet

    use_solr = args.get('use_solr', False)  # A special key to force Solr
    if not use_solr and config.required:
        required = set(config.required).intersection(args)
        if required:
            for key in required:
                if not args[key]:
                    raise FallBackException
        else:
            raise FallBackException

    query, params = search.buildQueryAndParameters(**args)

    if query != {}:
        __traceback_info__ = (query, params, args)
        response = search(query, **params)
    else:
        return SolrResponse()

    def wrap(flare):
        """ wrap a flare object with a helper class """
        adapter = queryMultiAdapter((flare, request), IFlare)
        return adapter is not None and adapter or flare

    schema = search.getManager().getSchema() or {}
    results = response.results()
    for idx, flare in enumerate(results):
        flare = wrap(flare)
        for missing in set(schema.stored).difference(flare):
            flare[missing] = MV
        results[idx] = wrap(flare)
    padResults(results, **params)           # pad the batch
    return response
Exemplo n.º 12
0
def solrSearchResults(request=None, **keywords):
    """ perform a query using solr after translating the passed in
        parameters with portal catalog semantics """
    site = getSite()
    search = queryUtility(ISearch, context=site)
    config = queryUtility(ISolrConnectionConfig, context=site)

    if request is None:
        # try to get a request instance, so that flares can be adapted to
        # ploneflares and urls can be converted into absolute ones etc;
        # however, in this case any arguments from the request are ignored
        args = deepcopy(keywords)
        request = getattr(site, 'REQUEST', None)
    elif IHTTPRequest.providedBy(request):
        args = deepcopy(request.form)
        args.update(keywords)  # keywords take precedence
    else:
        assert isinstance(request, dict), request
        args = deepcopy(request)
        args.update(keywords)  # keywords take precedence
        # if request is a dict, we need the real request in order to
        # be able to adapt to plone flares
        request = getattr(site, 'REQUEST', args)

    if 'path' in args and 'navtree' in args['path']:
        raise FallBackException  # we can't handle navtree queries yet

    use_solr = args.get('use_solr', False)  # A special key to force Solr
    if not use_solr and config.required:
        required = set(config.required).intersection(args)
        if required:
            for key in required:
                if not args[key]:
                    raise FallBackException
        else:
            raise FallBackException

    query, params = search.buildQueryAndParameters(**args)

    if query != {}:
        __traceback_info__ = (query, params, args)
        response = search(query, **params)
    else:
        return SolrResponse()

    def wrap(flare):
        """ wrap a flare object with a helper class """
        adapter = queryMultiAdapter((flare, request), IFlare)
        return adapter is not None and adapter or flare

    schema = search.getManager().getSchema() or {}
    results = response.results()
    for idx, flare in enumerate(results):
        flare = wrap(flare)
        for missing in set(schema.stored).difference(flare):
            flare[missing] = MV
        results[idx] = wrap(flare)
    padResults(results, **params)  # pad the batch
    return response
Exemplo n.º 13
0
    def extractCredentials(self, request):
        """Extracts HTTP basic auth credentials from a request.

        First we need to create a request that contains some credentials.

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest(
          ...     environ={'HTTP_AUTHORIZATION': u'Basic bWdyOm1ncnB3'})

        Now create the plugin and get the credentials.

          >>> plugin = HTTPBasicAuthCredentialsPlugin()
          >>> from pprint import pprint
          >>> pprint(plugin.extractCredentials(request))
          {'login': u'mgr', 'password': u'mgrpw'}

        Make sure we return `None`, if no authentication header has been
        specified.

          >>> print(plugin.extractCredentials(TestRequest()))
          None

        Also, this plugin can *only* handle basic authentication.

          >>> request = TestRequest(environ={'HTTP_AUTHORIZATION': 'foo bar'})
          >>> print(plugin.extractCredentials(TestRequest()))
          None

        This plugin only works with HTTP requests.

          >>> from zope.publisher.base import TestRequest
          >>> print(plugin.extractCredentials(TestRequest('/')))
          None

        According to RFC 2617, password can contain one or more colons;
        user ID can't contain any colon.

          >>> from zope.publisher.browser import TestRequest as BrowserRequest
          >>> request = BrowserRequest('/',
          ...     environ={'HTTP_AUTHORIZATION': u'Basic bWdyOm1ncnB3OndpdGg6Y29sb24='})
          >>> pprint(plugin.extractCredentials(request))
          {'login': u'mgr', 'password': u'mgrpw:with:colon'}

        """
        if not IHTTPRequest.providedBy(request):
            return None

        if request._auth:
            if request._auth.lower().startswith(u'basic '):
                credentials = request._auth.split()[-1]
                if isinstance(credentials, unicode):
                    # No encoding needed, should be base64 string anyways.
                    credentials = credentials.encode()
                login, password = base64.b64decode(credentials).split(b':', 1)
                return {'login': login.decode('utf-8'),
                        'password': password.decode('utf-8')}
        return None
Exemplo n.º 14
0
    def logout(self, request):
        """Performs logout by clearing session data credentials."""
        if not IHTTPRequest.providedBy(request):
            return False

        sessionData = ISession(request)['z3c.authenticator.credential.session']
        sessionData['credentials'] = None
        sessionData['camefrom'] = None
        transaction.commit()
        return True
Exemplo n.º 15
0
    def logout(self, request):
        """Performs logout by clearing session data credentials."""
        if not IHTTPRequest.providedBy(request):
            return False

        sessionData = ISession(
            request)['zope.app.authentication.browserplugins']
        sessionData['credentials'] = None
        transaction.commit()
        return True
Exemplo n.º 16
0
    def logout(self, request):
        """Performs logout by clearing session data credentials."""
        if not IHTTPRequest.providedBy(request):
            return False

        sessionData = ISession(request)[
            'zope.app.authentication.browserplugins']
        sessionData['credentials'] = None
        transaction.commit()
        return True
Exemplo n.º 17
0
def solrSearchResults(request=None, **keywords):
    """ perform a query using solr after translating the passed in
        parameters with portal catalog semantics """
    search = queryUtility(ISearch)
    config = queryUtility(ISolrConnectionConfig)
    if request is None:
        # try to get a request instance, so that flares can be adapted to
        # ploneflares and urls can be converted into absolute ones etc;
        # however, in this case any arguments from the request are ignored
        request = getattr(getSiteManager(), "REQUEST", None)
        args = keywords
    elif IHTTPRequest.providedBy(request):
        args = request.form.copy()  # ignore headers and other stuff
        args.update(keywords)  # keywords take precedence
    else:
        assert isinstance(request, dict), request
        args = request.copy()
        args.update(keywords)  # keywords take precedence
        # if request is a dict, we need the real request in order to
        # be able to adapt to plone flares
        request = getattr(getSiteManager(), "REQUEST", args)
    if "path" in args and "navtree" in args["path"]:
        raise FallBackException  # we can't handle navtree queries yet
    use_solr = args.get("use_solr", False)  # A special key to force Solr
    if not use_solr and config.required:
        required = set(config.required).intersection(args)
        if required:
            for key in required:
                if not args[key]:
                    raise FallBackException
        else:
            raise FallBackException
    schema = search.getManager().getSchema() or {}
    params = cleanupQueryParameters(extractQueryParameters(args), schema)
    languageFilter(args)
    prepareData(args)
    mangleQuery(args, config, schema)
    query = search.buildQuery(**args)
    optimizeQueryParameters(query, params)
    __traceback_info__ = (query, params, args)
    response = search(query, fl="* score", **params)

    def wrap(flare):
        """ wrap a flare object with a helper class """
        adapter = queryMultiAdapter((flare, request), IFlare)
        return adapter is not None and adapter or flare

    results = response.results()
    for idx, flare in enumerate(results):
        flare = wrap(flare)
        for missing in set(schema.stored).difference(flare):
            flare[missing] = MV
        results[idx] = wrap(flare)
    # padResults(results, **params)           # pad the batch
    return response
Exemplo n.º 18
0
def get_request_language(request=None, default=capi.default_language):
    """Get current request's language; if no request use specified default.
    
    If the request instance is handy, it may be passed in as a parameter thus
    avoidng the need to call for it.
    """
    if request is None:
        request = common.get_request()
    if IHTTPRequest.providedBy(request):
        return request.locale.getLocaleID()
    return default
Exemplo n.º 19
0
def get_request_language(request=None, default=capi.default_language):
    """Get current request's language; if no request use specified default.
    
    If the request instance is handy, it may be passed in as a parameter thus
    avoidng the need to call for it.
    """
    if request is None:
        request = common.get_request()
    if IHTTPRequest.providedBy(request):
        return request.locale.getLocaleID()
    return default
Exemplo n.º 20
0
    def extractCredentials(self, request):
        if not IHTTPRequest.providedBy(request):
            return None

        # this is an access token in the URL  ?access_token=...
        if not hasattr(request, 'form'):
            return None
        access_token = (request.form.get('access_token', None) or
                        request.form.get('form.field.access_token', None))
        if access_token is not None:
            return {'access_token': access_token}
        return None
Exemplo n.º 21
0
 def challenge(self, request):
     if not IHTTPRequest.providedBy(request):
         return False
     site = hooks.getSite()
     path = request['PATH_INFO'].split('/++/')[
         -1]  # strip virtual host stuff
     if not path.startswith('/'):
         path = '/' + path
     camefrom = request.getApplicationURL() + path
     if 'login' in camefrom:
         camefrom = '/'.join(camefrom.split('/')[:-1])
     url = '%s/@@%s?%s' % (absoluteURL(site, request), self.loginpagename,
                           urlencode({'camefrom': camefrom}))
     request.response.redirect(url)
     return True
Exemplo n.º 22
0
 def challenge(self, request):
     if not IHTTPRequest.providedBy(request):
         return False
     site = hooks.getSite()
     path = request['PATH_INFO'].split('/++/')[-1] # strip virtual host stuff
     if not path.startswith('/'):
         path = '/' + path
     camefrom = request.getApplicationURL() + path
     if 'login' in camefrom:
         camefrom = '/'.join(camefrom.split('/')[:-1])
     url = '%s/@@%s?%s' % (absoluteURL(site, request),
                           self.loginpagename,
                           urlencode({'camefrom': camefrom}))
     request.response.redirect(url)
     return True
Exemplo n.º 23
0
    def extractCredentials(self, request):
        """Extracts HTTP basic auth credentials from a request.

        First we need to create a request that contains some credentials.

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest(
          ...     environ={'HTTP_AUTHORIZATION': u'Basic bWdyOm1ncnB3'})

        Now create the plugin and get the credentials.

          >>> plugin = HTTPBasicAuthCredentialsPlugin()
          >>> plugin.extractCredentials(request)
          {'login': u'mgr', 'password': u'mgrpw'}

        Make sure we return `None`, if no authentication header has been
        specified.

          >>> print plugin.extractCredentials(TestRequest())
          None

        Also, this plugin can *only* handle basic authentication.

          >>> request = TestRequest(environ={'HTTP_AUTHORIZATION': 'foo bar'})
          >>> print plugin.extractCredentials(TestRequest())
          None

        This plugin only works with HTTP requests.

          >>> from zope.publisher.base import TestRequest
          >>> print plugin.extractCredentials(TestRequest('/'))
          None

        """
        if not IHTTPRequest.providedBy(request):
            return None

        if request._auth:
            if request._auth.lower().startswith(u'basic '):
                credentials = request._auth.split()[-1]
                login, password = base64.decodestring(credentials).split(':')
                return {
                    'login': login.decode('utf-8'),
                    'password': password.decode('utf-8')
                }
        return None
Exemplo n.º 24
0
    def extractCredentials(self, request):
        """Extracts HTTP basic auth credentials from a request.

        First we need to create a request that contains some credentials.

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest(
          ...     environ={'HTTP_AUTHORIZATION': u'Basic bWdyOm1ncnB3'})

        Now create the plugin and get the credentials.

          >>> plugin = HTTPBasicAuthCredentialsPlugin()
          >>> sorted(plugin.extractCredentials(request).items())
          [('login', 'mgr'), ('password', 'mgrpw')]

        Make sure we return `None`, if no authentication header has been
        specified.

          >>> print(plugin.extractCredentials(TestRequest()))
          None

        Also, this plugin can *only* handle basic authentication.

          >>> request = TestRequest(environ={'HTTP_AUTHORIZATION': 'foo bar'})
          >>> print(plugin.extractCredentials(TestRequest()))
          None

        This plugin only works with HTTP requests.

          >>> from zope.publisher.base import TestRequest
          >>> print(plugin.extractCredentials(TestRequest('/')))
          None

        """
        if not IHTTPRequest.providedBy(request):
            return None

        if request._auth:
            if request._auth.lower().startswith(u'basic '):
                credentials = request._auth.split()[-1]
                if isinstance(credentials, six.text_type):
                    credentials = credentials.encode('utf-8')
                login, password = base64.decodestring(credentials).split(b':')
                return {'login': login.decode('utf-8'),
                        'password': password.decode('utf-8')}
        return None
Exemplo n.º 25
0
    def extractCredentials(self, request):
        """Extracts credentials from a session if they exist."""
        if not IHTTPRequest.providedBy(request):
            return None

        sessionData = ISession(request)[
            'zope.app.authentication.browserplugins']
        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        if login and password:
            credentials = SessionCredentials(login, password)
            sessionData['credentials'] = credentials
        credentials = sessionData.get('credentials', None)
        if not credentials:
            return None
        return {'login': credentials.getLogin(),
                'password': credentials.getPassword()}
Exemplo n.º 26
0
    def extractCredentials(self, request):
        if not IHTTPRequest.providedBy(request):
            return

        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        gebdate = request.get(self.gebdatefield, None)
        cookie = request.get(self.cookie_name, None)

        if login and password and gebdate:
            cookie = self.make_cookie(login, password, gebdate)
            request.response.setCookie(self.cookie_name, cookie, path="/")
        elif cookie:
            val = base64.decodestring(urllib.unquote(cookie)).decode("utf-8")
            login, password, gebdate = val.split(":")
        else:
            return
        return {"login": login, "password": password, "gebdate": gebdate}
Exemplo n.º 27
0
    def extractCredentials(self, request):
        """Extracts HTTP basic auth credentisla from a request.

        First we need to create a request that contains some credentials.

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest(
          ...     environ={'HTTP_AUTHORIZATION': u'Basic bWdyOm1ncnB3'})

        Now create the plugin and get the credentials.

          >>> plugin = HTTPBasicAuthCredentialsPlugin()
          >>> plugin.extractCredentials(request)
          {'login': u'mgr', 'password': u'mgrpw'}

        Make sure we return `None`, if no authentication header has been
        specified.

          >>> print plugin.extractCredentials(TestRequest())
          None

        Also, this plugin can *only* handle basic authentication.

          >>> request = TestRequest(environ={'HTTP_AUTHORIZATION': 'foo bar'})
          >>> print plugin.extractCredentials(TestRequest())
          None

        This plugin only works with HTTP requests.

          >>> from zope.publisher.base import TestRequest
          >>> print plugin.extractCredentials(TestRequest('/'))
          None

        """
        if not IHTTPRequest.providedBy(request):
            return None

        if request._auth:
            if request._auth.lower().startswith(u"basic "):
                credentials = request._auth.split()[-1]
                login, password = base64.decodestring(credentials).split(":")
                return {"login": login.decode("utf-8"), "password": password.decode("utf-8")}
        return None
Exemplo n.º 28
0
    def extractCredentials(self, request):
        if not IHTTPRequest.providedBy(request):
            return

        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        cookie = request.get(self.cookie_name, None)

        if login and password:
            val = base64.encodestring('%s:%s' % (login, password))
            request.response.setCookie(self.cookie_name,
                                       urllib.quote(val),
                                       path='/')
        elif cookie:
            val = base64.decodestring(urllib.unquote(cookie))
            login, password = val.split(':')
        else:
            return

        return {'login': login, 'password': password}
Exemplo n.º 29
0
    def extractCredentials(self, request):
        if not IHTTPRequest.providedBy(request):
            return

        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        cookie = request.get(self.cookie_name, None)

        if login and password:
            val = base64.encodestring('%s:%s' % (login, password))
            request.response.setCookie(self.cookie_name,
                                       urllib.quote(val),
                                       path='/')
        elif cookie:
            val = base64.decodestring(urllib.unquote(cookie))
            login, password = val.split(':')
        else:
            return

        return {'login': login, 'password': password}
Exemplo n.º 30
0
    def challenge(self, request):
        """Issues an HTTP basic auth challenge for credentials.

        The challenge is issued by setting the appropriate response headers.
        To illustrate, we'll create a plugin:

          >>> plugin = HTTPBasicAuthCredentialsPlugin()

        The plugin adds its challenge to the HTTP response.

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()
          >>> response = request.response
          >>> plugin.challenge(request)
          True
          >>> response._status
          401
          >>> response.getHeader('WWW-Authenticate', literal=True)
          'basic realm="Zope"'

        Notice that the realm is quoted, as per RFC 2617.

        The plugin only works with HTTP requests.

          >>> from zope.publisher.base import TestRequest
          >>> request = TestRequest('/')
          >>> response = request.response
          >>> print(plugin.challenge(request))
          False

        """
        if not IHTTPRequest.providedBy(request):
            return False
        request.response.setHeader("WWW-Authenticate",
                                   'basic realm="%s"' % self.realm,
                                   literal=True)
        request.response.setStatus(401)
        return True
Exemplo n.º 31
0
    def challenge(self, request):
        """Issues an HTTP basic auth challenge for credentials.

        The challenge is issued by setting the appropriate response headers.
        To illustrate, we'll create a plugin:

          >>> plugin = HTTPBasicAuthCredentialsPlugin()

        The plugin adds its challenge to the HTTP response.

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()
          >>> response = request.response
          >>> plugin.challenge(request)
          True
          >>> response._status
          401
          >>> response.getHeader('WWW-Authenticate', literal=True)
          'basic realm="Zope"'

        Notice that the realm is quoted, as per RFC 2617.

        The plugin only works with HTTP requests.

          >>> from zope.publisher.base import TestRequest
          >>> request = TestRequest('/')
          >>> response = request.response
          >>> print plugin.challenge(request)
          False

        """
        if not IHTTPRequest.providedBy(request):
            return False
        request.response.setHeader("WWW-Authenticate",
                                   'basic realm="%s"' % self.realm,
                                   literal=True)
        request.response.setStatus(401)
        return True
Exemplo n.º 32
0
    def extractCredentials(self, request):
        if not IHTTPRequest.providedBy(request):
            return

        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        cookie = request.get(self.cookie_name, None)

        if login and password:
            login = login.encode('utf-8')
            password = password.encode('utf-8')
            cookie = self.make_cookie(login, password)
            request.response.setCookie(self.cookie_name, cookie, path="/")
        elif cookie:
            val = base64.decodebytes(
                urllib.parse.unquote(cookie).encode("utf-8"))
            login, password = val.split(b":")
        else:
            return

        return {
            "login": login.decode('utf-8'),
            "password": password.decode('utf-8')
        }
Exemplo n.º 33
0
    def challenge(self, request):
        """Challenges by redirecting to a login form.

        To illustrate, we'll create a test request:

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()

        and confirm its response's initial status and 'location' header:

          >>> request.response.getStatus()
          599
          >>> request.response.getHeader('location')

        When we issue a challenge using a session plugin:

          >>> plugin = SessionCredentialsPlugin()
          >>> plugin.challenge(request)
          True

        we get a redirect:

          >>> request.response.getStatus()
          302
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@loginForm.html?camefrom=%2F'

        The plugin redirects to the page defined by the loginpagename
        attribute:

          >>> plugin.loginpagename = 'mylogin.html'
          >>> plugin.challenge(request)
          True
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@mylogin.html?camefrom=%2F'

        It also provides the request URL as a 'camefrom' GET style parameter.
        To illustrate, we'll pretend we've traversed a couple names:

          >>> env = {
          ...     'REQUEST_URI': '/foo/bar/folder/page%201.html?q=value',
          ...     'QUERY_STRING': 'q=value'
          ...     }
          >>> request = TestRequest(environ=env)
          >>> request._traversed_names = [u'foo', u'bar']
          >>> request._traversal_stack = [u'page 1.html', u'folder']
          >>> request['REQUEST_URI']
          '/foo/bar/folder/page%201.html?q=value'

        When we challenge:

          >>> plugin.challenge(request)
          True

        We see the 'camefrom' points to the requested URL:

          >>> request.response.getHeader('location') # doctest: +ELLIPSIS
          '.../@@mylogin.html?camefrom=%2Ffoo%2Fbar%2Ffolder%2Fpage+1.html%3Fq%3Dvalue'

        This can be used by the login form to redirect the user back to the
        originating URL upon successful authentication.
        """
        if not IHTTPRequest.providedBy(request):
            return False

        site = hooks.getSite()
        # We need the traversal stack to complete the 'camefrom' parameter
        stack = request.getTraversalStack()
        stack.reverse()
        # Better to add the query string, if present
        query = request.get('QUERY_STRING')

        camefrom = '/'.join([request.getURL(path_only=True)] + stack)
        if query:
            camefrom = camefrom + '?' + query
        url = '%s/@@%s?%s' % (absoluteURL(site, request), self.loginpagename,
                              urlencode({'camefrom': camefrom}))
        request.response.redirect(url)
        return True
Exemplo n.º 34
0
    def challenge(self, request):
        """Challenges by redirecting to a loging form.

        To illustrate, we'll create a test request:

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()

        and confirm its response's initial status and 'location' header:

          >>> request.response.getStatus()
          599
          >>> request.response.getHeader('location')

        When we issue a challenge using a session plugin:

          >>> plugin = SessionCredentialsPlugin()
          >>> plugin.challenge(request)
          True

        we get a redirect:

          >>> request.response.getStatus()
          302
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@loginForm.html?camefrom=http%3A%2F%2F127.0.0.1'

        The plugin redirects to the page defined by the loginpagename
        attribute:

          >>> plugin.loginpagename = 'mylogin.html'
          >>> plugin.challenge(request)
          True
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@mylogin.html?camefrom=http%3A%2F%2F127.0.0.1'

        It also provides the request URL as a 'camefrom' GET style parameter.
        To illustrate, we'll pretend we've traversed a couple names:

          >>> request._traversed_names = ['foo', 'bar']
          >>> request.getURL()
          'http://127.0.0.1/foo/bar'

        When we challenge:

          >>> plugin.challenge(request)
          True

        We see the 'camefrom' points to the traversed URL:

          >>> request.response.getHeader('location') # doctest: +ELLIPSIS
          '.../@@mylogin.html?camefrom=http%3A%2F%2F127.0.0.1%2Ffoo%2Fbar'

        This can be used by the login form to redirect the user back to the
        originating URL upon successful authentication.
        """
        if not IHTTPRequest.providedBy(request):
            return False

        site = hooks.getSite()
        camefrom = request.getURL()
        url = '%s/@@%s?%s' % (absoluteURL(site, request),
                              self.loginpagename,
                              urlencode({'camefrom': camefrom}))
        request.response.redirect(url)
        return True
Exemplo n.º 35
0
    def challenge(self, request):
        """Challenges by redirecting to a login form.

        To illustrate, we'll create a test request:

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()

        and confirm its response's initial status and 'location' header:

          >>> request.response.getStatus()
          599
          >>> request.response.getHeader('location')

        When we issue a challenge using a session plugin:

          >>> plugin = SessionCredentialsPlugin()
          >>> plugin.challenge(request)
          True

        we get a redirect:

          >>> request.response.getStatus()
          302
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@loginForm.html?camefrom=http%3A%2F%2F127.0.0.1'

        The plugin redirects to the page defined by the loginpagename
        attribute:

          >>> plugin.loginpagename = 'mylogin.html'
          >>> plugin.challenge(request)
          True
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@mylogin.html?camefrom=http%3A%2F%2F127.0.0.1'

        It also provides the request URL as a 'camefrom' GET style parameter.
        To illustrate, we'll pretend we've traversed a couple names:

          >>> env = {
          ...     'REQUEST_URI': '/foo/bar/folder/page%201.html?q=value',
          ...     'QUERY_STRING': 'q=value'
          ...     }
          >>> request = TestRequest(environ=env)
          >>> request._traversed_names = [u'foo', u'bar']
          >>> request._traversal_stack = [u'page 1.html', u'folder']
          >>> request['REQUEST_URI']
          '/foo/bar/folder/page%201.html?q=value'

        When we challenge:

          >>> plugin.challenge(request)
          True

        We see the 'camefrom' points to the requested URL:

          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@mylogin.html?camefrom=http%3A%2F%2F127.0.0.1%2Ffoo%2Fbar%2Ffolder%2Fpage+1.html%3Fq%3Dvalue'

        This can be used by the login form to redirect the user back to the
        originating URL upon successful authentication.

        Now that the 'camefrom' is an absolute URL, quickly demonstrate that
        'camefrom' information that inadvertently points to a different host,
        will by default not be trusted in a redirect:

          >>> camefrom = request.response.getHeader('location')
          >>> request.response.redirect(camefrom)
          'http://127.0.0.1/@@mylogin.html?camefrom=http%3A%2F%2F127.0.0.1%2Ffoo%2Fbar%2Ffolder%2Fpage+1.html%3Fq%3Dvalue'
          >>> suspicious_camefrom = 'http://example.com/foobar'
          >>> request.response.redirect(suspicious_camefrom) # doctest: +ELLIPSIS
          Traceback (most recent call last):
          ...
          ValueError: Untrusted redirect to host 'example.com:80' not allowed.


        """
        if not IHTTPRequest.providedBy(request):
            return False

        site = hooks.getSite()
        redirectWithComeFrom(request, '%s/@@%s' % (absoluteURL(site, request),
                                                   self.loginpagename))
        return True
Exemplo n.º 36
0
    def challenge(self, request):
        """Challenges by redirecting to a login form.

        To illustrate, we'll create a test request:

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()

        and confirm its response's initial status and 'location' header:

          >>> request.response.getStatus()
          599
          >>> request.response.getHeader('location')

        When we issue a challenge using a session plugin:

          >>> plugin = SessionCredentialsPlugin()
          >>> plugin.challenge(request)
          True

        we get a redirect:

          >>> request.response.getStatus()
          302
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@loginForm.html?camefrom=%2F'

        The plugin redirects to the page defined by the loginpagename
        attribute:

          >>> plugin.loginpagename = 'mylogin.html'
          >>> plugin.challenge(request)
          True
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@mylogin.html?camefrom=%2F'

        It also provides the request URL as a 'camefrom' GET style parameter.
        To illustrate, we'll pretend we've traversed a couple names:

          >>> env = {
          ...     'REQUEST_URI': '/foo/bar/folder/page%201.html?q=value',
          ...     'QUERY_STRING': 'q=value'
          ...     }
          >>> request = TestRequest(environ=env)
          >>> request._traversed_names = [u'foo', u'bar']
          >>> request._traversal_stack = [u'page 1.html', u'folder']
          >>> request['REQUEST_URI']
          '/foo/bar/folder/page%201.html?q=value'

        When we challenge:

          >>> plugin.challenge(request)
          True

        We see the 'camefrom' points to the requested URL:

          >>> request.response.getHeader('location') # doctest: +ELLIPSIS
          '.../@@mylogin.html?camefrom=%2Ffoo%2Fbar%2Ffolder%2Fpage+1.html%3Fq%3Dvalue'

        This can be used by the login form to redirect the user back to the
        originating URL upon successful authentication.
        """
        if not IHTTPRequest.providedBy(request):
            return False

        site = hooks.getSite()
        # We need the traversal stack to complete the 'camefrom' parameter
        stack = request.getTraversalStack()
        stack.reverse()
        # Better to add the query string, if present
        query = request.get('QUERY_STRING')

        camefrom = '/'.join([request.getURL(path_only=True)] + stack)
        if query:
            camefrom = camefrom + '?' + query
        url = '%s/@@%s?%s' % (absoluteURL(site, request),
                              self.loginpagename,
                              urlencode({'camefrom': camefrom}))
        request.response.redirect(url)
        return True
Exemplo n.º 37
0
 def logout(self, request):
     if not IHTTPRequest.providedBy(request):
         return
     request.response.expireCookie(self.cookie_name, path=self.cookie_path )
Exemplo n.º 38
0
    def extractCredentials(self, request):  # noqa
        """Extracts credentials from a session if they exist."""
        if not IHTTPRequest.providedBy(request):
            return None
        session = ISession(request)
        # Fun. Direct access created a default. .get doesn't
        session_data = session['zope.pluggableauth.browserplugins']
        login = request.get(self.loginfield, None)
        password = request.get(self.passwordfield, None)
        tan_a = request.get(self.tan_a_field, None)
        tan_b = request.get(self.tan_b_field, None)
        hash = request.get(self.hash_field, None)
        credentials = None
        redirect = request.response.redirect

        def _validate_tans(a, b, creds):
            tan = str(creds.tan)
            if tan[creds.tanA] == a and \
               tan[creds.tanB] == b:
                return True
            return False

        def _validate_captcha():
            return submit(request['recaptcha_challenge_field'],
                          request['recaptcha_response_field'],
                          PRIVKEY,
                          '')
            # netifaces.ifaddresses('eth0')[2][0]['addr']
        if login and password and not tan_a and not tan_b and not hash:
            # 1st phase, user has provided login and password
            log.info('First Phase: Got login and password, no TANs.')

            credentials = TwoFactorSessionCredentials(login, password)
            session_data['credentials'] = credentials
            # Send email to user
            self.send_tan_email(login, credentials.tan)
            log.info("Thank you for logging in. Then Tan is %s. " %
                     credentials.tan)
            url = '%s/@@tanForm.html?h=%s&a=%s&b=%s' % \
                  (request.getURL(),
                   credentials.hash,
                   credentials.tanA + 1,
                   credentials.tanB + 1)
            if request.get('camefrom'):
                url += "&camefrom=%s" % request['camefrom']
            redirect(url)

        elif not login and not password and hash:
            # 2nd phase, user has given TANs and the hash.
            log.info('2nd Phase. No login or password, but TANs.')
            credentials = session_data.get('credentials', None)

            if not (tan_a and tan_b):
                msg = u"There was a problem reading your TAN digits. " + \
                      u"Please try again."
                log.info(msg)
                return redirect('@@tanForm.html?e=%s&hash=%s&a=%s&b=%s' %
                                (msg,
                                 hash,
                                 credentials.tanA + 1,
                                 credentials.tanB + 1))

            # Validate the captcha
            r = _validate_captcha()
            if not r.is_valid:
                msg = u"The captcha did not validate. Please try again."
                log.info(msg)
                return redirect(
                    '@@tanForm.html?e=%s&h=%s&a=%s&b=%s&tan_a=%s&tan_b=%s' %
                    (msg,
                     hash,
                     credentials.tanA + 1,
                     credentials.tanB + 1,
                     tan_a,
                     tan_b))

            log.info('The captcha is valid, continuing...')

            # No credentials, fail
            if not credentials:
                msg = u"We couldn't find your credentials. Please try again."
                log.info(msg)
                return redirect('@@loginForm.html?e=%s' %
                                (msg))

            # No or wrong hash provided, fail
            if credentials.hash != hash:
                msg = u"Somehow this page doesn't fit to the previous one." + \
                      u"Please start from scratch."
                log.info(msg)
                return redirect('@@loginForm.html?e=%s' %
                                (msg))

            # Took longer than TIMEOUT, fail
            if credentials.timestamp < datetime.now() - TIMEOUT:
                msg = u"A timeout has been reached. " + \
                      u"Please start from scratch."
                log.info(msg)
                return redirect('@@loginForm.html?e=%s' %
                                (msg))

            # Can't validate tans, fail
            if not _validate_tans(tan_a, tan_b, credentials):
                msg = u"The provided TAN digits don't fit. Please try again."
                log.info(msg)
                return redirect('@@tanForm.html?e=%s&a=%s&b=%s' %
                                (msg,
                                 credentials.tanA + 1,
                                 credentials.tanB + 1))

            credentials.validated = True
            log.info('Credentials are valid')

            session_data['credentials'] = credentials
            if request.get('camefrom'):
                redirect(request.get('camefrom'))
            else:
                redirect('./@@contents.html')
        elif not session_data:
            # Just display loginForm.html
            return None

        session_data = session['zope.pluggableauth.browserplugins']
        credentials = session_data.get('credentials', None)

        if not credentials:
            log.info('credentials are None')
            return None

        if not credentials.validated:
            log.warn("User is not validated. Don't log in!")
            return None

        log.info("All fine, user can be logged in, return credentials.")
        return {'login': credentials.getLogin(),
                'password': credentials.getPassword()}
Exemplo n.º 39
0
    def challenge(self, request):
        """Challenges by redirecting to a login form.

        To illustrate how a session plugin works, we'll first setup some session
        machinery:

          >>> from z3c.authenticator.testing import sessionSetUp
          >>> sessionSetUp()

        and we'll create a test request:

          >>> from zope.publisher.browser import TestRequest
          >>> request = TestRequest()

        and confirm its response's initial status and 'location' header:

          >>> request.response.getStatus()
          599
          >>> request.response.getHeader('location')

        When we issue a challenge using a session plugin:

          >>> plugin = SessionCredentialsPlugin()
          >>> plugin.challenge(request)
          True

        we get a redirect:

          >>> request.response.getStatus()
          302
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@loginForm.html'

        and the camefrom session contains the camefrom url which is our
        application root by default:

          >>> session = ISession(request, None)
          >>> sessionData = session['z3c.authenticator.credential.session']
          >>> sessionData['camefrom']
          '/'

        The plugin redirects to the page defined by the loginpagename
        attribute:

          >>> plugin.loginpagename = 'mylogin.html'
          >>> plugin.challenge(request)
          True
          >>> request.response.getHeader('location')
          'http://127.0.0.1/@@mylogin.html'

        and the camefrom session contains the camefrom url which is our
        application root by default:

          >>> session = ISession(request, None)
          >>> sessionData = session['z3c.authenticator.credential.session']
          >>> sessionData['camefrom']
          '/'

        It also provides the request URL as a 'camefrom' GET style parameter.
        To illustrate, we'll pretend we've traversed a couple names:

          >>> env = {
          ...     'REQUEST_URI': '/foo/bar/folder/page%201.html?q=value',
          ...     'QUERY_STRING': 'q=value'
          ...     }
          >>> request = TestRequest(environ=env)
          >>> request._traversed_names = [u'foo', u'bar']
          >>> request._traversal_stack = [u'page 1.html', u'folder']
          >>> request['REQUEST_URI']
          '/foo/bar/folder/page%201.html?q=value'

        When we challenge:

          >>> plugin.challenge(request)
          True

        We see the url points to the login form URL:

          >>> request.response.getHeader('location') # doctest: +ELLIPSIS
          'http://127.0.0.1/@@mylogin.html'

        and the camefrom session contains the camefrom url:

          >>> session = ISession(request, None)
          >>> sessionData = session['z3c.authenticator.credential.session']
          >>> sessionData['camefrom']
          u'/foo/bar/folder/page%201.html?q=value'

        If the given challenge argument doesn't provide IHTTPRequest the
        result will always be False:

          >>> plugin.challenge(None)
          False

        This can be used by the login form to redirect the user back to the
        originating URL upon successful authentication.
        """
        if not IHTTPRequest.providedBy(request):
            return False

        site = hooks.getSite()
        # We need the traversal stack to complete the 'camefrom' parameter
        stack = request.getTraversalStack()
        stack.reverse()
        # Better to add the query string, if present
        query = request.get('QUERY_STRING')

        camefrom = '/'.join([request.getURL(path_only=True)] + stack)
        if query:
            camefrom = camefrom + '?' + query
        url = '%s/@@%s' % (absoluteURL(site, request), self.loginpagename)
        # only redirect to the login form
        request.response.redirect(url)
        # and store the camefrom url into a session variable, then this url
        # should not get exposed in the login form url.
        session = ISession(request, None)
        sessionData = session['z3c.authenticator.credential.session']
        # XXX: this might be problematic with non-ASCII html page names
        sessionData['camefrom'] = camefrom.replace(' ', '%20')
        return True