What is the issue with the HTML Standard?
During the investigation of a Gecko webcompat issue, it was discovered that there is a difference in the ordering of tasks ran from a same-document navigation's popstate and hashchange events between browsers, as can be seen in the following snippet:
history.pushState({}, null, "#/");
onpopstate = ev => {
console.log(ev);
setTimeout(() => console.log("setTimeout"), 0);
}
onhashchange = console.log;
history.back();
which, in Blink/Webkit produces popstate, hashchange, setTimeout but in Gecko results in popstate, setTimeout, hashchange.
According to the spec, in #update-document-for-history-step-application step 6.4.3, we first synchronously fire a popstate event, and then later in step 6.4.5 we queue a task to fire a hashchange event. This should result in the setTimeout task being enqueued on the timer task source before the hashchange event firing task is enqueued on the DOM manipulation task source. Where we run into an issue, however, is that when taking a task to run next, the task queue chosen is implementation-defined - so either the setTimeout or the hashchange task could be fired first.
Is there a way this case (the relative ordering of tasks from popstate event handler and the hashchange task) could made formally specified in order to avoid future interoperability issues?