2

Я хочу, чтобы получить список городов, где связаны друг название города и относится страницу для этого города:URIs с немецкими специальными символами не работает (ошибка 404) в Zend Framework 2

enter image description here

ссылки (созданная в скрипте вида) выглядит следующим образом:

http://project.loc/catalog/Berlin (in the HTML source code url-encoded: Berlin) 
http://project.loc/catalog/Erlangen (in the HTML source code url-encoded: Erlangen) 
http://project.loc/catalog/Nürnberg (in the HTML source code url-encoded: N%C3%BCrnberg) 

«Берлин», «Эрланген» и т.д. работа, но если название города содержит немецкий специальный символ (ä, ö, ü, Ä, Ö, Ü или ß), как "Нюрнберг", возникает ошибка 404:

404 произошла ошибка Страница не найдена. Запрошенный URL-адрес не может быть , сопоставленный маршрутизацией. Нет Исключение отсутствует

Почему? И как это сделать?

Заранее благодарен!

EDIT:

Мои настройки маршрутизатора:

'router' => array(
    'routes' => array(
     'catalog' => array(
      'type' => 'literal', 
      'options' => array(
       'route' => '/catalog', 
       'defaults' => array(
        'controller' => 'Catalog\Controller\Catalog', 
        'action'  => 'list-cities', 
       ), 
      ), 
      'may_terminate' => true, 
      'child_routes' => array(
       'city' => array(
        'type' => 'segment', 
        'options' => array(
         'route' => '/:city', 
         'constraints' => array(
          'city' => '[a-zA-ZäöüÄÖÜß0-9_-]*', 
         ), 
         'defaults' => array(
          'controller' => 'Catalog\Controller\Catalog', 
          'action'  => 'list-sports', 
         ), 
        ), 
        'may_terminate' => true, 
        'child_routes' => array(
        // ... 
        ), 
       ), 
      ), 
     ), 
    ), 
), 
+0

Не очевидно ли, что это не соответствует указанным ограничениям? – CBroe

+0

Да, вы правы. Я только что отредактировал настройки маршрутизатора. Он все еще не работает. – automatix

+0

Вы показали, как выглядят URL-адреса, но вы использовали правильную кодировку URL для этих специальных символов? – CBroe

ответ

3

Вы должны изменить свои ограничения, вы можете использовать регулярное выражение, которое будет соответствовать UTF8 символов, что-то вроде этого:

'/[\p{L}]+/u' 

Обратите внимание на модификатор/u (юникод).

EDIT:

Проблема заключается в resolved.

Объяснение:

регулярное выражение Route maches URI, с preg_match(...) (строка 116 или 118 из Zend \ Mvc \ маршрутизатора \ Http \ Regex). Чтобы обработать строку с «специальными символами» (128+), необходимо пройти модификатор шаблона u до preg_match(...). Как это:

$thisRegex = '/catalog/(?<city>[\p{L}]*)'; 
$regexStr = '(^' . $thisRegex . '$)u'; // <-- here 
$path = '/catalog/Nürnberg'; 
$matches = array(); 
preg_match($regexStr, $path, $matches); 

И поскольку RegEx Маршрут проходит строку URL-enccoded в preg_match(...), это furthermode нужно декодировать строку первой:

$thisRegex = '/catalog/(?<city>[\p{L}]*)'; 
$regexStr = '(^' . $thisRegex . '$)u'; 
$path = rawurldecode('/catalog/N%C3%BCrnberg'); 
$matches = array(); 
preg_match($regexStr, $path, $matches); 

Эти два шага не предусмотрены в RegEx пути, так что preg_match(...) получает steing как '/catalog/N%C3%BCrnberg' и пытается Мах его регулярное выражение, как '/catalog/(?<city>[\\p{L}]*)/u'

решением является использование пользовательского REGE x Маршрут. Here - пример.

+0

Спасибо! Это не работает для меня, но, возможно, я неправильно использую ваше регулярное выражение. Я заменил '' city '=>' [a-zA-ZäöüÄÖÜß0-9 _-] * ', 'с'' city '=>'/^ \ p {L} [\ p {L} _.-] + $/u ', ' – automatix

+0

, может быть, это был плохой пример, это просто чтобы увеличить флаг/u. try '/ [\ p {L}] +/u' – Andrew

+0

Наконец-то он работает! Спасибо за столь важный намек на модификатор! – automatix