2

This is my current .htaccess:

RewriteEngine On
RewriteRule ^([\w-]+)/([a-z0-9]+)/([a-z-0-9]+)$ index.php?p=$1&bay=$2&map=$3 [L]
RewriteRule ^test/([\w-]+)/(\d+)$ index.php?page=$1&tab=$2 [L]

I got a problem with this rule:

RewriteRule ^test/([\w-]+)/(\d+)$ index.php?page=$1&tab=$2 [L]

I wanted to rewrite these URLs:

1 - example.com/test/?page=example-1&tab=1

2 - example.com/test/?page=example2&tab=1

And i wanted these results bellow:

1 - example.com/test/example-1/1

2 - example.com/test/example2/1

But only the first result works, and for some reason (that i don't know) i need to change example2 to Example2 to be able to access this URL: example.com/test/example2/1.

I solved this problem changing the order of the rules:

RewriteEngine On
RewriteRule ^test/([\w-]+)/(\d+)$ index.php?page=$1&tab=$2 [L]
RewriteRule ^([\w-]+)/([a-z0-9]+)/([a-z-0-9]+)$ index.php?p=$1&bay=$2&map=$3 [L]

Why do i needed to change the order of the rules? How does the rules was being affected by order?

1 Answer 1

3
RewriteRule ^([\w-]+)/([a-z0-9]+)/([a-z-0-9]+)$ index.php?p=$1&bay=$2&map=$3 [L]
RewriteRule ^test/([\w-]+)/(\d+)$ index.php?page=$1&tab=$2 [L]

You basically have a "conflict" with these two rules. These rules are processed in the order in which they appear in the file. Some of your URLs, that you are expecting to be processed by the second rule, are matched and consequently processed by the first rule instead. Once the URL is processed by the first rule, the second rule is effectively bypassed.

(You should have been able to have seen this by debugging the URL parameters your script was seeing. index.php should have still been called.)

1. example.com/test/example-1/1

This "works" because it is not matched by the first rule. The first rule does not allow hyphens in the second path segment, ie. ([a-z0-9]+) does not match example-1. The regex only matches 1 or more a-z (lowercase) and 0-9 characters. So, processing continues and is caught by the second rule, which matches successfully.

i need to change example2 to Example2

For the same reason as above. Example2 (with an uppercase E) does not match the first rule (specifically, ([a-z0-9]+) does not match Example2). As noted above, the first rule only matches lowercase a-z (and 0-9) in the second path segment. So, processing falls through to the second rule, which matches due to the \w shorthand character class which also includes the uppercase A-Z letters.

In some ways (apart from the uppercase letters and hyphen in the second path segment) the first rule is more "generic" so ends up catching the URLs you are expecting to fall through to the second rule.

The more specific rule(s) should appear first. The rules should be in order of specificity. The more specific rules first; the more generic rules last.

So, in your case - for these specific URLs - you can solve the problem by simply reversing these directives.

This may be sufficient for your particular URLs. For example, if all URLs that start /test/ should be processed by the (new) first rule then all should be good. However, if there are any "special cases" that should be processed by the second rule, such as /test/123/123 then you will need to readdress these rules and/or URL structure.


Aside:

I wanted to rewrite these URLs:

1 - example.com/test/?page=example-1&tab=1

2 - example.com/test/?page=example2&tab=1

And i wanted these results bellow:

1 - example.com/test/example-1/1

2 - example.com/test/example2/1

It's really the other way round. (Although many do describe it in this way, it is confusing, as it seemingly describes the overall result you are trying to achieve, not the process?)

For example, you are rewritting example.com/test/example-1/1 to example.com/test/?page=example-1&tab=1 (not the other way round). The later is the "result".

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.