Esempio n. 1
0
def fb_login(request):
    """
    Login using Facebook and generate auth token

    :param request:
    :return:
    """

    response = HTTPFound(location=request.route_url('home_page'))
    provider_name = 'fb'
    result = authomatic.login(WebObAdapter(request, response), provider_name)
    # if result and result.user.credentials:
    #     # get fb authenticated user
    #     result.user.update()
    user = User.register_user(32341235034, "arti",
                              "dsfjdy3aodfi3adfj330dsfmadi3",
                              "*****@*****.**")
    # user = User.register_user(result.user.id,result.user.name,result.user.credentials.token,result.user.email)# Generate auth token
    auth_tkt = User._get_auth_tkt(user)
    header = remember(request, auth_tkt)
    # Add auth token headers to response
    header_list = response._headerlist__get()
    [header_list.append(auth_header) for auth_header in header]
    response._headerlist__set(header_list)
    return response
Esempio n. 2
0
    def authomatic_login(self):
        # LOGGER.debug('authomatic_login')
        _authomatic = authomatic(self.request)
        provider = self.request.matchdict.get('provider')

        # Start the login procedure.
        response = Response()
        result = _authomatic.login(WebObAdapter(self.request, response),
                                   provider)

        # LOGGER.debug('authomatic result: %s', result)
        # LOGGER.debug('authomatic response: %s', response)

        if result:
            if result.error:
                # Login procedure finished with an error.
                return self.login_failure(message=result.error.message)
            elif result.user:
                if not (result.user.name and result.user.id):
                    result.user.update()
                # Hooray, we have the user!
                LOGGER.info("login successful for user %s", result.user.name)
                if result.provider.name == 'github':
                    # TODO: fix email ... get more infos ... which login_id?
                    login_id = "{0.username}@github.com".format(result.user)
                    return self.login_success(login_id=login_id,
                                              name=result.user.name)
                else:
                    # TODO: change login_id ... more infos ...
                    return self.login_success(login_id=result.user.id,
                                              email=result.user.email or '',
                                              openid=result.user.id,
                                              name=result.user.name
                                              or 'Unknown')
        return response
Esempio n. 3
0
def login(request):
    provider_name = request.matchdict.get('provider_name')
    response = Response()
    result = authomatic.login(WebObAdapter(request, response), provider_name)

    if result:
        response.write(
            fixtures.render_login_result('pyramid', result).encode())

    return response
Esempio n. 4
0
def social_auth(request):
    # Get the internal provider name URL variable.
    provider_name = request.matchdict.get("provider")

    # Start the login procedure.
    adapter = WebObAdapter(request, request.response)
    result = request.authomatic.login(adapter, provider_name)
    if result:
        if result.error:
            return handle_auth_error(request, result)
        elif result.user:
            return handle_auth_success(request, result)
    return request.response
Esempio n. 5
0
def login(request):

    # We will need the response to pass it to the WebObAdapter.
    response = Response()

    # Get the internal provider name URL variable.
    provider_name = request.matchdict.get('provider_name')

    # Start the login procedure.
    result = authomatic.login(WebObAdapter(request, response), provider_name)

    # Do not write anything to the response if there is no result!
    if result:
        # If there is result, the login procedure is over and we can write to
        # response.
        response.write('<a href="..">Home</a>')

        if result.error:
            # Login procedure finished with an error.
            response.write(
                u'<h2>Damn that error: {0}</h2>'.format(result.error.message))

        elif result.user:
            # Hooray, we have the user!

            # OAuth 2.0 and OAuth 1.0a provide only limited user data on login,
            # We need to update the user to get more info.
            #if not (result.user.name and result.user.id):
            result.user.update()

            #print(result.user.profile)
            # Welcome the user.
            response.write(u'<h1>Hi {0}</h1>'.format(result.user.first_name))
            response.write(u'<h2>Your id is: {0}</h2>'.format(result.user.id))
            response.write(
                u'<h2>Your email is: {0}</h2>'.format(result.user.email))

            # Seems like we're done, but there's more we can do...

            # If there are credentials (only by AuthorizationProvider),
            # we can _access user's protected resources.
            if result.user.credentials:

                # Each provider has it's specific API.
                if result.provider.name == 'google':
                    response.write('Your are logged in with Google.<br />')

    # It won't work if you don't return the response
    return response
