Can't make an alias for an directory - apache

I want to make short my URL with URL Rewriting, but i dont know how, i made reasearch but no result (url rewriting work on my server):
My url is like :
My-Domaine.com/Directory1/web/app.php/Directory2/ (Symfony 2 project)
I want to make something like this :
My-Domaine.com/Directory/
My htaccess is like this :
RewriteEngine on
RewriteRule /Directory1/web/app.php/Directory2/ Directory/ [PT]
IndexIgnore .htaccess */.??* *~ *# */HEADER* */README* */_vti*
AuthName www.My-Domaine.com
RewriteCond %{HTTP_HOST} ^My-Domaine.com$ [OR]
RewriteCond %{HTTP_HOST} ^My-Domaine.com$
RewriteRule ^/?$ "3W.My-Domaine.com/Directory1/web/app.php/Directory2/" [L]
Sory for my english, thanks for your help.

It will probably be easier to use an Alias instead of url rewriting.
You would just need to add something like this to the host configuration.
Alias /Directory "var/www/Directory1/web/"
<Directory "var/www/Directory1/web/">
Options Indexes MultiViews FollowSymLinks
AllowOverride All
</Directory>
This way you can also avoid the possibility of stepping on the URL rewriting that Symfony uses to direct requests to the front controllers.

Related

How to search and replace GET parameters with mod_rewrite

I try write a rewrite rule on an apache webserver configuration in the httpd.conf file, which should replace every GET parameter key which contains &foo= to &poo= but shouldn't change any other GET parameter.
For example:
https://test.com/imb/rs/search?test=abc&foo=123&test2=def&foo=456
Should be changed to:
https://test.com/imb/rs/search?test=abc&poo=123&test2=def&poo=456
I tried it with:
RewriteCond %{QUERY_STRING} ^(.*)&foo=(.*)$
RewriteRule ^(.*)$ $1?%1?&poo=%2 [NC]
But it only changed the last occurrence of foo to poo.
My httpd.conf file is structured as follows:
<Directory ~ "^/imb/rs/*">
Options Indexes FollowSymLinks
AllowOverride All
Order allow,deny
Allow from all
RewriteEngine on
RewriteCond %{QUERY_STRING} ^(.*)&foo=(.*)$
RewriteRule ^(.*)$ $1?%1&poo=%2 [NC]
</Directory>
<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond %{QUERY_STRING} ^(.*)&foo=(.*)$
RewriteRule ^(.*)$ $1?%1&poo=%2 [NC]
</IfModule>
The /imb/rs/ part is written because the url starts with https://test.com/imb/rs/ and continues after that. I thought that would match my case.
Does anyone have an idea how I could solve this?
<Directory ~ "^/imb/rs/*">
Options Indexes FollowSymLinks
AllowOverride All
Order allow,deny
Allow from all
RewriteEngine on
RewriteCond %{QUERY_STRING} ^(.*)&foo=(.*)$
RewriteRule ^(.*)$ $1?%1&poo=%2 [NC]
</Directory>
<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond %{QUERY_STRING} ^(.*)&foo=(.*)$
RewriteRule ^(.*)$ $1?%1&poo=%2 [NC]
</IfModule>
There are a few issues here. The <Directory> container is not going to match the request, so the mod_rewrite directives inside this container are not processed. Only the mod_rewrite directives outside the <Directory> container are processed, but this will only replace the last instance of &foo= in the query string (since the regex is greedy and the rewrite engine makes just a single pass in a vHost/server context).
<Directory ~ "^/imb/rs/*">
You are mixing regex and wildcard syntax. However, this should be an absolute filesystem path, not a URL-path, as this appears to be ("url starts with https://test.com/imb/rs/"). But you do not need to use the regex version of the <Directory> directive here anyway. I'm assuming /imb/rs is a physical directory and not simply a virtual URL-path?
AllowOverride All
You are explicitly enabling .htaccess overrides. If you do have a .htaccess file that contains mod_rewrite directives in this directory then this will completely override the <Directory> container in the server config. You should probably be disabling .htaccess overrides altogether.
Order allow,deny
Allow from all
These are Apache 2.2 directives and are formerly deprecated on Apache 2.4 (which I would assume you are using). You should be using the equivalent Require all granted instead. (But you do need to make sure you are using Apache 2.4 directives throughout - do not mix the two.)
Options Indexes FollowSymLinks
Aside: Are you intentionally allowing mod_autoindex to generate directory listings of your content? Generally, this should be disabled (ie. remove Indexes from this rule).
Try the following instead:
<Directory "/absolute/file/path/to/imb/rs">
Options Indexes FollowSymLinks
AllowOverride None
Require all granted
RewriteEngine On
RewriteCond %{QUERY_STRING} (.*)&foo=(.*)
RewriteRule (.*) $1?%1&poo=%2 [L]
</Directory>
And remove the rule from outside the <Directory> container.
So, the rule you had in the beginning was basically OK. The start-of-string and end-of-string anchors are not required here, since the regex is greedy. The NC flag is not required. The L flag is not strictly required, but would be if you add any more rules later.
I found this solution which works only with 1 occurrence, not with multiple.
This one takes only the first occurrence:
RewriteCond %{QUERY_STRING} (.*?)foo(.*) [NC]
RewriteRule ^ %{REQUEST_URI}?%1poo%2 [NC]
This one takes only the last occurrence:
RewriteCond %{QUERY_STRING} (.*)foo(.*) [NC]
RewriteRule ^ %{REQUEST_URI}?%1poo%2 [NC]
But I couldn't find a way to replace all of them.

