Django after @login_required redirect to next
django, django-admin, django-forms, python
Solution
The query string is implicitly passed to any view, without you having to write any special code.
All you have to do is make sure that the `next` key is passed from the actual login form (in your case, this is the form that is rendered in `/accounts/login/`), to the `/accounts/auth` view.
To do that, you need to make sure you have the request template context processor (`django.core.context_processors.request`) enabled in your settings. To do this, first you need to import the default value for `TEMPLATE_CONTEXT_PROCESSORS`, then add the request processor to it in your `settings.py`, like this:
from django.conf import global_settings
TEMPLATE_CONTEXT_PROCESSORS = global_settings.TEMPLATE_CONTEXT_PROCESSORS + (
"django.core.context_processors.request",
)
Then in the form:
<form method="POST" action="/accounts/auth">
{% csrf_token %}
<input type="hidden" name="next" value="{{ request.GET.next }}" />
{{ login_form }}
<input type="submit">
</form>
Now, in your `/accounts/auth` view:
def foo(request):
if request.method == 'POST':
# .. authenticate your user
# redirect to the value of next if it is entered, otherwise
# to /accounts/profile/
return redirect(request.POST.get('next','/accounts/profile/'))
Problem
I feel like this is an easy question and I'm just missing 1 small step. I want to do any number of the following (as the term in the next parameter): ``` [not signed in] -> profile -> login?next=/accounts/profile/ -> auth -> profile. [not signed in] -> newsfeed -> login?next=/newsfeed/` -> auth -> newsfeed. ``` Whereas I am currently going: ``` [not signed in] -> profile -> login?next=/accounts/profile/ -> auth -> loggedin [not signed in] -> newsfeed -> login?next=/newsfeed/ -> auth -> loggedin ``` I am looking to somehow pass the `next` parameter from a form on `login` to `auth` and have `auth` redirect to this parameter Currently I am trying in my `login.html`: ``` <input type='text' name="next" value="{{ next }}"> ``` however this is not getting the next value. I can see from the debug tool bar: ``` GET data Variable Value u'next' [u'/accounts/profile/'] ``` `views`: ``` def auth_view(request): username = request.POST.get('username', '') password = request.POST.get('password', '') user = auth.authenticate(username=username, password=password) if user is not None: auth.login(request, user) print request.POST return HttpResponseRedirect(request.POST.get('next'),'/accounts/loggedin') else: return HttpResponseRedirect('/accounts/invalid') ``` `login.html`: ``` {% extends "base.html" %} {% block content %} {% if form.errors %} <p class="error"> Sorry, you have entered an incorrect username or password</p> {% endif %} <form action="/accounts/auth/" method="post">{% csrf_token %} <label for="username">User name:</label> <input type="text" name="username" value="" id="username"> <label for="password">Password:</label> <input type="password" name="password" value="" id="password"> <input type='text' name="next" value="{{ request.GET.next }}"> <input type="submit" value="login"> </form> {% endblock %} ``` `settings`: ``` from django.conf.urls import patterns, include, url from django.contrib import admin admin.autodiscover() urlpatterns = patterns('', # Examples: url(r'^admin/', include(admin.site.urls)), ('^accounts/', include('userprofile.urls')), url(r'^accounts/login/$', 'django_yunite.views.login'), url(r'^accounts/auth/$', 'django_yunite.views.auth_view'), url(r'^accounts/logout/$', 'django_yunite.views.logout'), url(r'^accounts/loggedin/$', 'django_yunite.views.loggedin'), url(r'^accounts/invalid/$', 'django_yunite.views.invalid_login'), ) ``` `settings`: ``` # Build paths inside the project like this: os.path.join(BASE_DIR, ...) import os BASE_DIR = os.path.dirname(os.path.dirname(__file__)) # SECURITY WARNING: don't run with debug turned on in production! DEBUG = True TEMPLATE_DEBUG = True ALLOWED_HOSTS = [] # Application definition INSTALLED_APPS = ( 'django.contrib.admin', 'django.contrib.auth', 'django.contrib.contenttypes', 'django.contrib.sessions', 'django.contrib.messages', 'django.contrib.staticfiles', 'debug_toolbar', 'userprofile', ) MIDDLEWARE_CLASSES = ( 'django.contrib.sessions.middleware.SessionMiddleware', 'django.middleware.common.CommonMiddleware', 'django.middleware.csrf.CsrfViewMiddleware', 'django.contrib.auth.middleware.AuthenticationMiddleware', 'django.contrib.messages.middleware.MessageMiddleware', 'django.middleware.clickjacking.XFrameOptionsMiddleware', ) ROOT_URLCONF = 'django_yunite.urls' WSGI_APPLICATION = 'django_yunite.wsgi.application' # Internationalization # https://docs.djangoproject.com/en/1.6/topics/i18n/ LANGUAGE_CODE = 'en-ca' TIME_ZONE = 'EST' USE_I18N = True USE_L10N = True USE_TZ = True # Static files (CSS, JavaScript, Images) # https://docs.djangoproject.com/en/1.6/howto/static-files/ STATIC_URL = '/static/' STATICFILES_DIRS = ( ('assets', '/home/user/GitHub/venv_yunite/django_yunite/static/'), ) TEMPLATE_DIRS = ( './templates', '/article/templates', ) STATIC_ROOT = "/home/user/Documents/static/" AUTH_PROFILE_MODULE = 'userprofile.UserProfile' ``` the print statment shows an empty `u'next'`