tildeio/router.js — pull request #11 by machty (2013-03-30 03:57:16+00:00)
Title: Rewrite/refactor of router.js. Multiple features. 

This rewrite was originally only intended to solve the first feature
described below (unified `handleURL` and `transitionTo` behavior), which
called for a major restructuring of the code to allow for both
`transitionTo` and `handleURL` transitions to be pausable when promise
contexts were encountered. 75% of this rather major code change is
restructuring to solve this first problem, but I've foraged on ahead
to take a stab at some other major issues that many have been
complaining about. I recognize this is a major PR to keep in one's
brain, and if you'd like me to split things out, I can do it, but
I figured I'd at least give everyone a chance to weigh in on the
proposed changes and understand everything that's wacky or missing
from the new router. Without further do:

## `handleURL` and `transitionTo` behavior is unified

Previously, only
`handleURL` would cause the router to go into a loading state when a
promise was encountered. Now the logic is as follows:
For both `transitionTo` and `handleURL`, if a promise context is
provided to a route, check and see if a global loading state exists
(as before). If so, pause the transition until promise resolves and
enter the loading state in the meantime, else continue with the
transition under the assumption that leafier routes can handle the
unresolved promise. At some point in the future, we should reconsider
per-route loading states like router v1.

## Preventable/redirectable transitions

Please see API described at https://gist.github.com/machty/5170781

## URL-less routes

Setting notAccessibleByURL to true on a handler will
make it inaccessible to URL changes, and will prevent a URL update
from happening at the end of a transitionTo

## Promise-based URL-changing

Previously, transitionTo would immediately
try to serialize transitioned-to route to determine the new URL, but
if the context is a simple promise object (not an Ember Data Deferred
with knowledge of its `id` property), the serialize can't succeed
until the promise has been resolved. @wycats suggested that the update
shouldn't happen until promises are resolved, but then again, often
enough data is available to serialize even if the promise isn't
resolved, and it would be undesirable to have transitionTo'd into a
route and unnecessarily be waiting for the URL to show up.

So this PR
takes an eager but configurable approach to this problem. By default,
the serialization attempt happens immediately. If one of the params
set by a router's `serialize` method has a null/undefined value, the
serialize is considered a failure, and the URL change won't be
attempted until after all promises have resolved. This behavior is
also configurable via the `updateURLImmediately` property on the
router. If set to true, if the serialization fails, an error is raised
while retrying later. If set to false, the first serialization attempt
is never made, and is only attempted at the end of the transition
after all promises have resolved. Closes #9.