Esempio n. 6
0
def login(request: Request) -> Response:
    """User logs in using GitHub."""
    response = Response()
    result = request.authomatic.login(WebObAdapter(request, response), "github")
    if result is None:
        return response
    if result.error:
        return exception_response(401, json_body={"error": result.error.message})

    result.user.update()
    username = result.user.username
    user = User.by_username(username, db=request.db)
    if user is None:
        return exception_response(401, json_body={"error": "Not authorized."})

    return Response(json_body={"token": request.create_jwt_token(str(user.id))})
Esempio n. 7
0
 def login_view(self):
     log.debug('login_view')
     response = Response()
     dpconf = dict(class_=oauth2.Dataporten,
                   consumer_key=self.settings.get('oauth_client_id', ''),
                   consumer_secret=self.settings.get(
                       'oauth_client_secret', ''))
     authomatic = Authomatic(config=dict(dp=dpconf), secret='mumbojumbo')
     result = authomatic.login(WebObAdapter(self.request, response), 'dp')
     if result:
         # The login procedure is over
         log.debug('login_view - login complete')
         return self.login_complete(result)
     else:
         log.debug('login_view - login not complete')
         return response
Esempio n. 8
0
    def handle(self) -> Response:

        # Login is always state changing operation
        if self.request.method != 'POST' and not self.request.params:
            self.do_bad_request()

        # We will need the response to pass it to the WebObAdapter.
        response = Response()

        # Get handle to Authomatic instance
        authomatic = get_authomatic(self.request.registry)

        # Start the login procedure.
        class InternalPOSTWebObAdapter(WebObAdapter):
            """Having CSRF token in form data messes Authomatic internally so we strip it away with this hack.."""
            @property
            def params(self):
                return dict()

        if "csrf_token" in self.request.POST:
            # This was internal HTTP POST by our own site to this view
            # TODO: Make it use to explicit post parameter to detect this
            self.process_form()
            adapter = InternalPOSTWebObAdapter(self.request, response)
        else:
            adapter = WebObAdapter(self.request, response)

        authomatic_result = authomatic.login(adapter, self.provider_name)

        if not authomatic_result:
            # Guess it wants to redirect us to Facebook et. al and it set response through the adapter
            return response

        # Grab exception if we get any
        e = None

        if not authomatic_result.error:
            # Login succeeded
            try:
                return self.do_success(authomatic_result)
            except NotSatisfiedWithData as ex:
                # TODO: Clean this up - some scoping issues?
                authomatic_result.error = ex
                e = ex

        return self.do_error(authomatic_result, e)
Esempio n. 9
0
 def __call__(self):
     response = Response()
     oauth = component.getUtility(IOAuthSettings)
     result = oauth.login(WebObAdapter(self.request, response), self.__provider__)
     if result:
         if result.error:
             return HTTPForbidden()
         elif result.user:
             if not (result.user.name and result.user.id):
                 result.user.update()
             self._stamp_time(result.provider.access_token_response.data)
             new_user = self.__user_class__(first_name=result.user.first_name,
                                            last_name=result.user.last_name,
                                            email=result.user.email,
                                            password="",
                                            access_token=result.provider.access_token_response.data)
             self.context.insert(new_user, check_member=True)
             response.headers = new_user.authenticate(self.request)
     return response
Esempio n. 10
0
    def authomatic_login(self):
        # LOGGER.debug('authomatic_login')
        _authomatic = authomatic(self.request)
        provider = self.request.matchdict.get('provider')

        # Start the login procedure.
        response = Response()
        result = _authomatic.login(WebObAdapter(self.request, response), provider)

        LOGGER.debug('authomatic result: {}'.format(result))
        # LOGGER.debug('authomatic response: %s', response)

        if result:
            if result.error:
                # Login procedure finished with an error.
                return self.login_failure(message=result.error.message)
            elif result.user:
                if not (result.user.name and result.user.id):
                    result.user.update()
                # Hooray, we have the user!
                LOGGER.debug("login successful for user {}".format(result.user.name))
                if result.provider.name == 'github':
                    return self.login_success(login_id=result.user.username, provider=result.provider.name,)
                elif result.provider.name == 'ceda_oauth':
                    return self.login_success(login_id=result.user.name, provider=result.provider.name,)
                elif result.provider.name == 'keycloak':
                    LOGGER.debug('credentials: {}'.format(result.provider.credentials))
                    client = KeycloakClient(self.request.registry)
                    user_info = client.introspect_access_token(result.provider.credentials.token)
                    return self.login_success(
                        login_id=user_info['preferred_username'],
                        provider=result.provider.name,
                        token={
                            'access_token': result.provider.credentials.token,
                            'refresh_token': result.provider.credentials.refresh_token,
                            'expires_in': result.provider.credentials.expire_in,
                            'expires_at': result.provider.credentials.expiration_time,
                            'token_type': result.provider.credentials.token_type,
                        })
                else:
                    raise Exception('Unknown provider')
        return response
