web-dev-qa-db-fra.com

Existe-t-il un moyen d’attraper tous les itinéraires sans correspondance avec Backbone?

Je veux avoir un itinéraire «capturer tout» qui fonctionne lorsqu'aucun des autres itinéraires définis ne correspond. Un type de gestionnaire d'erreur 404 NotFound.

J'ai essayé d'ajouter ceci, ce qui fonctionne mais empêche les autres itinéraires de correspondre:

this.route(/(.*)/, 'notFound', this.notFound);

Quelqu'un a-t-il résolu ce problème avant?

40
evilcelery

Répondre ici pour être complet.

Vous pouvez le faire de 2 façons. Définissez l'expression régulière à l'aide de route(), comme dans la question. Cependant, à cause de ce bogue , il vous faudrait définir tous vos itinéraires via la méthode route(), et dans l’ordre inverse (tout en bas). Ceci vous empêche d'utiliser le hash de routes. La (ma) méthode préférée est:

routes: {
  'users/search': 'searchUsers',
  'users/:id': 'loadUser',

  '*notFound': 'notFound'
}

La clé '*notFound' peut en réalité être tout ce qui commence par *. Vous avez juste besoin de caractères après le * pour éviter une erreur d’analyse.

81
evilcelery

Il existe un autre moyen, sans doute plus simple/plus élégant, de résoudre ce problème. Backbone.History.start() renvoie true ou false selon qu'elle correspond ou non à un itinéraire. Donc, si vous faites juste:

if (!Backbone.history.start()) router.navigate('404', {trigger:true});

au lieu de l'habituel:

Backbone.History.start();

cela aura le même effet que les autres réponses.

20
machineghost

Ce minuscule plugin fait son travail: https://github.com/STRML/backbone.routeNotFound

C’est la façon la plus élégante et la plus robuste de résoudre ce problème que j’ai trouvée jusqu’à présent. Toutefois, gardez bien à l’esprit qu’en l’utilisant, vous bousillez les entrailles de Backbone.

2
Pawel Dobierski

Sans un exemple de votre code de routage actuel, je suppose que vous feriez en sorte que votre capture corresponde à votre dernière route

1
Dan

Ajoutez-le simplement comme dernier itinéraire de la liste. De cette façon, il ne sera apparié que comme option de secours.

0
McGarnagle

Vous pouvez le pirater comme suit:

var _loadUrl = Backbone.history.loadUrl;
Backbone.history.loadUrl = function (fragment) {
    var result = _loadUrl.apply(Backbone.history, fragment);
    // the loadUrl returns false if no route was found.
    if(!result){
        // call 404 route on router if it exists.
        var handler = Backbone.history.handlers.filter( o => o.route.test("404") )
        if(handler.length) {
            Backbone.history.navigate("/404")

        }
    }
}

Ensuite, dans votre routeur, vous pouvez faire comme ceci:

var Router = Backbone.Router.extend({
    routes: {
        "404": "pageNotFound"
    },

    pageNotFound: function () {
        alert("trigger pageNotFound route")
    }
});
0
winthers