         # recursively alias this route without this optional edge:
         routeWithoutThisEdge = "/#{
           route.slice(0, i).concat(route.slice i + 1).join '/'
-          # route.filter (_, k)-> k isnt i
         }"
         @addRoute routeWithoutThisEdge, listener
         edge = edge.substr 0, len # get rid of the "?" from the route


  handleRoute:(frag, options={})->
    {shouldPushState, state} = options
    shouldPushState ?= yes
    node = @tree
    params = {}

class KDRouter extends KDObject

  @stayOpen = (fn)->


  listenerKey = 'ಠ_ಠ'

  createObjectRef =(obj)->
    return unless obj?.bongo_? and obj?.getId?
    constructorName   : obj.bongo_?.constructorName
    id                : obj.getId()

  revive =(objRef, callback)->
    unless objRef?.constructorName? and objRef.id? then callback null
    else KD.remote.cacheable objRef.constructorName, objRef.id, callback

  constructor:(routes)->
    super()
    @tree   = {} # this is the tree for quick lookups
    @routes = {} # this is the flat namespace containing all routes
    @addRoutes routes
    # this handles the case that the url is an "old-style" hash fragment hack.
    if location.hash.length
      @utils.defer =>
        hashFragment = location.hash.substr 1
        @handleRoute hashFragment, shouldPushState: yes
    @startListening()

  onpopstate:(event)=> # fat-arrow binding makes this handler easier to remove.
    revive event.state, (err, state)=>
      if err?
        new KDNotificationView title: 'An unknown error has occurred.'
      else
        @handleRoute location.pathname,
          shouldPushState   : no
          state             : state

  startListening:->
    return no  if @isListening # make this action idempotent
