visionmedia / page.js

Micro client-side router inspired by the Express router
http://visionmedia.github.com/page.js
7.67k stars 687 forks source link

`options` is undefined - accessing `dispatch` from `options` #522

Closed rockerest closed 5 years ago

rockerest commented 5 years ago

Version 1.11.2 breaks the documented ability to call page() without any options.

This line used to reference an internal clone of the (safely resolved) dispatch key, but it now references the options object directly leading to a fatal thrown error if no options are provided.

Edit 1:
To be honest, I don't understand how .start() is being called, but I trust that it must be somehow.

My code is roughly as follows:

var router = page;

router( url, ...handlers );
// Etc., register all routes

router();

The stack trace points to those lines in the start method, but I can't personally figure out how they're being called. I suspect someone familiar with the codebase knows offhand, given that the documentation says that page() and page.start() are the same. <End edit 1>

Expected: Documented ability to not pass in an options object when starting page should work.
Actual: Not passing in an object causes a fatal error.

Version working: <= 1.11.1
Version not working == 1.11.2

WesleyDRobinson commented 5 years ago

I'm working on a PR. Are there any tests to be added?

This issue can be resolved by initializing and using opts in lines 547-568 similarly to the .configure method:

Page.prototype.start = function(options) {
    var opts = options || {};
    this.configure(opts);

    if (false === opts.dispatch) return;
    this._running = true;

    var url;
    if(isLocation) {
      var window = this._window;
      var loc = window.location;

      if(this._hashbang && ~loc.hash.indexOf('#!')) {
        url = loc.hash.substr(2) + loc.search;
      } else if (this._hashbang) {
        url = loc.search + loc.hash;
      } else {
        url = loc.pathname + loc.search + loc.hash;
      }
    }

    this.replace(url, null, true, opts.dispatch);
  };