In a page, test.php, I simply activate error reporting, I deactivate the logging, and I call a function test(), which does not exist. As expected, if I run the code I receive the error message:
(!) Fatal error: Uncaught Error: Call to undefined function test() in [path-to]/test.php on line 7 (!) Error: Call to undefined function test() in [path-to]/test.php on line 7 Call Stack # Time Memory Function Location 1 0.1336 355848 {main}( ) .../test.php:0
Now, in another page, index.php, I have only a button - named testButton. If I press it, an ajax request to the page test.php is performed. In index.php I expected to see that:
test.php is handled by the error callback of the ajax request;Unfortunately none of this happens. When I press the button:
success callback of the ajax request is called;Could you help me find the problem, or identify the bug?
Thank you.
Used system:
test.php:
<?php
error_reporting(E_ALL);
ini_set('display_errors', 1);
ini_set('log_errors', 0);
$data = test();
index.php:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="viewport" content="width=device-width, initial-scale=1, user-scalable=yes" />
<meta charset="UTF-8" />
<!-- The above 3 meta tags must come first in the head -->
<title>Test: Displaying Errors</title>
<script src="https://code.jquery.com/jquery-3.3.1.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function () {
$('#testButton').click(function (event) {
$.ajax({
method: 'post',
dataType: 'html',
url: 'test.php',
data: {},
success: function (response, textStatus, jqXHR) {
$('#result').html('Successful test... Unfortunately :-)');
},
error: function (jqXHR, textStatus, errorThrown) {
/*
* When an HTTP error occurs, errorThrown receives the textual portion of
* the HTTP status, such as "Not Found" or "Internal Server Error". This
* portion of the HTTP status is also called "reason phrase".
*/
var message = errorThrown;
/*
* If a response text exists, then set it as message,
* instead of the textual portion of the HTTP status.
*/
if (jqXHR.responseText !== null && jqXHR.responseText !== 'undefined' && jqXHR.responseText !== '') {
message = jqXHR.responseText;
}
$('#result').html(message);
}
});
});
});
</script>
</head>
<body>
<h3>
Test: Displaying Errors
</h3>
<div id="result">
Hier comes the test result. Since an error is thrown, I expect it to appear hear.
</div>
<br/>
<form method="post" action="">
<button type="button" id="testButton" name="testButton">
Start the test
</button>
</form>
</body>
</html>
The success and error functions in your jQuery AJAX call simply checks for the HTTP status code for the request. When PHP produces errors it does not change the status code, and so jQuery triggers the success function. If you want to use the jQuery error, you will have to change the status code. You can do this by catching the Error (PHP >= 7):
try {
$data = test();
}
catch (\Error $e) {
http_response_code(500);
echo $e->getMessage();
}
Or you could keep the status code as 200 (default) and send your response in JSON including the success and error properties you like, as well as any other things you may want to return with the request.
header('Content-type: application/json');
$response['success'] = true;
$response['error'] = null;
try {
$data = test();
}
catch (\Error $e) {
$response['success'] = false;
$response['error'] = $e->getMessage();
}
echo json_encode($response);
And make sure to remove the dataType property from the ajax request to let jQuery automatically determine the type header.
If your program is throwing errors unexpectedly, this probably means you're doing something wrong. If you expect it to throw errors, you need to catch them. This either means wrapping things in try/catch blocks or a combination of set_exception_handler(), set_error_handler() and register_shutdown_function() to accomplish this globally.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With