2 votes

CakePHP utilise des expressions régulières pour l'unicode

Je souhaite effectuer la modification suivante dans les routes CakePHP. Tout mot ou groupe de mots (séparés par un trait d'union) après l'URL d'un site web comme example.com/someword o example.com/some-word doit être redirigé vers controller => posts, action => view . Mais mon problème est que le(s) mot(s) doit(vent) être en unicode. J'ai essayé cette expression régulière pour le texte de l'URL, mais cela ne fonctionne pas.

Router::connect ( '/:link', array ('controller' => 'posts', 'action' => 'view' ), array ('pass' => array ('link'), 'link' => '/^['.json_decode('" \u0531 "').'-'.json_decode('"" \u0587 "').'-]+$/u' ) ) ;

Je tiens cependant à préciser que ma regex

'/^['.json_decode('"\u0531"').'-'.json_decode('"\u0587"').'-]+$/u',

fonctionne parfaitement si je suis sur le point de faire un preg_match habituel comme

$regg = '/^['.json_decode('"\u0531"').'-'.json_decode('"\u0587"').'-]+$/u';
if (preg_match($regg, "my unicode string", $match)) {
  var_dump($match);   // outputs string as expected
}
die;

EDIT

Je me retrouve avec le code suivant

Router::connect ( '/:link', array ('controller' => 'posts', 'action' => 'view' ), array    ('pass' => array ('link'), 'link' => '((?![a-zA-Z]).)+' ) ); 

comme faire en sorte que mon url contienne tout, sauf des lettres anglaises, mais ce n'est pas ce dont j'ai besoin, si j'ai 2 ou plusieurs langues différentes de l'anglais - cette méthode ne fonctionnera pas. Je veux donc envoyer le mot de chaque langue dans une action séparée.

cake version 2.x

EDIT 2

Il existe des solutions alternatives, comme dans les réponses ci-dessous, pour contourner la question, mais je cherche la manière exacte de faire ce dont j'ai besoin.

Remerciements

0voto

manzapanza Points 4270

De http://en.wikipedia.org/wiki/Query_string en Encodage de l'URL paragraphe vous ne pouvez pas utiliser ces caractères dans une chaîne de requête d'url :

En particulier, l'encodage de la chaîne de requête utilise les règles suivantes :

  • Les lettres (A-Z et a-z), les chiffres (0-9) et les caractères ".", "-", "~" et "_" sont laissés tels quels.
  • L'ESPACE est codé comme "+" ou "%20" [8].
  • Tous les autres caractères sont codés en représentation hexagonale %HH, les caractères non ASCII étant d'abord codés en UT encodage spécifié)

Si vous avez deux langues (ou plus), vous pouvez envisager d'ajouter dans la table des posts un champ slug pour chaque langue, par exemple pour l'anglais et le russe :

postes

  • id
  • titre_fr
  • titre_rus
  • slug_eng
  • limace_rus

Sur Post.php beforeValidate ou beforeSave :

if(isset($this->data['Post']['title_eng'])){
    $this->data['Post']['slug_eng'] = Inflector::slug(strtolower($this->data['Post']['title_eng']), '-');
}
if(isset($this->data['Post']['title_rus'])){
    $this->data['Post']['slug_rus'] = Inflector::slug(strtolower($this->data['Post']['title_rus']), '-');
}

Le lien à l'intérieur d'une vue :

echo $this->Html->link($post['Post']['title_eng'], array('controller' => 'posts', 'action' => 'view', 'slug_eng' => $post['Post']['slug_eng']));
echo $this->Html->link($post['Post']['title_rus'], array('controller' => 'posts', 'action' => 'view', 'slug_rus' => $post['Post']['slug_rus']));    

L'itinéraire :

Router::connect('/posts/:slug_eng', array('controller' => 'posts','action' => 'view', 'eng'), array('pass' => array('slug_eng'), 'slug_eng' => '[a-zA-Z0-9]+'));
Router::connect('/ru/posts/:slug_rus', array('controller' => 'posts','action' => 'view', 'rus'), array('pass' => array('slug_rus'), 'slug_rus' => '[a-zA-Z0-9]+'));

Le contrôleur Postes :

public function view($locale, $slug){
    ....
    validate and sanitize here
    ...
    $post = $this->Post->find('first', array('conditions' => array('slug_' . $locale => $slug)));
    ....
}

0voto

Notakilla Points 96

Je suggère d'utiliser des caractères génériques

Router::connect('/*', array('controller' => 'posts', 'action' => 'view'));

D'autres routes peuvent être ajoutées avant cette ligne, par exemple

Router::connect('/:digits', array('controller' => 'posts', 'action' => 'view'), array('pass' => array('digits'), 'digits' => '/d+');
Router::connect('/*', array('controller' => 'posts', 'action' => 'view'));

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X