jQuery AJAX HTTP error codes not being picked up in Safari - javascript

I'm using jQuery.ajax() to send data to my own PHP file for adding subscribers to a MailChimp list. The Javascript looks like this:
$.ajax({
url: url,
method: 'POST',
data: params, // the data is working so here is just the variable I'm using
error: function(response) {
console.error($.parseJSON(response));
// show some response text through DOM manipulation
}, success: function (response) {
console.log($.parseJSON(response));
// show some response text through DOM manipulation
}
});
The PHP looks like this (at least just for the HTTP status code response):
// All my PHP code, which is working is above this
$result = curl_exec($ch);
echo $result; // This is for the response text in the ajax call
http_response_code(intval(json_decode($result)->status)); // This should be sending a success code or triggering errors
On Chrome, if I get a good response (a HTTP status in the 200s), the success function will run. If I trigger an error (in my testing, a HTTP status in the 400s), the error function will run. All is good.
However, on Safari, whether it is a 200 or a 400 code, the success function runs. There seems to be no detection in my Javascript of error codes when using the Safari browser. How can I fix this? Why is it different between Chrome and Safari?
In case it matters, I'm working locally with CodeKit and MAMP PRO to run my project. Thanks.

You need to send the response code before the actual response, i.e.,
$result = curl_exec($ch);
http_response_code(intval(json_decode($result)->status)); // This should be sending a success code or triggering errors
echo $result; // This is for the response text in the ajax call
This is because http_response_code is essentially running a header("HTTP/1.0 $code $codeMessage") and the header needs to be sent before the response.

Related

Using ajax long polling to update a response on my page from an external API

I have the following ajax long polling script
(function poll(){
$.ajax({ url: "<?php echo URL::to('/internal/v1/checkTxn'); ?>", success: function(data){
//Update your dashboard gauge
console.log(data.status); //Data is getting logged
if(data.status == 'success'){ //This condition is not being checked
console.log('suucesful'); //Not coming
}
}, dataType: "json", complete: poll, timeout: 1000 });
})();
The backend PHP code is as follows
if(isset($_POST['status']) && $_POST['status']){
$data = ['status'=>$_POST['status']];
$json = json_encode( $data );
echo $json;
}
Flow
When I render the page, the ajax script runs and waits for response. When I checked the network tab, ajax was endlessly making requests to the URL specified.
I get a form post from an external website to the backend PHP which I need to push to the jquery.
But when a post is happening, nothing is being logged in the console. But if I hard code some values in the $json and echo it, its coming up in the console.
I am facing two issues
When a post happens on the PHP script, its not coming up in the ajax code.
When I hard code (simulated the response posted by the external form post) the $json and echo it, its coming up in the console, but the condition for data.status== 'success' is not getting checked.
What is wrong in this. Am I missing something?
UPDATE
I could fix the "condition not being checked" as there was something wrong the json being echoed.
Now to avoid confusion, the flow for this
User open the page,
> The ajax starts the long polling process to my PHP code, waiting for a
> response.User enters payment details in a form which is my html,clicks on pay, a pop up appears
> which renders the banks login page (Payment gateway).After user entering all
> details in the pop up (banks page), bank sents a server to server call about the status of
> transaction to my notificationURL
> ('mydomain.com/internal.v1/checkTxn'). As soon as I get a POST on this
> URL(I will close the pop up), my ajax polling should get the data posted to my PHP and there by
> I will show the status of TXN to the user on the same card form he entered his details earlier and
> the pop window closes. The response here is returned by my PHP code to the ajax.
The
> post coming to my PHP code is a server to server post which is posted
> by a Payment Gateway.
1. let's debug this:
set your ajax error call back,
$(function(){
(function poll(){
$.ajax({ url: "http://tinyissue.localhost.com/test.php", success: function(data){
//Update your dashboard gauge
console.log(data.status); //Data is getting logged
if(data.status == 'success'){ //This condition is not being checked
console.log('suucesful'); //Not coming
}
},error:function(err){
console.info('error fired...');
console.info(err);
}, dataType: "json", complete: poll, timeout: 1000 });
})();
});
run this, you will get console
error fired...
Object {readyState: 4, responseText: "", status: 200, statusText: "OK"}
2. Why went to error callback:
Why ajax response status is 200 and statusText is "OK" , error callback still fired instead of success?
Your AJAX request contains the following setting:
dataType: "json"
The documentation states that jQuery:
Evaluates the response as JSON and returns a JavaScript object. (...)
The JSON data is parsed in a strict manner; any malformed JSON is
rejected and a parse error is thrown.
This means that if server returns invalid JSON with a 200 OK status then jQuery fires the error function and set the textStatus parameter to "parsererror".
Solution: make sure that the server returns valid JSON. It is worth noting that an empty response is also considered invalid JSON; you could return {} or null for example which validate as JSON.
3. Why ajax return invalid JSON:
In your mind, at server side, you checked the $_POST['status'] to make sure last call success in the loop poll, only $_POST['status'] is set, you will echo json, or it echo nothing.
But, unfortunately, at the beginning of the call loop, the first time the ajax called, you didn't set status to post. Then it echo nothing, then it went error callback, also went complete callback, then call again without status to post. See, it went a bad cycle.
4. Solution:
Set a status value to post at the first ajax call.
$(function(){
(function poll(){
var status = 'success';
$.ajax({ url: "http://tinyissue.localhost.com/test.php", success: function(data){
//Update your dashboard gauge
console.log(data.status); //Data is getting logged
status = data.status;
if(data.status == 'success'){ //This condition is not being checked
console.log('suucesful'); //Not coming
}
},error:function(err){
console.info('error fired...');
console.info(err);
status = 'error';
}, type:'post',dataType: "json", data:{status:status}, complete: poll, timeout: 1000 });
})();
});
If you are using long polling, you could have a cache issue.
First, when your post comes to your system, check that checkTxn changes.
Last, you can add a random parameter (by adding date in millis, for example) in url query, you will not use it, but your server will think your requests are different.
Please, check it and let us know.
#Edit: Sure #Ajeesh, I'll explain it:
(function poll(){
$.ajax({ url: "<?php echo URL::to('/internal/v1/checkTxn'); ?>?_ts=" + new Date().getTime(), success: function(data){
//Update your dashboard gauge
console.log(data.status); //Data is getting logged
if(data.status == 'success'){ //This condition is not being checked
console.log('suucesful'); //Not coming
}
}, dataType: "json", complete: poll, timeout: 1000 });
})();
By doing this, cache will not be used, because all queries are different for your server/browser.
On the other hand, I ask you for any changes in your page when you receive the POST, so, if not, your ajax will never receive the notification, do you know what I mean?

