It gives me URLs like that : http://localhost/service-brussels/
(service is the key and brussels
its place). This URL works perfectly.
But, when I type this URL : http://localhost/service-new-york/
it doesn’t works anymore. The cause of the problem must be the fact that the place contains several hyphens (new-york
) whereas the first one (brussels
) contains no hyphens.
Does anyone know how to solve this please ?
RewriteRule ^([a-zA-Z0-9-éçèà]+)-([a-zA-Z0-9-éçèà]+)$ cities.php?key=$1&place=$2 [L] [R=302,L]
In Keys.php
<?php
$seo_keys = array(
'service'=> 'Service',
'new-service'=> 'New Service'
);
$seo_places = array(
'brussels'=>'Brussels',
'new-york'=>'New York'
);
?>
In cities.php
<?php
require_once('Keys.php');
$place=$seo_places[$_GET['place']];
$motCle=$seo_keys[$_GET['key']];
?>
I got an error
2
Answers
This is not resolvable in its current form since both "keys" and "places" can contain hyphens and the delimiter you are using between "keys" and "places" is also a hyphen. This is ambiguous, since it’s not possible to parse
/key-place
or/key-place-place
or/key-key-place
using simple pattern matching (in.htaccess
) without prior knowledge of existing keys and places. (It would need to be parsed later in your PHP code by searching for valid keys/places in the array (or database), which is inefficient and could still potentially result in conflicts if a "key" and "place" should happen to overlap. eg./one-two-three
, whereone-two
is a "key", buttwo-three
is a "place".)Note that literal hyphens inside a regex character class need to be the first or last character or backslash-escaped to negate their special meaning (as a range specifier).
Note also that this regex does not permit a trailing slash, so it would not seem to match your example URL(s) anyway (that include a trailing slash)? This would then have resulted in a 404, since the rule would not have done anything.
However, I suspect (if the first example URL worked and the 2nd didn’t) then your "error" is an E_NOTICE generated by PHP due to an "undefined index". This is because regex is greedy by default so the above regex would have returned
service-new
andyork
respectively for your "key" and "place", which don’t exist in your lookup arrays. Needless to say, you will need more robust error checking here, since you are accepting raw user input (the URL) so these "errors" are inevitable.Solution
The easiest/logical solution here is to use a different character as the delimiter, such as a slash, so you would then have URLs of the form:
"keys" and "places" cannot contain a slash, so this gets round the obvious ambiguity.
Your rule in
.htaccess
would then become:Note that this forces a trailing slash on the requested URL. If you wish to make the trailing slash optional (although only one URL should be canonical) then you should implement an additonal redirect to redirect to the canonical URL (either with or without the trailing slash).
Aside: Just an observation, but your "keys" appear to be lowercased, but you are permitting uppercased letters in the regex?
Similar/related questions:
This solution is working for me. What do you think?