Skip to content

Instantly share code, notes, and snippets.

@xavi-
Last active December 19, 2015 02:19
Show Gist options
  • Save xavi-/5882483 to your computer and use it in GitHub Desktop.
Save xavi-/5882483 to your computer and use it in GitHub Desktop.
A JavaScript version of the bug described in http://stackoverflow.com/questions/17351590
// A JavaScript version of the bug described in http://stackoverflow.com/questions/17351590
var names = {};
function fetchName(id, callback) {
if(id in names) { callback(names[id]); }
else {
$.get("/what-the-name", { id: id }, function(name) {
names[id] = name;
callback(name);
});
}
}
function showName(id) {
fetchName(id, function(name) {
$("#name").text(name);
});
$("#name").text("fetching name...");
}
showName(id); // WHY DOES $("#name") ALWAYS SHOW "featching name..."!!!
// A JavaScript version of the bug described in http://stackoverflow.com/questions/17351590
// In this javascript example `$("#name").text("fetching name...")` is actionA and
// `$("#name").text(name)` is actionB. When `names` contains the `id` passed in,
// actionB happens before actionA and `#name` is forever set to "fetching name...".
// Basically the problem is that the callback passed to `fetchName` is sometimes
// executed synchronously and at other times asynchronously. This inconsistency can
// lead to infuriatingly subtle bugs. In this javascript example it's easy enough to
// set `#name` before calling `fetchName`, but that's not always the case. It's
// also unfortunate the burden is placed on callers `fetchName`. IMO the more ideal
// solution would be to ensure `fetchName` has consistant async semantics, which is
// fairly straight forward in javascript thanks `setTimeout(..., 0)`.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment