def profile_authenticate(self, facebook_id=None, facebook_email=None):
        '''
        Authenticate the facebook user by id OR facebook_email
        We filter using an OR to allow existing members to connect with
        their facebook ID using email.

        :param facebook_id:
            Optional string representing the facebook id

        :param facebook_email:
            Optional string with the facebook email

        :return: The signed in :class:`User`.
        '''
        logger.info("PA01 Inside profile authentication")
        if facebook_id or facebook_email:
            profile_class = get_profile_model()
            logger.info("PA02 Profile class %s" % profile_class)
            profile_query = profile_class.objects.all().order_by('user')
            profile_query = profile_query.select_related('user')
            logger.info("PA03 Profile query %s" % profile_query)
            profile = None

            # filter on email or facebook id, two queries for better
            # queryplan with large data sets
            if facebook_id:
                profiles = profile_query.filter(facebook_id=facebook_id)[:1]
                logger.info("PA04 Profiles from facebook_id %s" % profiles)
                profile = profiles[0] if profiles else None
                logger.info("PA05 Profile %s" % profile)
            if profile is None and facebook_email:
                try:
                    profiles = profile_query.filter(
                        user__email__iexact=facebook_email)[:1]
                    logger.info("PA06 Profiles from email %s" % profiles)
                    profile = profiles[0] if profiles else None
                    logger.info("PA07 Profile %s" % profile)
                except DatabaseError:
                    logger.info("PA08 Database error")
                    try:
                        user = get_user_model(
                        ).objects.get(email=facebook_email)
                        logger.info("PA09 User from model %s" % user)
                    except get_user_model().DoesNotExist:
                        logger.info("PA10 No model")
                        user = None
                    profile = try_get_profile(user) if user else None
                    logger.info("PA11 Profile %s" % profile)

            if profile:
                # populate the profile cache while we're getting it anyway
                user = profile.user
                logger.info("PA07 User from profile %s" % user)
                user._profile = profile
                if facebook_settings.FACEBOOK_FORCE_PROFILE_UPDATE_ON_LOGIN:
                    logger.info("UA10 Require user update")
                    user.fb_update_required = True
                return user
Example #2
0
    def clean_username(self):
        """
        Validate that the username is alphanumeric and is not already
        in use.

        """
        try:
            get_user_model().objects.get(
                username__iexact=self.cleaned_data['username'])
        except get_user_model().DoesNotExist:
            return self.cleaned_data['username']
        raise forms.ValidationError(
            _("A user with that username already exists."))
Example #3
0
    def test_follow_og_share_error(self):
        user_url = 'http://www.fashiolista.com/style/neni/'
        kwargs = dict(item=user_url)
        user = get_user_model().objects.all()[:1][0]
        profile = try_get_profile(user)
        user_or_profile = get_instance_for_attribute(
            user, profile, 'facebook_open_graph')
        user_or_profile.facebook_open_graph = True
        user_or_profile.save()

        some_content_type = ContentType.objects.all()[:1][0]
        share = OpenGraphShare.objects.create(
            user_id=user.id,
            facebook_user_id=13123123,
            action_domain='fashiolista:follow',
            content_type=some_content_type,
            object_id=user.id,
        )
        share.set_share_dict(kwargs)
        share.save()
        update_user_attributes(user, profile, dict(new_token_required=False))
        from open_facebook.exceptions import FacebookUnreachable, OAuthException
        with mock.patch('open_facebook.api.OpenFacebook') as mocked:
            instance = mocked.return_value
            instance.set = Mock(side_effect=FacebookUnreachable('broken'))
            share.send(graph=instance)
            self.assertEqual(share.error_message, 'broken')
            self.assertFalse(share.completed_at)
            user = get_user_model().objects.get(id=user.id)
            if profile:
                profile = get_profile_model().objects.get(id=profile.id)
            new_token_required = get_user_attribute(
                user, profile, 'new_token_required')
            self.assertEqual(new_token_required, False)

        # now try with an oauth exception
        return
        # Can't figure out how to test this
        with mock.patch('open_facebook.api.OpenFacebook') as mocked:
            instance = mocked.return_value
            instance.set = Mock(side_effect=OAuthException('permissions'))
            share.send(graph=instance)
            self.assertEqual(share.error_message, 'permissions')
            self.assertFalse(share.completed_at)
            user = get_user_model().objects.get(id=user.id)
            if profile:
                profile = get_profile_model().objects.get(id=profile.id)
            new_token_required = get_user_attribute(
                user, profile, 'new_token_required')
            self.assertEqual(new_token_required, True)
Example #4
0
 def profile_or_self(self):
     user_or_profile_model = get_model_for_attribute('facebook_id')
     user_model = get_user_model()
     if user_or_profile_model == user_model:
         return self
     else:
         return self.get_profile()
Example #5
0
    def test_follow_og_share_error(self):
        from django_facebook.models import OpenGraphShare
        user_url = 'http://www.fashiolista.com/style/neni/'
        kwargs = dict(item=user_url)
        user = get_user_model().objects.all()[:1][0]
        profile = try_get_profile(user)
        user_or_profile = get_instance_for_attribute(
            user, profile, 'facebook_open_graph')
        user_or_profile.facebook_open_graph = True
        user_or_profile.save()

        from django.contrib.contenttypes.models import ContentType
        some_content_type = ContentType.objects.all()[:1][0]
        share = OpenGraphShare.objects.create(
            user_id=user.id,
            facebook_user_id=13123123,
            action_domain='fashiolista:follow',
            content_type=some_content_type,
            object_id=user.id,
        )
        share.set_share_dict(kwargs)
        share.save()
        from open_facebook.exceptions import FacebookUnreachable
        with mock.patch('open_facebook.api.OpenFacebook') as mocked:
            instance = mocked.return_value
            instance.set = Mock(side_effect=FacebookUnreachable('broken'))
            share.send(graph=instance)
            self.assertEqual(share.error_message, 'broken')
            self.assertFalse(share.completed_at)
Example #6
0
def create_profile(sender, instance, created, **kwargs):
#Create a matching profile whenever a user object is created.
    if sender == get_user_model():
        user = instance
        profile_model = get_profile_model()
        if profile_model == BotaniserProfile and created:
            profile, new = BotaniserProfile.objects.get_or_create(user=instance)
Example #7
0
    def test_user_registered_signal(self):
        # Ensure user registered, pre update and post update signals fire

        def user_registered(sender, user, facebook_data, **kwargs):
            user.registered_signal = True

        def pre_update(sender, user, profile, facebook_data, **kwargs):
            user.pre_update_signal = True

        def post_update(sender, user, profile, facebook_data, **kwargs):
            user.post_update_signal = True

        Profile = get_profile_model()
        user_model = get_user_model()
        signals.facebook_user_registered.connect(
            user_registered, sender=user_model)
        signals.facebook_pre_update.connect(pre_update, sender=user_model)
        signals.facebook_post_update.connect(post_update, sender=user_model)

        graph = get_facebook_graph(access_token='short_username')
        facebook = FacebookUserConverter(graph)
        user = _register_user(self.request, facebook)
        self.assertEqual(hasattr(user, 'registered_signal'), True)
        self.assertEqual(hasattr(user, 'pre_update_signal'), True)
        self.assertEqual(hasattr(user, 'post_update_signal'), True)
