469,645 Members | 1,653 Online
Bytes | Developer Community
New Post

Home Posts Topics Members FAQ

Post your question to a community of 469,645 developers. It's quick & easy.

Apache ErrorDocument / PHP header() interaction does not work as expected


I recently worked on error handling and three related issues/questions
came up.
1.) I am trying to trigger Apache ErrorDocument handlers by setting
appropriate HTTP status codes in my PHP code, but I don't get the
expected results.

My PHP file:

----------------
<?php
header("HTTP/1.0 500 Internal Server Error");
----------------
In my Apache configuration I have this:

----------------
ErrorDocument 500 "test error 500 handler
----------------

The status code is sent to the browser, but the ErrorDocument handler
is never triggered, it looks like Apache passes the value on to the
client, but does not interpret it.

The last posting on this page suggests something to this effect:

http://www.webmasterworld.com/apache/3205630.htm
This surprises me, is that really how it works? In my Perl
applications running under mod_perl, returning status 500 does *both*,
send that status to the browser and make Apache interpret and act upon
the value. What is mod_perl doing differently?

I can actually have two separate status values, one that gets sent to
the browser (Apache2::RequestRec::status()), and one that is returned
to the Apache server (the handler() method's return value). Does
something similar exist in PHP? Or do I really have to replicate the
ErrorDocument functionality in my PHP code?
2.) In my tests with mod_perl just now I also realized that mod_perl
will properly signal an error 500 condition to Apache if a Perl error
such as a syntax error or an unhandled exception occurs. A configured
ErrorDocument 500 handler will be triggered, as I would expect it to
be.

It seems that PHP does not signal an error 500 to Apache when PHP code
fails. Wouldn't this be a useful addition for exactly this reason
(ability to use Apache ErrorDocument).
3.) While playing around with set_error_handler(), I also saw that
syntax errors are not trappable with a custom error handler. I use an
autoloader that loads classes on demand, and if one of the class files
loaded at run-time has a syntax error, my error handler is bypassed.
Combined with the inability to trigger ErrorDocuments described above,
doesn't this mean that it is absolutely impossible to hide such errors
from users by replacing them with a "friendly" error page when using
PHP?

That would mean that I am not even able to emulate the ErrorDocument
feature in PHP code.

May 10 '07 #1
4 6532
On May 10, 10:19 am, "liyan...@gmail.com" <liyan...@gmail.comwrote:
I recently worked on error handling and three related issues/questions
came up.

1.) I am trying to trigger Apache ErrorDocument handlers by setting
appropriate HTTP status codes in my PHP code, but I don't get the
expected results.

My PHP file:

----------------
<?php
header("HTTP/1.0 500 Internal Server Error");
----------------

In my Apache configuration I have this:

----------------
ErrorDocument 500 "test error 500 handler
----------------

The status code is sent to the browser, but the ErrorDocument handler
is never triggered, it looks like Apache passes the value on to the
client, but does not interpret it.

The last posting on this page suggests something to this effect:

http://www.webmasterworld.com/apache/3205630.htm

This surprises me, is that really how it works? In my Perl
applications running under mod_perl, returning status 500 does *both*,
send that status to the browser and make Apache interpret and act upon
the value. What is mod_perl doing differently?

I can actually have two separate status values, one that gets sent to
the browser (Apache2::RequestRec::status()), and one that is returned
to the Apache server (the handler() method's return value). Does
something similar exist in PHP? Or do I really have to replicate the
ErrorDocument functionality in my PHP code?

2.) In my tests with mod_perl just now I also realized that mod_perl
will properly signal an error 500 condition to Apache if a Perl error
such as a syntax error or an unhandled exception occurs. A configured
ErrorDocument 500 handler will be triggered, as I would expect it to
be.

It seems that PHP does not signal an error 500 to Apache when PHP code
fails. Wouldn't this be a useful addition for exactly this reason
(ability to use Apache ErrorDocument).

3.) While playing around with set_error_handler(), I also saw that
syntax errors are not trappable with a custom error handler. I use an
autoloader that loads classes on demand, and if one of the class files
loaded at run-time has a syntax error, my error handler is bypassed.
Combined with the inability to trigger ErrorDocuments described above,
doesn't this mean that it is absolutely impossible to hide such errors
from users by replacing them with a "friendly" error page when using
PHP?

That would mean that I am not even able to emulate the ErrorDocument
feature in PHP code.
well you /can/ do
sendErrorDocumentAndQuit($code)
{
$arrStatusCodes = array(
404=>'Page Not Found',
500=>'Custom Internal Server Error'
);
if( !in_array($code,array_keys($arrStatusCodes)) )
{
$code = 403;
}
header( 'HTTP/1.1 ' . $code . ' "' . $arrStatusCodes[$code] . '"' );
include( '/path/to/aliased/errordocs/'.$code.'.html' );
exit();
}
sendErrorDocumentAndQuit(404);

there's no 302, little overhead but of course emulating some of these
errors should only be done with care, 500 for instance. You are
"lying" about Apache's _real_ state, which is 200/304 if Apache is
really OK.

You're right though, there isn't the tight integration with Apache API
that Perl has.

Using mod_security - which of course is an apache module, you can trap
any response body string - such as errors, or <?php etc... that you
consider should never be sent to the user, so it should be possible to
spark off an action which might result in a standard error page.

May 10 '07 #2
On May 10, 12:00 pm, shimmyshack <matt.fa...@gmail.comwrote:
well you /can/ do
sendErrorDocumentAndQuit($code)
That is basically what I meant with emulating the Apache behavior in
PHP. I would like to avoid that, mostly because, as I mentioned, some
errors cannot be intercepted at the PHP code level.

Using mod_security - which of course is an apache module...
Thanks for this hint, this looks pretty interesting.

May 10 '07 #3
On 10.05.2007 11:19 li******@gmail.com wrote:
>
I can actually have two separate status values, one that gets sent to
the browser (Apache2::RequestRec::status()), and one that is returned
to the Apache server (the handler() method's return value). Does
something similar exist in PHP? Or do I really have to replicate the
ErrorDocument functionality in my PHP code?
php module handler always returns OK (=200) to apache, no matter what
the script did. See for yourself:

http://lxr.php.net/source/php-src/sa..._apache2.c#487

I'm afraid, there's no way to change this behaviour in php code.
>
3.) While playing around with set_error_handler(), I also saw that
syntax errors are not trappable with a custom error handler. I use an
autoloader that loads classes on demand, and if one of the class files
loaded at run-time has a syntax error, my error handler is bypassed.
Combined with the inability to trigger ErrorDocuments described above,
doesn't this mean that it is absolutely impossible to hide such errors
from users by replacing them with a "friendly" error page when using
PHP?
Cleanup callbacks (output buffering, destructors, shutdown functions)
are still executed in case of fatals, you can use them to produce nicer
post mortem error message, e.g.

function check_fatals($buf) {
if(strpos($buf, 'Fatal'))
return 'pardon!';
return $buf;
}

ob_start('check_fatals');
include 'whatever.php';
--
gosha bine

extended php parser ~ http://code.google.com/p/pihipi
blok ~ http://www.tagarga.com/blok
May 10 '07 #4
On May 10, 5:35 pm, gosha bine <stereof...@gmail.comwrote:
php module handler always returns OK (=200) to apache, no matter what
the script did. See for yourself:
Thanks a lot, that is the sort of confirmation I wanted to hear.
That's really unfortunate, it would be useful if PHP would send 500 to
Apache in case of a PHP script error.
Cleanup callbacks (output buffering, destructors, shutdown functions)
are still executed in case of fatals
Interesting idea, I'll take a look at that.

Thanks again...

May 10 '07 #5

This discussion thread is closed

Replies have been disabled for this discussion.

Similar topics

1 post views Thread by gsb | last post: by
reply views Thread by gheharukoh7 | last post: by
By using this site, you agree to our Privacy Policy and Terms of Use.