Esempio n. 11
0
 def verify(self):
     result = authomatic.login(WebObAdapter(request, response), "oi")
     if result:
         if result.error:
             redirect("/user/logged_in")
         if not (result.user.name and result.user.id):
             result.user.update()
         user = get_user(result.user.id)
         if not user:
             user = toolkit.get_action('user_create')(
                 context={
                     'ignore_auth': True
                 },
                 data_dict={
                     'email': result.user.email,
                     'name': get_username(result.user.id),
                     'password': unique_string()
                 })
         session['openid-user'] = user['name']
         session.save()
         redirect("/")
Esempio n. 12
0
def login(request):
    response = Response()
    result = authomatic.login(WebObAdapter(request, response), 'dp')
    if result:
        # If there is a result, the login procedure is over and we can write to response.
        response.write('<a href="..">Home</a>')

        if result.error:
            response.write(u'<h2>Login failed: {0}</h2>'.format(
                result.error.message))
        elif result.user:
            # OAuth 2.0 provides only limited user data on login,
            # We need to update the user to get more info.
            if not (result.user.name and result.user.id):
                result.user.update()

            response.write(u'<h1>Hi {0}</h1>'.format(result.user.name))
            response.write(u'<h2>Your id is: {0}</h2>'.format(result.user.id))
            response.write(u'<h2>Your email is: {0}</h2>'.format(
                result.user.email))

    return response
Esempio n. 13
0
    def authomatic_login(self):
        _authomatic = authomatic(self.request)

        provider_name = self.request.matchdict.get('provider_name')

        # Start the login procedure.
        response = Response()
        result = _authomatic.login(WebObAdapter(self.request, response),
                                   provider_name)

        if result:
            if result.error:
                # Login procedure finished with an error.
                return self.login_failure(message=result.error.message)
            elif result.user:
                if not (result.user.name and result.user.id):
                    result.user.update()
                # Hooray, we have the user!
                logger.info("login successful for user %s", result.user.name)
                if result.provider.name in [
                        'openid', 'dkrz', 'ipsl', 'smhi', 'badc', 'pcmdi'
                ]:
                    # TODO: change login_id ... more infos ...
                    return self.login_success(login_id=result.user.id,
                                              email=result.user.email,
                                              openid=result.user.id,
                                              name=result.user.name)
                elif result.provider.name == 'github':
                    # TODO: fix email ... get more infos ... which login_id?
                    login_id = "{0.username}@github.com".format(result.user)
                    #email = "{0.username}@github.com".format(result.user)
                    # get extra info
                    if result.user.credentials:
                        pass
                    return self.login_success(login_id=login_id,
                                              name=result.user.name)
        return response
Esempio n. 14
0
def facebook_login_view(request):
    from pyramid.response import Response
    from authomatic.providers import oauth2
    from authomatic.adapters import WebObAdapter
    from authomatic import Authomatic

    CONFIG = {
        'fb': {
            'class_': oauth2.Facebook,
            'consumer_key': request.registry.settings['facebook.key'],
            'consumer_secret': request.registry.settings['facebook.secret'],
            'scope': ['public_profile', 'email']
        }
    }

    authomatic = Authomatic(config=CONFIG, secret='mysecret')
    response = Response()
    result = authomatic.login(WebObAdapter(request, response), 'fb')
    if result:
        if result.error:
            response.write(result.error.message)
        elif result.user:
            if result.user.credentials:
                url = 'https://graph.facebook.com/me?fields=id,name,email,first_name,last_name'
                fb_response = result.provider.access(url)
                if fb_response.status == 200:
                    data = fb_response.data
                    response.write('facebook id: {} <br />'.format(data['id']))
                    response.write('facebook name: {} <br />'.format(
                        data['name']))
                    response.write('facebook first name: {} <br />'.format(
                        data['first_name']))
                    response.write('facebook last name: {} <br />'.format(
                        data['last_name']))
                    response.write('facebook email: {} <br />'.format(
                        data['email']))
    return response