Example #8
0
    def setUp(self):
        from django_facebook.test_utils.mocks import MockFacebookAPI, MockFacebookAuthorization, RequestMock
        import sys
        import StringIO
        self.prints = sys.stdout = StringIO.StringIO()

        from open_facebook import api
        import open_facebook

        self.originalAPI = open_facebook.OpenFacebook
        self.originalAuthorization = open_facebook.FacebookAuthorization

        open_facebook.OpenFacebook = api.OpenFacebook = MockFacebookAPI
        open_facebook.FacebookAuthorization = api.FacebookAuthorization = MockFacebookAuthorization

        rf = RequestMock()
        self.request = rf.get('/')
        self.client = Client()

        # time to setup the test user
        user_model = get_user_model()
        user_dict = dict(
            username='tschellenbach',
            is_staff=False,
            is_active=True,
            email="[email protected]",
        )
        test_ip = '127.0.0.1'
        # hack to make fashiolista tests run ok
        if is_user_attribute('registration_ip'):
            user_dict['registration_ip'] = test_ip
            user_dict['last_login_ip'] = test_ip
        user_model.objects.create(**user_dict)
    def user_authenticate(self, facebook_id=None, facebook_email=None):
        '''
        Authenticate the facebook user by id OR facebook_email
        We filter using an OR to allow existing members to connect with
        their facebook ID using email.

        This decorator works with django's custom user model

        :param facebook_id:
            Optional string representing the facebook id.
        :param facebook_email:
            Optional string with the facebook email.

        :return: The signed in :class:`User`.
        '''
        logger.info("UA01 Inside User Authenticate function")
        user_model = get_user_model()
        logger.info("UA02 User model %s" % user_model)
        if facebook_id or facebook_email:
            # match by facebook id or email
            auth_conditions = []
            if facebook_id:
                logger.info("UA03 facebook id %s" % facebook_id)
                auth_conditions.append(Q(facebook_id=facebook_id))
            if facebook_email:
                logger.info("UA04 facebook email %s" % facebook_email)
                auth_conditions.append(Q(email__iexact=facebook_email))
            # or the operations
            auth_condition = reduce(operator.or_, auth_conditions)
            logger.info("UA05 Auth conditions %s" % auth_condition)

            # get the users in one query
            users = list(user_model.objects.filter(auth_condition))
            logger.info("UA06 Users from query %s" % users)

            # id matches vs email matches
            id_matches = [u for u in users if u.facebook_id == facebook_id]
            email_matches = [u for u in users if u.facebook_id != facebook_id]
            logger.info("UA07 Id matches %s" % id_matches)
            logger.info("UA08 email model %s" % email_matches)

            # error checking
            if len(id_matches) > 1:
                raise ValueError(
                    'found multiple facebook id matches. this shouldnt be allowed, check your unique constraints. users found %s' % users)

            # give the right user
            user = None
            if id_matches:
                user = id_matches[0]
                logger.info("UA09 User matches from id %s" % user)
            elif email_matches:
                user = email_matches[0]
                logger.info("UA09 User matches from email %s" % user)

            if user and facebook_settings.FACEBOOK_FORCE_PROFILE_UPDATE_ON_LOGIN:
                logger.info("UA10 Require user update")
                user.fb_update_required = True
            return user
Example #10
0
 def clean_email(self):
     """
     Validate that the supplied email address is unique for the
     site.
     """
     if get_user_model().objects.filter(email__iexact=self.cleaned_data['email']):
         raise forms.ValidationError(_("This email address is already in use. Please supply a different email address."))
     return self.cleaned_data['email']
    def register(self, request, form=None, **kwargs):
        """
        Create and immediately log in a new user.

        """
        username, email, password = kwargs['username'], kwargs[
            'email'], kwargs['password1']
        # Create user doesn't accept additional parameters,
        user_model = get_user_model()
        new_user = get_user_model(
        ).objects.create_user(username, email, password)

        signals.user_registered.send(sender=self.__class__,
                                     user=new_user,
                                     request=request)
        authenticated_user = self.authenticate(request, username, password)
        return authenticated_user
    def profile_authenticate(self, facebook_id=None, facebook_email=None):
        '''
        Authenticate the facebook user by id OR facebook_email
        We filter using an OR to allow existing members to connect with
        their facebook ID using email.

        :param facebook_id:
            Optional string representing the facebook id

        :param facebook_email:
            Optional string with the facebook email

        :return: The signed in :class:`User`.
        '''
        if facebook_id or facebook_email:
            profile_class = get_profile_model()
            profile_query = profile_class.objects.all().order_by('user')
            profile_query = profile_query.select_related('user')
            profile = None

            # filter on email or facebook id, two queries for better
            # queryplan with large data sets
            if facebook_id:
                profiles = profile_query.filter(facebook_id=facebook_id)[:1]
                profile = profiles[0] if profiles else None
            if profile is None and facebook_email:
                try:
                    profiles = profile_query.filter(
                        user__email__iexact=facebook_email)[:1]
                    profile = profiles[0] if profiles else None
                except DatabaseError:
                    try:
                        user = get_user_model(
                        ).objects.get(email=facebook_email)
                    except get_user_model().DoesNotExist:
                        user = None
                    profile = user.get_profile() if user else None

            if profile:
                # populate the profile cache while we're getting it anyway
                user = profile.user
                user._profile = profile
                if facebook_settings.FACEBOOK_FORCE_PROFILE_UPDATE_ON_LOGIN:
                    user.fb_update_required = True
                return user
