-
Notifications
You must be signed in to change notification settings - Fork 1.1k
/
social_auth.py
89 lines (73 loc) · 3.22 KB
/
social_auth.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
from social.exceptions import AuthAlreadyAssociated, AuthException, \
AuthForbidden
def social_details(strategy, response, *args, **kwargs):
return {'details': strategy.backend.get_user_details(response)}
def social_uid(strategy, details, response, *args, **kwargs):
return {'uid': strategy.backend.get_user_id(details, response)}
def auth_allowed(strategy, details, response, *args, **kwargs):
if not strategy.backend.auth_allowed(response, details):
raise AuthForbidden(strategy.backend)
def social_user(strategy, uid, user=None, *args, **kwargs):
provider = strategy.backend.name
social = strategy.storage.user.get_social_auth(provider, uid)
if social:
if user and social.user != user:
msg = 'This {0} account is already in use.'.format(provider)
raise AuthAlreadyAssociated(strategy.backend, msg)
elif not user:
user = social.user
return {'social': social,
'user': user,
'is_new': user is None,
'new_association': False}
def associate_user(strategy, uid, user=None, social=None, *args, **kwargs):
if user and not social:
try:
social = strategy.storage.user.create_social_auth(
user, uid, strategy.backend.name
)
except Exception as err:
if not strategy.is_integrity_error(err):
raise
# Protect for possible race condition, those bastard with FTL
# clicking capabilities, check issue #131:
# https://github.com/omab/django-social-auth/issues/131
return social_user(strategy, uid, user, *args, **kwargs)
else:
return {'social': social,
'user': social.user,
'new_association': True}
def associate_by_email(strategy, details, user=None, *args, **kwargs):
"""
Associate current auth with a user with the same email address in the DB.
This pipeline entry is not 100% secure unless you know that the providers
enabled enforce email verification on their side, otherwise a user can
attempt to take over another user account by using the same (not validated)
email address on some provider. This pipeline entry is disabled by
default.
"""
if user:
return None
email = details.get('email')
if email:
# Try to associate accounts registered with the same email address,
# only if it's a single object. AuthException is raised if multiple
# objects are returned.
users = list(strategy.storage.user.get_users_by_email(email))
if len(users) == 0:
return None
elif len(users) > 1:
raise AuthException(
strategy.backend,
'The given email address is associated with multiple accounts'
)
else:
return {'user': users[0]}
def load_extra_data(strategy, details, response, uid, user, *args, **kwargs):
social = kwargs.get('social') or strategy.storage.user.get_social_auth(
strategy.backend.name,
uid
)
if social:
extra_data = strategy.backend.extra_data(user, uid, response, details)
social.set_extra_data(extra_data)