jQuery.ajax() just receives an error, however jQuery.post() works - javascript

Debated whether to put this on WordPress.SE or here; decided that since it's primarily a jQuery question I'd post it here with the note that it occurred during WordPress development for context.
Long story short, following a guide on how to use AJAX in WordPress to the letter—including pasting in the same code excerpts to see if they run—doesn't work on my dev server. The designated PHP function is never executed, and the call just returns a 0 when I dump the response to a an output div.
I added an error: field to the AJAX call and that triggered, but other than revealing that there was an error, I couldn't figure out what was actually at issue.
Here's a look at the AJAX call, as shown in the guide.
jQuery.ajax({
type : "post",
dataType : "json",
url : myAjax.ajaxurl,
data : {action: "my_user_vote", post_id : post_id, nonce: nonce},
success: function(response) {
if(response.type == "success") {
jQuery("#vote_counter").html(response.vote_count)
}
else {
alert("Your vote could not be added")
}
}
})
Remembering having had this problem before, I decided to review an old project from a year ago, and found the following workaround, which seems to do the same thing, but actually returns the proper response from the script.
Functional workaround, does what is expected
var ajaxurl = '<?php bloginfo('url'); ?>/wp-admin/admin-ajax.php';
var data = {action: "my_user_vote", post_id : post_id, nonce: nonce};
// Handle any returned values
jQuery.post(ajaxurl, data, function(response) {
if(response.type == "success") {
jQuery("#vote_counter").html(response.vote_count)
}
else {
alert("Your vote could not be added")
}
});
Ostensibly, it seems that the latter is just a longwinded way of executing the former, but for some reason only the latter works. What could be causing the error on the first block?
EDIT: It seems this may be a WordPress problem after all. I've already sent the code I was working on the other night to production, so to reproduce it I put it into a plugin and tried to run it on the default theme. It's working on the front end, but it's not working when I take it to a back-end page (which is what I was working on at the time). According to the console, it appears to be an issue with enqueueing the scripts on the back end.
To mitigate that issue, I dumped the following on an otherwise blank back-end page:
This post has <div id='vote_counter'>0</div> votes<br>
<div id="output">Test</div>
<script>
jQuery(document).ready( function() {
jQuery(".user_vote").click( function() {
post_id = jQuery(this).attr("data-post_id")
nonce = jQuery(this).attr("data-nonce")
jQuery.ajax({
type : "post",
dataType : "json",
url : "<?php bloginfo('url'); ?>/wp-admin/admin-ajax.php",
data : {action: "my_user_vote", post_id : post_id, nonce: nonce},
success: function(response) {
jQuery("#output").html(response)
jQuery("#vote_counter").html(5)
},
error: function(response) {
jQuery("#output").html(response)
jQuery("#vote_counter").html(10)}
})
})
})
</script>
<?php
$link = admin_url('admin-ajax.php?action=my_user_vote');
echo '<a class="user_vote" href="' . $link . '">vote for this article</a>';
Long story short: There is no longer any external script to enqueue, the link is coded directly into it, and the count should update to 5 on success or 10 on failure (since this is a back-end page and therefore there's no page_id to check for). All extraneous data fields have been dropped, since they won't be used in this form.
To simplify generating the response, I trimmed the code back to just the following:
function my_user_vote() {
$result = array(
'status' => 'success',
'count' => 5
);
$result = json_encode($result);
echo $result;
die();
}
What now happens is we get redirected to a blank page with the JSON response dumped on it. Tried dropping in the .post() method from above and that's doing the same thing for some reason.
TL;DR: This probably needs a move to wp.se.

Related

Use Javascript array in PHP

I know this question has been asked before several times on this forum, but I think I am missing something. Or maybe it is because I don't know JSON/AJAX that well.
Here is the thing.
I got some javascript/JQuery code on a page, say on index.php, (not yet in a seperate JS file) which let you put any number in an array from 1 to 10. If it's already in it, it will be removed if clicked again.
Now I want to pass that JS array to PHP, so I can create tables with it.
Here's what I have done.
$(".Go").click(function() {
var enc = JSON.stringify(tableChoice);
$.ajax({
method: 'POST',
url: 'calc.php',
data: {
elements: enc
},
success: function(data) {
console.log(enc);
}
});
});
And in my calc.php I got this to get the values to PHP.
<?php
$data = json_decode($_POST['elements'],true);
echo $data;
?>
Now here comes the noob question:
If I click my (.Go) button, what really happens?
Because the console.log let's me see the correct values, but how do I access it? The page (index.php) doesn't automatically go to the calc.php.
When I use a <form> tag it will take me there, but it shows this error:
Undefined index: elements
I am sure I am looking at this the wrong way, interpreting it wrong.
Can someone please help me understand what it is I should be doing to continue with the JS array in PHP.
With a XHR request you don't do a page reload. With your $.ajax method you post data to the server and receive information back. Since you can see information in your console, the success method is triggered.
You might want to take a look at your DevTools in for example Chrome. When you open your Network tab and filter on XHR you see what happens. You can inspect your XHR further by looking into the data you've send and received.
So my question to you is: what do you want to happen onSuccess()? What should happen with the data you receive from your backend?
In JavaScript:
$(".Go").click(function() {
var enc = JSON.stringify(tableChoice);
$.ajax({
method: 'POST',
url: 'calc.php',
data: {
"elements="+enc;
},
success: function(data) {
console.log(data);// You can use the value of data to anywhere.
}
});
});
In PHP:
<?php
if(isSet($_POST[elements]))
{
$data = json_decode($_POST['elements'],true);
echo $data;
}
else
{
echo "Elements not set";
}
?>

Create JSON in javascript and create a file on webserver via ajax and php

I've searched and read all I can find on the subject but can't get it to work at all.
I'm creating an array in javascript and then trying to use ajax to send to a php so it creates a json file on the webserver. Sorry if the lingo is off but this is my first attemp at working with ajax and php.
The array looks something like this but with more elements, i think the [] might cause a problem but I have no idea how to get rid of them....
[{"elementId":"ID","elementValue":"VALUE","elementType":"text","legendActive":"false"}]
Here's the code i have, I'm not sure the path is correct but I tried many different variations with no success...
Javascript and ajax...
function saveUserInputs(){
var userSettings=[];
inputs=$('form').find(':input:not(:submit), fieldset');
inputs.each(function(){
if (this.id.length>0){
var elementId=$(this).prop('id');
var elementValue=$(this).val();
var elementType=$(this).prop('type');
var elementChecked=$(this).prop('checked');
var legendActive=$(this).hasClass('disabled-legend-element');
userSettings.push({elementId: elementId, elementValue: elementValue, elementType: elementType, elementChecked: elementChecked, legendActive: legendActive});
};
});
$.ajax({
type : "POST",
url: "http://www.lacomptabilite.ca/public_html/test.php",
dataType : "json",
data : { "json" : JSON.stringify(userSettings)},
success: function (data) {alert(data); },
error: function() {alert("Error!");}
});
};
PHP, which is located in the public_html folder on the server...
<?php
$json = $_POST['json'];
if (json_decode($json) != null) { /* sanity check */
$file = fopen('new_map_data.json','w');
fwrite($file, $json);
fclose($file);
} else {
// handle error
echo 'empty';
}
?>
I can't even get the success or failure functions to work. Any one have an idea of what I'm doing wrong?
EDIT: Moved all my files over to the web server as suggested but still getting a 403 forbidden error. When I check the port for the php file it's 80 and when I check it from JS it's blank, could that be the problem?
EDIT #2: Turns out it had nothing to do with a communication or permissions problem. Problem what one of the string elements I was sending over was {"id":"panelProfile","value":null,"type":"select-one"} and for some reason ajax or php don't like having the word "select" in the json file. Changed it to "combobox" and everything works fine.
Properly you should use jQuery functions serialize, fix the userSettings and replace with this code
var userSettings = $('form').serialize();
FU ERROR 403!
As per my edit here's what I found with updated working code. Error 403 can be caused by a number of things which are not obvious, one seems to be file size and another which was my problem was using the word 'select' within my json file. I think this might have to do with the fact it's a reserved word related to SQL but I'm not 100% sure all I know is it didn't work!
If you're sending files cross domain you need to add this to javascript...
$.support.cors=true;
...and this to $.ajax...
crossDomain: true,
Here's the complete code that worked for me... I added 2 different urls for information purposes only, one is for cross domain path and the commented out one is if all your files are on the same domain, port and protocol. If that's the case you don't need $.support.cors=true; and crossDomain: true,
AJAX:
$.support.cors=true;
$.ajax({
crossDomain: true,
method: "post",
//url: "/php/userJson.php",
url: "http://www.yourDomain.com/php/userJson.php",
dataType: "json",
data: {"json" : userSettings},
success: function (suc) {alert (JSON.stringify(suc))},
error: function(error) {alert (JSON.stringify(error))}
});
Here's the php code, I left some commented out lines that I found useful for trouble shooting purposes.
PHP:
<?php
//echo $_SERVER["HTTP_HOST"];
//echo $_SERVER["REQUEST_URI"];
//echo $_SERVER["SERVER_NAME"];
//echo $_SERVER["SERVER_PROTOCOL"];
//echo $_SERVER["REQUEST_METHOD"];
//echo $_SERVER["QUERY_STRING"];
//echo $_SERVER["HTTP_REFERER"];
$json=$_POST['json'];
if (json_decode($json) != null){
$file=fopen('user_data.json','w+');
fwrite($file, $json);
fclose($file);
}else{
echo "empty";
}
?>
EDIT: ADDED CODE TO RETRIEVE FILE FROM SERVER...
$.ajax({
crossDomain: true,
method: "GET",
url: "http://www.yourDomain.com/php/user_data.json",
dataType: "json",
success: function (success) {alert (JSON.stringify(success))},
error: function(error) {alert (JSON.stringify(error))}
});

Check if Cross Domain RSS has changed using Ajax

I have a website which loads a RSS news feed http://www.tagesschau.de/xml/rss2
I want to check every 60 seconds if the RSS feed has been updated. If it has changed it should reload the RSS feed. With Ajax I thought it would work great, though I am stuck here:
<script type="text/javascript" src="../js/jquery.ajax-cross-origin.min.js"></script>
<script type="text/javascript">
function checkRSS() {
$.ajax({
crossOrigin: true,
type: 'GET',
proxy: "../php/proxy.php",
url: "http://www.tagesschau.de/xml/rss2",
dataType: "xml",
success: function (xml) {
//console.log(xml);
},
error: function(xml) {
console.log(xml);
}
});
}
setInterval("checkRSS()", 60000);
</script>
(I commented the success event console.log to see if Ajax would trigger the success or error event. It triggered the error event.)
In the console I get status: 200, readyState: 4 and statusText: "success".
Does anybody know why the error event is triggered? I checked the url through http://jsonlint.com. It does load the list but gives me an error. Is this the problem?
Ajax-Cross-Origin plugin: http://www.ajax-cross-origin.com/how.html#js-what-is-this-plugin
EDIT
I added a proxy php file from the Ajax-Cross-Origin plugin (and added its link in the Ajax code above):
<?php
$url = (isset($_GET['url'])) ? $_GET['url'] : false;
if(!$url) exit;
$referer = (isset($_SERVER['HTTP_REFERER'])) ? strtolower($_SERVER['HTTP_REFERER']) : false;
$is_allowed = $referer && strpos($referer, strtolower($_SERVER['SERVER_NAME'])) !== false;
$string = ($is_allowed) ? utf8_encode(file_get_contents($url)) : 'You are not allowed to use this proxy!';
$json = json_encode($string);
$callback = (isset($_GET['callback'])) ? $_GET['callback'] : false;
if($callback){
$jsonp = "$callback($json)";
header('Content-Type: application/javascript');
echo $jsonp;
exit;
}
echo $json;
?>
Maybe a stupid question, but should I change HTTP_REFERER and SERVER_NAME into something?
What happens now is that the success event is triggered -YES!- but the outcome of its log contains nothing more then " ".
Cross Site Scripting policies will make this tricky... your best bet is probably to use a 3rd party API such as Superfeedr or Google Feed API.
The benefit of this is that they will handle the load from you and will still be able to retrieve updates from the original feed pretty quickly.

My ajax call not pulling in dynamic data from PHP/Mysql

Hello: I am working on a project where I am going to have divisions from a league listed as buttons on a page. And when you click on a button a different team list shows for each division. All divisions and teams are stored in a mysql database and are linked together by the "div_id". The plan was have the buttons use javascript or Jquery to send the 'div_id" to a function; which would then use ajax to access an external php file and then look up all the teams for that division using the div_id and print them on the page. I have been piecing this all together and getting the various pieces to work. But when I put it all together; it seems like the ajax part - does not pull in fresh data from the database if the data is changed. In fact, if I change the PHP file to echo some more data or something, it keeps using the original unaltered file. So, if the data is changed that is not updated, and if the file is changed that is not updated. I did find if I actually copied the file with a new name and then had my ajax call use that file instead; it would run it with new code and the new data at that time. But then everything is now locked in at that point and cannot get any changes.
So - I do not know much about ajax and trying to do this. I am not sure if this is totally normal for what I am using and for a dynamic changing team list, it cannot be done this way with ajax calling a PHP file.
OR - maybe there is something wrong with the ajax code and file I have which is making it behave this way? I will paste in the code of my ajax code and also the php file…
here is the ajax call:
var answer = DivId;
$.ajax({
type: 'GET',
url: 'path_to_file/gscript2.php',
data: 'answer=' + answer,
success: function(response) {
$('#ajax_content').html(response);
}
});
and here is the script.php file that it calls (removed db credentials):
<?php
if (!empty($_SERVER['HTTP_X_REQUESTED_WITH'])
&& strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest'
) {
// AJAX request
$answer = $_GET['answer'];
$div_id=$answer;
echo "div id is: " . $div_id . "<br/>";
mysql_connect($hostname,$username, $password) OR DIE ('Unable to connect to database! Please try again later.');
mysql_select_db($dbname);
$result_g1 = mysql_query("SELECT * FROM teams WHERE div_id=$div_id");
while($row = mysql_fetch_array($result_g1, MYSQL_BOTH))
{
$team_id=$row[team_id];
$team_name=$row[team_name];
echo $team_id . " " . $team_name . "<br/>";
}
}
?>
So - to sum up - is there something wrong with this making it do this? Or is what it is doing totally normal and I have to find a different way?
Thanks so much...
Most likely your browser is caching.
Try adding cache: false as such:
$.ajax({
cache: false,
type: 'GET',
...
The jQuery documentation explains that by doing so, it simply adds a GET parameter to make every request unique in URL.
It works by appending "_={timestamp}" to the GET parameters.
I believe this is caused by your browser's cache mechanism.
Try adding a random number to the request so the browser won't cache the results:
var answer = DivId;
$.ajax({
type: 'GET',
url: 'path_to_file/gscript2.php?r=' + Math.random(),
data: 'answer=' + answer,
success: function(response) {
$('#ajax_content').html(response);
}
});
Or turning jQuery's caching option off by:
var answer = DivId;
$.ajax({
type: 'GET',
url: 'path_to_file/gscript2.php',
data: 'answer=' + answer,
success: function(response) {
$('#ajax_content').html(response);
},
cache: false
});
Or (globally):
$.ajaxSetup({ cache: false });

Sending data from javascript to php using via Ajax using jQuery. How to view the data back?

I know this question has been asked a lot as I have been googling since morning but I just can't think what's going on in my code.
I have a index.php (which is my website) that uses forms to receive information from user, then invokes a javascript file separately which in turn invokes another backend php file (this backend php file queries a database using mysql and does some stuff).
The problem is I am not sure what information is getting passed to the backend php from my js. I have just learnt jQuery and Ajax so I really don't know what is that small mistake I am making.
From my understanding, the backend php does its stuff and passes the value to javascript to be displayed on the web page. But my data is not getting sent / displayed. I am getting a error 500 internal server error.
Here are the pieces of code that are currently is question:
Javascript:
var data1 = {week:week, group:grp_name};
$.ajax({
dataType: "json",
type: "POST",
url : "php/remindUsers.php",
success : function(response){
alert ("success !");
},
error : function(response){
console.log(response);
alert("fail!");
}
})
});
PHP backend (remindUsers.php):
<?php
if (isset($_POST['week'])) {
$week = $_POST['week'];
}
if (isset($_POST['group'])) {
$group_name = $_POST['group'];
}
echo $week;
?>
I am ommiting out the sql code pieces because they work fine.
Edit: Now my status code is 200, response text is also ok . My response text shows a weird "enter' sign next to the actual response text expected. Is this normal ? And it is still going into the error block , not the success block of code.
I can not fully answer your question because I need more debug information about whats going on but theres 2-3 things about your code bugging me a little that might fix your bug.
First, use isset in your backend like this:
if (isset($_GET['your_input_name'])) {
$someData = $_GET['your_input_name'];
}
The isset part is very important here. Set it up and try it again. If you stop having a 500 error. Its probably because your data was never send to your backend or because your not checking the good input name.
Second, About input name. I can see in your code that you send:
var data1 = {week:week, group:grp_name};
So in your backend you should use the name of the value like this to retrieve your data:
$week = $_POST("week");
Third, I am not a json pro but maybe your json is not valid. Even if he is ok I suggest you build a "cleaner" one like this:
var data = [
{ 'name' : 'week', 'value' : week}
];
And finally, if you are using forms to send data to php then you can use something like that :
var myForm = $("#myForm").serializeArray();
$.ajax({
url: 'yourUrl',
type: "GET",
data: myForm,
dataType: 'json',
success: function(res){
//your success code
},
error: function(){
//your error code
}
});
I hope this helps.
You can't have these tags <body>,... in your PHP response over json.
It must be only:
<?php
$week = $_POST("data");
$json = json_decode($week);
echo json_encode($json);
?>
Remove the comment on
//data : {week :week}
And set a variable week with a valid value:
data : {week :week}
and so:
$.ajax({
dataType: "json",
type: "POST",
url : "php/remindUsers.php",
data : {week :week} ,
success : function(response){
console.log(response);
},
In order to see what is the shape of response.
You are doing a couple things wrong. First, you don't want to stringify your data before sending it to the server. You want to send JSON, so your commented line is the correct one. There is also a problem with the PHP. The data going to the server will look like:
{week: "Something"}
So in your PHP, you want to access the data like:
$_POST["week"];
USE THIS
PHP
$week = $_POST['data'];
$json = json_encode($week);
echo $json;
JS
$.ajax({
dataType: "json",
type: "POST",
url : "php/remindUsers.php"
//data : {week :week} ,
data: {data:{week:'week', group:'grp_name'}} ,
success : function(response){
alert ("success !");
},
error : function(response){
alert("fail!");
}
})
I would say wrap the php in a function and echo the json. Also its good to check if there was POSTed data, and if not return an error message. This is not tested, but will hopefully point you in the right direction.
<?php
function getJSON() {
if (isset($_POST["data"] && !empty($_POST['data']) ) {
$week = $_POST["data"];
$json = json_decode($week);
echo $json;
} else {
echo "There was a problem returning your data";
}
}
getJSON();
?>
Actually as I write this, I realized you could try these headers in your AJAX POST:
accepts: 'application/json',
contentType: 'application/json',
dataType: 'json'
Hope that helps.
It worked. I figured out the answer thanks to another SO post.
TIL : Even if server response is ok, the error condition will be triggered because the data returned to javascript from php is not json,since i had explicitly mentioned dataType: "json" in the ajax request.
Link here:
Ajax request returns 200 OK, but an error event is fired instead of success
Thanks folks for helping me and steering me in the right direction. Cheers!

Categories

Resources