Example #13
0
    def test_connect(self):
        '''
        Test if we can do logins
        django_facebook.connect.connect_user
        '''
        user = get_user_model().objects.all()[:1][0]
        url = self.url

        # test registration flow
        from django_facebook.connect import connect_user
        with patch('django_facebook.views.connect_user', return_value=(CONNECT_ACTIONS.REGISTER, user)) as wrapped_connect:
            post_data = dict(access_token='short_username',
                             next='%s?register=1' % url, facebook_login=1)
            response = self.client.post(url, post_data, follow=True)
            self.assertEqual(wrapped_connect.call_count, 1)
            self.assertIn('register', response.redirect_chain[0][0])
            self.assertEqual(response.status_code, 200)

        # user register next instead of next
        with patch('django_facebook.views.connect_user', return_value=(CONNECT_ACTIONS.REGISTER, user)) as wrapped_connect:
            post_data = dict(access_token='short_username', register_next='%s?register=1' % url, facebook_login=1)
            response = self.client.post(url, post_data, follow=True)
            self.assertEqual(wrapped_connect.call_count, 1)
            self.assertIn('register', response.redirect_chain[0][0])
            self.assertEqual(response.status_code, 200)

        # test login
        with patch('django_facebook.views.connect_user', return_value=(CONNECT_ACTIONS.LOGIN, user)) as wrapped_connect:
            post_data = dict(access_token='short_username',
                             next='%s?loggggg=1' % url, facebook_login=1)
            response = self.client.post(url, post_data, follow=True)
            self.assertEqual(wrapped_connect.call_count, 1)
            self.assertIn('?loggggg=1', response.redirect_chain[0][0])
            self.assertEqual(response.status_code, 200)

        # test connect
        with patch('django_facebook.views.connect_user', return_value=(CONNECT_ACTIONS.CONNECT, user)) as wrapped_connect:
            post_data = dict(access_token='short_username',
                             next='%s?loggggg=1' % url, facebook_login=1)
            response = self.client.post(url, post_data, follow=True)
            self.assertEqual(wrapped_connect.call_count, 1)
            assert '?loggggg=1' in response.redirect_chain[0][0]
            self.assertEqual(response.status_code, 200)

        # test connect
        from django_facebook import exceptions as facebook_exceptions
        profile_error = facebook_exceptions.IncompleteProfileError()
        profile_error.form = None
        with patch('django_facebook.views.connect_user', return_value=(CONNECT_ACTIONS.REGISTER, user), side_effect=profile_error) as wrapped_connect:
            post_data = dict(access_token='short_username',
                             next='%s?loggggg=1' % url, facebook_login=1)
            response = self.client.post(url, post_data, follow=True)
            self.assertEqual(wrapped_connect.call_count, 1)
            self.assertEqual(response.status_code, 200)
            self.assertTrue(response.context)
            assert response.template.name in facebook_settings.FACEBOOK_REGISTRATION_TEMPLATE or response.template.name == facebook_settings.FACEBOOK_REGISTRATION_TEMPLATE
    def register(self, request, form=None, **kwargs):
        """
        Create and immediately log in a new user.

        """
        if username_as_username_field():
            username, email, password = kwargs["username"], kwargs["email"], kwargs["password1"]
            # Create user doesn't accept additional parameters,
            new_user = get_user_model().objects.create_user(username, email, password)
            username_field = username
        else:
            email, password = kwargs["email"], kwargs["password1"]
            # Create user doesn't accept additional parameters,
            new_user = get_user_model().objects.create_user(email, password)
            username_field = email

        signals.user_registered.send(sender=self.__class__, user=new_user, request=request)
        authenticated_user = self.authenticate(request, username_field, password)
        return authenticated_user
Example #15
0
def create_profile(sender, instance, created, **kwargs):

  '''
  Create a matching profile whenever a user object is created.
  '''
  print '=======', sender,instance,created
  if sender == get_user_model():
    user = instance 
    profile_model = get_profile_model()

    if profile_model == STUserProfile and created:
      profile, new = STUserProfile.objects.get_or_create(user=instance)
