Лучше ли обрабатывать дружественные / чистые / красивые URL с помощью mod_rewrite или языка, подобного PHP? - PullRequest
9 голосов
/ 23 января 2010

Я занимаюсь разработкой своего первого PHP-сайта приличного размера, и меня немного смущает вопрос о том, какой «правильный путь» (при условии, что когда-либо существует такая вещь) обрабатывать чистые / дружественные / красивые URL в приложении.

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

1. Используйте mod_rewrite для обработки всех потенциальных URL. Это будет выглядеть, но не идентично следующему:

RewriteRule ^article/?([^/]*)/?([^/]*)/?([^/]*) /content/articles.php?articleid=$1&slug=$2
RewriteRule ^users/?([^/]*)/?([^/]*) /content/users.php?userid=$1&username=$2
RewriteRule ^search/?([^/]*)/? /content/search.php?query=$1

2. Передайте все в какой-нибудь скрипт-обработчик и дайте ему позаботиться о деталях:

RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule (.*) handler.php?content=$1

Ясно, что это все не проверенный «воздушный кодекс», но вы понимаете, в чем суть.

  • Один из этих двух способов будет намного медленнее другого? Предположительно, mod_rewrite медленнее, так как я буду вынужден использовать для этого файлы .htaccess.
  • Есть ли серьезные недостатки у любого из этих подходов?
  • Есть ли «лучшие практики» для такого рода вещей, или это то, что каждый разработчик стремится решить для себя? Я знаю, что WordPress использует второй вариант (хотя это было больше проблем, чем стоило, когда я точно исследовал, как они это сделали).

Ответы [ 5 ]

5 голосов
/ 23 января 2010

Опция 1 (.htaccess и несколько файлов .php) часто использовалась «в прошлом»;Теперь я вижу вариант 2 (каждый запрос проходит через один файл .php) используется намного больше.

Основные преимущества, которые я вижу с вариантом 2:

  • вы можете добавлять / изменять любые URL-адреса без необходимости изменения какого-либо физического файла, например .htaccess
    • , что означает, что формат URL-адресов можно настроить в разделе администратора вашего приложения, например
  • у вас есть только одна точка входа в ваш код PHP.
    • , что означает, что все идет, хотя index.php: если вам нужен код, выполняемый для всех запросов, поместите его туда, и вы уверены, что он всегда будет выполняться.
    • Используетсянапример, много для фреймворков MVC.


Пару лет назад я бы выбрал вариант 1;теперь, когда я использую MVC и Frameworks, я всегда использую вариант 2.

4 голосов
/ 23 января 2010

Неужели это "стоит ли использовать фреймворки?" замаскированный вопрос.

Использование mod_rewrite для определения ваших URL-маршрутов является быстрым и легким (если вы понимаете регулярные выражения ...), но код вашего приложения не обращает внимания на URL-адреса, если вы не дублируете информацию где-либо.

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

Использование компонента маршрутизации в вашем приложении (например, компонента в Symfony ) означает, что вы можете прикреплять имена к вашим маршрутам, позволяя вам определять свои URL-адреса один раз и повторно использовать их много раз:

# apps/frontend/config/routing.yml
homepage:
  url:   /
  param: { module: default, action: index }

Это позволяет легко ссылаться на страницы вашего сайта без повторения:

<?php echo url_for('@homepage') ?>
2 голосов
/ 23 января 2010

Используйте вариант № 2 - почему? RewriteRules в .htaccess являются мощным инструментом, но они являются своего рода static . Я имею в виду, что вы не можете легко управлять тогда с помощью PHP (или того, что вы собираетесь использовать). Также .htaccess не обеспечивает такой большой гибкости, но имеет некоторые преимущества (например: это немного быстрее).

Опция № 2 также нуждается в .htaccess, как вы заметили, но в большинстве случаев RewriteRule принимает следующую форму:

RewriteRule (.\*) index.php

Где index.php - ваш фронт-контроллер.

Самым большим преимуществом (IMO) этого решения является то, что каждый маршрут описан в PHP (или что бы вы ни использовали), поэтому доступ к этим маршрутам, их изменение намного проще. Кроме того, эти маршруты можно использовать не только для преобразования URL в набор переменных, но и наоборот - для создания URL из набора переменных.

Я думаю, что следующий пример (из фреймворка Symfony) объяснит, о чем я говорю:

// apps/.../config/routing.yml - Describes routing rules
post:
   url:          /read/:id/:slug
   params:       { module: blog, action: index }
   requirements: { id: \d+, slug: \w+ }

// apps/.../modules/blog/templates/indexSuccess.php - template for index action
<?php echo link_to($post['title'], '@post?id=' . $post['id'] . '&slug=' . $post['slug']); ?>
//creates: <a href="/read/123/my-first-blog-post.html">My first blog post</a>

Теперь, когда вы изменяете свой rounting.yml файл и заменяете /read/:id/:slug на /:slug_:id, все ваши ссылки в приложении превращаются в /my-first-blog-post_123.html.

Делать такие и другие вещи, когда вы используете опцию №2, намного проще.

1 голос
/ 23 января 2010

Чистые красивые URL, по-видимому, предоставляются популярной системой управления контентом на основе PHP-сценариев Drupal, использующей комбинацию правил modrewrite в .htaccess и подключаемых модулей PHP Drupal, таких как path и pathauto.

Учитывая успех и популярность этого инструмента, а также его способность работать на самом скромном виртуальном хостинге, я думаю, что это будет ваш ответ.

1 голос
/ 23 января 2010

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

Я думаю, что «наилучшей практики» как таковой нет, оба метода одинаково часто используются. Если структура вашего проекта это позволяет, и вы чувствуете себя как дома, разбирая URL в PHP (где находится остальная часть вашего проекта), поместите все в один файл контроллера и позвольте приложению обрабатывать все остальное.

Если производительность действительно важна, я подозреваю, что Apache обрабатывает адреса быстрее, потому что между ними нет интерпретируемого языка. (У меня нет точных данных для этого, хотя). Но, как я уже сказал, вам, вероятно, лучше всего выбрать тот, который будет наиболее приемлем для вас в долгосрочной перспективе.

...