Chrome profiler - Why do functions sometimes stop for a little time? - javascript

Here is a picture of my web execution captured by Chrome Performance Devtools:
I notice that functions will be stopped many times during execution, when my web functions are stopped Chrome executes some RegExp operations (as shown in the picture). I don't understand what this is, and why it happens. Please help explain, thanks.
Update: here is a function which is also executed in the same manner:

What you describe
The way you describe the problem it sounds like you think the JavaScript virtual machine is putting the functions on hold (stopping them) while they are executing (i.e. before they return) to do something else and then resumes the functions.
The image you are showing does not suggest that at all to me.
What I'm seeing
The VM executes:
callback, which calls
some function whose name is hidden by a tooltip, which calls:
fireWith, which calls:
fire, which calls:
etc...
Then the deepest function returns, and the one that called it returns, and so on and so forth until fire returns, fireWith returns, the function whose name we cannot read returns, and callback returns.
Then the VM runs a RegExp function, and it calls a function named callback again, and the whole thing starts anew. In other words, the second column with callback and the rest is a new invocation of the functions. The functions are not "stop[ping] for a little time": they are called multiple times.
I see this all the time in libraries that respond to events. They typically will loop over event handlers to call them. Given a complex enough library, there'a fair amount of glue code that may sit between the loop that calls the handlers and your custom code so there's a lot of repetitive calls that show up in profiling.

Related

Can someone explain JS Event Loop?