Example #16
0
 def _create_unique_username(cls, base_username):
     '''
     Check the database and add numbers to the username to ensure its unique
     '''
     usernames = list(get_user_model().objects.filter(
         username__istartswith=base_username).values_list(
             'username', flat=True))
     usernames_lower = [str(u).lower() for u in usernames]
     username = str(base_username)
     i = 1
     while base_username.lower() in usernames_lower:
         base_username = username + str(i)
         i += 1
     return base_username
Example #17
0
    def test_update_access_token(self):
        request = RequestMock().get('/')
        request.session = {}
        request.user = AnonymousUser()
        graph = get_persistent_graph(request, access_token='paul')
        action, user = connect_user(self.request, facebook_graph=graph)
        first_user_id = user.id

        # new token required should start out as False
        profile = try_get_profile(user)
        new_token_required = get_user_attribute(
            user, profile, 'new_token_required')
        self.assertEqual(new_token_required, False)

        # we manually set it to true
        update_user_attributes(
            user, profile, dict(new_token_required=True), save=True)
        if profile:
            profile = get_profile_model().objects.get(id=profile.id)
        user = get_user_model().objects.get(id=user.id)
        new_token_required = get_user_attribute(
            user, profile, 'new_token_required')
        self.assertEqual(new_token_required, True)

        # another update should however set it back to False
        request.facebook = None
        graph = get_facebook_graph(request, access_token='paul2')
        logger.info('and the token is %s', graph.access_token)
        action, user = connect_user(self.request, facebook_graph=graph)
        user = get_user_model().objects.get(id=user.id)
        self.assertEqual(user.id, first_user_id)
        if profile:
            profile = get_profile_model().objects.get(id=profile.id)
        user = get_user_model().objects.get(id=user.id)
        new_token_required = get_user_attribute(
            user, profile, 'new_token_required')
        self.assertEqual(new_token_required, False)
Example #18
0
	def authenticate(self, fn, request, *args, **kwargs):
		redirect_uri = self.get_redirect_uri(request)
		oauth_url = get_oauth_url(
			self.scope_list, redirect_uri, extra_params=self.extra_params)

		graph = None
		try:
			# call get persistent graph and convert the
			# token with correct redirect uri
			graph = require_persistent_graph(
				request, redirect_uri=redirect_uri)
			# Note we're not requiring a persistent graph here
			# You should require a persistent graph in the view when you start
			# using this

			facebook = OpenFacebook(graph.access_token)
			user = facebook.get('me')
			email = user.get('email')

			user_model = get_user_model()
			user = user_model.objects.filter(email=email)
			a = 0
			if user:
				response = self.execute_view(
					fn, request, graph=graph, *args, **kwargs)
			else:
				response = HttpResponse("Voce nao tem permissao para acessar o sistema<br>Para ter acesso repasse esse email para o administrador: " + email)
		except open_facebook_exceptions.OpenFacebookException as e:
			permission_granted = has_permissions(graph, self.scope_list)
			if permission_granted:
				# an error if we already have permissions
				# shouldn't have been caught
				# raise to prevent bugs with error mapping to cause issues
				a = 0
				if a == 0:
					response = self.authentication_failed(
					fn, request, *args, **kwargs)
				else:
					raise
			elif request.REQUEST.get('attempt') == '1':
				# Doing a redirect could end up causing infinite redirects
				# If Facebook is somehow not giving permissions
				# Time to show an error page
				response = self.authentication_failed(
					fn, request, *args, **kwargs)
			else:
				response = self.oauth_redirect(oauth_url, redirect_uri, e)
		return response
Example #19
0
 def test_follow_og_share(self):
     user_url = 'http://www.fashiolista.com/style/neni/'
     kwargs = dict(item=user_url)
     user = get_user_model().objects.all()[:1][0]
     from django.contrib.contenttypes.models import ContentType
     some_content_type = ContentType.objects.all()[:1][0]
     share = OpenGraphShare.objects.create(
         user_id=user.id,
         facebook_user_id=13123123,
         action_domain='fashiolista:follow',
         content_type=some_content_type,
         object_id=user.id,
     )
     share.set_share_dict(kwargs)
     share.save()
     share.send()
