I'm building a forum and I use this code to load all the comments forum_retrieve.php and this works fine at this point.
$(document).ready(function() {
$('#results_holder').load('forum_retrieve.php<? echo ' ? forum_id = ' . urlencode($forum_id) ?>').show();
});
But when a user submits the form to forum_handle.php (to save the comment to sql) and gets redirected back using:
if ($connect->query($sql) === TRUE) {
header('Location: forums.php?id=' . $_POST['forum_id']);
} else {
the Ajax wont load the new results, even if I submit 5 comments, they wont load until I refresh the page or click on another page and come back.
I have even tried putting the ajax on a time delay of 30 seconds and it still wont load the new results even though I can see it in sql before the timer is up.
I have tried using no caching headers. I have also tried $(window).ready.
Shouldn't a new query be made every time the document is loaded?I don't get why its choosing not to. Any suggestion will be greatly appreciated.
First things first: load() is not intended to be used as you imagined, not at all. It just fires a function when your $('#results_holder') is loaded. That's it. You are passing no function there, hence you get no result.
Then, as pointed out by Daniel, the load() function is fired only once, as soon as the document is ready. Then the script stops to run, so there's no chance for it to work as you want it.
What you want to do is to fetch, from time to time, the content from forum_retrieve.php and display it in a proper container.
Try something like this:
$(document).ready(function() {
var forumID = '<?= urlencode($forum_id) ?>';
setInterval(function() {
$.get({
url: 'forum_retrieve.php',
data: {forum_id: forumID}
})
.done(function(data) { $('#results_holder').html(data); });
}, 10000);
});
This fires a function every 10000ms (= 10sec) to retrieve the content from forum_retrieve.php and inject it into the $('#results_holder') element. Let me know if it works!
Related
Preface
For this question, I have a MVC partial view. The view has a section which displays a list of documents. Each document has a hyperlink: when clicked, the hyperlink takes the user to a second page view displaying additional information.
The link is inside an unordered list:
<a style="text-decoration:underline;" onclick="sendToDocketSearch('#currentDocument.DktYear','#currentDocument.DktSequence','#currentDocument.DktSubActionID');">#currentDocument.DktYear.ToString().PadLeft(2, '0') - #currentDocument.DktSequence.ToString().PadLeft(5, '0')</a>
When the user clicks the link, it takes them to a sendToDocketSearch javascript function (to prepare to search for the document):
var sendToDocketSearch = function (yearOfDocket, sequenceOfDocket, dktSubActionIDOfDocket) {
jQuery.ajax({
type: "POST",
url: "#Url.Action("DocketSearchOnDemand")",
dataType: "json",
contentType: "application/json; charset=utf-8",
data: JSON.stringify({ docketYear: yearOfDocket,
docketSequence: sequenceOfDocket,
DktSubActionID: dktSubActionIDOfDocket,
userIsAuthorized: '#Model.userIsAuthorized' }),
success: function (data) {
alert(data);
},
failure: function (errMsg) {
alert(errMsg);
}
});
submitForm();
}
Note that the page/view/form is submitted after the following controller method is run:
public ActionResult DocketSearchOnDemand(string docketYear, string docketSequence, decimal DktSubActionID, bool userIsAuthorized, PortalIndexView viewmodel)
{
System.Web.HttpContext.Current.Session.Add("userIsAuthorized", userIsAuthorized);
string docketSearch = docketYear + "-" + docketSequence;
System.Web.HttpContext.Current.Session["DocketSearchOnDemand"] = docketSearch;
if (DktSubActionID > 0)
{
System.Web.HttpContext.Current.Session["DktSubActionID"] = DktSubActionID.ToString();
System.Web.HttpContext.Current.Session["searchingCustomID"] = true;
}
else
{
System.Web.HttpContext.Current.Session["DktSubActionID"] = "1";
System.Web.HttpContext.Current.Session["searchingCustomID"] = false;
}
return View(viewmodel);
}
The above controller method runs; then, because the form is submitted, the HttpPost action for the page takes place. When running it on my local PC, the link is clicked and the next page is loaded without drama.
Problem
The problems start when I upload the code to the dev/test server. I don't know how to use breakpoints while troubleshooting an active website, so I follow along with the browser developer tool to monitor network traffic.
When clicking the link when running the website on my localserver, the process continues:
the hyperlink takes me to a method where I pass information to be searched
the page/view/form is submitted
the controller redirects where I have to go.
When I click the link on the site and it's on the server, the first click is completely ignored - network traffic shows that it tries to navigate to the controller via the javascript function above, but the failure happens so fast I can't even take a screenshot of it. The page reloads a second time at this point.
When I click on the same link a second time, it works without fail.
I believe the view/javascript/controller code works because it works the second time (and on subsequent attempts). It just flagrantly fails the first time on the server; after that, the user is fine. I'd like to prevent that "first-time" failure, however, and I'm wondering what the problem could be...
Bad timing
I may be passing the information too early (or too late for my website/server to process it properly). The page does it correctly the second time, so maybe I'm just "jumping the gun" by not waiting a little longer for page-loading processes to sort themselves out. (Maybe I can fiddle around with the $(document).ready() javascript portion of the first page to "delay" allowing people to click a link.)
Code error
I'll be glad to admit bad code if I'm genuinely messing something up. Maybe it's my javascript function, or maybe it's the code in my controller; at any rate, something is making the first pass of that function call be rejected. Maybe my code is bad because the problem doesn't happen the second time, and I'm getting a false sense of security (i.e. there are problems with my code that the system is willing to forgive after the page has thoroughly loaded).
Server problem/miscellaneous
I'm wondering if I missed something when I uploaded my latest changes, or if I should have contacted my network team in case there are permissions that need to be activated for the site to work smoothly. I'm already in touch with them regarding something else, so I might take advantage of the opportunity today.
There is an alternative in place that could help me prevent this problem from happening, but I want to find out why the "first-time" failure happens. Other similar actions fail the first time on the site, and I'd like to apply the insights from fixing this issue to them.
Thank you for looking at this issue. Have a great day.
Are you sure you want to call submitForm(); before your jQuery.ajax has finished? your ajax call is async so it will hit submitForm(); before it has had time to finish. should submitForm(); be in your success event instead?
Hi so i am getting a cookie passed in from another website which brings in some data i need to put in the query string.. i know how to put it in the query string that's not my questions.
My question is what jquery function can i use onpage load which will redirect to the query string.. now i don't want to page to load twice i want this to happen and look like it has only loaded once. I have tried to use a .one jquery but that's not needed anymore as the if statement will validate if the query string needs to change. Also that function is not working correctly anyway.
$(document).one('load', function() {
if (window.location.pathname == '/items.aspx'){
window.location.replace("items.aspx?item1=a80af972-4f78-de11");
}
});
any ideas would be great.
Thanks
You could use window.location.href="items.aspx?item1=a80af972-4f78-de11"but that will also reload the page. Depending on your users internet connection it could seem like one page load.
Another thing worth noting: You are waiting for $(document).on("load") which gets fired when the page is loaded which is exactly what you don't want.
Try this for speed increase:
$(document).ready(function() {
if (window.location.pathname == '/items.aspx'){
window.location.href = "items.aspx?item1=a80af972-4f78-de11";
}
});
Still - this is a thing to do on the server side. Something in the backend like "if item1 is undefined load item a80af972-4f78-de11" would be best.
I have a situation where I need to increase the number of time article has been read.
Once someone opens an article it should be reflected in the database by incrementing number of reads by one. Simple.
Sending POST request to the server increments the number of reads by one. The article in question is supplied via URL parameter.
Doing it manually by typing the URL in a browser works as expected. So server side is not at fault.
My problems start with the javascript side of it or rather jquery. I hook the event to the article link. So every time a user clicks on the article link it increments the number of reads like so:
$('#list-articles .article-link').click(function(e){
var oid = $(this).parent().parent().attr('data-oid').toString(); //Get the article id
$.post( "/articles/viewed/" + oid );
});
Now this does not work! Number is not increased.
I don't prevent default action since I need the link to actually open and display the article.
Now if I put an alert right after the post like this:
$('#list-articles .article-link').click(function(e){
var oid = $(this).parent().parent().attr('data-oid').toString(); //Get the article id
$.post( "/articles/viewed/" + oid );
alert(oid);
});
This variant works. After I dismiss the alert window, the number is incremented. Why is this so?? How can I fix this to actually work without the alert event present?
UPDATE
Thank you for helping to solve this. All answers are great and help one way or another. The only variant that works so far is disabling async on ajax call. It would be great if someone could elaborate on why switching the async mode off in ajax fixed it. So the post request in the original was never executed? If I was simply checking too early and the number increase was not visible upon page load, it should be still visible on the next page reload, right? SInce it wasn't updated on the database at all I assume that post was not run at all. Why is this so? I want to understand the issue so I do't get into this problem again. Thanks.
Your problem could be due to $.post being asynchronous and you checking this too soon and try posting synchronously:
$.ajax({
type: 'POST',
url: "/articles/viewed/" + oid,
async:false
});
Prevent default. Wait for the response from the server to say incrementing article reads by 1 was successful, then redirect to the article.
If it works with the alert in place it sounds like a race condition.
I use Jquery-ajax calls to post information to a page and display the returned info. The problem I encounter is the following:
When a user makes the first ajax call everything seems normal. When a user does not reload the page and makes the same request for a second time the post-call is made 2 times and the get-call as well. The 3th time there are 4post+4get requests. 4th time 8Post/8Gets. And so on.. until the browser (firefox latest v.) freezes for a while.
I'm a beginning programmer and I don't know what the cause might be. I don't know where to look inside my code. Prehaps you guys can give me a hint. My other ajax requests are fine and only post+get once.
Firebug log:
This is a piece of my code:
$(document).ready(function() {
$('#datepicker').change(function()
{
sendDate($('#datepicker').val());
});
});
function sendDate(str)
{
$.ajax(
{
type: "POST",
url: "manage_processor.php",
data: { chosendate: str },
success: function(data)
{
$('#printdiv').html(data);
}
});
}
Hope anyone can shine some light on this situation.
If I might venture a guess, I suspect the returned data contains a script tag referencing your javascript file. This would explain the GET request you are seeing. Every time the request data is put into #printdiv your script is loaded again and an identical javascript handler would be bound to the same event. This would explain the number of handlers doubling after every request.
Quick test: put console.log( 'script loaded' ); at the top of manage_functions.js. If I'm right it will log after every request.
I'm writing a small script to capture link clicks and save the link's URL into a database table in order to track how many times each link on a particular page is clicked. The links are to external sites.
So, I capture the click event in my JavaScript function, use jQuery to post to a PHP page that saves the data in MySQL, and then the JavaScript function redirects the user to the URL of the link they clicked on.
The problem I'm running into is that it seems like the post never completes because the of redirect. I've worked around this by calling the redirect inside the post callback, but that adds a few second delay because it doesn't get called until after the post completes. I'm looking for a way to just post the data and redirect the user immediately, regardless of whether or not the post succeeds or fails.
This is the current code with the workaround. It works fine, but adds the delay:
function trackClicks(event)
{
var clicked = $(this).attr('href');
$.post
(
$('#track-click-post-url').attr('value'),
{
action: 'track_landing_page_clicks',
clicked_url: clicked,
nonce: $('#track-click-nonce').attr('value')
},
function( response )
{
window.location = clicked;
}
);
event.preventDefault();
}
And this is what I'd like to do, but when I try it never completes:
function trackClicks(event)
{
var clicked = $(this).attr('href');
$.post
(
$('#track-click-post-url').attr('value'),
{
action: 'track_landing_page_clicks',
clicked_url: clicked,
nonce: $('#track-click-nonce').attr('value')
}
);
window.location = clicked;
event.preventDefault();
}
jQuery doesn't provide a callback for what you're looking for. Here are the available ready states:
Value State Description
0 UNSENT open()has not been called yet.
1 OPENED send()has not been called yet.
2 HEADERS_RECEIVED send() has been called, and headers and status are available.
3 LOADING Downloading; responseText holds partial data.
4 DONE The operation is complete.
You're looking for readystate 2, as that's the earliest you're aware of the fact that the server received the message.
This should get you off the ground:
var xhr = new XMLHttpRequest();
xhr.open("POST", clicked);
xhr.onreadystatechange = function() {
if (xhr.readyState >= 2) window.location = clicked;
};
xhr.send($('#track-click-post-url').attr('value'));
https://developer.mozilla.org/en/XMLHttpRequest for further reading.
Why do you post using Javascript when you are going to load a page any way?
Just update the db with the link clicked on the new page.
Perhaps using the referrer URL to track on what page the click was.
Or some other solution to get on what page the click was (e.g. url param) or some other way.
When you leave a page, all pending requests are killed, and the new page loads. The 1st way is the correct way. Yes, there will be a delay when a link is clicked, that's because the POST request is running.
You can't run a request in the background of a page, if the user is not on that page.
Maybe you can save the link URL in a cookie, and put it into the DB when the next page loads.