Создан 12 дек.
Джеймс Уайтли, Джеймс Уайтли Ваша проблема не связана с кодом, который вы используете для навигации.Вы никогда не зайдете так далеко.
Посмотрите на инструменты разработчика в вашем браузере. Осмотрите консоль. Вы должны увидеть сообщение об ошибке, например:
У вас такая же проблема с полем пароля.
1 Нажимая «Принять все файлы cookie», вы соглашаетесь с тем, что Stack Exchange может хранить файлы cookie на вашем устройстве и раскрывать информацию в соответствии с нашей Политикой использования файлов cookie.
В этом руководстве я объясню, как выполнить перенаправление на определенный раздел страницы в HTML.Мы знаем, что гиперссылки используются веб-браузерами для перехода со страницы на страницу.
Помните, что каждый идентификатор может появиться только один раз на одной странице, чтобы раздел можно было отличить от других разделов.
Создайте гиперссылку, используя тот же идентификатор, что и цель ссылки. Это будет с гиперссылкой #.
По умолчанию после запуска кода появится экран, показанный ниже.
Итак, из приведенного выше кода мы можем увидеть, как мы можем перенаправить на определенный раздел страницы. В этом примере также объясняется, хотите ли вы перейти к определенному разделу той же страницы или к другой веб-странице.
Надеюсь, вам понравился этот урок, пожалуйста, оставьте свои комментарии ниже и не забудьте подписаться на наш сайт, чтобы узнать больше о таких темах.
В этой статье объясняется, как работают «Включаемые», и приводятся шаги по использованию «Включений на стороне сервера», «Включений PHP» и «Включений JavaScript».
Server Side Includes был впервые разработан, чтобы позволить веб-разработчикам «включать» HTML-документы внутрь других страниц. По сути, фрагмент, который находится в одном документе, включается в другой, когда страница запускается на сервере и отправляется в веб-браузер.
SSI включен на большинство веб-серверов, но вам, возможно, придется включить его, чтобы он заработал. Если вы не знаете, поддерживает ли ваш сервер SSI, обратитесь к своему хостинг-провайдеру.
Вот пример того, как вы можете использовать SSI для включения фрагмента HTML на все ваши веб-страницы:
Как и SSI, PHP - это технология серверного уровня. Если вы не уверены, есть ли на вашем сайте функциональность PHP, обратитесь к своему хостинг-провайдеру.
Вот простой сценарий PHP, который вы можете использовать для включения фрагмента HTML на любую веб-страницу с поддержкой PHP:
JavaScript - еще один способ включить HTML на страницы вашего сайта.Этот метод не требует программирования на уровне сервера, но он немного сложнее - и он, очевидно, работает для браузера, который поддерживает Javascript, что в большинстве случаев требуется, если пользователь не решит отключить его.
Сохраните HTML-код общих элементов вашего сайта в файл JavaScript. Любой HTML, записанный в этом файле, должен быть выведен на экран с помощью функции document.write .
Что включает в себя HTML?
Включаемый элемент - это раздел HTML, который сам по себе не является полным HTML-документом. Вместо этого это часть другой страницы, которую можно вставить в целую веб-страницу с помощью программирования. Большинство включаемых файлов - это те вышеупомянутые элементы, которые повторяются на нескольких страницах веб-сайта.Например:
- Навигация
- Информация об авторских правах
- Области заголовка
- Области нижнего колонтитула
Как "Включает" делает веб-дизайн более эффективным
Почти все веб-сайты включают элементы дизайна, которые повторяются на каждой странице сайта, включая область заголовка, где расположен логотип, меню навигации и область нижнего колонтитула.
Повторяющиеся элементы на сайте обеспечивают единообразие взаимодействия с пользователем.Посетителю не нужно находить навигацию на каждой странице, потому что, как только они ее нашли, они знают, где она будет на других страницах сайта, который они посещают.
Включенный контент устраняет необходимость редактировать каждую страницу вашего сайта для этого повторяющегося контента. Вместо этого вы редактируете один файл, а затем весь сайт, и каждая его страница получает обновление.
Повторяющийся контент в системах управления контентом
Если ваш сайт использует CMS, то, скорее всего, он использует определенные шаблоны или темы, являющиеся частью этого программного обеспечения.Даже если вы создадите эти шаблоны с нуля, сайт все равно будет использовать эту структуру для страниц. Таким образом, эти шаблоны CMS содержат области сайта, повторяющиеся на каждой странице. Вы просто авторизуетесь на сервере CMS и редактируете необходимые шаблоны. Все страницы сайта, использующие этот шаблон, будут обновлены.
Даже если вы не используете систему управления контентом для своего сайта, вы все равно можете воспользоваться включенными файлами. В HTML включает , помогающий упростить управление этими шаблонными областями вашего сайта.
Другие методы включения
Есть несколько других способов включить HTML на свои страницы. Некоторые из них сложнее других, и многие из них действительно устарели по сегодняшним меркам.
- CGI Включает : Вы можете использовать Perl или другой язык программирования для создания ваших страниц, а затем включать все, что вы хотите, либо в виде «требуемых» файлов, либо считывая их вручную.
- Flash Включает : Если вы создаете свой сайт полностью в Adobe Flash, вы можете использовать его для включения элементов сайта.Этот метод устарел, и в наши дни полнофункциональные Flash-сайты - большая редкость.
- Фреймы включают : вместо того, чтобы использовать одни и те же элементы снова и снова на нескольких страницах, создайте сайт с фреймами, где фреймы являются дублированными частями сайта. Однако, за исключением элемента iframe, фреймов устарели в HTML5 .
- Инструменты управления контентом Включает : Создание шаблонов - одно из основных преимуществ CMS, и именно так эта работа сегодня выполняется на большинстве сайтов.
Как сделать ссылку на разные разделы ...
Вы разрабатывали свой сайт и сообразили, что страница может быть сколь угодно длинной. Это здорово, но может быть неприятно, когда вы имеете дело с более длинными страницами. Помогите своим посетителям, предоставив ссылки, которые быстро приведут их в определенные места на странице. Для этого вы создадите цель и ссылку .
Цель
Первый шаг - установить цель.Цель - это место на странице, куда вы хотите, чтобы пользователь перешел. Поместите курсор на страницу, куда вы хотите переместить цель, а затем перейдите к Insert> Target . В появившемся окне введите имя вашей цели. Для ясности назовите это как-нибудь интуитивно понятным. Например, если ваша страница содержит список профилей сотрудников, и вы хотите, чтобы привязка переходила к профилю Джона Смита, вы должны назвать привязку как-то вроде jsmith .
Вы также можете вручную ввести код для цели в редакторе кода :
Targetname - это имя вашей цели.
Ссылка
Следующим шагом будет создание ссылки на только что установленную цель. Для этого поместите курсор на страницу, на которой вы хотите разместить ссылку, а затем перейдите в Вставка> Ссылка . В появившемся окне введите текст, который будет отображаться в виде ссылки, и в поле URL-адреса введите #targetname , где targetname - это имя вашей цели. В нашем примере мы должны ввести #jsmith .
Вы также можете ввести этот код в редактор кода :
Текст вашей ссылки
Targetname должно совпадать с именем, которое вы дали цели, и вы должны заменить Your Link Text любым текстом, который вы хотите, чтобы посетители нажимали. Чтобы продолжить приведенный выше пример, наш код будет выглядеть примерно так:
Щелкните здесь, чтобы узнать о Джоне Смите.
Полное руководство по перенаправлению Django - настоящий Python
Когда вы создаете веб-приложение Python с помощью платформы Django, вам в какой-то момент придется перенаправить пользователя с одного URL-адреса на другой.
В этом руководстве вы узнаете все, что вам нужно знать о перенаправлениях HTTP и о том, как с ними бороться в Django. В конце этого руководства вы увидите:
В этом руководстве предполагается, что вы знакомы с основными строительными блоками приложения Django, такими как представления и шаблоны URL.
Перенаправления Django: очень простой пример
В Django вы перенаправляете пользователя на другой URL, возвращая экземпляр HttpResponseRedirect
или HttpResponsePermanentRedirect
из вашего представления. Самый простой способ сделать это - использовать функцию redirect ()
из модуля django.shortcuts
. Вот пример:
# views.py
из django.shortcuts перенаправление импорта
def redirect_view (запрос):
ответ = перенаправление ('/ успешное перенаправление /')
ответ на ответ
Просто вызовите redirect ()
с URL-адресом в вашем представлении.Он вернет класс HttpResponseRedirect
, который вы затем вернете из своего представления.
Представление, возвращающее перенаправление, должно быть добавлено в ваш urls.py
, как и любое другое представление:
# urls.py
из пути импорта django.urls
из .views import redirect_view
urlpatterns = [
путь ('/ redirect /', redirect_view)
# ... здесь другие шаблоны URL
]
Предполагая, что это основной urls.py
вашего проекта Django, URL / redirect /
теперь перенаправляет на / redirect-success /
.
Чтобы избежать жесткого кодирования URL-адреса, вы можете вызвать redirect ()
с именем представления или шаблона URL-адреса или модели, чтобы избежать жесткого кодирования URL-адреса перенаправления. Вы также можете создать постоянное перенаправление, передав ключевое слово аргумент постоянный = True
.
Эта статья могла бы на этом закончиться, но тогда ее вряд ли можно было бы назвать «Полное руководство по перенаправлениям Django». Мы подробно рассмотрим функцию redirect ()
через минуту, а также рассмотрим мельчайшие детали кодов состояния HTTP и различных классов HttpRedirectResponse
, но давайте сделаем шаг назад и начнем с фундаментального вопроса.
Зачем перенаправлять
Вы можете спросить, зачем вообще нужно перенаправлять пользователя на другой URL. Чтобы понять, где перенаправления имеют смысл, посмотрите, как сам Django включает перенаправления в функции, которые фреймворк предоставляет по умолчанию:
- Когда вы не вошли в систему и запрашиваете URL-адрес, требующий аутентификации, например, администратор Django, Django перенаправляет вас на страницу входа.
- При успешном входе в систему Django перенаправляет вас на изначально запрошенный URL.
- Когда вы меняете пароль с помощью администратора Django, вы перенаправляетесь на страницу, которая указывает, что изменение было успешным.
- Когда вы создаете объект в админке Django, Django перенаправляет вас к списку объектов.
Как могла бы выглядеть альтернативная реализация без перенаправления? Если пользователю необходимо войти в систему для просмотра страницы, вы можете просто отобразить страницу, на которой написано что-то вроде «Щелкните здесь, чтобы войти». Это могло бы работать, но было бы неудобно для пользователя.
Сокращатели URL-адресов, такие как http://bit.ly, являются еще одним примером того, где могут пригодиться перенаправления: вы вводите короткий URL-адрес в адресную строку браузера, а затем перенаправляетесь на страницу с длинным и громоздким URL-адресом.
В других случаях перенаправления - это не просто вопрос удобства. Перенаправления - важный инструмент, помогающий пользователю в работе с веб-приложением. После выполнения какой-либо операции с побочными эффектами, например создания или удаления объекта, рекомендуется выполнить перенаправление на другой URL-адрес, чтобы предотвратить случайное выполнение операции дважды.
Одним из примеров такого использования перенаправления является обработка формы, когда пользователь перенаправляется на другой URL-адрес после успешной отправки формы. Вот пример кода, который показывает, как вы обычно обрабатываете форму:
1 из форм импорта django
2из django.http import HttpResponseRedirect
3from django.shortcuts перенаправление импорта, рендеринг
4
5def send_message (имя, сообщение):
6 # Код для фактической отправки сообщения находится здесь
7
8класс ContactForm (forms.Form):
9 имя = формы.CharField ()
10 сообщение = forms.CharField (widget = forms.Textarea)
11
12def contact_view (запрос):
13 # Метод запроса "POST" указывает
14 # что форма была отправлена
15, если request.method == 'POST': # 1
16 # Создайте экземпляр формы с отправленными данными
17 форма = ContactForm (request.POST) # 2
18 # Проверить форму
19 если form.is_valid (): # 3
20 # Если форма действительна, выполнить какое-то
21 # операция, например отправка сообщения
22 send_message (
23 форма.cleaned_data ['имя'],
24 form.cleaned_data ['сообщение']
25)
26 # После успешной операции
27 # перенаправление на другую страницу
28 возвратное перенаправление ('/ success /') # 4
29 еще: # 5
30 # Создать пустой экземпляр формы
31 форма = ContactForm ()
32
33 возврат рендеринга (запрос, 'contact_form.html', {'form': form})
Назначение этого представления - отображать и обрабатывать контактную форму, которая позволяет пользователю отправить сообщение.Давайте проследим его шаг за шагом:
Сначала представление смотрит на метод запроса. Когда пользователь посещает URL-адрес, связанный с этим представлением, браузер выполняет запрос GET
.
Если представление вызывается с запросом POST
, данные POST
используются для создания экземпляра объекта ContactForm
.
Если форма действительна, данные формы передаются в send_message ()
. Эта функция не имеет отношения к данному контексту и поэтому здесь не показана.
После отправки сообщения представление возвращает перенаправление на URL-адрес / success /
. Это тот шаг, который нас интересует. Для простоты URL здесь жестко запрограммирован. Позже вы увидите, как этого избежать.
Если представление получает запрос GET
(или, если быть точным, любой запрос, который не является запросом POST
), оно создает экземпляр ContactForm
и использует django.shortcuts.render ()
для рендеринга contact_form.html
шаблон.
Если теперь пользователь нажимает кнопку перезагрузки, перезагружается только URL-адрес / success /
. Без перенаправления перезагрузка страницы приведет к повторной отправке формы и отправке другого сообщения.
За кулисами: как работает перенаправление HTTP
Теперь вы знаете, почему перенаправления имеют смысл, но как они работают? Давайте кратко рассмотрим, что происходит, когда вы вводите URL-адрес в адресной строке браузера.
Краткое руководство по HTTP
Предположим, вы создали приложение Django с представлением «Hello World», которое обрабатывает путь / hello /
.Вы запускаете свое приложение на сервере разработки Django, поэтому полный URL-адрес - http://127.0.0.1:8000/hello/
.
Когда вы вводите этот URL-адрес в браузере, он подключается к порту 8000
на сервере с IP-адресом 127.0.0.1
и отправляет запрос HTTP GET
для пути / hello /
. Сервер отвечает HTTP-ответом.
HTTP основан на тексте, поэтому относительно легко отслеживать обмен данными между клиентом и сервером.Вы можете использовать инструмент командной строки curl
с опцией --include
, чтобы просмотреть полный ответ HTTP, включая заголовки, например:
$ curl --include http://127.0.0.1:8000/hello/
HTTP / 1.1 200 ОК
Дата: вс, 1 июля 2018 г. 20:32:55 GMT
Сервер: WSGIServer / 0.2 CPython / 3.6.3
Тип содержимого: текст / html; charset = utf-8
Параметры X-Frame: SAMEORIGIN
Длина содержимого: 11
Привет мир
Как видите, ответ HTTP начинается со строки состояния, которая содержит код состояния и сообщение о состоянии.За строкой состояния следует произвольное количество заголовков HTTP. Пустая строка указывает конец заголовков и начало тела ответа, которое содержит фактические данные, которые сервер хочет отправить.
Коды состояния перенаправления HTTP
Как выглядит ответ перенаправления? Предположим, что путь / redirect /
обрабатывается функцией redirect_view ()
, показанной ранее. Если вы обращаетесь к http://127.0.0.1:8000/redirect/
с curl
, ваша консоль будет выглядеть так:
$ curl - включить http: // 127.0.0.1: 8000 / перенаправление /
HTTP / 1.1 302 Найдено
Дата: вс, 1 июля 2018 г. 20:35:34 GMT
Сервер: WSGIServer / 0.2 CPython / 3.6.3
Тип содержимого: текст / html; charset = utf-8
Расположение: / redirect-success /
Параметры X-Frame: SAMEORIGIN
Content-Length: 0
Два ответа могут выглядеть похожими, но есть некоторые ключевые различия. Редирект:
- Возвращает другой код состояния (
302
по сравнению с 200
) - Содержит заголовок
Location
с относительным URL-адресом - Заканчивается пустой строкой, поскольку тело ответа перенаправления пусто
Основным отличительным признаком является код состояния.В спецификации стандарта HTTP сказано следующее:
Код состояния 302 (Найдено) указывает, что целевой ресурс временно находится под другим URI. Поскольку перенаправление может иногда изменяться, клиент должен продолжать использовать действующий URI запроса для будущих запросов. Серверу СЛЕДУЕТ генерировать поле заголовка Location в ответе, содержащем ссылку URI для другого URI. Пользовательский агент МОЖЕТ использовать значение поля Location для автоматического перенаправления.(Источник)
Другими словами, всякий раз, когда сервер отправляет код состояния 302
, он говорит клиенту: «Эй, в данный момент то, что вы ищете, можно найти в другом месте».
Ключевая фраза в спецификации - «МОЖЕТ использовать значение поля Location для автоматического перенаправления». Это означает, что вы не можете заставить клиента загрузить другой URL. Клиент может дождаться подтверждения пользователя или вообще не загружать URL.
Теперь вы знаете, что перенаправление - это просто HTTP-ответ с кодом состояния 3xx
и заголовком Location
.Ключевой вывод здесь заключается в том, что перенаправление HTTP похоже на любой старый ответ HTTP, но с пустым телом, кодом состояния 3xx и заголовком Location
.
Вот и все. Мы на мгновение свяжем это с Django, но сначала давайте взглянем на два типа перенаправления в диапазоне кода статуса 3xx
и поймем, почему они важны для веб-разработки.
Временные и постоянные перенаправления
Стандарт HTTP определяет несколько кодов состояния перенаправления, все в диапазоне 3xx
.Два наиболее распространенных кода состояния: 301 Постоянное перенаправление
и 302 Найдено
.
Код состояния 302 Найдено
указывает на временное перенаправление. Временное перенаправление гласит: «В настоящий момент то, что вы ищете, можно найти по этому другому адресу». Думайте об этом как о вывеске магазина с надписью: «Наш магазин в настоящее время закрыт на ремонт. Пожалуйста, пройдите в другой наш магазин за углом ». Поскольку это только временно, вы проверите исходный адрес в следующий раз, когда пойдете за покупками.
Примечание: В HTTP 1.0 сообщение для кода состояния 302 было Временное перенаправление
. Сообщение было изменено на Найдено
в HTTP 1.1.
Как следует из названия, постоянные перенаправления должны быть постоянными. Постоянное перенаправление сообщает браузеру: «То, что вы ищете, больше не по этому адресу. Теперь он находится по новому адресу и больше никогда не будет по старому ».
Постоянное перенаправление похоже на вывеску магазина с надписью «Мы переехали.Наш новый магазин не за горами ». Это изменение является постоянным, поэтому в следующий раз, когда вы захотите пойти в магазин, вы сразу перейдете по новому адресу.
Примечание. Постоянные перенаправления могут иметь непредвиденные последствия. Завершите это руководство, прежде чем использовать постоянное перенаправление, или сразу переходите к разделу «Постоянные перенаправления являются постоянными».
Браузеры ведут себя аналогичным образом при обработке перенаправления: когда URL-адрес возвращает постоянный ответ перенаправления, этот ответ кэшируется.В следующий раз, когда браузер встречает старый URL-адрес, он запоминает перенаправление и напрямую запрашивает новый адрес.
Кэширование перенаправления позволяет избежать ненужных запросов и ускорить работу пользователей.
Кроме того, различие между временными и постоянными перенаправлениями актуально для поисковой оптимизации.
Перенаправляет в Django
Теперь вы знаете, что перенаправление - это просто HTTP-ответ с кодом состояния 3xx
и заголовком Location
.
Такой ответ можно построить самостоятельно из обычного объекта HttpResponse
:
def hand_crafted_redirect_view (запрос):
response = HttpResponse (статус = 302)
ответ ['Location'] = '/ redirect / success /'
ответ на ответ
Это решение технически правильное, но требует довольно небольшого набора текста.
HTTPResponseRedirect
, класс Вы можете сэкономить время на вводе текста с помощью класса HttpResponseRedirect
, подкласса HttpResponse
.Просто создайте экземпляр класса с URL-адресом, на который вы хотите перенаправить в качестве первого аргумента, и класс установит правильный статус и заголовок Location:
def redirect_view (запрос):
return HttpResponseRedirect ('/ redirect / success /')
Вы можете поиграть с классом HttpResponseRedirect
в оболочке Python, чтобы увидеть, что вы получаете:
>>> >>> из django.http import HttpResponseRedirect
>>> redirect = HttpResponseRedirect ('/ перенаправление / успех /')
>>> перенаправить.status_code
302
>>> перенаправление ['Местоположение']
'/ перенаправление / успех /'
Существует также класс для постоянных перенаправлений, который метко назван HttpResponsePermanentRedirect
. Он работает так же, как HttpResponseRedirect
, с той лишь разницей, что он имеет код статуса 301 (перемещен навсегда)
.
Примечание: В приведенных выше примерах URL-адреса перенаправления жестко запрограммированы. Жесткое кодирование URL-адресов - плохая практика: если URL-адрес когда-либо изменится, вам придется искать по всему вашему коду и изменять любые вхождения.Давай исправим это!
Вы можете использовать django.urls.reverse ()
для создания URL-адреса, но есть более удобный способ, как вы увидите в следующем разделе.
Перенаправление
()
Функция Чтобы облегчить вам жизнь, Django предоставляет универсальную функцию быстрого доступа, которую вы уже видели во введении: django.shortcuts.redirect ()
.
Вы можете вызвать эту функцию с помощью:
- Экземпляр модели или любой другой объект с методом
get_absolute_url ()
- URL-адрес или имя представления и позиционные и / или ключевые аргументы
- A URL
Он предпримет соответствующие шаги, чтобы преобразовать аргументы в URL и вернуть HTTPResponseRedirect
.Если вы передадите constant = True
, он вернет экземпляр HttpResponsePermanentRedirect
, что приведет к постоянному перенаправлению.
Вот три примера, иллюстрирующие различные варианты использования:
Прохождение модели:
из перенаправления импорта django.shortcuts
def model_redirect_view (запрос):
product = Product.objects.filter (Featured = True) .first ()
возврат перенаправления (продукт)
redirect ()
вызовет продукт .get_absolute_url ()
и использовать результат в качестве цели перенаправления. Если данный класс, в данном случае Product
, не имеет метода get_absolute_url ()
, это приведет к ошибке TypeError
.
Передача имени URL-адреса и аргументов:
из перенаправления импорта django.shortcuts
def fixed_featured_product_view (запрос):
...
product_id = settings.FEATURED_PRODUCT_ID
возвратное перенаправление ('product_detail', product_id = product_id)
redirect ()
попытается использовать заданные аргументы для обратного URL.В этом примере предполагается, что ваши шаблоны URL содержат такой шаблон:
путь ('/ product / /', 'product_detail_view', name = 'product_detail')
Передача URL:
из перенаправления импорта django.shortcuts
def Featured_product_view (запрос):
возврат перенаправления ('/ products / 42 /')
redirect ()
будет обрабатывать любую строку, содержащую /
или .
в качестве URL-адреса и использовать его как цель перенаправления.
Вид на основе классов
RedirectView
Если у вас есть представление, которое ничего не делает, кроме возврата перенаправления, вы можете использовать представление на основе классов django.views.generic.base.RedirectView
.
Вы можете настроить RedirectView
под свои нужды с помощью различных атрибутов.
Если класс имеет атрибут .url
, он будет использоваться как URL-адрес перенаправления. Заполнители форматирования строки заменяются именованными аргументами из URL-адреса:
# urls.ру
из пути импорта django.urls
из .views импортировать SearchRedirectView
urlpatterns = [
путь ('/ search / /', SearchRedirectView.as_view ())
]
# views.py
из django.views.generic.base импортировать RedirectView
класс SearchRedirectView (RedirectView):
url = 'https://google.com/?q=%(term)s'
Шаблон URL-адреса определяет аргумент , термин
, который используется в SearchRedirectView
для создания URL-адреса перенаправления. Путь / search / kittens /
в вашем приложении перенаправит вас на https: // google.com /? q = котята
.
Вместо подкласса RedirectView
для перезаписи атрибута url
, вы также можете передать аргумент ключевого слова url
в as_view ()
в ваших urlpatterns
:
# urls.py
из django.views.generic.base импортировать RedirectView
urlpatterns = [
путь ('/ search / /',
RedirectView.as_view (url = 'https: //google.com/? Q =% (term) s')),
]
Вы также можете перезаписать get_redirect_url ()
, чтобы получить полностью настраиваемое поведение:
из случайного выбора импорта
из джанго.views.generic.base импорт RedirectView
класс RandomAnimalView (RedirectView):
animal_urls = ['/ собака /', '/ кошка /', '/ попугай /']
is_permanent = Истина
def get_redirect_url (* args, ** kwargs):
возвратный выбор (self.animal_urls)
Это представление на основе классов перенаправляет на URL, выбранный случайным образом из .animal_urls
.
django.views.generic.base.RedirectView
предлагает еще несколько хуков для настройки. Вот полный список:
.url
Если этот атрибут установлен, это должна быть строка с URL-адресом для перенаправления. Если он содержит заполнители форматирования строки, такие как % (name) s
, они раскрываются с использованием аргументов ключевого слова, переданных в представление.
. Имя_шаблона
Если этот атрибут установлен, это должно быть имя шаблона URL для перенаправления. Любые позиционные аргументы и аргументы ключевого слова, переданные в представление, используются для изменения шаблона URL-адреса.
.постоянный
Если этот атрибут равен True
, представление возвращает постоянное перенаправление. По умолчанию это Ложь
.
.query_string
Если этот атрибут равен True
, представление добавляет любую предоставленную строку запроса к URL-адресу перенаправления. Если это False
, которое является значением по умолчанию, строка запроса отбрасывается.
get_redirect_url (* аргументы, ** kwargs)
Этот метод отвечает за создание URL-адреса перенаправления.Если этот метод возвращает None
, представление возвращает статус 410 Gone
.
Реализация по умолчанию сначала проверяет .url
. Он обрабатывает .url
как строку формата «старого стиля», используя любые именованные параметры URL, переданные в представление, чтобы раскрыть любые именованные спецификаторы формата.
Если .url
не установлен, он проверяет, установлен ли .pattern_name
. Если это так, он использует его для обратного URL-адреса с любыми позиционными аргументами и аргументами ключевого слова, которые он получил.
Вы можете изменить это поведение любым способом, перезаписав этот метод. Просто убедитесь, что он возвращает строку, содержащую URL-адрес.
Примечание. Представления на основе классов - мощная концепция, но может быть немного сложно осмыслить. В отличие от обычных представлений на основе функций, в которых относительно просто следить за потоком кода, представления на основе классов состоят из сложной иерархии примесей и базовых классов.
Отличным инструментом для понимания класса представления на основе классов является веб-сайт Classy Class-Based Views.
Функциональность RandomAnimalView
из приведенного выше примера можно реализовать с помощью этого простого представления на основе функций:
из случайного выбора импорта
из django.shortcuts перенаправление импорта
def random_animal_view (запрос):
animal_urls = ['/ собака /', '/ кошка /', '/ попугай /']
возврат перенаправления (выбор (animal_urls))
Как видите, подход на основе классов не дает очевидных преимуществ, но добавляет некоторую скрытую сложность. Возникает вопрос: когда следует использовать RedirectView
?
Если вы хотите добавить перенаправление прямо в свои адреса .py
, использование RedirectView
имеет смысл. Но если вы обнаружите, что перезаписываете get_redirect_url
, представление на основе функций может быть проще для понимания и более гибким для будущих улучшений.
Расширенное использование
Как только вы узнаете, что, вероятно, хотите использовать django.shortcuts.redirect ()
, перенаправление на другой URL-адрес становится довольно простым. Но есть несколько сложных вариантов использования, которые не так очевидны.
Передача параметров с перенаправлением
Иногда требуется передать некоторые параметры представлению, в которое выполняется перенаправление.Лучше всего передать данные в строке запроса URL-адреса перенаправления, что означает перенаправление на URL-адрес, подобный этому:
http://example.com/redirect-path/?parameter=value
Предположим, вы хотите перенаправить с some_view ()
на product_view ()
, но передаете необязательный параметр category
:
из django.urls import reverse
из urllib.parse import urlencode
def some_view (запрос):
...
base_url = reverse ('product_view') # 1 / products /
query_string = urlencode ({'категория': категория.id}) # 2 category = 42
url = '{}? {}'. format (base_url, query_string) # 3 / products /? category = 42
возврат перенаправления (url) # 4
def product_view (запрос):
category_id = request.GET.get ('категория') # 5
# Сделайте что-нибудь с category_id
Код в этом примере довольно плотный, поэтому давайте рассмотрим его шаг за шагом:
Сначала вы используете django.urls.reverse ()
, чтобы получить сопоставление URL-адресов с product_view ()
.
Затем вам нужно построить строку запроса.Это часть после вопросительного знака. Для этого рекомендуется использовать urllib.urlparse.urlencode ()
, так как он позаботится о правильном кодировании любых специальных символов.
Теперь вам нужно соединить base_url
и query_string
с вопросительным знаком. Строка формата отлично подходит для этого.
Наконец, вы передаете url
на django.shortcuts.redirect ()
или в класс ответа перенаправления.
В product_view ()
, вашей цели перенаправления, параметр будет доступен в запросе .ПОЛУЧИТЕ словарь
. Параметр может отсутствовать, поэтому вам следует использовать request.GET.get ('category')
вместо requests.GET ['category']
. Первый возвращает None
, если параметр не существует, а второй вызовет исключение.
Примечание: Обязательно проверьте все данные, которые вы читаете из строк запроса. Может показаться, что эти данные находятся под вашим контролем, потому что вы создали URL-адрес перенаправления.
В действительности перенаправление может быть изменено пользователем, и ему нельзя доверять, как и любому другому вводу пользователя.Без надлежащей проверки злоумышленник может получить несанкционированный доступ.
Специальные коды переадресации
Django предоставляет классы ответа HTTP для кодов состояния 301
и 302
. Они должны охватывать большинство случаев использования, но если вам когда-либо придется возвращать коды состояния 303
, 307
или 308
, вы можете довольно легко создать свой собственный класс ответа. Просто создайте подкласс HttpResponseRedirectBase
и перезапишите атрибут status_code
:
класс HttpResponseTemporaryRedirect (HttpResponseRedirectBase):
status_code = 307
В качестве альтернативы вы можете использовать файл django.shortcuts.redirect ()
для создания объекта ответа и изменения возвращаемого значения. Этот подход имеет смысл, когда у вас есть имя представления, URL-адреса или модели, на которую вы хотите перенаправить:
def временный_редирект_вью (запрос):
ответ = перенаправление ('success_view')
response.status_code = 307
ответ на ответ
Примечание: Фактически существует третий класс с кодом состояния в диапазоне 3xx
: HttpResponseNotModified
с кодом состояния 304
.Это указывает на то, что URL-адрес содержимого не изменился и что клиент может использовать кэшированную версию.
Можно утверждать, что ответ 304 Not Modified
перенаправляет на кешированную версию URL, но это немного натянуто. Следовательно, он больше не указан в разделе «Перенаправление 3xx» стандарта HTTP.
Подводные камни
перенаправления, которые просто не перенаправляют
Простота django.shortcuts.redirect ()
может быть обманчивой.Сама функция не выполняет перенаправление: она просто возвращает объект ответа перенаправления. Вы должны вернуть этот объект ответа из своего представления (или в промежуточном программном обеспечении). В противном случае перенаправления не произойдет.
Но даже если вы знаете, что просто вызвать redirect ()
недостаточно, легко внести эту ошибку в работающее приложение с помощью простого рефакторинга. Вот пример, чтобы проиллюстрировать это.
Предположим, вы создаете магазин и имеете представление, которое отвечает за отображение продукта.Если товара не существует, вы перенаправляете на домашнюю страницу:
def product_view (запрос, product_id):
пытаться:
product = Product.objects.get (pk = product_id)
кроме Product.DoesNotExist:
возврат перенаправления ('/')
вернуть визуализацию (запрос, 'product_detail.html', {'product': product})
Теперь вы хотите добавить второе представление для отображения отзывов покупателей о продукте. Он также должен перенаправлять на домашнюю страницу для несуществующих продуктов, поэтому в качестве первого шага вы извлекаете эту функциональность из product_view ()
во вспомогательную функцию get_product_or_redirect ()
:
def get_product_or_redirect (product_id):
пытаться:
вернуть товар.objects.get (pk = product_id)
кроме Product.DoesNotExist:
возврат перенаправления ('/')
def product_view (запрос, product_id):
product = get_product_or_redirect (product_id)
вернуть визуализацию (запрос, 'product_detail.html', {'product': product})
К сожалению, после рефакторинга редирект больше не работает.
Результат redirect ()
возвращается из get_product_or_redirect ()
, но product_view ()
его не возвращает.Вместо этого он передается в шаблон.
В зависимости от того, как вы используете переменную product
в шаблоне product_detail.html
, это может не приводить к сообщению об ошибке, а просто отображать пустые значения.
перенаправления, которые не перестают перенаправлять
При работе с перенаправлениями вы можете случайно создать цикл перенаправления, если URL-адрес A вернет перенаправление, которое указывает на URL-адрес B, который возвращает перенаправление на URL-адрес A, и так далее. Большинство HTTP-клиентов обнаруживают этот вид цикла перенаправления и отображают сообщение об ошибке после нескольких запросов.
К сожалению, эту ошибку сложно обнаружить, потому что на стороне сервера все выглядит нормально. Если ваши пользователи не жалуются на проблему, единственным признаком того, что что-то может быть не так, является то, что у вас есть несколько запросов от одного клиента, которые все быстро приводят к ответу перенаправления, но нет ответа со статусом 200 OK
.
Вот простой пример цикла переадресации:
def a_view (запрос):
возвратное перенаправление ('другое_представление')
def another_view (запрос):
возврат перенаправления ('a_view')
Этот пример иллюстрирует принцип, но он слишком упрощен.Петли перенаправления, с которыми вы столкнетесь в реальной жизни, вероятно, будет труднее обнаружить. Давайте посмотрим на более подробный пример:
def Featured_products_view (запрос):
Feature_products = Product.objects.filter (Featured = True)
если len (Feature_products == 1):
возвратное перенаправление ('product_view', kwargs = {'product_id': Feature_products [0] .id})
вернуть визуализацию (запрос, 'Feature_products.html', {'product': Feature_products})
def product_view (запрос, product_id):
пытаться:
product = Продукт.objects.get (pk = product_id, in_stock = True)
кроме Product.DoesNotExist:
возврат перенаправления ('Feature_products_view')
вернуть визуализацию (запрос, 'product_detail.html', {'product': product})
Featured_products_view ()
извлекает все рекомендуемые продукты, другими словами экземпляров Product
с .featured
, установленным на True
. Если существует только один рекомендуемый продукт, он перенаправляется непосредственно на product_view ()
. В противном случае он отображает шаблон с набором запросов Feature_products
.
product_view
выглядит знакомым по предыдущему разделу, но имеет два незначительных отличия:
- Представление пытается получить продукт
, который есть в наличии, на что указывает то, что для .in_stock
установлено значение True
. - Представление перенаправляется на
Feature_products_view ()
, если товара нет на складе.
Эта логика работает нормально до тех пор, пока ваш магазин не станет жертвой собственного успеха, и один рекомендуемый продукт, который у вас есть в настоящее время, не закончится.Если вы установите .in_stock
на False
, но забыли установить .featured
на False
, то любой посетитель вашего feature_product_view ()
теперь застрянет в цикле перенаправления.
Не существует надежного способа предотвратить этот вид ошибок, но хорошей отправной точкой является проверка, использует ли представление, на которое вы перенаправляете, перенаправление.
Постоянные перенаправления постоянны
Постоянные перенаправления могут быть похожи на плохие татуировки: в то время это могло показаться хорошей идеей, но как только вы поймете, что это была ошибка, от них будет довольно сложно избавиться.
Когда браузер получает постоянный ответ перенаправления для URL-адреса, он кэширует этот ответ на неопределенный срок. Каждый раз, когда вы запрашиваете старый URL в будущем, браузер не загружает его, а загружает новый URL напрямую.
Довольно сложно убедить браузер загрузить URL-адрес, который однажды вернул постоянное перенаправление. Google Chrome особенно агрессивен, когда дело касается кеширования перенаправлений.
Почему это может быть проблемой?
Представьте, что вы хотите создать веб-приложение с помощью Django.Вы регистрируете свой домен на myawesomedjangowebapp.com
. В качестве первого шага вы устанавливаете приложение блога по адресу https://myawesomedjangowebapp.com/blog/
, чтобы создать список рассылки запуска.
Домашняя страница вашего сайта по адресу https://myawesomedjangowebapp.com/
все еще находится в разработке, поэтому вы перенаправляете на https://myawesomedjangowebapp.com/blog/
. Вы решили использовать постоянное перенаправление, потому что слышали, что постоянные перенаправления кэшируются, а кеширование делает работу быстрее, а чем быстрее, тем лучше, потому что скорость является фактором ранжирования в результатах поиска Google.
Как оказалось, вы не только отличный разработчик, но и талантливый писатель. Ваш блог становится популярным, а список рассылки по запуску растет. Через пару месяцев ваше приложение будет готово. Теперь у него блестящая домашняя страница, и вы наконец удалили перенаправление.
Вы отправляете электронное письмо с объявлением со специальным кодом скидки в свой обширный список рассылки, посвященный запуску. Вы откидываетесь и ждете, пока придут уведомления о регистрации.
К вашему ужасу, ваш почтовый ящик заполняется сообщениями от сбитых с толку посетителей, которые хотят посетить ваше приложение, но всегда перенаправляются в ваш блог.
Что случилось? Читатели вашего блога посетили https://myawesomedjangowebapp.com/
, когда перенаправление на https://myawesomedjangowebapp.com/blog/
было еще активным. Поскольку это было постоянное перенаправление, оно было кешировано в их браузерах.
Когда они щелкали ссылку в вашем письме с объявлением о запуске, их браузеры не удосужились проверить вашу новую домашнюю страницу и сразу перешли на ваш блог. Вместо того, чтобы праздновать свой успешный запуск, вы заняты инструктажем пользователей, как возиться с chrome: // net-internals
для сброса кеша их браузеров.
Постоянный характер перманентных перенаправлений также может укусить вас при разработке на вашем локальном компьютере. Давайте вернемся к тому моменту, когда вы реализовали роковую постоянную переадресацию для myawesomedjangowebapp.com.
Вы запускаете сервер разработки и открываете http://127.0.0.1:8000/
. Как и предполагалось, ваше приложение перенаправляет ваш браузер на http://127.0.0.1:8000/blog/
. Удовлетворенный своей работой, вы останавливаете сервер разработки и идете обедать.
Вы возвращаетесь с полным животом, готовым взяться за работу с клиентами.Клиент хочет внести простые изменения в свою домашнюю страницу, поэтому вы загружаете проект клиента и запускаете сервер разработки.
Но подождите, что здесь происходит? Домашняя страница не работает, теперь она возвращает 404! Из-за дневного спада вам нужно время, чтобы заметить, что вас перенаправляют на http://127.0.0.1:8000/blog/
, которого нет в проекте клиента.
Для браузера не имеет значения, что URL http://127.0.0.1:8000/
теперь обслуживает совершенно другое приложение.Все, что имеет значение для браузера, это то, что этот URL-адрес однажды в прошлом возвращал постоянное перенаправление на http://127.0.0.1:8000/blog/
.
Вывод из этой истории заключается в том, что вам следует использовать постоянную переадресацию только для тех URL-адресов, которые вы больше не собираетесь использовать. Есть место для перманентных перенаправлений, но вы должны осознавать их последствия.
Даже если вы уверены, что вам действительно нужна постоянная переадресация, рекомендуется сначала реализовать временную переадресацию, а переключаться на ее постоянного родственника только тогда, когда вы на 100% уверены, что все работает, как задумано.
Непроверенные перенаправления могут нарушить безопасность
С точки зрения безопасности перенаправления - относительно безопасный метод. Злоумышленник не может взломать веб-сайт с перенаправлением. В конце концов, перенаправление просто перенаправляет на URL-адрес, который злоумышленник может просто ввести в адресной строке своего браузера.
Однако, если вы используете какой-либо пользовательский ввод, например параметр URL-адреса, без надлежащей проверки в качестве URL-адреса перенаправления, злоумышленник может злоупотребить этим для фишинг-атаки. Такой вид перенаправления называется открытым или непроверенным перенаправлением.
Существуют законные варианты использования для перенаправления на URL-адрес, считываемый из пользовательского ввода. Ярким примером является представление входа в систему Django. Он принимает URL-параметр следующий
, который содержит URL-адрес страницы, на которую пользователь перенаправляется после входа в систему. Чтобы перенаправить пользователя в его профиль после входа в систему, URL-адрес может выглядеть следующим образом:
https://myawesomedjangowebapp.com/login/?next=/profile/
Django действительно проверяет следующий параметр
, но предположим на секунду, что это не так.
Без проверки злоумышленник может создать URL-адрес, который перенаправляет пользователя на веб-сайт, находящийся под его контролем, например:
https://myawesomedjangowebapp.com/login/?next=https://myawesomedjangowebapp.co/profile/
Веб-сайт myawesomedjangowebapp.co
может затем отобразить сообщение об ошибке и заставить пользователя снова ввести свои учетные данные.
Лучший способ избежать открытых перенаправлений - не использовать вводимые пользователем данные при создании URL-адреса перенаправления.
Если вы не можете быть уверены, что URL-адрес безопасен для перенаправления, вы можете использовать функцию django.utils.http.is_safe_url ()
для его проверки. Строка документации довольно хорошо объясняет его использование:
is_safe_url (url, host = None, allowed_hosts = None, require_https = False)
Вернуть True
, если URL-адрес является безопасным перенаправлением (т. Е. Не указывает на другой хост и использует безопасную схему).
Всегда возвращайте False
по пустому URL-адресу.Если require_https
равно True
, только «https» будет считаться допустимой схемой, в отличие от «http» и «https» со значением по умолчанию False
. (Источник)
Давайте рассмотрим несколько примеров.
Безопасным считается относительный URL:
>>> >>> # Сначала импортируйте функцию.
>>> из django.utils.http import is_safe_url
>>> is_safe_url ('/ профиль /')
Правда
URL-адрес, указывающий на другой хост, обычно не считается безопасным:
>>> >>> is_safe_url ('https: // myawesomedjangowebapp.ru / profile / ')
Ложь
URL, указывающий на другой хост, считается безопасным, если его хост указан в allowed_hosts
:
>>> >>> is_safe_url ('https://myawesomedjangowebapp.com/profile/',
... allowed_hosts = {'myawesomedjangowebapp.com'})
Правда
Если аргумент require_https
равен True
, URL-адрес, использующий схему http
, не считается безопасным:
>>> >>> is_safe_url ('http: // myawesomedjangowebapp.com / profile / ',
... allowed_hosts = {'myawesomedjangowebapp.com'},
... require_https = True)
Ложь
Сводка
На этом заканчивается руководство по перенаправлению HTTP с помощью Django. Поздравляем: теперь вы затронули все аспекты перенаправления, от низкоуровневых деталей протокола HTTP до высокоуровневых способов работы с ними в Django.
Вы узнали, как выглядит перенаправление HTTP, каковы разные коды состояния и чем различаются постоянные и временные перенаправления.Эти знания не относятся к Django и ценны для веб-разработки на любом языке.
Теперь вы можете выполнить перенаправление с помощью Django либо с помощью классов ответа перенаправления HttpResponseRedirect
и HttpResponsePermanentRedirect
, либо с помощью вспомогательной функции django.shortcuts.redirect ()
. Вы видели решения для нескольких сложных случаев использования и знаете, как избежать распространенных ошибок.
Если у вас есть дополнительные вопросы о перенаправлении HTTP, оставьте комментарий ниже, а пока удачного перенаправления!
ссылок: ссылка на странице
Создание ссылок на якоря очень похоже на обычные ссылки.Обычные ссылки всегда указывают на верх страницы. Якоря указывают на место на странице. Знак # перед местом ссылки указывает, что ссылка указывает на привязку на странице. (Якорь означает определенное место в середине вашей страницы).
Чтобы привязать привязку, вам необходимо:
- Создать ссылку, указывающую на привязку
- Создайте саму привязку.
Якорь создается с помощью тега .
Если вы хотите создать привязку с именем chapter4, вы просто добавляете эту строку в том месте, где должна быть привязка: После этого вы можете создать ссылку, указывающую на привязку, используя обычный тег , например: