]> git.parisson.com Git - django-social-auth.git/commitdiff
Odnoklassniki OAuth 2.0 authentication support added.
authorStas Kravets <skravets@applebough.(none)>
Mon, 18 Apr 2011 14:02:30 +0000 (18:02 +0400)
committerStas Kravets <skravets@applebough.(none)>
Mon, 18 Apr 2011 14:02:30 +0000 (18:02 +0400)
social_auth/backends/contrib/odnoklassniki.py [new file with mode: 0644]

diff --git a/social_auth/backends/contrib/odnoklassniki.py b/social_auth/backends/contrib/odnoklassniki.py
new file mode 100644 (file)
index 0000000..d05d64d
--- /dev/null
@@ -0,0 +1,88 @@
+"""
+Odnoklassniki.ru OAuth2 support
+
+Take a look to http://dev.odnoklassniki.ru/wiki/display/ok/The+OAuth+2.0+Protocol
+
+You need to register OAuth application here:
+http://dev.odnoklassniki.ru/wiki/pages/viewpage.action?pageId=13992188
+
+Then setup your application according manual and use information from registration
+mail to set settings values
+
+"""
+
+from django.conf import settings
+from django.utils import simplejson
+
+from urllib import urlencode, unquote
+from urllib2 import Request, urlopen
+from hashlib import md5
+
+from social_auth.backends import OAuthBackend, BaseOAuth2, USERNAME
+
+ODNOKLASSNIKI_API_URL       = 'http://api.odnoklassniki.ru/fb.do'
+ODNOKLASSNIKI_OAUTH2_SCOPE  = [''] # Enough for authentication
+
+EXPIRES_NAME = getattr(settings, 'SOCIAL_AUTH_EXPIRATION', 'expires')
+
+class OdnoklassnikiBackend(OAuthBackend):
+    """Odnoklassniki authentication backend"""
+    name = 'odnoklassniki'
+    EXTRA_DATA = [('refresh_token', 'refresh_token'),
+                  ('expires_in', EXPIRES_NAME)]
+
+    def get_user_id(self, details, response):
+        """Return user unique id provided by Odnoklassniki"""
+        return int(response['uid'])
+    
+    def get_user_details(self, response):
+        """Return user details from Odnoklassniki request"""
+        values = { USERNAME: response['uid'], 'email': '', 'fullname': unquote(response['name']),
+                  'first_name': unquote(response['first_name']), 'last_name': unquote(response['last_name'])}
+        return values
+    
+
+class OdnoklassnikiOAuth2(BaseOAuth2):
+    """Odnoklassniki OAuth2 support"""
+    AUTH_BACKEND = OdnoklassnikiBackend
+    AUTHORIZATION_URL = 'http://www.odnoklassniki.ru/oauth/authorize'
+    ACCESS_TOKEN_URL = ' http://api.odnoklassniki.ru/oauth/token.do'
+    SETTINGS_KEY_NAME = 'ODNOKLASSNIKI_OAUTH2_CLIENT_KEY'
+    SETTINGS_SECRET_NAME = 'ODNOKLASSNIKI_OAUTH2_CLIENT_SECRET'
+
+    def get_scope(self):
+        return ODNOKLASSNIKI_OAUTH2_SCOPE + getattr(settings, 'ODNOKLASSNIKI_OAUTH2_EXTRA_SCOPE', [])
+
+    def user_data(self, access_token):
+        """Return user data from Odnoklassniki REST API"""
+        data = {'access_token': access_token, 'method': 'users.getCurrentUser'}
+        return odnoklassniki_api(data)
+
+def odnoklassniki_sig(data):
+    """ Calculates signature of request data
+        access_token value must be included """
+        
+    suffix = md5(data['access_token'] + settings.ODNOKLASSNIKI_OAUTH2_CLIENT_SECRET).hexdigest()
+    
+    check_list = sorted(list(item + '=' + data[item] for item in data if item != 'access_token'))
+    
+    return md5(''.join(check_list) + suffix).hexdigest() 
+    
+def odnoklassniki_api(data):
+    """ Calls Odnoklassniki REST API method
+        http://dev.odnoklassniki.ru/wiki/display/ok/Odnoklassniki+Rest+API
+    """
+    data.update({'application_key': settings.ODNOKLASSNIKI_OAUTH2_APP_KEY, 'format': 'JSON'})
+    data['sig'] = odnoklassniki_sig(data)
+
+    params = urlencode(data)
+    request = Request(ODNOKLASSNIKI_API_URL + '?' + params)
+    try:
+        return simplejson.loads(urlopen(request).read())
+    except (TypeError, KeyError, IOError, ValueError, IndexError):
+        return None
+
+# Backend definition
+BACKENDS = {
+    'odnoklassniki': OdnoklassnikiOAuth2
+}
\ No newline at end of file