Example #20
0
    def test_fb_update_required(self):
        def pre_update(sender, user, profile, facebook_data, **kwargs):
            user.pre_update_signal = True

        Profile = get_profile_model()
        user_model = get_user_model()
        signals.facebook_pre_update.connect(pre_update, sender=user_model)
        facebook = get_facebook_graph(access_token='tschellenbach')

        facebook_settings.FACEBOOK_FORCE_PROFILE_UPDATE_ON_LOGIN = True
        action, user = connect_user(self.request, facebook_graph=facebook)
        self.assertEqual(action, CONNECT_ACTIONS.LOGIN)
        self.assertTrue(hasattr(user, 'pre_update_signal'))

        facebook_settings.FACEBOOK_FORCE_PROFILE_UPDATE_ON_LOGIN = False
        action, user = connect_user(self.request, facebook_graph=facebook)
        self.assertEqual(action, CONNECT_ACTIONS.LOGIN)
        self.assertFalse(hasattr(user, 'pre_update_signal'))
    def register(self, request, form=None, **kwargs):
        """
        Create and immediately log in a new user.

        """
        email = kwargs['email']
        # Create user doesn't accept additional parameters,
        new_user = get_user_model(
        ).objects.create(email=email, username=email, password='')

        signals.user_registered.send(sender=self.__class__,
                                     user=new_user,
                                     request=request)
        # Create facebook user profile as we do not use special signal anymore
        FacebookUserProfile.objects.create(user=new_user)
        # Dirty fix to return user
        authenticated_user = new_user
        return authenticated_user
Example #22
0
def _get_old_connections(facebook_id, current_user_id=None):
    """
    Gets other accounts connected to this facebook id, which are not
    attached to the current user
    """
    user_or_profile_model = get_model_for_attribute("facebook_id")
    other_facebook_accounts = user_or_profile_model.objects.filter(facebook_id=facebook_id)
    kwargs = {}

    if current_user_id:
        # if statement since we need to support both
        user_model = get_user_model()
        if user_or_profile_model == user_model:
            kwargs["id"] = current_user_id
        else:
            kwargs["user"] = current_user_id
        other_facebook_accounts = other_facebook_accounts.exclude(**kwargs)
    return other_facebook_accounts
Example #23
0
 def pre_save(self, obj):
     print 'trying to save a report....'
     species = self.request.DATA['name']
     obj.species = Species.objects.get(name=species)
     obj.points = obj.species.calculate_score()
     obj.user = get_user_model().objects.get(username='chid')
     lat = self.request.DATA['lat']
     lon = self.request.DATA['lon']
     obj.location = Location.objects.get_or_create(lat=lat, lon=lon)[0]
     print 'saved most things....'
     img_string = self.request.DATA['imageSrc']
     img_data = img_string.decode("base64")
     filename = str(obj.species.name.replace(' ', '_')) + 'photo.jpg'
     img_file = open(filename, "wb")
     img_file.write(img_data)
     img_file.close()
     print 'after photo process'
     obj.photo = img_file
     print 'after photo...'
Example #24
0
 def test_send(error, expected_error_message, expected_new_token, has_permissions=False):
     user, profile, share = self.share_details
     update_user_attributes(
         user, profile, dict(new_token_required=False), save=True)
     with mock.patch('open_facebook.api.OpenFacebook') as mocked:
         instance = mocked.return_value
         instance.set = Mock(side_effect=error)
         instance.has_permissions = Mock(return_value=has_permissions)
         instance.access_token = get_user_attribute(
             user, profile, 'access_token')
         share.send(graph=instance)
         self.assertEqual(share.error_message, expected_error_message)
         self.assertFalse(share.completed_at)
         user = get_user_model().objects.get(id=user.id)
         if profile:
             profile = get_profile_model().objects.get(id=profile.id)
         new_token_required = get_user_attribute(
             user, profile, 'new_token_required')
         self.assertEqual(new_token_required, expected_new_token)
