I want to know if there is an equivalent of ajaxStart or ajaxStop in Angular 2.
I want to check if there's an ajax which runs into the document.
According the official documentation of ajaxStart, it will be triggered when there is any Ajax Request. And I want something like this in Angular 2.
$( document ).ajaxStart(function() {
$( "#loading" ).show();
});
I do this:
into my app.component.ts, I show my loader
when my ajax is success, I hide my loader
But, some of my page doesn't have ajax call, so if I show my loader using my app.component.ts, it will be impossible to hide this, because, none of ajax request is present into this page.
I think, if I listen if ajax is not present into my page, if will hide my loader.
I use localStorage to save the status of ajax.
If the page has ajax, I set a value to that xhr
Otherwise, I remove the status stored into localStorage.
Each time, the user arrive in the page. My script check, if there is an ajax running into that page.
app.component.ts
if(localStorage.getITem("xhr")) {
// action here
}
request.service.ts
...
let checkForAjax: any = {
setXhr () {
localStorage.setItem("xhr", "1");
},
removeXhr () {
localStorage.removeItem("xhr");
}
}
...
into get request, I do this (before success callback):
checkForAjax.setXhr()
And into callback of get request, I just remove the status.
checkForAjax.removeXhr()
By the way, I haven't the xhr status, after my ajax is successed. So If I check it into my app.component.ts, I just test if there's a property xhrinto my localStorage.
I work now, but I want another way to listen for ajax with angular 2.
Is that way exist?
How can it will be done?
You could make use of Promises
https://stackoverflow.com/a/30008115/3152269 explains it better than i ever could, but it seems right up your alley
What i generally do when i shoot off an ajax request is to make a promise to run some code after it receives a response.
This makes Ajax calls easier to read and ensures the code doesn't run unless you want it to.
Related
I have a page where I can insert some javascript / jquery to manipulate the output. I don't have any other control over the page markup etc.
I need to add an extra element via jquery after each present on the page. The issue is that the elements are generated via an asynchronous call on the existing page which occurs after $(document).ready is complete.
Essentially, I need a way of calling my jquery after the page has loaded and the subsequent ajax calls have completed. Is there a way to detect the completion of any ajax call on the page and then call my own custom function to insert the additional elements after the newly created s ?
Unfortunately this doesn't apply since it seems the OP isn't using $.ajax() or any jQuery ajax method for actually loading content, but leaving it here in case future googler's are doing this.
You can use any of the global ajax events that meet your needs here, you're probably after $.ajaxComplete() or $.ajaxSuccess().
For example:
$(document).ajaxSuccess(function() {
alert("An individual AJAX call has completed successfully");
});
//or...
$(document).ajaxComplete(function() {
alert("ALL current AJAX calls have completed");
});
If you want to run just some generic function then attach them to document (they're just events underneath). If you want to show something in particular, for example a modal or message, you can use them a bit neater (though this doesn't seem to be what you're after), like this:
$("#myModal").ajaxComplete(function() {
$(this).fadeIn().delay(1000).fadeOut();
});
This example just shows and hides elements at the start and end of ajax calls using jQuery:
$("#contentLoading").ajaxSend(function(r, s) {
$(this).show();
$("#ready").hide();
});
$("#contentLoading").ajaxStop(function(r, s) {
$(this).hide();
$("#ready").show();
});
#contentLoading is an gif image progress indicator.
As i could understand, you are using some jQuery's Ajax function in your ready handler. So you could just pass it another function, which will be invoked after your Ajax function gets response. For example
$(document).ready(function(){
$("#some_div").load('/some_url/', function(){
/* Your code goes here */
});
});
You could rewrite the send() function of the XMLHttpRequest object.
See a solution for doing just so using pure Javascript here.
You could use .live()/.delegate().
I have the following javascript code:
$.post("<receiver>", postdata);
And gets postdata not always. If I write the following code all works good:
$.post("<receiver>", postdata);
alert('bla-bla-bla, read me for a second');
Why? The page is changing on the save button as the javascript runs. But I need to send post data before redirecting.
You should redirect inside the success callback of your AJAX call:
$.post("<receiver>", postdata, function() {
window.location.href = '...';
});
The reason why your code works if you put an alert immediately after the $.post call is because when this alert pops up, the browser suspends the execution and your AJAX call has enough time to complete.
Don't forget that the first A in AJAX stands for Asynchronous meaning that you could only consume the results returned from the server inside the success callback.
Also if this AJAX call is performed inside some .submit() event handler of a form or inside some .onclick() handler of a submit button or an anchor you should make sure that you have canceled the default action by returning false otherwise your AJAX call will never have the time to execute before the browser redirects away from the page.
Example:
$('#myForm').submit({
$.post("<receiver>", postdata, function() {
...
});
return false; // <!-- That's the important bit
});
Ah, so it seems that the missing portion of your question is you are sending data on click of something yes? Presumably a link? That link causes the browser to follow it immediately, and in your example the alert is delaying the browser enough that your post has enough time to complete.
You need to ensure that the default action of that link is blocked, and do the redirect in the callback of your $.post() instead:
$("a.some_class").click(function(evt)
{
evt.preventDefault(); // makes sure browser doesn't follow the link
// gather your post data here ...
var $this = this;
$.post("<receiver>", postdata, function()
{
window.location.href = $this.attr("href");
});
})
Your alert is causing your script to pause and therefore allowing time for your $.post() to complete.
You should put your redirect script in your $.post() callback.
because it causes a delay. While you press OK the request (which takes at least a few milliseconds) gets finished and the stuff depending on it can follow.
To prevent this, you can pass a callback function that runs after the request got its response.
$.post( url, postdata, function() {
// Success.
} )
The .post is asynchronous.
If you change page during the post process () the POST request will get aborted.
Your alert is preventing this page change
You should replace your .post with a .ajax synchronous request, validating form submission on success ( return true; ) . Or do as suggested by #DarinDimitrov or #Curt
Our application is JSF2 framework when we make Ajax Calls in certain scenarios we need to re-invoke the java-script(jQuery-for UI style) ,when the Ajax response returns back from server.
The javascripts are not getting called ,when the Ajax response come back..
Is there any way to enable this ?
Either use jQuery.delegate() or jQuery.on() (depending on jQuery version) instead to reapply the functions on every change in the HTML DOM tree, e.g.:
jQuery(selector).on(eventName, callbackFunction);
or let JSF re-invoke the JS functions by specifying an JSF ajax event handler by jsf.ajax.addOnEvent, e.g.:
jsf.ajax.addOnEvent(function(data) {
if (data.status == "success") { // Can be 'begin', 'complete' and 'success'.
// Re-invoke your JS functions here.
}
});
So I have a normal link on my website, and I want to add tracking for it. I could envision a bunch of ways to do this, but I've settled on this as being really easy by writing a small jquery function, and dropping a small snippet in my tags:
click me!
javascript:
function saveClick(someparamhere){
$.ajax({
url: "somepage.php",
data: {param:someparamhere}
});
}
Now, I know my syntax might be bad, I'm just asking about the overall concept here. When you click the link, I want javascript to issue the call to saveClick which immediately makes an ajax call. There's no success handler because I don't really care if or what gets returned. I'll just have somepage.php log the event. Then, after all of that, I want the tag to go to it's href.
Is that the case? Will the ajax call be issued before the document goes to the other page? Will this work in all cases?
Has anybody ever done something like this? Any experience would be appreciated ....
If you want to make sure the AJAX call goes through you could do:
click me!
$('[data-parameters]').bind('click', function (event) {
//cache this element to use in AJAX function
var $this = $(this);
//prevent the default naviation
event.preventDefault();
$.ajax({
url: "somepage.php",
data: {param:$this.attr('data-parameters')}
success : function () {
//now navigate to the requested page
location = $this[0].href;
}
});
});
UPDATE
$.ajax() exposes a timeout function:
timeoutNumber
Set a timeout (in milliseconds) for the request. This will override
any global timeout set with $.ajaxSetup(). The timeout period starts
at the point the $.ajax call is made; if several other requests are in
progress and the browser has no connections available, it is possible
for a request to time out before it can be sent. In jQuery 1.4.x and
below, the XMLHttpRequest object will be in an invalid state if the
request times out; accessing any object members may throw an
exception. In Firefox 3.0+ only, script and JSONP requests cannot be
cancelled by a timeout; the script will run even if it arrives after
the timeout period.
So you could set a timeout and an error function that mimics the success function. The documentation does state that: it is possible for a request to time out before it can be sent but if your timeout is a very small (maybe zero) delay then it could reduce the lag between the user clicking the link and the browser loading the new page.
I simply wouldn't do that... it could bring to situation your onclick event isn't fired.
I think it would be better to call a javascript function on click that does your ajax call and then bring the user to the target page.
You can do this, for example, this way:
...
your javascript function then, shall be something like:
myfunc(paramofpageclickhere) {
//do ajax call
saveClick(someparamhere);
//go to target page
location.href = "target.htm";
}
I have an app that loads several resources when it's first run, which are stored in localStorage. I have a function that checks whether all the local storage variables are set, so that part is working okay.
My method of working is like this:
Display a loading message.
Initialize the AJAX requests.
Start a timer interval to check if everything has loaded.
When the data has loaded, initialize the application etc.
If the data did not load, display an error message.
The problem is with #5 - how to detect if there was an error? For example if there was a connection problem or the sever sent back invalid data for whatever reason. Here is my current code - downloadData just performs a basic AJAX request:
// check local storage and download if any missing
if ( !checkLocalStorage() )
{
$('#content').before( '<div class="notice" id="downloading">Downloading data, please wait...</div>' );
for ( var i in db_tables )
{
if ( localStorage[db_tables[i]] == null )
downloadData( db_tables[i] );
}
}
// check progress
var timer = setInterval( function() {
if ( checkLocalStorage() )
{
// everything is downloaded
$('#downloading').hide();
clearInterval(timer);
initApp();
}
}, 500 );
Could you turn it around a bit? Something like this (with sensible variable names and a "real" API) would simplify things:
Display a loading message.
Instantiate an application initializer, ai.
Crank up the AJAX requests:
Success handlers call ai.finished(task).
Error handlers call ai.error(task).
Register with the initializer, ai.register(task), in case a "you're taking too long" check is desired.
Once all the AJAX requests have called ai.finished, initialize the application etc.
If any of the AJAX tasks called ai.error, then display an error message and start cleaning things up.
This way you wouldn't need to setInterval() and the individual AJAX tasks will tell you when they have finished or fallen over. You might still want the interval to deal with tasks that are taking too long but most of the logic would be notification based rather than polling based.
Seeing your actual ajax calls in downloadData would help, but I suggest you look over the jquery AJAX API again. Ajax calls have callbacks not just for overall completion but specifically for success and failure including errors. Try to do something like retrying if there is an error and if it continues to fail you can warn the user. You can also use these callbacks to notify your application when the loading is done instead of using an interval timer.