So I kind of understand the JS event loop, but still have a few questions. Here is my scenario and a few questions.
So let's say I have these functions:
function1 - reads an absolute huge file.
function2 - console.log("Hey");
function3 - console.log("What's up");
The way I am understanding this, and correct me if I'm wrong, what would happen is that the function1, function2, and function3, would be added to the queue. Then function1 would be added to the call stack followed by the next two functions.
Now the part where I'm confused is because the first function is going to take an extremely long time what happens to it? Does it get pushed somewhere else so that the next two functions are executed? I think the answer to this is that the only way it gets pushed somewhere else so that you can continue running is to make it an asynchronous function. And the way you make it a asynchronous function is either by using a callback function or promises. If this is the case how does it know that this is a asynchronous function? And where does it get pushed to so that the other two functions can be executed since they are relatively simple?
I think I answered the question myself but I keep confusing myself so if somebody could explain in extremely simple terms that would be great and sorry for the extremely stupid question.
Ordinary function calls are not pushed on the event queue, they're just executed synchronously.
Certain built-in functions initiate asynchronous operations. For instance, setTimeout() creates a timer that will execute the function asynchronously at a future time. fetch() starts an AJAX request, and returns a promise that will resolve when the response is received. addEventListener() creates a listener that will call the function when the specified event occurs on an element.
In all these cases, what effectively happens is that the callback function is added to the event queue when the corresponding condition is reached.
When one of these functions is called, it runs to completion. When the function returns, the event loop pulls the next item off the event queue and runs its callback, and so on.
If the event queue is empty, the event loop just idles until something is added. So when you're just starting at a simple web page, nothing may happen until you click on something that has an event listener, then its listener function will run.
In interactive applications like web pages, we try to avoid writing functions that take a long time to run to completion, because it blocks the user interface (other asynchronous actions can't interrupt it). So if you're going to read a large file, you use an API that reads it incrementally, calling an event listener for each block. That will allow other functions to run between processing of each block.
There's nothing specific that identifies asynchronous functions, it's just part of the definition of each function. You can't say that any function that has a callback argument is asynchronous, because functions like Array.forEach() are synchronous. And promises don't make something asychronous -- you can create a promise that resolves synchronously, although there's not usually a point to it (but you might do this as a stub when the caller expects a promise in the general case). The keyword async before a function definition just wraps its return value in a promise, it doesn't actually make it run asynchronously.

How can stringByEvaluatingJavaScriptFromString be re-entrant?

I'm building a hybrid native/HTML5 app on iOS. As part of the native/HTML5 bridge, I'm executing some JavaScript code via stringByEvaluatingJavaScriptFromString.
I make sure to call this function from the main dispatch queue on the native side. Most of the time, the effect on the JavaScript side is that the invoked JavaScript code is called directly from the top level (of the JavaScript stack), even if multiple calls to stringByEvaluatingJavaScriptFromString occur in close proximity.
Occasionally, however, I see evidence that a call to stringByEvaluatingJavaScriptFromString occurs during the middle of method execution - that is, a method called by e.g. an event handler doesn't return before the method called by stringByEvaluatingJavaScriptFromString starts to execute.
Given that JavaScript is single-threaded, how is this possible?
This question has been plaguing me for months, and I finally have proof of the answer.
While iOS generally executes stringByEvaluatingJavaScriptFromString calls at the top of the JavaScript stack, there are certain system calls that appear to "yield" to pending evaluations. The one I have specifically identified is XmlHttpRequest.send(): if there happen to be pending evaluations at the time send() is called, send() will block until those evaluations are executed. There may be others as well.
If this behavior is undesirable, you can avoid the re-entrancy of code by wrapping the function invoked by stringByEvaluatingJavaScriptFromString in setTimeout(..., 0). See this question for background information on why such calls can be useful.
Edit: Though it occurs to me after writing this that it's a bit strange that xhr.send() will execute any pending evaluations, but won't execute pending timeouts. I'll have to do some more experiments...
Edit 2: Experiments indicate that xhr.send() does not in fact execute pending timeouts. The inconsistency is a bit odd, but there you have it.

Creating javascript objects

Set UP:
Hi. I am trying to learn about creating/instantiating objects. I was thinking I should be able to create multiple objects that may have different amounts of similar works (like gather news articles) and would "report completion" regardless of the order created. So far I am not clear on this, so here is a basic example followed by the stated question:
function test(count){
this.count = count;
for(var i = 0; i< count; i++){}
console.log(i);
}
new test(1000);
new test(10);
Actual Question:
Based on the code above, I would expect the second instance to print first, but it does not. What would be the correct way to set this up so that which ever object finishes its work would print first?
* Modify my question *
Sorry...what I am really intending to ask is how to set objects to have more of an asynchronous behavior. I am new to Stack, so please let me know if I should close/move this question.
In general JavaScript is uses a synchronous execution model, the event queue. All calls are placed here, basically in the order they appear in your source code (respecting the scope they are in).
So if you start some function, nothing else is executed until that very function is finished. In your case you place both calls on the event queue, but the second call will only be executed, when the first one has finished.
There, however, exceptions: Worker or AJAX requests.
Here the execution is outside the usual event queue and you use message handlers or callbacks to use the results, after the execution is finished. In most cases, however, you can't be sure in which order the calls are finished as there are many circumstances affecting the ordering of execution (network delay, cpu usage, etc.)
In your case, it seems, you want to load external resources, anyway. So have a look at how AJAX works.
You're not creating different parallel execution threads : the first test(1000) is wholly executed before the following line even starts.
In Javascript, when you're not using webworkers (which you should probably not use), all your code is always executed in a single thread. This thread is awaken by the browser on events and goes back to sleep when the function called by the browser returns.
Note that even with threads, even in naturally parallel languages, you hardly would have had any guarantee regarding what loop ends first.
The reason why the second instance does not print first is that the first call new test(1000) runs to completion before the next line new test(10) starts executing.
If you want the second call to run first, swap the two lines...
Edit:
By the way, any decent compiler will remove this line completely:
for(var i = 0; i< count; i++){}
So you can't even expect the first call to take more time than the second...
The second instance gets instantiated only after first object is instantiated.
So it first prints 1000 after it comes to new test(10)
Because it is single threaded program

Does JavaScript execute top to bottom?

Does the code (e.g. functions) execute at the same time or does it follows the order in which it was written (top to bottom)? I know that order matters in HTML, what about JavaScript?
For instance, if there are two function calls one after the other, will they get executed simultaneously or one after the other even if they have nothing to do with each other?
It may seem as if Javascript functions are executing in an unpredictable order because the model for Javascript in a browser is event-driven. This means that a Javascript program typically attaches event handlers to DOM elements and these are triggered by user actions such as clicking or moving the pointer over an element. However, the script that sets up the event handlers runs as a traditional structured imperative program.
A further complication is that modern Javascript applications make extensive use of asynchronous functions. This means that a function call might return quickly but will have set in motion an action which completes at a later time. An obvious example is the sending of requests to a server in so-called AJAX applications. Typically the request function is passed a callback function which is called when the request completes. However the Javascript program will go on to the next statement without waiting for the completion of the request. This can be somewhat confusing if you aren't thinking clearly enough about what your program is actually doing.
Another example that you might sometimes encounter is the launching of animations in jQuery. These too work asynchronously and you can pass a callback function that runs after the animation completes. Once again this can be surprising sometimes if you expect the next statement to be executed after the animation completes rather than after it starts.
It occurs in the order it was written (with various exceptions). More specifically it's an imperative structured object-oriented prototype based scripting language :)
See Imperative Programming

When is JavaScript synchronous?

I have been under the impression for that JavaScript was always asynchronous. However, I have learned that there are situations where it is not (ie DOM manipulations). Is there a good reference anywhere about when it will be synchronous and when it will be asynchronous? Does jQuery affect this at all?
JavaScript is always synchronous and single-threaded. If you're executing a JavaScript block of code on a page then no other JavaScript on that page will currently be executed.
JavaScript is only asynchronous in the sense that it can make, for example, Ajax calls. The Ajax call will stop executing and other code will be able to execute until the call returns (successfully or otherwise), at which point the callback will run synchronously. No other code will be running at this point. It won't interrupt any other code that's currently running.
JavaScript timers operate with this same kind of callback.
Describing JavaScript as asynchronous is perhaps misleading. It's more accurate to say that JavaScript is synchronous and single-threaded with various callback mechanisms.
jQuery has an option on Ajax calls to make them synchronously (with the async: false option). Beginners might be tempted to use this incorrectly because it allows a more traditional programming model that one might be more used to. The reason it's problematic is that this option will block all JavaScript on the page until it finishes, including all event handlers and timers.
JavaScript is single threaded and has a synchronous execution model. Single threaded means that one command is being executed at a time. Synchronous means one at a time i.e. one line of code is being executed at time in order the code appears. So in JavaScript one thing is happening at a time.
Execution Context
The JavaScript engine interacts with other engines in the browser.
In the JavaScript execution stack there is global context at the bottom and then when we invoke functions the JavaScript engine creates new execution contexts for respective functions. When the called function exits its execution context is popped from the stack, and then next execution context is popped and so on...
For example
function abc()
{
console.log('abc');
}
function xyz()
{
abc()
console.log('xyz');
}
var one = 1;
xyz();
In the above code a global execution context will be created and in this context var one will be stored and its value will be 1... when the xyz() invocation is called then a new execution context will be created and if we had defined any variable in xyz function those variables would be stored in the execution context of xyz(). In the xyz function we invoke abc() and then the abc() execution context is created and put on the execution stack... Now when abc() finishes its context is popped from stack, then the xyz() context is popped from stack and then global context will be popped...
Now about asynchronous callbacks; asynchronous means more than one at a time.
Just like the execution stack there is the Event Queue. When we want to be notified about some event in the JavaScript engine we can listen to that event, and that event is placed on the queue. For example an Ajax request event, or HTTP request event.
Whenever the execution stack is empty, like shown in above code example, the JavaScript engine periodically looks at the event queue and sees if there is any event to be notified about. For example in the queue there were two events, an ajax request and a HTTP request. It also looks to see if there is a function which needs to be run on that event trigger... So the JavaScript engine is notified about the event and knows the respective function to execute on that event... So the JavaScript engine invokes the handler function, in the example case, e.g. AjaxHandler() will be invoked and like always when a function is invoked its execution context is placed on the execution context and now the function execution finishes and the event ajax request is also removed from the event queue... When AjaxHandler() finishes the execution stack is empty so the engine again looks at the event queue and runs the event handler function of HTTP request which was next in queue. It is important to remember that the event queue is processed only when execution stack is empty.
For example see the code below explaining the execution stack and event queue handling by Javascript engine.
function waitfunction() {
var a = 5000 + new Date().getTime();
while (new Date() < a){}
console.log('waitfunction() context will be popped after this line');
}
function clickHandler() {
console.log('click event handler...');
}
document.addEventListener('click', clickHandler);
waitfunction(); //a new context for this function is created and placed on the execution stack
console.log('global context will be popped after this line');
And
<html>
<head>
</head>
<body>
<script src="program.js"></script>
</body>
</html>
Now run the webpage and click on the page, and see the output on console. The output will be
waitfunction() context will be popped after this line
global context will be emptied after this line
click event handler...
The JavaScript engine is running the code synchronously as explained in the execution context portion, the browser is asynchronously putting things in event queue. So the functions which take a very long time to complete can interrupt event handling. Things happening in a browser like events are handled this way by JavaScript, if there is a listener supposed to run, the engine will run it when the execution stack is empty. And events are processed in the order they happen, so the asynchronous part is about what is happening outside the engine i.e. what should the engine do when those outside events happen.
So JavaScript is always synchronous.
JavaScript is single-threaded, and all the time you work on a normal synchronous code-flow execution.
Good examples of the asynchronous behavior that JavaScript can have are events (user interaction, Ajax request results, etc) and timers, basically actions that might happen at any time.
I would recommend you to give a look to the following article:
How JavaScript Timers Work
That article will help you to understand the single-threaded nature of JavaScript and how timers work internally and how asynchronous JavaScript execution works.
To someone who really understands how JS works this question might seem off, however most people who use JS do not have such a deep level of insight (and don't necessarily need it) and to them this is a fairly confusing point, I will try to answer from that perspective.
JS is synchronous in the way its code is executed. each line only runs after the line before it has completed and if that line calls a function after that is complete etc...
The main point of confusion arises from the fact that your browser is able to tell JS to execute more code at anytime (similar to how you can execute more JS code on a page from the console). As an example JS has Callback functions who's purpose is to allow JS to BEHAVE asynchronously so further parts of JS can run while waiting for a JS function that has been executed (I.E. a GET call) to return back an answer, JS will continue to run until the browser has an answer at that point the event loop (browser) will execute the JS code that calls the callback function.
Since the event loop (browser) can input more JS to be executed at any point in that sense JS is asynchronous (the primary things that will cause a browser to input JS code are timeouts, callbacks and events)
I hope this is clear enough to be helpful to somebody.
Definition
The term "asynchronous" can be used in slightly different meanings, resulting in seemingly conflicting answers here, while they are actually not. Wikipedia on Asynchrony has this definition:
Asynchrony, in computer programming, refers to the occurrence of events independent of the main program flow and ways to deal with such events. These may be "outside" events such as the arrival of signals, or actions instigated by a program that take place concurrently with program execution, without the program blocking to wait for results.
non-JavaScript code can queue such "outside" events to some of JavaScript's event queues. But that is as far as it goes.
No Preemption
There is no external interruption of running JavaScript code in order to execute some other JavaScript code in your script. Pieces of JavaScript are executed one after the other, and the order is determined by the order of events in each event queue, and the priority of those queues.
For instance, you can be absolutely sure that no other JavaScript (in the same script) will ever execute while the following piece of code is executing:
let a = [1, 4, 15, 7, 2];
let sum = 0;
for (let i = 0; i < a.length; i++) {
sum += a[i];
}
In other words, there is no preemption in JavaScript. Whatever may be in the event queues, the processing of those events will have to wait until such piece of code has ran to completion. The EcmaScript specification says in section 8.4 Jobs and Jobs Queues:
Execution of a Job can be initiated only when there is no running execution context and the execution context stack is empty.
Examples of Asynchrony
As others have already written, there are several situations where asynchrony comes into play in JavaScript, and it always involves an event queue, which can only result in JavaScript execution when there is no other JavaScript code executing:
setTimeout(): the agent (e.g. browser) will put an event in an event queue when the timeout has expired. The monitoring of the time and the placing of the event in the queue happens by non-JavaScript code, and so you could imagine this happens in parallel with the potential execution of some JavaScript code. But the callback provided to setTimeout can only execute when the currently executing JavaScript code has ran to completion and the appropriate event queue is being read.
fetch(): the agent will use OS functions to perform an HTTP request and monitor for any incoming response. Again, this non-JavaScript task may run in parallel with some JavaScript code that is still executing. But the promise resolution procedure, that will resolve the promise returned by fetch(), can only execute when the currently executing JavaScript has ran to completion.
requestAnimationFrame(): the browser's rendering engine (non-JavaScript) will place an event in the JavaScript queue when it is ready to perform a paint operation. When JavaScript event is processed the callback function is executed.
queueMicrotask(): immediately places an event in the microtask queue. The callback will be executed when the call stack is empty and that event is consumed.
There are many more examples, but all these functions are provided by the host environment, not by core EcmaScript. With core EcmaScript you can synchronously place an event in a Promise Job Queue with Promise.resolve().
Language Constructs
EcmaScript provides several language constructs to support the asynchrony pattern, such as yield, async, await. But let there be no mistake: no JavaScript code will be interrupted by an external event. The "interruption" that yield and await seem to provide is just a controlled, predefined way of returning from a function call and restoring its execution context later on, either by JS code (in the case of yield), or the event queue (in the case of await).
DOM event handling
When JavaScript code accesses the DOM API, this may in some cases make the DOM API trigger one or more synchronous notifications. And if your code has an event handler listening to that, it will be called.
This may come across as pre-emptive concurrency, but it is not: it is the JavaScript code that initiates the API call, and thus controls that the API can do some stuff, but this is just like a function call: once your event handler(s) return(s), the DOM API will eventually also return, and the original JavaScript code will continue after the API call it made.
In other cases the DOM API will just dispatch an event in the appropriate event queue, and JavaScript will pick it up once the call stack has been emptied.
See synchronous and asynchronous events
"I have been under the impression for that JavaScript was always
asynchronous"
You can use JavaScript in a synchronous way, or an asynchronous way. In fact JavaScript has really good asynchronous support. For example I might have code that requires a database request. I can then run other code, not dependent on that request, while I wait for that request to complete. This asynchronous coding is supported with promises, async/await, etc. But if you don't need a nice way to handle long waits then just use JS synchronously.
What do we mean by 'asynchronous'. Well it does not mean multi-threaded, but rather describes a non-dependent relationship. Check out this image from this popular answer:
A-Start ------------------------------------------ A-End
| B-Start -----------------------------------------|--- B-End
| | C-Start ------------------- C-End | |
| | | | | |
V V V V V V
1 thread->|<-A-|<--B---|<-C-|-A-|-C-|--A--|-B-|--C-->|---A---->|--B-->|
We see that a single threaded application can have async behavior. The work in function A is not dependent on function B completing, and so while function A began before function B, function A is able to complete at a later time and on the same thread.
So, just because JavaScript executes one command at a time, on a single thread, it does not then follow that JavaScript can only be used as a synchronous language.
"Is there a good reference anywhere about when it will be synchronous and when it will be asynchronous"
I'm wondering if this is the heart of your question. I take it that you mean how do you know if some code you are calling is async or sync. That is, will the rest of your code run off and do something while you wait for some result? Your first check should be the documentation for whichever library you are using. Node methods, for example, have clear names like readFileSync. If the documentation is no good there is a lot of help here on SO. EG:
How to know if a function is async?

Categories