Choo: Ignore links

Created on 14 Aug 2017  Â·  9Comments  Â·  Source: choojs/choo

I'm trying to use a third party library with choo. I've actually done it before with choo v3, and now I'm passing it to choo v6. Now this library defines image links like this:

<a href="/link/to/image.jpg">
  <img src="/link/to/image.jpg"/>
</a>

So, my problem is that choo try to handle the image route and throws route not found.
Now, in choo docs it says that links are ignored when:

  • the click event had .preventDefault() called on it
  • the link has a target="_blank" attribute with rel="noopener noreferrer"
  • a modifier key is enabled (e.g. ctrl, alt, shift or meta)
  • the link's href starts with protocol handler such as mailto: or dat:
  • the link points to a different host
  • the link has a download attribute

So, my question is is there an easier way to ignore links? without having to use preventDefault and programatic navigation? I remember that before there was a noroute data attribute or similar (maybe in sheet-router times?) is there still something like that?

Most helpful comment

Glad to hear. If you don't want to fiddle with the source of nanohref, you could just extend choo with this functionality.

var Choo = require('choo')
var nanohref = require('nanohref')

function MyApp(opts) {
  Choo.call(this, Object.assign({}, opts, { href: false }))
}

MyApp.prototype = Object.create(Choo.prototype)

MyApp.prototype.start = function () {
  Choo.prototype.start.call(this)

  var self = this
  nanohref(function (anchor) {
    var href = anchor.href
    var currHref = window.location.href
    if (href === currHref || anchor.dataset.noroute) return
    self.emitter.emit(self._events.PUSHSTATE, href)
  })
}

All 9 comments

It would seem that the download attribute is what you are looking for. Because by the looks of it, it's a link for downloading an image, no?

No, it's a link to a custom image viewer (https://github.com/sachinchoolur/lightgallery.js)

I see. Well the library does prevent default (see source), so I'm having a hard time seeing why choo would try and handle the route.

If I remember correctly, in earlier versions you had to use event.preventDefault() as well as event.stopPropagation() to stop choo from handling links. Can't confirm if that's still the case now, but could be worth trying.

Oh right, i see what you're doing. What you're doing is a bit of an edge
case, as you're linking to a route on the same host that the router is not
supposed to handle.

Ideally in cases like these the image would be served from a different
host, which allows it to continue as intended.

Perhaps you could instead define a view that all it does is render the
image? Or perhaps a view that all it does is redirect to the requested
resource?

Not sure if any of these cut it tho; maybe you're right and we should
indeed allow for a custom way to flag a link that it shouldn't be handled.
But could you perhaps give any of the above a shot before we get into how
these could be handled? Thanks!

On Tue, Aug 15, 2017, 11:11 Brecht Savelkoul notifications@github.com
wrote:

If I remember correctly, in earlier versions you had to use
event.preventDefault() as well as event.stopPropagation() to stop choo
from handling links. Can't confirm if that's still the case now, but could
be worth trying.

—
You are receiving this because you are subscribed to this thread.
Reply to this email directly, view it on GitHub
https://github.com/choojs/choo/issues/546#issuecomment-322419325, or mute
the thread
https://github.com/notifications/unsubscribe-auth/ACWlei9IMuxt8gUJM0_yAr7oQekCJijSks5sYWCqgaJpZM4O2Xz7
.

I'll see how could I resolve this and comeback with any conclusion I could get :)

So, I solve my issue. After reading @tornqvist comment I rechecked my source and realized that I was using an old version of nanocomponent, in which the load method didn't pass the source element, so my third party library never get hit. I updated Nanocomponent and worked fine.
Anyway, I still try an option to use some attribute for edge cases, and I changed this line in my local Nanohref module by this.

    if (!anchor || anchor.dataset.noroute) return

and set my link like

<a href="/link/to/image.jpg" data-noroute>
  <img src="/link/to/image.jpg"/>
</a>

And worked perfectly. Anyway, is still an edge case as you said, so it is up to you @yoshuawuyts. If you feel like it worth adding I can submit a PR to nanohref, if not then this issue is reference enough for anyone with some similar use case. :)

Glad to hear. If you don't want to fiddle with the source of nanohref, you could just extend choo with this functionality.

var Choo = require('choo')
var nanohref = require('nanohref')

function MyApp(opts) {
  Choo.call(this, Object.assign({}, opts, { href: false }))
}

MyApp.prototype = Object.create(Choo.prototype)

MyApp.prototype.start = function () {
  Choo.prototype.start.call(this)

  var self = this
  nanohref(function (anchor) {
    var href = anchor.href
    var currHref = window.location.href
    if (href === currHref || anchor.dataset.noroute) return
    self.emitter.emit(self._events.PUSHSTATE, href)
  })
}

I'm closing this because it's resolved.

Was this page helpful?
0 / 5 - 0 ratings