Forum Moderators: phranque
index.php
reviews.php?article=23
showthread.php?thread=34&page=2
and I would like the add a query string onto the end of each of these pages. (I'd like to try hidden and also not hidden to the user).
Can anyone enlighten me as to how to do this?
I understand how to make a dynamic URL into static, but not on how do actually add a string to a url!
Apache's mod_rewrite [httpd.apache.org] can be used to do this easily -- It's given as an example in the main document or in the Rewriting Guide linked from the main document, IIRC.
Jim
Cross-posting here... You already found [QSA]
The example code applies, but I don't think you need to use the [NE] flag if your queries contain only "?" and "&" as special characters. You probably do want to use the [QSA] flag if you wish to add additional query parameters to the existing query strings.
If your code is in .htaccess, you may not need the leading slash on the RewriteRule pattern. An end anchor on the pattern will speed up processing a little, and make the pattern less ambiguous. Special characters such as "." in patterns must be "escaped" by preceding them with a backslash.
Unless you want to continue with further testing and rewriting of the newly-modified URL, add the [L] flag. This will cause the rewrite engine to stop processing rewrites for this request only if the pattern matches and the URL is modified by a RewriteRule. For example, in the code below, leaving off the [L] on the first RewriteRule would result in two copies of the "cheese" query being added to a request with a blank query string.
That first example you provide is a special case, in that index.php has no existing query string. Because of that, you can't just tack on "&keyword=cheese" because the initial "?" is missing. In that case, you need to detect the blank query string, and handle it separately.
# For blank query only
RewriteCond %{QUERY_STRING} ^$
RewriteRule ^(.*)\.php$ /$1.php?keyword=cheese [L]
#
# Append to existing query
RewriteCond %{REQUEST_URI} \.php$
RewriteRule ^(.*)$ /$1&keyword=cheese [QSA,L]
If your rule is to be placed in httpd.conf, put the leading slash back on the patterns, i.e. "^/(.*)\.php$"
Jim
I pasted:
RewriteEngine on
# For blank query only
RewriteCond %{QUERY_STRING} ^$
RewriteRule ^(.*)\.php$ /$1.php?keyword=cheese [L]
#
# Append to existing query
RewriteCond %{REQUEST_URI} \.php$
RewriteRule ^(.*)$ /$1&keyword=cheese [QSA,L]
Into my .htaccess - but I just get the pages not loading when I try... i.e I type in the URL, click go and nothing happens (it just keeps trying to load the page).
Do you have access to your raw log files and/or error log? They can be a great help in debugging this stuff. Unfortunately, there's no one-size-fits-all solution due to varying requirements and server configurations.
The basic difference between .htaccess and httpd.conf environments is that the leading slash is stripped off the requested URI as seen by RewriteRule in .htaccess context. If you move code from httpd.conf to .htaccess or vice-versa, this has to be taken into account. Generally, it *is* a good idea to test code in a per-directory .htaccess context and then move it to httpd.conf once it is debugged - this can save a bunch of server restarts. But there are some differences that must be accounted for.
Sometimes, it appears that adding "RewriteBase /" before the first RewriteRule or RewriteCond in .htaccess can be used to compensate for the environment difference, but I haven't actually ever done that myself.
Anyway, have a look at your error logs if possible; Seeing what the server was trying to do and what it "did wrong" is a big help.
Jim
That would be the [NE] flag, probably.
For the edification of our readers, please feel free to post relevant parts of the final working version - just strip out any site-specific URL stuff and use "example.com" to comply with our TOS. Often, one good example is worth a hundred posts!
Thanks,
Jim
RewriteEngine on
RewriteCond %{QUERY_STRING} ^$
RewriteRule ^(.*)\.php$ /$1.php?test [L,NE,R]
It redirects all of the .php files to .php?test
I would like to use a string like "%6a%65%74" instead of "test", but the NE does not have any effect for some reason (I've already tried it). It still gets decoded.
What, precisely, do you mean by this?
> It still gets decoded.
Do you mean it gets decoded in the browser address bar, or in your server logs, or somewhere else? I guess the question is, where is the string 'exposed' as plain text that you don't want it to be?
I note that you have added an [R] flag to the Rule, which makes this an external redirect, rather than a server-internal filepath/querystring substitution. An external redirect means that mod_rewrite will change the URL, and then (as its written here with [R]) send a 302-Moved Temporarily server response back to the browser, along with this new URL. The browser itself will decode the encoded URL parts.
So, I'm wondering if you really want to involve the browser at all, or just to replace the requested URL with a new local filepath/querystring, and then fetch the file. This latter (without using [R] is the more usual case when rewriting URLs to feed into scripts, but might not be what you want. However, the [NE] flag operates only within the server, and can't stop a browser from decoding a %-encoded string.
Jim
When I use "%69%6e%6b%6a%65%74" is comes back appearing as text in the users bar as "9sdjsh" or something similar.
I basically want the page to forcfully change the url and display the new URL it is showing. If the decoding can't be changed, it does not matter - I will have to work around it in other ways :)
I have been trying to get the following working since yesterday:
RewriteCond %{REQUEST_URI} \.php$
RewriteRule ^(.*)$ /$1&keyword=cheese [QSA,L]
Unfortunatly, it just seems to skip the $1 part and requests a file called "&keyword=cheese". If I can get this part working I am sorted :)
> in the users bar as "9sdjsh" or something similar.
Yes, it always will - browsers will decode the %-encoded strings, and that's out of your control. The only way to avoid it with standard encoded strings is to not pass the new URL back to the user's browser. An alternative is to create and use your own encoding system that the browser will leave alone.
RewriteCond %{REQUEST_URI} \.php$
RewriteRule ^(.*)$ /$1&keyword=cheese [QSA,L]Unfortunatly, it just seems to skip the $1 part and requests a file called "&keyword=cheese". If I can get this part working I am sorted .
That's weird...
Your could try something like this to 'brute-force' it:
RewriteCond %{QUERY_STRING} ^(.+)$
RewriteRule ^(.*\.php)$ /$1%1&keyword=cheese [L]
RewriteCond %{QUERY_STRING} ^$
RewriteRule ^(.*\.php)$ /$1?keyword=cheese [L]
Jim