Apache rewrite 1 file globally to new file URL

I have a file with an identical name that exists in 15 subdirectories. Let's say it's called blah.txt.
I'm looking to do a global rewrite within httpd.conf to match any subdirectory's blah.txt and Rewrite it to a singular http://myserver/blah.txt.
If I add the following to an .htaccess, it works great. I hit the subdirectory's txt file, and I'm 301 forwarded. However doing this means I need to manage 15 .htaccess's. I'm trying to avoid that.
RewriteEngine On
RewriteRule ^(blah)\.txt http://myserver/blah.txt [L,R=301]
If I put this same text into httpd.conf under the <Directory /> section, I get a 404 on the subdirectory's blah.txt.
<Directory />
Options All Indexes FollowSymLinks
AllowOverride All
Allow from all
RewriteEngine On
RewriteRule ^(blah)\.txt http://myserver/blah.txt [L,R=301]
</Directory>
How can I have this global match within httpd.conf?
Edit: If I change the httpd.conf rewrite to the below, it seems like it wants to work, however I get stuck in an infinite loop because it's constantly matching the same file name.
RewriteEngine On
RewriteRule blah.txt http://myserver/blah.txt [L,R=301]
Still looking for a way to have it match in subdirectories and redirect to the same filename.
Edit 2: I think I got this working - but would love confirmation!
I added a RewriteCond to my rule. Basically, I think, this means that if the URI does not contain "firmware", then rewrite.
<Directory />
Options All Indexes FollowSymLinks
AllowOverride All
Allow from all
RewriteEngine On
RewriteCond %{REQUEST_URI} !(firmware) [NC]
RewriteRule blah.txt firmware/series/version/blah.txt [R=301,L]
</Directory>
It seems to be working without looping
As per my Edit 2: I think I got this working.
I added a RewriteCond to my rule. Basically, I think, this means that if the URI does not contain "firmware", then rewrite.
<Directory />
Options All Indexes FollowSymLinks
AllowOverride All
Allow from all
RewriteEngine On
RewriteCond %{REQUEST_URI} !(firmware) [NC]
RewriteRule blah.txt firmware/series/version/blah.txt [R=301,L]
</Directory>
After quite a bit of testing, it seems to be working without looping

Deny access to all content except content from one folder

I want to allow access to only one folder of my site in a given subdomain, and have another subdomain pointing to same documentRoot with full access. I want this to avoid duplicated urls (for SEO purposes).
In the restricted virtualHost I have this configuration ...
<Directory /var/www/secundary.mysite.com/web>
Options -Includes +ExecCGI
AllowOverride All
RewriteEngine On
RewriteCond %{QUERY_STRING} !/bundles.*$ [NC]
RewriteRule ^.*$ - [F]
</Directory>
So I expect that navigation to mysite.com give a forbidden response, but www.mysite.com/bundles/js/script.js returns a normal response.
The result is that every request to secundary.mysite.com returns a normal response. Am I missing something, or ...?
I have been using a wrong variable. I wrote %{QUERY_STRING} instead %{REQUEST_URI} that was the variable that I wanted to match again the regular expression. The correct syntax for my purpose was:
<Directory /var/www/secundary.mysite.com/web>
Options -Includes +ExecCGI
AllowOverride All
RewriteEngine On
RewriteCond %{REQUEST_URI} !^/bundles(.*)$ [NC]
RewriteRule ^.*$ - [F]
</Directory>

apache htaccess rewrite with alias

