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

Is it possible to replace/redirect a route request? #228

Closed
tyzen9 opened this issue Nov 21, 2018 · 4 comments
Closed

Is it possible to replace/redirect a route request? #228

tyzen9 opened this issue Nov 21, 2018 · 4 comments

Comments

@tyzen9
Copy link

tyzen9 commented Nov 21, 2018

I am struggling with a way to redirect a route request under a certain condition. In this case, I would like to look at each router request and determine if the user needs to perform the setup for the system. However, I don't seem to have a clear grasp on how or if this is possible, and what done() does.

I am trying to use a before hook (which seems to always execute), but both the requested route and the setup route execute if (condition == true).

How can I interrupt a request to a route, and replace it with an alternative route?

(pseudocode)

              var init = function() {
		router.hooks({
			before: function(done, params){
				// Before we route, if condition, then route the user to the setup screen
				if (condition == true) {
					// Route user to setup screen
					done(false);
					router.navigate("setup");
				}
				done();
			}
		});

		// set the valid routes and their actions
		router.on({
			  'home': function () {  
			       $("#content").load("/view/home.htm", function() {
 		               HOME.init(); 
			  },
			  'login': function () {
				$("#content").load("/view/login.htm", function() {
				LOGIN.init();
			   },
		           'setup': function () {  
				$("#content").load("/view/setup.htm", function() {
				SETUP.init();
			   },
			  'logout': function () {
                                 // This triggers an event which will call router.navigate('login')
				 REST_SERVICE.deleteToken(TOKEN.decode().id);
			  }
		}).resolve();

		// If a non-supported route is passed in
     	       router.notFound(function () { navigate("home");	});
@krasimir
Copy link
Owner

I see your point. I think this is not a concern of the routing. When the user wants to move to a page he needs to click somewhere right. This means that you can plug your code there and only redirect if your conditions are true. I'll suggest to try shifting such decisions out of the routing. You'll make your app more robust and flexible.

@weisborg
Copy link

This is related to #243 and really a problem of hooks being there to do this, but never actually being able to do it. The documentation on the GIT page shows them used this way, so is misleading.

People using Navigo use it to handle the clicking of links and URLs to do something. Saying you need to redirect with other code defeats the purpose of Navigo. To use Navigo the best way possible I have the URLs in the HREF of my links, so it changes the URLs and #! hashes which Navigo listens for.

Having Navigo capture click events with data-navigo and such did not allow opening in a new tab, favorites, or anything useful. Adding my own click handler for all anchor tags to do what is suggested here would go right back to not being able to do those things.

@nenadalm
Copy link

nenadalm commented May 6, 2020

Hi. I needed to redirect user in my route handler, so I was searching if there is some supported way and then I used this:

navigo.historyAPIUpdateMethod('replaceState');
navigo.navigate(url);
navigo.historyAPIUpdateMethod('pushState');

I use my own wrapper of navigo and the above is code of redirect function. So in my handler, I can just call route.redirect(newUrl) and current url will be replaced with newUrl (which means that back button will take me to url before current url). For me, navigo translates strings (urls) to handlers and allows me to create strings (urls) given name and parameters (named routes). I don't really need anything more than that (so navigo does even more then I need or use).

@krasimir
Copy link
Owner

The problem describe here is a legit one. I'm still on defence whether this should be handled on a route level. However with the latest release (version 8.0.0) the following works:

<a href="/about" data-navigo>About</a>
const router = new Navigo("/");
const before = (done, match) => {
  done(false);
  router.navigate("login");
};

router
  .on(
    "/about",
    (match) => {
      console.log(match);
      render("About");
    },
    { before: before }
  )
  .on("/login", (match) => {
    console.log(match);
    render("Login");
  })
  .on((match) => {
    console.log(match);
    render("home");
  })
  .resolve();

When the user clicks on the HTML link it gets redirected to /login.

I'll close this issue because I guess there was a bug before that was preventing the router to work this way but now you can totally use the before hook and navigate to redirect.

@stheisen let me know if you still (two years later :D) need help with this.

P.S.
Version 8.0.0 is not officially released but can be installed via npm install navigo@beta or yarn add navigo@beta. Migration guide is available here https://github.com/krasimir/navigo/blob/big-rewrite/CHANGELOG.md#migration-guide and the new documentation here https://github.com/krasimir/navigo/blob/big-rewrite/DOCUMENTATION.md.

krasimir pushed a commit that referenced this issue Dec 29, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants