W3C home > Mailing lists > Public > whatwg@whatwg.org > November 2010

[whatwg] pushState and session history issues

From: Ian Hickson <ian@hixie.ch>
Date: Tue, 30 Nov 2010 02:06:49 +0000 (UTC)
Message-ID: <Pine.LNX.4.64.1011192209310.26618@ps20323.dreamhostps.com>
On Thu, 12 Aug 2010, Mihai Parparita wrote:
> On Thu, Aug 12, 2010 at 4:56 PM, Ian Hickson <ian at hixie.ch> wrote:
> > On Tue, 27 Jul 2010, Mihai Parparita wrote:
> > > https://webkit.org/b/42861 has more tests, but briefly, the behavior
> > > in the latest stable versions of these browser is:
> > > - Firefox will not create a session history entry if the navigation is
> > > executed inline, or during an onload handler
> > > - Chrome will not create a session history entry if the navigation is
> > > executed inline, or within 5 seconds of the onload handler firing
> > > - Safari will always create a session history entry
> > > - IE will not create a session history entry for hash changes during
> > > onload only
> > >
> > > My proposed change to WebKit is to not create a session history 
> > > entry for location changes that happen before onload fires if they 
> > > are not in response to a user gesture. I would also be modifying 
> > > Chrome to remove its custom logic for this and just inherit 
> > > WebKit's.
> > >
> > > Does anyone see any compatibility problems with this? Should the 
> > > HTML5 history section mention anything about navigations caused 
> > > script vs. user gestures*? I realize that replace() should obviate 
> > > the need for such a heuristic, but given that 1) other browsers seem 
> > > to do this and 2) sites like hp.com don't get it right, there may be 
> > > a need for it.
> > >
> > > * It only alludes to something similar: "In addition, a user agent 
> > > could ignore calls to pushState() that are invoked on a timer, or 
> > > from event listeners that are not triggered in response to a clear 
> > > user action, or that are invoked in rapid succession."
> >
> > IE's behaviour seems the narrowest; would it be acceptable? Failing 
> > that, how about any navigations until the end of the load event task?
> 
> Based on the way the discussion has evolved in 
> https://webkit.org/b/42861, the consensus is that your second option 
> ("any navigations until the end of the load event task") is preferable 
> (given that sites already do this, e.g. the Wikipedia mobile 
> "redirect").  Would form submits also be counted as navigation?

"Navigation" is anything that runs the "navigate" algorithm in the spec, 
which is everything from scripted form submission to a user typing a URL 
in the location bar.


> > The proposal here would be to just assume a scripted navigation is 
> > done with replacement enabled in the condition described above, right?
> 
> And yes, this woud be just be navigation with replacement enabled.

Here is a list of the ways the spec currently lets you trigger 
navigation, and what I've done for each one regarding this issue:

   <meta http-equiv=refresh> - unchanged; this already does replacement 
   anyway.

   <iframe src and srcdoc>, <frame> - unchanged; these aren't redirects.

   <object data> - unchanged; always does replacement anyway.

   <form> submission - changed to do replacement if the submission was 
   invoked from .submit() and the load, pageshow, and popstate events have 
   not yet finished being fired for this document.

   hyperlinks - unchanged; these are assumed to be new documents, not 
   redirects, and so should not replace.

   window.open - unchanged; if opening a new window or if the 'replace' 
   argument is set, then this already did replacement; in the case of 
   navigating another window, Firefox didn't do anything special, IE 
   doesn't seem to either though that seems to actually differ based on 
   how you measure it (e.g. history.length vs the UI's back button).

   location.href - changed like form submission.

   location.assign() - unchanged, on the assumption that we always want 
   this to not replace, since if you want to replace you can use...:

   location.replace() - unchanged, since it always replaces.

   location.reload() - unchanged; always replaces.

   user reload UI - unchanged; always replaces.

   user manually opening of a link from inside a sandbox - unchanged, 
   mostly a UI issue.

   history.back()/.forward() and user history traversal - unchanged;
   this is an internal issue (entry update) and is supposed to be 
   transparent to the user and script as far as possible.

   showModalDialog - unchanged; always replaces.

   opening a link from the OS (e.g. following an HTTP link from an IM app 
   or trying to open a resource that matched a registerProtocolHandler() 
   registration) - unchanged, same as hyperlinks.

   handling an encoding change during parsing - unchanged; always 
   replaces.

   following cite="" links - unchanged, same as hyperlinks.



On Fri, 27 Aug 2010, Mihai Parparita wrote:
> On Fri, Aug 27, 2010 at 4:03 PM, Ian Hickson <ian at hixie.ch> wrote:
> > 
> > BTW, there's another problem with this API, which is that since 
> > popstates are dropped while the document is loading, calling 
> > pushState() while the document is loading leads to a very confused 
> > state. Should we make pushState() throw an exception if called before 
> > load? (replaceState() is probably ok, though even that's a bit dodgy.)
> 
> This seems related to the thread from around a month ago when I asked 
> about setting location.href before onload (Gecko, and now WebKit, will 
> not create a new session history entry if this happens before load). 
> Throwing an exception, ignoring the pushState, or having it be treated 
> as replaceState all make sense to me.
> 
> > I assume we don't want to change this, in which case I should probably 
> > put a note in the spec warning about using pushState() and 
> > replaceState() before load. Any opinions on this?
> 
> At least a note that the pending state object is not affected by 
> push/replaceState makes sense.

After thinking about this for a while, I couldn't really bring myself to 
adding a warning that described the behaviour as completely broken as it 
was. So I instead changed the spec a bit: now, if you call pushState() or 
replaceState() before the first popstate has fired, it will update the 
state object so the first popstate will make sense.

I hope that implementations can be updated accordingly in time. If not, I 
guess I'll change it back and add the warning after all.

-- 
Ian Hickson               U+1047E                )\._.,--....,'``.    fL
http://ln.hixie.ch/       U+263A                /,   _.. \   _\  ;`._ ,.
Things that are impossible just take longer.   `._.-(,_..'--(,_..'`-.;.'
Received on Monday, 29 November 2010 18:06:49 UTC

This archive was generated by hypermail 2.4.0 : Wednesday, 22 January 2020 16:59:28 UTC