Esempio n. 15
0
def login(request):

    # We will need the response to pass it to the WebObAdapter.
    response = Response()

    # Get the internal provider name URL variable.
    provider_name = request.matchdict.get('provider_name')

    # Start the login procedure.
    result = authomatic.login(WebObAdapter(request, response), provider_name)

    # Do not write anything to the response if there is no result!
    if result:
        # If there is result, the login procedure is over and we can write to response.
        response.write('<a href="..">Home</a>')

        if result.error:
            # Login procedure finished with an error.
            response.write(u'<h2>Damn that error: {}</h2>'.format(
                result.error.message))

        elif result.user:
            # Hooray, we have the user!

            # OAuth 2.0 and OAuth 1.0a provide only limited user data on login,
            # We need to update the user to get more info.
            if not (result.user.name and result.user.id):
                result.user.update()

            # Welcome the user.
            response.write(u'<h1>Hi {}</h1>'.format(result.user.name))
            response.write(u'<h2>Your id is: {}</h2>'.format(result.user.id))
            response.write(u'<h2>Your email is: {}</h2>'.format(
                result.user.email))

            # Seems like we're done, but there's more we can do...

            # If there are credentials (only by AuthorizationProvider),
            # we can _access user's protected resources.
            if result.user.credentials:

                # Each provider has it's specific API.
                if result.provider.name == 'fb':
                    response.write('Your are logged in with Facebook.<br />')

                    # We will access the user's 5 most recent statuses.
                    url = 'https://graph.facebook.com/{}?fields=feed.limit(5)'
                    url = url.format(result.user.id)

                    # Access user's protected resource.
                    access_response = result.provider.access(url)

                    if access_response.status == 200:
                        # Parse response.
                        statuses = access_response.data.get('feed').get('data')
                        error = access_response.data.get('error')

                        if error:
                            response.write(
                                u'Damn that error: {}!'.format(error))
                        elif statuses:
                            response.write(
                                'Your 5 most recent statuses:<br />')
                            for message in statuses:

                                text = message.get('message')
                                date = message.get('created_time')

                                response.write(u'<h3>{}</h3>'.format(text))
                                response.write(u'Posted on: {}'.format(date))
                    else:
                        response.write('Damn that unknown error!<br />')
                        response.write(u'Status: {}'.format(response.status))

                if result.provider.name == 'tw':
                    response.write('Your are logged in with Twitter.<br />')

                    # We will get the user's 5 most recent tweets.
                    url = 'https://api.twitter.com/1.1/statuses/user_timeline.json'

                    # You can pass a dictionary of querystring parameters.
                    access_response = result.provider.access(url, {'count': 5})

                    # Parse response.
                    if access_response.status == 200:
                        if type(access_response.data) is list:
                            # Twitter returns the tweets as a JSON list.
                            response.write('Your 5 most recent tweets:')
                            for tweet in access_response.data:
                                text = tweet.get('text')
                                date = tweet.get('created_at')

                                response.write(u'<h3>{}</h3>'.format(
                                    text.replace(u'\u2026', '...')))
                                response.write(u'Tweeted on: {}'.format(date))

                        elif access_response.data.get('errors'):
                            response.write(u'Damn that error: {}!'.\
                                                format(response.data.get('errors')))
                    else:
                        response.write('Damn that unknown error!<br />')
                        response.write(u'Status: {}'.format(response.status))

    # It won't work if you don't return the response
    return response
