Skip to content

Small fix for post-login redirect #32

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 14 additions & 6 deletions la_facebook/callbacks/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ def __call__(self, request, access, token):
else:
logger.debug("BaseFacebookCallback.__call__:'\
existing django user found for this facebook identifier")
ret = self.handle_unauthenticated_user(request, user, access,
ret = self.handle_unauthenticated_user(request, user, access,
token, user_data)
if isinstance(ret, HttpResponse):
return ret
Expand All @@ -55,7 +55,7 @@ def fetch_user_data(self, request, access, token):
def lookup_user(self, request, access, user_data):
raise NotImplementedError("Callbacks must have a lookup_user method")

def redirect_url(self, request, fallback_url=settings.LOGIN_REDIRECT_URL,
def redirect_url(self, request, fallback_url=settings.LOGIN_REDIRECT_URL,
redirect_field_name="next", session_key_value="redirect_to"):
"""
Returns the URL to be used in login procedures by looking at different
Expand All @@ -73,10 +73,18 @@ def redirect_url(self, request, fallback_url=settings.LOGIN_REDIRECT_URL,
if hasattr(request, "session"):
redirect_to = request.session.get(session_key_value)
# Heavier security check -- don't allow redirection to a different host.
netloc = urlparse.urlparse(redirect_to)[1]
if netloc and netloc != request.host:
logger.warning("redirect_to host does not match orgin")
redirect_to = fallback_url
if redirect_to:
netloc = urlparse.urlparse(redirect_to)[1]
if netloc and netloc != request.host:
logger.warning("redirect_to host does not match orgin")
redirect_to = fallback_url
else:
# There ought to have been a value in the session. This
# is probably a developer error, so log a warning.
logger.warning("Session found, but no redirect_to. Check "
"that you have set up the facebook_login "
"view with a 'next' querystring "
"parameter. Using fallback.")
if not redirect_to:
logger.debug("no redirect found, using fallback")
redirect_to = fallback_url
Expand Down
24 changes: 24 additions & 0 deletions la_facebook/tests/test_callbacks.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,9 @@
except ImportError:
raise ImportError("callback tests require Django > 1.3 for RequestFactory")

from django.conf import settings
from django.contrib.auth.models import User, AnonymousUser
from django.contrib.sessions.middleware import SessionMiddleware

from la_facebook.access import OAuthAccess, OAuth20Token
from la_facebook.callbacks.base import BaseFacebookCallback
Expand Down Expand Up @@ -56,6 +58,28 @@ def test_redirect_url(self):
resp = callback.redirect_url(self.request)
self.assertEquals(resp,'dummy')

def test_redirect_url_no_next_no_session(self):
request = factory.get('/callback')
callback = BaseFacebookCallback()
resp = callback.redirect_url(request)
self.assertEquals(resp, settings.LOGIN_REDIRECT_URL)

def test_redirect_url_no_next_session(self):
request = factory.get('/callback')
callback = BaseFacebookCallback()
SessionMiddleware().process_request(request)
callback = BaseFacebookCallback()
resp = callback.redirect_url(request)
self.assertEquals(resp, settings.LOGIN_REDIRECT_URL)

def test_redirect_url_in_session(self):
request = factory.get('/callback')
SessionMiddleware().process_request(request)
request.session['redirect_to'] = 'session_redirect'
callback = BaseFacebookCallback()
resp = callback.redirect_url(request)
self.assertEquals(resp, 'session_redirect')

def test_identifier_from_data(self):
callback = BaseFacebookCallback()
data = {'name':'test name','id':'testid'}
Expand Down