We are changing our domain name and this is meant to work for stand alone applications. In Apache virtual host file the DocumentRoot is /var/www/website/html, not /var/www/example/html as in this block:
Alias /apps/dept /var/www/example/html/apps/dept
<Directory "/var/www/example/html/apps/dept/">
Options FollowSymLinks
AllowOverride All
Order allow,deny
Allow from all
</Directory>
I put an .htaccess file in /var/www/example/html/apps/dept directory as follows:
RewriteEngine On
RewriteBase /apps/dept/
RewriteCond %{HTTP_HOST} ^example.orgname.state.tx.us/apps/dept [NC]
RewriteRule ^(.*)$ http://example.orgname.texas.gov/apps/dept/$1 [L,R=301]
This seems to follow what is recommended here, http://httpd.apache.org/docs/current/mod/mod_rewrite.html and Apache : How to Use Rewrite Engine Inside Alias. I see no results. The new domain has a virutal host config in the VH file, also. This same basic rewrite works for our Drupal website which does not use an alias. What changes might be necessary to have the domain name rewritten with an appended application pathname? Is the RewriteBase incorrect?
Thx.
So you only want to redirect /apps/dept/, correct? This should work. Place it as an .htaccess or in the Apache config for example.orgname.state.tx.us and all should work as expected.
RewriteEngine on
RewriteRule ^/apps/dept/(.*)$ http://example.orgname.texas.gov/apps/dept/$1 [NC,L,R=301]
So now, any requests going to this URL
http://example.orgname.state.tx.us/apps/dept/
Will now go to this URL:
http://example.orgname.texas.gov/apps/dept/
And any request parameters to the right of the URL will be passed along as well.
EDIT Just reread what you wrote here:
I put an .htaccess file in /var/www/example/html/apps/dept directory
as follows.
The .htaccess I described above should be placed in /var/www/example/html/ and not in the /apps/dept subdirectory.
But if you want the same behavior from an .htaccess placed in /apps/dept then use this:
RewriteEngine on
RewriteRule ^(.*)$ http://example.orgname.texas.gov/apps/dept/$1 [NC,L,R=301]
This way any request made from /apps/dept will to to example.orgname.texas.gov/apps/dept/ including subdirectories of /apps/dept such as /apps/dept/test_app1, /apps/dept/test_app2 or /apps/dept/test_app3.
Or perhaps try this:
RewriteEngine on
RewriteRule (.*)$ http://example.orgname.texas.gov/apps/dept/$1 [NC,L,R=301]
Note I removed the ^ which would force the RewriteRule to match the beginning of the URL.
You cannot match Request URI in %{HTTP_HOST} variable, it matches only domain name. Chang your rule to:
RewriteEngine On
RewriteBase /apps/dept/
RewriteCond %{HTTP_HOST} ^example\.orgname\.state\.tx\.us$ [NC]
RewriteRule ^(.*)$ http://example.orgname.texas.gov/apps/dept/$1 [L,R=301]

mod_rewrite in <Location /> in apache conf causing rewrite in .htaccess file not to work?

I am using zend framework, which has a nifty example .htaccess used for redirecting non-existing locations to index.php to be processed by the framework:
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} -s [OR]
RewriteCond %{REQUEST_FILENAME} -l [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [NC,L]
RewriteRule ^.*$ /site/index.php [NC,L]
And here is the apache config for /site
Alias /site "/path/to/zf/project/public"
<Directory "/path/to/zf/project/public">
Options Indexes MultiViews FollowSymLinks
AllowOverride All
Order allow,deny
Allow from all
</Directory>
While we are upgrading the site, I want to redirect all traffic to a specific file (offline.html, for example) except for a certain IP (127.0.0.1, for example), so I am trying to use this rule in the apache config:
<Location />
Options Indexes MultiViews FollowSymLinks
AllowOverride All
Order allow,deny
Allow from all
RewriteEngine On
RewriteBase /
RewriteCond %{REMOTE_HOST} !^127\.0\.0\.1
RewriteCond %{REQUEST_URI} !/offline\.html$
RewriteRule .* /offline.html [R=302,L]
</Location>
This seems to work, but for some reason it makes my .htaccess file seem not to work. I can access /site just fine, but I can't go any deeper to, for example, /site/controller/action.
Thanks!
The Apache 2.2 and Apache 2.4 documentation of mod_rewrite clearly state that rewrite rules in <Location> directives should be avoided. This caution was not included in the Apache 2.0 documentation.
Although rewrite rules are syntactically permitted in <Location> and <Files> sections (including their regular expression counterparts), this should never be necessary and is unsupported. A likely feature to break in these contexts is relative substitutions.
So strange things can happen. You could remove the <Location> section (and RewriteBase directive) and use these new rewrite rules directly in the <VirtualHost> definition, without any <Directory> or <Location> section. It's even faster.
The only problem with global level rewrite rules is that you do not have the REQUEST_FILENAME already computed (you could hack that a little but here you do not even need REQUEST_FILENAME).
You also have one error in your RewriteRule, you use a Redirect so the rewrite Rule should use a absolute url:
RewriteRule .* http://www.example.com/offline.html [R=302,L]
About the maintenance page, a classic way of handling it is with these two lines:
ErrorDocument 503 /htdocs/err/503.html
RedirectMatch 503 ^/(?!err/)
Where you do not filter on local IP, but the interesting part is that the code used for maintenance is 503 (temporary unavailable) which is more correct (in fact a redirect 307 is even more correct but old browser could have problems with it). To do the same with a local IP restriction and a RewriteRule it would be:
ErrorDocument 503 /offline.html
RewriteCond %{REMOTE_HOST} !^127\.0\.0\.1
RewriteCond %{ENV:REDIRECT_STATUS} !=503
RewriteRule ^ - [L,R=503]
To have these rules in the htaccess file, you'll have to add/remove them by hand when you want to use "offline mode".
A better way to do this through the application is to create a controller plugin.
If the APPLICATION_ENV = 'offline', the plugin would do _forward('offline', 'error', 'default');
Alternatively, you could write the logic in a subclass of Zend_Controller_Action which you use as the base class for your controllers.