Esempio n. 16
0
def authomatic_login(request):
    """
    Signs in a user session using an external provider.
    """

    provider_name = request.matchdict.get("provider_name", "").lower()
    response = Response()
    verify_provider(provider_name)
    try:
        authomatic_handler = authomatic_setup(request)

        # if we directly have the Authorization header, bypass authomatic login and retrieve 'userinfo' to signin
        if "Authorization" in request.headers and "authomatic" not in request.cookies:
            provider_config = authomatic_handler.config.get(provider_name, {})
            provider_class = resolve_provider_class(provider_config.get("class_"))
            provider = provider_class(authomatic_handler, adapter=None, provider_name=provider_name)
            # provide the token user data, let the external provider update it on login afterwards
            token_type, access_token = request.headers.get("Authorization").split()
            data = {"access_token": access_token, "token_type": token_type}
            cred = Credentials(authomatic_handler.config, token=access_token, token_type=token_type, provider=provider)
            provider.credentials = cred
            result = LoginResult(provider)
            # pylint: disable=W0212
            result.provider.user = result.provider._update_or_create_user(data, credentials=cred)  # noqa: W0212

        # otherwise, use the standard login procedure
        else:
            result = authomatic_handler.login(WebObAdapter(request, response), provider_name)
            if result is None:
                if response.location is not None:
                    return HTTPTemporaryRedirect(location=response.location, headers=response.headers)
                return response

        if result:
            if result.error:
                # Login procedure finished with an error.
                error = result.error.to_dict() if hasattr(result.error, "to_dict") else result.error
                LOGGER.debug("Login failure with error. [%r]", error)
                return login_failure(request, reason=result.error.message)
            if result.user:
                # OAuth 2.0 and OAuth 1.0a provide only limited user data on login,
                # update the user to get more info.
                if not (result.user.name and result.user.id):
                    try:
                        response = result.user.update()
                    # this error can happen if providing incorrectly formed authorization header
                    except OAuth2Error as exc:
                        LOGGER.debug("Login failure with Authorization header.")
                        ax.raise_http(http_error=HTTPBadRequest, content={"reason": str(exc.message)},
                                      detail=s.ProviderSignin_GET_BadRequestResponseSchema.description)
                    # verify that the update procedure succeeded with provided token
                    if 400 <= response.status < 500:
                        LOGGER.debug("Login failure with invalid token.")
                        ax.raise_http(http_error=HTTPUnauthorized,
                                      detail=s.ProviderSignin_GET_UnauthorizedResponseSchema.description)
                # create/retrieve the user using found details from login provider
                return login_success_external(request,
                                              external_id=result.user.username or result.user.id,
                                              email=result.user.email,
                                              provider_name=result.provider.name,
                                              external_user_name=result.user.name)
    except Exception as exc:
        exc_msg = "Unhandled error during external provider '{}' login. [{!s}]".format(provider_name, exc)
        LOGGER.exception(exc_msg, exc_info=True)
        ax.raise_http(http_error=HTTPInternalServerError, detail=exc_msg)

    LOGGER.debug("Reached end of login function. Response: %r", response)
    return response