Why php json response does not send back the data array to ajax jquery request?

I have made an ajax request to the php server where I send a data from a form request and I would to get back the same data from the server just for testing requests and responses of the same data throwing between the client and the server.
$.ajax({
method: "POST",
url: "addRaces",
dataType: "json",
data : sending_data,
success : ...
})
sending_data is an array like {field_form_name : value}
The server responds to the request with the following code :
$data = [];
foreach ($request->Input() as $key => $value) {
$data[$key] = $value;
}
return json_encode($data);
The same data should come back to the client, but nothing happen with an alert(response) or a jquery showing debug data like $('#debug').html(response);
The strange thing coming up when I try to push the server answer like
return json_encode([
'debug' => $data['name']
]);
and showing results to client like
$('#debug').html(response.debug);
it is working for a single key-value response showing the properly value field I have send from the client.
Other wise whether I send the full data as an array nothing is shown in the debug area of the client.
return json_encode($data); wont work. as it is returning the json string to the calling method which is not your jQuery at front end. Don't confuse front end (html javascript, jQuery, etc...) with back end (PHP) the two of them are running in different machines. One at client end and another at your server.
you should use echo json_encode($data); this will output the json string and your web server will send it to the front end.
Make sure you are echoing the data not returning as #bansi said, if you are echoing it already then debug using var_dump(json_encode($data)) . If json_encode() found errors it will return False instead of the expected json array.
You should debug using the developer tools instead of using code $('#debug').html(response.debug);. The Network tab of developer tools is very useful to debug HTTP requests, it will show response header and body of your requests.
In your case, just change return to echo like #bansi's answer. The return command does not print the data so you did not get anything in the response.

Using AJAX to call a php function keeps failing

im having a problem trying to get an ajax call to trigger a php function and then return successfully. As far as i can see my syntax is correct.
But all i get back is failed! Any ideas?
EDIT
I have changed my AJAX request to send without using data, just to rule out that being a problem and i have implemented some of the things people suggested below but to no avail, heres what my 2 files look like now:
ship.js:
function set_ship()
{
//var datastring = {'ship':'true'};
$.ajax({
type:'POST',
url:'soap/classes/class.ship.php',
success: function(success){
alert('success');
},
error: function(fail){
console.log(fail);
}
});
}
And my PHP class.ship.php:
<?php
var_dump("hello");
header('Content-type: application/json');
echo json_encode(array("result"=>"true"));
From the var_dump on my PHP script i can see that the class.ship.php isnt even being called for some reason.
Thanks
Please try this
json_encode(array("result"=>"true"));
because
json_encode(true) // will return just "true" which is not a valid json
Also try serializing the dataString , by doing
data: datastring.serialize();
lowercase JSON_ENCODE
success: function(success), error: function(fail)
check what is returned in network tab of firebug.
You need to set the content header to json header('Content-type: application/json'); and make sure you request return only json coz ajax is waiting only for "JSON" and it will throw parse error
if(isset($_POST['ship']) && $_POST['ship'] == "true"){
$result = "result";
header('Content-type: application/json');
echo json_encode(true);
}
I would suggest that you check what it being actually returned by the server.
The error callback receives one argument representing the xhr object, so you can inspect that directly by placing a breakpoint or using console logging, like this
error: function(xhr) {
console.log(xhr);
}
Likewise, the success callback receives three parameters: the status, the returned data and the XMLHTTPRequest Object, so you can check those in the very same way:
success: function(status, data, xhr) {
console.log(status, data, xhr);
}
You should look for the response status code and the response text in the xhr object to understand what is going wrong. If you're seeing a 200 OK response status, the data returned from the server is probably not being interpreted correctly as JSON data, so you should try setting the response header server side to application/json.
An error might occur also if something else is appended or prepended to your response. This happens especially when warnings occur in the code before returning and you have error reporting set to ON.

Ajax in Codeigniter doesn't work for a specific controller in remote host

My web application does Ajax request to a Codeigniter-php code in a remote server. It works in localhost but not with a specific controller in remote host. It is strange because works in localhost for both controllers.
The request:
$.ajax({
async:true,
type: "POST",
dataType: "json",
url:"/CI/site/index.php/contact/submitContact",
data: "", //data example
success:arrived,
error:problems });
function arrived(data){
var dataJson = eval(data);
}
function problems(){
$("#result").text('Problems.');
}
I check the arrived with log_message. With the next function works fine:
function submitContact(){
log_message('error', 'submitContact. ');
//If data are received
if($_POST){
log_message('error', 'data. [application/controllers/contact.php]');
}
}
However, If I change the request to url:"/CI/site/index.php/control/controlHome", there isn't any log message and the output is the next:
POST http://www.page.com/CI/site/index.php/control/controlHome 500 (Internal Server Error)
The function /application/controllers/control.php is the next:
function controlHome(){
log_message('error', 'controlHome. [application/controllers/control.php]');
//If data are received
if($_POST){
log_message('error', 'data. [application/controllers/control.php]');
}
}
Also I've tried with complete url in the ajax code but the result is the same. Any setting is required?
Check this AJAX csrf protection with codeigniter 2. This solve my same problem
http://aymsystems.com/ajax-csrf-protection-codeigniter-20
UPDATE:
I checked your control.php file on my test server.
if($_POST) { /* i only commented gangway library functions */
} else { /* only replace the load->view with an print_r $data; and its work */ }
And put to comment the gangway library on construct. And control/controlHome works normaly without any error. Check your gangway library THAT's cause error 500.

Ajax call from Greasemonkey to a Servlet: response failure

Though I've programming experience, am completely new to GS, JS, or anything related to UI.
Scenario: Making an AJAX call from Greasemonkey script to a Servlet
Greasemonkey/JS Code:
function getResultsData(query){
alert("Getting the Data");
$.ajax(
{
cache: false,
data: {"q":query},
dataType:"text",
url: "http://myserver.com:8000/search?",
success: processData
}); //end of $.ajax }
function processData(data){
alert("Got the data");
var myResultDiv = document.getElementById("searchRes");
myResultDiv.innerHTML = data; }
Servlet Code:
System.out.println("-----------This is an AJAX call------------------");
//Commented the original logic
resp.setContentType("text/plain");
resp.setCharacterEncoding("UTF-8");
resp.getWriter().write("Text from Servlet");
Problem:
GS/JS code works perfectly if the url (in $.ajax) is some other existing API. Response reflects in the UI
However, when I give my server's url, I can observe in the Firebug.Console that there's no http response for that call but the status says 200 OK with the whole entry turned 'RED'.
When I test the url copied from Firebug's 'http call entry', it's working perfectly as I can see the response 'Text from Servlet' on the new tab.
Can someone please help.
NOTE Website on which greasemonkey runs, and my server belong to same domain, i.e.
Greasemonkey website: wwww.example.com
My server: www.myserver.example.com
Thanks to #mattedgod. His comment triggered me to research more and I found the answer.
Add the following snippet to make it work.
response.setHeader("Access-Control-Allow-Origin", "*");
Surprisingly, it doesn't work if I explicitly specify my own server's full http address in the header. I yet to find out why.

Categories

Resources