Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Partially recast the router API to be a lot more intuitive. #2469

Merged
merged 5 commits into from Jul 12, 2019

Conversation

@isiahmeadows
Copy link
Collaborator

commented Jul 12, 2019

Description

  • m.route.prefix(...)m.route.prefix = ...
  • oncreate: m.route.linkm(m.route.Link, ...)
  • Add m.route.SKIP

Motivation and Context

Fixes #2387
Fixes #2072
Fixes #1792
Fixes #2354 (not in the way they wanted, but it at leasts unblocks them)
Fixes quite a few issues reported on Gitter.

For m.route.Link:

  • More intuitive
  • More accessible
  • More ergonomic
  • It can be disabled
  • It can be cancelled
  • It can be changed
  • Oh, and you can use it isomorphically.

For m.route.prefix

  • You can read it.
  • You can write to it, of course.
  • It's literally just setting a property.

For m.route.SKIP

  • You can type-check routes, now.
  • You can hide routes and pretend they don't exist.
  • You can check existence of something and fall back later.

For the router itself (and the rest of Mithril):

  • You can now require("mithril") and all its submodules without a DOM at all. There is a catch: you can't instantiate any routes, you can't mount anything, and you can't invoke m.render in any capacity. You can only use m.route.Link, m.route.prefix, hyperscript stuff, and mithril/stream, and you can use m.request with background: true if you use a global XHR polyfill. (You can't use m.request without background: true except with a DOM to redraw with.) The goal here is to try to get out of the way for simple testing and to defer the inevitable TypeErrors for the relevant DOM methods to runtime.

    The factory requires no arguments, and in terms of globals, you can just figure out based on what errors are thrown what globals to define. Their values don't matter - they just need to be set to something, even if it's just null or undefined, before Mithril executes.

Had to make quite a few other changes throughout the docs and tests to
update them accordingly. Oh, and that massive router overhaul enabled me
to do all this.

Also, slip in a few drive-by fixes to the mocks so they're a little
easier to work with and can accept more URLs. This was required for a
few of the tests.

How Has This Been Tested?

Added and updated a lot of tests.

Types of changes

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)
  • Documentation change

Checklist:

  • My code follows the code style of this project.
  • My change requires a change to the documentation.
  • I have updated the documentation accordingly.
  • I have read the CONTRIBUTING document.
  • I have added tests to cover my changes.
  • All new and existing tests passed.
  • I have updated docs/change-log.md

@project-bot project-bot bot added this to Needs triage in Triage/bugs Jul 12, 2019

@isiahmeadows isiahmeadows force-pushed the isiahmeadows:update-router branch from 83fd1cb to 6d82494 Jul 12, 2019

isiahmeadows added some commits Jul 12, 2019

Recast the router API to be a lot more intuitive.
Fixes #2387
Fixes #2072
Fixes quite a few issues reported on Gitter.

For `m.route.Link`:

- More intuitive
- More accessible
- More ergonomic
- It can be disabled
- It can be cancelled
- It can be changed
- Oh, and you can use it isomorphically.

For `m.route.prefix`

- You can *read* it.
- You can write to it, of course.
- It's literally just setting a property.

For the router itself (and the rest of Mithril):

- You can now `require("mithril")` and all its submodules without a DOM
  at all. There is a catch: you can't instantiate any routes, you can't
  mount anything, and you can't invoke `m.render` in any capacity. You
  can only use `m.route.Link`, `m.route.prefix`, hyperscript stuff, and
  `mithril/stream`, and you can use `m.request` with `background: true`
  if you use a global XHR polyfill. (You can't use `m.request` without
  `background: true` except with a DOM to redraw with.) The goal here is
  to try to get out of the way for simple testing and to defer the
  inevitable `TypeError`s for the relevant DOM methods to runtime.

  The factory requires no arguments, and in terms of globals, you can
  just figure out based on what errors are thrown what globals to
  define. Their values don't matter - they just need to be set to
  *something*, even if it's just `null` or `undefined`, before Mithril
  executes.

Had to make quite a few other changes throughout the docs and tests to
update them accordingly. Oh, and that massive router overhaul enabled me
to do all this.

Also, slip in a few drive-by fixes to the mocks so they're a little
easier to work with and can accept more URLs. This was required for a
few of the tests.
@isiahmeadows

This comment has been minimized.

Copy link
Collaborator Author

commented Jul 12, 2019

Apologies for the very large diff on api/tests/test-router.js - it's all intended to actually test for how ticks are fired. I was previously running into weird sequencing issues and having to add and subtract a lot of callAsyncs with varying levels of success (mostly fleeting at best), so I just switched to what m.route was using internally and relying directly on the number of ticks needed. They're easily adjusted, and I left a comment so if anyone needs to adjust them, they have an idea of what to do. (The ticks are intended to be lower precedence than promise microtasks, and the tests may break on IE. I also need to test them with the polyfill and with the hashchange fallback at some point.)

@isiahmeadows isiahmeadows merged commit 582bda5 into MithrilJS:next Jul 12, 2019

1 check passed

continuous-integration/travis-ci/pr The Travis CI build passed
Details

Triage/bugs automation moved this from Needs triage to Closed Jul 12, 2019

@isiahmeadows isiahmeadows deleted the isiahmeadows:update-router branch Jul 12, 2019

@spacejack

This comment has been minimized.

Copy link
Contributor

commented Jul 14, 2019

Sorry to point this out after the fact but was pondering the component attr name. In the hyperscript docs this parameter is referred to as the selector. I wonder if selector would be a better name for the attr?

I was also wondering if tag would be a better name. But we can't use that (I don't think?) because it would be interpreted as a vnode (child) rather than an attrs object. Which makes me wonder if it would be useful re-naming the vnode.tag property to something like vnode.__TAG to free up the name tag for application use in attrs.

@isiahmeadows

This comment has been minimized.

Copy link
Collaborator Author

commented Jul 16, 2019

@spacejack I wouldn't be against it in the future, but I'd like to flesh out changes to the vnode structure in a separate bug. Short term, I'm correcting the design bug (componentselector) in a followup PR. Edit: #2475

@isiahmeadows isiahmeadows referenced this pull request Jul 16, 2019
9 of 11 tasks complete
@soaxelbrooke

This comment has been minimized.

Copy link

commented Jul 24, 2019

Sorry if this isn't the right place to ask, but I couldn't find an answer in the docs. I've got a lot of m('a.someclass', { href, oncreate: m.route.link })s sitting around my codebase, and this is the only breaking change I need to accommodate. Should those be replaced with m(m.route.Link, m("a.someclass", { href }))?

@osban

This comment has been minimized.

Copy link
Contributor

commented Jul 24, 2019

@soaxelbrooke I think it should be m(m.route.Link, {href, class: 'someclass'})
Oh, you could also ask it in the Mithril Gitter chat.

@isiahmeadows

This comment has been minimized.

Copy link
Collaborator Author

commented Jul 26, 2019

@soaxelbrooke Either use class: "someclass" or selector: "a.someclass", whichever you prefer.

If anyone wants to update the docs to clarify this, I'd be more than willing to accept a pull request.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
4 participants
You can’t perform that action at this time.