Esempio n. 17
0
    def login(self):
        # We will need the response to pass it to the WebObAdapter.
        response = Response()

        # Get the internal provider name URL variable.
        provider_name = self.request.matchdict.get('provider_name')

        authomatic = self.request.registry.queryUtility(IAuthomatic)
        if authomatic is None:
            raise HTTPBadRequest(
                "We don't know how to process login - no providers configured."
            )

        came_from = self.request.GET.pop('came_from', None)
        if came_from:
            self.request.session['came_from'] = came_from
            self.request.session.changed()

        # Start the login procedure.
        result = authomatic.login(WebObAdapter(self.request, response),
                                  provider_name)

        # Do not write anything to the response if there is no result!
        if result:
            # If there is result, the login procedure is over and we can write to
            # response.
            # The question here is what kind of status does this page have...?
            #response.write('<a href="..">Home</a>')

            if result.error:
                # Login procedure finished with an error.
                logger.debug(
                    "Authomatic login with provider '%s' caused error:\n%s",
                    provider_name, result.error)
                response.write(u'<h2>Damn that error: {0}</h2>'.format(
                    result.error))

            elif result.user:
                # Hooray, we have the user!

                # OAuth 2.0 and OAuth 1.0a provide only limited user data on login,
                # We need to update the user to get more info.
                # However, as long as we have the ID we should be fine here
                updated = False
                if not result.user.id:
                    result.user.update()
                    updated = True

                # context should be root here
                users = self.context['users']
                user = users.find_providers_user(result)

                # FIXME: The result will contain information on wether the email is verified and so on.
                # In case it is, the provider should be added to existing user instead.

                # Check incoming came from param, here we want to remove it.
                came_from = self.request.session.get('came_from', None)

                # Allow any URL on a registered domain?
                if came_from is None:
                    came_from = self.request.registry.settings[
                        'kedja.client_url']
                else:
                    # Validate, pick first registered if none exist
                    # TODO: Allow other URLs
                    parsed = urlparse(came_from)
                    if not parsed.hostname in ['localhost', '127.0.0.1']:
                        # Nuke incoming in case it isn't localhost
                        came_from = self.request.registry.settings[
                            'kedja.client_url']
                    self.request.session.changed()

                if user is None:
                    # Now we do need more info
                    if not updated:
                        result.user.update()
                    # Create a temporary registration with this user
                    reg_tokens = self.request.registry.getAdapter(
                        self.context, IOneTimeRegistrationToken)
                    token = reg_tokens.create(result.user.to_dict())
                    # Redirect back to client with the token
                    # self.request.registry.settings['kedja.client_url']
                    registration_url = came_from + '/register?t=' + token
                    return HTTPFound(location=registration_url)

                # Update existing user in case something differs, but don't change usernames if they exist
                userdata = result.user.to_dict()
                for k in ('first_name', 'last_name'):
                    currdata = getattr(user, k, None)
                    if currdata:
                        userdata.pop(k, None)
                with self.request.get_mutator(user) as mutator:
                    mutator.update(userdata)

                # Login user
                cred = self.request.registry.content('Credentials',
                                                     user.userid)
                cred.save()
                auth_token = self.auth_tokens.create(cred)
                login_url = "{}/logging_in?u={}&t={}".format(
                    came_from, user.userid, auth_token)
                return HTTPFound(location=login_url)

        # It won't work if you don't return the response
        return response
Esempio n. 18
0
def google_login_view(request):
    from pyramid.response import Response
    from authomatic.providers import oauth2
    from authomatic.adapters import WebObAdapter
    from authomatic import Authomatic

    CONFIG = {
        'gl': {
            'class_': oauth2.Google,
            'consumer_key': request.registry.settings['google.key'],
            'consumer_secret': request.registry.settings['google.secret'],
            'scope': ['openid', 'profile', 'email']
        }
    }

    authomatic = Authomatic(config=CONFIG, secret='mysecret')
    response = Response()
    result = authomatic.login(WebObAdapter(request, response), 'gl')
    if result:
        if result.error:
            response.write(result.error.message)
        elif result.user:
            if result.user.credentials:
                # 參考資源 ----------------------------------
                # 套件官方範例程式:
                #   http://peterhudec.github.io/authomatic/examples/pyramid-simple.html

                # 有關 https://www.googleapis.com/plus/v1/people/me
                #   https://developers.google.com/identity/protocols/OpenIDConnect

                # 使用新舊 API 的 url
                #   https://github.com/omab/python-social-auth/blob/master/social/backends/google.py
                #   請看 def user_data(self, access_token, *args, **kwargs): (應於 65行)

                # for attr in dir(result.user):
                #     response.write(attr + '<br />')

                # result.user.update() 會使用新的 API,但執行會失敗!!!
                # 即 https://www.googleapis.com/plus/v1/people/me
                result.user.update()
                response.write('<p style="color:red;">')
                response.write('google id: ' + str(result.user.id) + '<br />')
                response.write('google name: ' + str(result.user.name) +
                               '<br />')
                response.write('google email: ' + str(result.user.email) +
                               '<br />')
                response.write('</p>')

                # 使用舊 API url,才可成功取得 userinfo
                url = 'https://www.googleapis.com/oauth2/v1/userinfo'
                gl_response = result.provider.access(url)

                # for attr in dir(gl_response):
                #     response.write(attr + '<br />')

                if gl_response.status == 200:
                    data = gl_response.data
                    response.write('<p style="color:blue;">')
                    response.write('google id: {} <br />'.format(data['id']))
                    response.write('google name: {} <br />'.format(
                        data['name']))
                    response.write('google email: {} <br />'.format(
                        data['email']))
                    response.write('</p>')
                else:
                    response.write('HTTP Status = ' + str(gl_response.status))
    return response