Dancer
Dancer copied to clipboard
request->uri_base contains dispatch.(f)cgi when Dancer is executed via DirectoryIndex (Apache 2.4)
Dancer version 1.3202 Dunno if this is a bug or wanted behaviour:
On one Dancer site I recently had an issue where dispatch.fcgi ended up in request->uri_base, for example request->uri_base = "http://www.example.com/dispatch.fcgi"
By accident I found that this only happened at the root "/" path of the site... Which led me to why it happened: I had a new (over-optimisation!?) Directive in the site's Apache .conf file. Illustrated with the example from Dancer::Deployment, I had this:
<VirtualHost *:80>
ServerName localhost
DocumentRoot "/path/to/rootdir"
<Directory "/path/to/rootdir">
AllowOverride None
Options +ExecCGI -MultiViews +SymLinksIfOwnerMatch
Order allow,deny
Allow from all
AddHandler fastcgi-script .fcgi
</Directory>
DirectoryIndex /dispatch.fcgi # <<-- this here
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule /(.*)$ /dispatch.fcgi$1 [QSA,L]
</VirtualHost>
As suggested in the Dancer::Deployment docs, my .conf ended with every path going through the rewrite engine, with "RewriteRule ^(.*)$ /dispatch.fcgi$1 [QSA,L]". However, I decided to be extra smart, and that the root "/" doesn't need to be elaborately parsed, thus I set a DirectoryIndex directive at the beginning of the config file, to break out of testing the URL early.
That didn't work as expected! As it seems, when dispatch.fcgi is called via DirectoryIndex, ".../dispatch.fcgi" ends up in request->uri_base. Obviously Apache calls the script different via DirectoryIndex (without appending the path, right?). And when no URI path is appended, Dancer's uri_base() algorithm decides that the script name is part of the uri_base...
If that's the feature/problem, then why is my current over-optimisation working?
... RewriteRule ^/$ /dispatch.fcgi [QSA,L] RewriteCond %{DOCUMENT_ROOT}%{REQUEST_FILENAME} !-f RewriteCond %{DOCUMENT_ROOT}%{REQUEST_FILENAME} !-d RewriteCond %{DOCUMENT_ROOT}%{REQUEST_FILENAME} !- RewriteRule ^(.*)$ /dispatch.fcgi [QSA,L]
The above "/"-edge-case-rewrite-rule is also passing nothing to dispatch.fcgi... Clearly, Apache handles scripts different via DirectoryIndex, and Dancer's uri_base() returns a different value.
Yes, that's how DirectoryIndex works, and why I said you needed to use mod_rewrite. This was the very first diagnosis and solution I suggested before you spent an hour plus on other configs :P
By the time the request gets to Dancer we've no way of telling that you use DirectoryIndex that I can think of so unless you can see something in the PSGI environment that we could test, I don't think it's possible to change this behaviour, and the only assistance I can give you is "if at first you don't succeed, maybe try doing what mst suggested in the first place".
I'm not closing this immediately because I'd like to give others a chance to explain why I'm completely wrong, since I'd be happy to trade any dignity I have on this ticket for the pleasant surprise that this is fixable after all ;)
Actually, took me more time to discuss the issue..., as once I stumbled over the behaviour again, I quickly discovered it to be related with DirectoryIndex. Anyway. As a final remark, let me emphasize that my intention wasn't to annoy you or anyone! So, really, thank you for looking into this again.