Django dynamic url in root domain overwrites all other urls - django

I want to have a dynamic root url for different users. All users get their own url. I want to have the dynamic url in the root but also be able to have more hardcoded urls as alternatives, for example on the url that the user will edit their profile.
The problem i have is that all urls redirect to view2 and none goes to view1.
path(r'edit/<str:user>/', views.view1, name='view1'),
path(r'<str:user>/', views.view2, name='view2'),
example.com/edit/user always gets redirected to example.com/user which is not wanted.
views:
def viewID(request):
return render(request, 'viewID.html')

This worked for me:
urls.py:
path('edit/<str:user>/', views.view1, name='view1'),
path('<str:user>/', views.view2, name='view2'),
views.py:
from django.http import HttpResponse
def view1(request, user):
return HttpResponse('This is view1: ' + user)
def view2(request, user):
return HttpResponse('This is view2: ' + user)

So the problem was quite frustrating. I needed to clear the cache or run in a private window since django kept appending a "/" to example.com/user/ which of course would go to view1 since it exects a key

Related

How to set LOGIN_URL variable in Django settings so it doesn't redirect anywhere while not logged in

When trying to access url get_room_messages if user is not logged in #login_required redirects him to: /accounts/login/?next=/get_room_messages
(as specified in docs)
I want it to do nothing (or redirect to the original url, in this example /get_room_messages). I don't want to hardcode it like #login_required(login_url='/get_room_messages'), ideal solution would be to get somehow original url and pass it into #login_required() decorator.
#login_required()
def get_room_messages(request):
user_id = request.user.user_ID
user = get_object_or_404(CustomUser, pk=user_id)
Thank you for help!

Redirecting to root URL from another app's view

I am trying to redirect to root URL when an app's URL is accessed without the user being logged-in.
I've tried to do so in 2 ways:
Using a decorator
#login_required(login_url = '')
def index(request):
return render(request, 'professors/index.html')
Which returned a 404 error saying the current path is accounts/login
Passing the views of the root page to redirect
def index(request):
if request.user.is_authenticated:
return render(request, 'professors/index.html')
else:
return redirect('login.views.index')
Which returned a 404 error saying the current path is professors/login.views.index
The root URL is localhost:8000/ and I am trying to redirect to it after accessing localhost:8000/professors/ when the user is not logged-in.
This problem is similar to what I've found here: Django redirect to root from a view
However, applying the solution did not work for me. It looks like when redirecting to root from an app's view, the root it is redirecting to is the app's root, and not the website's, and this is true for any URL redirected after accessing an app's URL. E.g., if the root URL is localhost:8000 and the app's URL is localhost:8000/professors/, then trying to access any other URL from the latter, will mean that localhost:8000/professors/ is the starting point and what I write in the login_url or redirect(redirect_URL) is added to that, which means that I can no longer access localhost:8000
Final note:
When I tried return redirect ('') in else it returned
NoReverseMatch at /professors/
Reverse for '' not found. '' is not a valid view function or pattern name.
Which shows that the starting point is again from localhost:800/professors/
Set your login_url parameter in login_required decorator,
#login_required(login_url='/')
def index(request):
return render(request, 'professors/index.html')
You can also set the LOGIN_URL in settings
#settings.py
LOGIN_URL='/'

Django LOGIN_REDIRECT_URL does not work with "next" request parameter

Django 1.11.3
The documentation about LOGIN_REDIRECT_URL says that:
The URL where requests are redirected after login when the
contrib.auth.login view gets no next parameter.
I have LOGIN_REDIRECT_URL="some_url" in setting.py
I see "next=" (no value, just the key) in the request url when I login, so I suspect that makes Django to ignore LOGIN_REDIRECT_URL and I end up on Admin default page.
I use default login Django functionality, no custom template or anything. How do I get rid of "next=" in my request when I login (completely, no key) to see if LOGIN_REDIRECT_URL will be actually used (hopefully) ?
That’s expected behavior. Normally you want the user requesting any view requiring login (with the #login_required decorator) to be redirected to that same view after login. This is documented here
Since your view url is empty (the home url) you get next=. It’s quite uncommon to have a login required on the home page, from a user perspective it means you can’t see what you're signing up for.
If you remove the #login_required decorator for your view and just add a login button on your homepage (that goes to the regular LoginView) it will not have the next parameter and your users will be redirected to LOGIN_REDIRECT_URL as expected.
Now, if really want users to have to login on your homepage and be redirected to LOGIN_REDIRECT_URL, you have two options:
Remove the #login_required decorator and do the check and redirect in your view:
from django.conf import settings
def homepage(request):
if not request.user.is_authenticated:
return redirect(settings.LOGIN_URL)
# rest of view code
If you're using class-based views, use the LoginRequiredMixin in your view and handle handle_no_permission() yourself:
from django.contrib.auth.views import redirect_to_login
from django.contrib.auth.mixins import LoginRequiredMixin
class Home(LoginRequiredMixin, View):
def get(self):
# your view code
def handle_no_permission(self):
# pass None to redirect_field_name in order to remove the next param
return redirect_to_login(self.request.get_full_path(), self.get_login_url(), None)
If you are having LOGIN_REDIRECT_URL in your settings.py, then in case you are not giving any next parameter to url, it will go to default url mentioned in LOGIN_REDIRECT_URL.
if LOGIN_REDIRECT_URL = 'some/path/'
https://yourdomain.com/login/ will redirect to 'some/path/'
https://yourdomain.com/login/?next=/override/default/path
will redirect to 'override/default/path'

Remove "?id=" from dynamic URLs

I'm pretty new to django and i'm working on a website that needs a dynamic URL for a database table, and it all works fine, but i would like to know how to remove the "?id=" from the url, so rather than
localhost:8000/dynamicurl/?id=XXXXX
The url becomes
localhost:8000/dynamicurl/XXXXX
Instead
I did a fine amount of searching in the documentation and didn't find a lot, though it's pretty likely i missed something.
EDIT:
thanks everyone for helping, the simplest answer was to remove the object i was using to fetch the ID and just replace it for ID in evert instance,
so my url became
url(r'^dynamicurl/(?P[0-9]+)/$', views.dynamicurl)
and my view became
def dynamicurl(request, id):
i'm like very very new to django FYI
you can capture a variable in url definition in the apps urls.py file. It would look something like this:
url(r'^dynamicurl/(?P<id>[0-9]+)?$', dynamicurl, name = 'dynamicurl'),
then in your view function you receive that parameter:
def dynamicurl(request, id):
If you are talking about how to change your url inside the urls, I suggest you to use code that already answered above: https://stackoverflow.com/a/41988051/6396981
But, if you talking about how to redirect localhost:8000/dynamicurl/?id=XXXXX to localhost:8000/dynamicurl/XXXXX, hope this usefull..
1. views.py
from django.http import HttpResponse
from django.views.generic.base import RedirectView
from django.core.urlresolvers import reverse
class RedirectView(RedirectView):
permanent = False
def get_redirect_url(self):
get_id = self.request.GET.get('id')
if get_id is not None:
return reverse('redirected_page', kwargs={'id': id})
return reverse('origin_page')
def redirected_view(request, id):
# your final view goes here...
return HttpResponse("You're looking for id: %d." % id)
2. urls.py
from django.conf.urls import url
from yourapp.views import views (RedirectView, redirected_view)
urlpatterns = [
# first view the pool to doing redirection
url(r'^pool/$', RedirectView.as_view(), name='origin_page'),
# the final url
url(r'^pool/(?P<id>[\d]+)/$', redirected_view, name='redirected_page'),
]

HttpResponseRedirect not working Django 1.7

I am having a problem with HttpResponseRedirect in Django. It seems that, whatever parameters I try, it either throws an error, or it redirects without changing the URL. I am using it on a custom login_user view, and I want the URL in the address bar to change after they are redirected. If I use redirect instead of HttpResponseRedirect, it does not change. Either way, I can get it to serve the correct template, but the URL stays the same. Being new to Django, it would be helpful if someone could explain to me how to do this and why my current code is not working.
I have seen a couple of similar questions to mine on Stack Exchange, but the answers have not helped.
Here are the relevant parts of my views.py (please note the indenting has gone weird due to copying and pasting in here, and is not the cause of the error).
from django.http import *
from django.contrib.auth import authenticate, login, logout
def login_user(request):
logout(request)
username = password = ''
if request.POST:
username = request.POST.get('username')
password = request.POST.get('password')
user = authenticate(username=username, password=password)
if user is not None:
if user.is_active:
login(request, user)
return HttpResponseRedirect('dashboard')
else:
state = "Your account is not active, please contact the app administrator."
else:
state = "Your username and/or password were incorrect."
state = "Please log in below..."
context = RequestContext(request, {
'state': state,
'username': username,
})
return render_to_response('bank/auth.html', {}, context)
dashboard is the name of another view, and it works fine in a redirect from my index view. I've also tried hard-coding the url in, but that doesn't work either. Any suggestions?? Thanks.
If you use HttpResponseRedirect, you must provide the url, not the name of the url.
You can either get the url by using reverse:
from django.core.urlresolvers import reverse
def my_view(request):
...
return HttpResponseRedirect(reverse('dashboard'))
or by using the redirect shortcut.
from django.shortcuts import redirect
def my_view(request):
...
return redirect('dashboard')
If using the either of the above approaches does not work, then there's probably a mistake somewhere else in the view. It's difficult to tell where, since the indentation is incorrect. Try adding some logging or print statements to see if you are really returning the redirect where you think you are.
In this particular case, the problem wasn't anything to do with my view code, it was actually a problem caused through using JQuery mobile. I found the answer here: Error with Redirects in JQuery Mobile which was to set the data-url attribute on the page div.
However, I have up-voted Alasdair's answer, as his way is the correct one of the ways I had tried.
I personally prefer the simple way as follows:
In urls.py:
url(r'^dashboard/$', 'appname.views.dashboard_view', name='dashboard_view'),
In views.py:
from django.http import HttpResponseRedirect
def dashboard_view(request):
...
return HttpResponseRedirect('/dashboard/')