Перенаправление страниц Python + Django

158

Как выполнить простое перенаправление (например, cflocationв ColdFusion или header(location:http://)для PHP) в Django?

Кайл Хейс
источник

Ответы:

250

Это просто:

from django.http import HttpResponseRedirect

def myview(request):
    ...
    return HttpResponseRedirect("/path/")

Больше информации в официальных документах Django

Обновление: Django 1.0

По-видимому, в Django теперь есть лучший способ сделать это generic views.

Пример -

from django.views.generic.simple import redirect_to

urlpatterns = patterns('',   
    (r'^one/$', redirect_to, {'url': '/another/'}),

    #etc...
)

Есть больше в общей документации представлений . Кредит - Карлес Барробес .

Обновление № 2: Django 1.3+

В Django 1.5 redirect_to больше не существует и был заменен RedirectView . Кредит Йонатану

from django.views.generic import RedirectView

urlpatterns = patterns('',
    (r'^one/$', RedirectView.as_view(url='/another/')),
)
Baishampayan Ghose
источник
8
Это больше не лучший метод с Django 1.0. Смотрите этот ответ: stackoverflow.com/questions/523356/python-django-page-redirect/…
Джейк
2
Почему бы не использовать redirectиз django.shortcuts?
Афшин Мехрабани
4
Я использую('^pattern/$', lambda x: redirect('/redirect/url/'))
mrmagooey
5
Это уже устарело, начиная с Django 1.5. Вместо этого используйте «RedirectView»: docs.djangoproject.com/en/1.5/ref/class-based-views/base/…
Йонатан
Это на самом деле не считается устаревшим, что вы говорите, не рекомендуется? перенаправить? Используя этот метод, я не знаю, как передать значение параметров лямбда, то есть url (r '^ (? P <location_id> \ d +) / $', лямбда x: HttpResponseRedirect (reverse ('dailyreport_location', args = ['% (location_id)',]))) не работает
радтек
113

В зависимости от того, что вы хотите (то есть, если вы не хотите выполнять какую-либо дополнительную предварительную обработку), проще использовать redirect_toобщий вид Django :

from django.views.generic.simple import redirect_to

urlpatterns = patterns('',
    (r'^one/$', redirect_to, {'url': '/another/'}),

    #etc...
)

Смотрите документацию для более продвинутых примеров.


Для Django 1.3+ используйте:

from django.views.generic import RedirectView

urlpatterns = patterns('',
    (r'^one/$', RedirectView.as_view(url='/another/')),
)
Карлес Барробес
источник
+1 за использование общего представления, а не реализацию своего собственного (независимо от того, насколько просто), как в (текущем) ответе с наибольшим количеством голосов.
день
У кого-нибудь есть примеры, если вы действительно хотите сделать дополнительную предварительную обработку?
eageranalyst
1
Затем я бы предложил написать пользовательское представление, которое выполняет обработку, а затем вызывает универсальное представление, или написать декоратор, например, pre_process и украсить универсальное представление: (r '^ one / $', pre_process (redirect_to), {'url ': '/другой/'})
Карлес Барробес
1
@niallsco: если вы хотите выполнить дополнительную обработку, тогда лучше использовать ярлык перенаправления, как описано здесь
Lie Ryan
1
В django 1.4 импорт redirect_to выдает предупреждение об отчуждении.
Joctee
38

На самом деле есть более простой способ, чем иметь представление для каждого перенаправления - вы можете сделать это непосредственно в urls.py:

from django.http import HttpResponsePermanentRedirect

urlpatterns = patterns(
    '',
    # ...normal patterns here...
    (r'^bad-old-link\.php',
     lambda request: HttpResponsePermanentRedirect('/nice-link')),
)

Цель может быть как вызываемой, так и строкой , что я и использую здесь.

Тедди
источник
2
Да, но использование redirect_toобщего представления, которое поставляется с django, еще проще и более читабельно. См. Ответ Карлса stackoverflow.com/questions/523356/python-django-page-redirect/…
День
28

Начиная с Django 1.1, вы также можете использовать более простой ярлык перенаправления :

from django.shortcuts import redirect

def myview(request):
    return redirect('/path')

Он также принимает необязательный аргумент постоянного ключевого слова.

Kennu
источник
14

Если вы хотите перенаправить целую подпапку, urlаргумент в RedirectView фактически интерполирован , так что вы можете сделать что-то вроде этого в urls.py:

from django.conf.urls.defaults import url
from django.views.generic import RedirectView

urlpatterns = [
    url(r'^old/(?P<path>.*)$', RedirectView.as_view(url='/new_path/%(path)s')),
]

Захваченный ?P<path>вами будет подан RedirectView. Эта захваченная переменная будет затем заменена в urlаргументе, который вы дали, давая нам, /new_path/yay/mypathесли ваш первоначальный путь был/old/yay/mypath .

Вы также можете сделать, ….as_view(url='…', query_string=True)если вы хотите скопировать строку запроса.

Одино - Вельмонт
источник
10

С Django версии 1.3 подход на основе классов:

from django.conf.urls.defaults import patterns, url
from django.views.generic import RedirectView

urlpatterns = patterns('',
    url(r'^some-url/$', RedirectView.as_view(url='/redirect-url/'), name='some_redirect'),
)

Этот пример живет в urls.py

Златко
источник
6

Осторожно. Я сделал это на сервере разработки и хотел изменить это позже.

Я должен был очистить свои кеши, чтобы изменить это. Чтобы избежать этой царапины в будущем, я смог сделать это временно так:

from django.views.generic import RedirectView

url(r'^source$', RedirectView.as_view(permanent=False, 
                                      url='/dest/')),
Гринго Суаве
источник
1

Вы можете сделать это в разделе администратора. Это объясняется в документации.

https://docs.djangoproject.com/en/dev/ref/contrib/redirects/

mcneo
источник
Хотя это не совсем относится к моему вопросу, это все же интересная информация.
Кайл Хейс
1

page_path = определить в urls.py

def deletePolls(request):
    pollId = deletePool(request.GET['id'])
    return HttpResponseRedirect("/page_path/")
Moddasir
источник
0

Это должно работать в большинстве версий django, я использую его в 1.6.5:

from django.core.urlresolvers import reverse
from django.http import HttpResponseRedirect
urlpatterns = patterns('',
    ....
    url(r'^(?P<location_id>\d+)/$', lambda x, location_id: HttpResponseRedirect(reverse('dailyreport_location', args=[location_id])), name='location_stats_redirect'),
    ....
)

В этом решении вы все равно можете использовать имя шаблона URL-адреса вместо жесткого URL-адреса. Параметр location_id из URL передается в лямбда-функцию.

radtek
источник