Example #25
0
    def user_authenticate(self, facebook_id=None, facebook_email=None):
        '''
        Authenticate the facebook user by id OR facebook_email
        We filter using an OR to allow existing members to connect with
        their facebook ID using email.

        This decorator works with django's custom user model
        '''
        user_model = get_user_model()
        if facebook_id or facebook_email:
            # match by facebook id or email
            auth_conditions = []
            if facebook_id:
                auth_conditions.append(Q(facebook_id=facebook_id))
            if facebook_email:
                auth_conditions.append(Q(email__iexact=facebook_email))
            # or the operations
            auth_condition = reduce(operator.or_, auth_conditions)

            # get the users in one query
            users = list(user_model.objects.filter(auth_condition))

            # id matches vs email matches
            id_matches = [u for u in users if u.facebook_id == facebook_id]
            email_matches = [u for u in users if u.facebook_id != facebook_id]

            # error checking
            if len(id_matches) > 1:
                raise ValueError(
                    'found multiple facebook id matches. this shouldnt be allowed, check your unique constraints. users found %s' % users)

            # give the right user
            user = None
            if id_matches:
                user = id_matches[0]
            elif email_matches:
                user = email_matches[0]

            if user and facebook_settings.FACEBOOK_FORCE_PROFILE_UPDATE_ON_LOGIN:
                user.fb_update_required = True
            return user
Example #26
0
    def _extend_access_token(self, access_token):
        from open_facebook.api import FacebookAuthorization
        results = FacebookAuthorization.extend_access_token(access_token)
        access_token = results['access_token']
        old_token = self.access_token
        token_changed = access_token != old_token
        message = 'a new' if token_changed else 'the same'
        log_format = 'Facebook provided %s token, which expires at %s'
        expires_delta = timedelta(days=60)
        logger.info(log_format, message, expires_delta)
        if token_changed:
            logger.info('Saving the new access token')
            self.access_token = access_token
            self.save()

        from django_facebook.signals import facebook_token_extend_finished
        facebook_token_extend_finished.send(
            sender=get_user_model(), user=self.get_user(), profile=self,
            token_changed=token_changed, old_token=old_token
        )

        return results
Example #27
0
    def register(self, request, form=None, **kwargs):
        """
        Create and immediately log in a new user.

        """
        fullname = request.GET.get('fullname', '')
        first_name = fullname.split(' ')[0]
        last_name = (' ').join(fullname.split(' ')[1:])
        username = email = request.GET.get('email', '')
        password = request.GET.get('password', '')

        # Create user doesn't accept additional parameters,
        new_user = get_user_model().objects.create_user(username, email, password)
        new_user.first_name = first_name
        new_user.last_name = last_name
        new_user.save()

        signals.user_registered.send(sender=self.__class__,
                                     user=new_user,
                                     request=request)
        # don't need to auto authenticate
        authenticated_user = self.authenticate(request, username, password)
        return authenticated_user
Example #28
0
    def setUp(self):
        FacebookTest.setUp(self)
        user_url = 'http://www.fashiolista.com/style/neni/'
        kwargs = dict(item=user_url)
        user = get_user_model().objects.all()[:1][0]
        profile = try_get_profile(user)
        user_or_profile = get_instance_for_attribute(
            user, profile, 'facebook_open_graph')
        user_or_profile.facebook_open_graph = True
        user_or_profile.save()

        some_content_type = ContentType.objects.all()[:1][0]
        share = OpenGraphShare.objects.create(
            user_id=user.id,
            facebook_user_id=13123123,
            action_domain='fashiolista:follow',
            content_type=some_content_type,
            object_id=user.id,
        )
        share.set_share_dict(kwargs)
        share.save()
        self.share = share
        self.share_details = user, profile, share
