Домой Edit me on GitHub

2019-10-07

Каналы передачи данных | Сетевое программирование | Базы данных | Основы Веб-программирования

Маршруты

../../_images/routes4.jpg

Сортировочная станция

Идея маршрута (англ. - route) впервые появилась в Ruby on Rails и быстро обрела популярность в других веб-фреймворках. Также концептуально очень близкой системой является URLConf в Django. В последующих разработках наиболее мощной реализацией данной идеи, вероятно, является http://routes.groovie.org/, используемая в Pylons.

Маршруты отвечают за ключевую проблему веб-разработки: сопоставление кода и URL. Например, какой код должен отвечать за обработку запросов по адресу «/2008/01/08» или «/login»? Во многих фреймворках используется фиксированная система диспетчеризации, например «/A/B/C» означает прочитать файл «C» в каталоге «B» (например /auth/login.php или /cgi-bin/hello.cgi), или вызвать метод «С» класса «B» в модуле «A».

Это работает прекрасно до тех пор, пока не возникает необходимости в реорганизации кода, и выясняется, что закладки пользователей стали недействительны. Кроме того, если вы хотите переделать адреса (например, создать раздел в подразделе), то нужно изменить уже отлаженную логику по генерации ссылок внутри сайта.

Маршруты предлагают иной подход. Вы определяете шаблоны URL и связываете их со своим кодом. Если вы измените свое решение по поводу конкретного URL, то просто поменяйте шаблон URL - код по-прежнему будет работать отлично, и не понадобится менять какую-либо логику.


Сопоставление с образом

Регулярные выражения дают огромные возможности для обработки URL-путей, но из-за ограничений, описанных в стандарте RFC 1738, большинство из них не нужны, при этом использование регулярных выражений затрудняет читабельность кода. Более современный подход придуманный Ruby on Rails это использовать технологию сопоставление с образом. Рассмотрим отличия на примере нашего блога:

Примечание

Исходный код доступен по адресу:

Предупреждение

Примеры работают только в Python3

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
from views import BlogRead, BlogIndex, BlogCreate, BlogDelete, BlogUpdate
from wsgi_basic_auth import BasicAuth

# third-party
import selector


def make_wsgi_app():
    passwd = {
        'admin': '123'
    }
    # BasicAuth applications
    create = BasicAuth(BlogCreate, 'www', passwd)
    update = BasicAuth(BlogUpdate, 'www', passwd)
    delete = BasicAuth(BlogDelete, 'www', passwd)

    # URL dispatching middleware
    dispatch = selector.Selector()
    dispatch.add('/', GET=BlogIndex)
    dispatch.prefix = '/article'
    dispatch.add('/add', GET=create, POST=create)
    dispatch.add('/{id:digits}', GET=BlogRead)
    dispatch.add('/{id:digits}/edit', GET=update, POST=update)
    dispatch.add('/{id:digits}/delete', GET=delete)
    return dispatch

if __name__ == '__main__':
    from paste.httpserver import serve
    app = make_wsgi_app()
    serve(app, host='0.0.0.0', port=8000)
Сравнение URL
Регулярные выражения Сопоставление с образом
/ /
/article/add /article/add
^/article/(?P<id>d+)/$ /article/{id:digits}
^/article/(?P<id>d+)/edit$ /article/{id:digits}/edit
^/article/(?P<id>d+)/delete$ /article/{id:digits}/delete
Previous: Разделение кода Next: Шаблоны