Example #29
0
def _update_user(user, facebook, overwrite=True):
    '''
    Updates the user and his/her profile with the data from facebook
    '''
    # if you want to add fields to ur user model instead of the
    # profile thats fine
    # partial support (everything except raw_data and facebook_id is included)
    facebook_data = facebook.facebook_registration_data(username=False)
    facebook_fields = ['facebook_name', 'facebook_profile_url', 'gender',
                       'date_of_birth', 'about_me', 'website_url', 'first_name', 'last_name']

    profile = try_get_profile(user)
    # which attributes to update
    attributes_dict = {}

    # send the signal that we're updating
    signals.facebook_pre_update.send(sender=get_user_model(), user=user,
                                     profile=profile, facebook_data=facebook_data)

    # set the facebook id and make sure we are the only user with this id
    current_facebook_id = get_user_attribute(user, profile, 'facebook_id')
    facebook_id_changed = facebook_data['facebook_id'] != current_facebook_id
    overwrite_allowed = overwrite or not current_facebook_id

    # update the facebook id and access token
    facebook_id_overwritten = False
    if facebook_id_changed and overwrite_allowed:
        # when not overwriting we only update if there is no
        # profile.facebook_id
        logger.info('profile facebook id changed from %s to %s',
                    repr(facebook_data['facebook_id']),
                    repr(current_facebook_id))
        attributes_dict['facebook_id'] = facebook_data['facebook_id']
        facebook_id_overwritten = True

    if facebook_id_overwritten:
        _remove_old_connections(facebook_data['facebook_id'], user.id)

    # update all fields on both user and profile
    for f in facebook_fields:
        facebook_value = facebook_data.get(f, False)
        current_value = get_user_attribute(user, profile, f, None)
        if facebook_value and not current_value:
            attributes_dict[f] = facebook_value

    # write the raw data in case we missed something
    serialized_fb_data = json.dumps(facebook.facebook_profile_data())
    current_raw_data = get_user_attribute(user, profile, 'raw_data')
    if current_raw_data != serialized_fb_data:
        attributes_dict['raw_data'] = serialized_fb_data

    image_url = facebook_data['image']
    # update the image if we are allowed and have to
    if facebook_settings.FACEBOOK_STORE_LOCAL_IMAGE:
        image_field = get_user_attribute(user, profile, 'image', True)
        if not image_field:
            image_name, image_file = _update_image(
                facebook_data['facebook_id'], image_url)
            image_field.save(image_name, image_file)

    # save both models if they changed
    update_user_attributes(user, profile, attributes_dict)
    if getattr(user, '_fb_is_dirty', False):
        user.save()
    if getattr(profile, '_fb_is_dirty', False):
        profile.save()

    signals.facebook_post_update.send(sender=get_user_model(),
                                      user=user, profile=profile, facebook_data=facebook_data)

    return user
Example #30
0
def _register_user(request, facebook, profile_callback=None,
                   remove_old_connections=False):
    '''
    Creates a new user and authenticates
    The registration form handles the registration and validation
    Other data on the user profile is updates afterwards

    if remove_old_connections = True we will disconnect old
    profiles from their facebook flow
    '''
    if not facebook.is_authenticated():
        raise ValueError(
            'Facebook needs to be authenticated for connect flows')

    # get the backend on new registration systems, or none
    # if we are on an older version
    backend = get_registration_backend()
    logger.info('running backend %s for registration', backend)

    # gets the form class specified in FACEBOOK_REGISTRATION_FORM
    form_class = get_form_class(backend, request)

    facebook_data = facebook.facebook_registration_data()

    data = request.POST.copy()
    for k, v in facebook_data.items():
        if not data.get(k):
            data[k] = v
    if remove_old_connections:
        _remove_old_connections(facebook_data['facebook_id'])

    if request.POST.get('force_registration_hard') or \
            request.GET.get('force_registration_hard'):
        data['email'] = data['email'].replace(
            '@', '+test%[email protected]' % randint(0, 1000000000))
        
    if not data['email']:
        data['email'] = '%[email protected]' % data['username'] 

    form = form_class(data=data, files=request.FILES,
                      initial={'ip': request.META['REMOTE_ADDR']})

    if not form.is_valid():
        # show errors in sentry
        form_errors = form.errors
        error = facebook_exceptions.IncompleteProfileError(
            'Facebook signup incomplete')
        error.form = form
        raise error

    try:
        # for new registration systems use the backends methods of saving
        new_user = None
        if backend:
            new_user = backend.register(request,
                                        form=form, **form.cleaned_data)
        # fall back to the form approach
        if new_user is None:
            raise ValueError(
                'new_user is None, note that backward compatability for the older versions of django registration has been dropped.')
    except IntegrityError as e:
        # this happens when users click multiple times, the first request registers
        # the second one raises an error
        raise facebook_exceptions.AlreadyRegistered(e)

    # update some extra data not yet done by the form
    new_user = _update_user(new_user, facebook)

    signals.facebook_user_registered.send(sender=get_user_model(),
                                          user=new_user, facebook_data=facebook_data, request=request, converter=facebook)
    # IS this the correct way for django 1.3? seems to require the backend
    # attribute for some reason
    new_user.backend = 'django_facebook.auth_backends.FacebookBackend'
    auth.login(request, new_user)

    return new_user