Is this a bug or I’m doing something wrong?
https://jsfiddle.net/m8cx61sq/6/
I need to intercept the router to redirect the user to an Authenticate page, if he is not authenticated yet. I did it using the route async function. The problem is: the Authenticate page has an empty router stack (so back() or navbar back-link won’t work).
To see the bug on fiddle: click on the About link (it will redirect you to the Dynamic Page). In this new page, the back cease to work =\
1 Like
It’s not clear how we supposed to secure routes (authentication) on f7-vue, if we can’t use async =\
You can, read my comments in GitHub issue
Guess I didn’t understood what you’re trying to say:
async and component can’t be used together…
In F7-Vue, you need to use component and resolve routes with component as well
It’s not clear how one can intercept (and cancel) a route navigation, redirect to another page (or show a popup), then continue the normal flow if user is authenticated.
So far, I’m making a custom navigate method that handles this =\
Very simple, here is your example fixed https://jsfiddle.net/qa4m0bod/
Mean that route can conain only one page/component-load prop:
{
path: '...',
// then only one of load-kind props
component: ...
// or
url: //
// or
async: //
...etc
}
Inside of async
you can resolve it, again, with only one kind of load-prop such are component
, url
, componentUrl
, content
, pageName
, el
, template
, templateUrl
If you need any kind of logic, whether to check or preload something before route load, then always use async
.
If you need to cancel route, call reject()
function in async. And after call router.navigate
if you need to redirect
My implementation (seems to work now, thank you):
// For me, the .vue extension is important (because I separate js from vue files)
import home from "./pages/home.vue"; // My home component
import addNewItem from "./pages/addNewItem.vue"; // My secure component
// I have an EventBus and, luckly, all F7 methods are available (without need to use global context)
import EventBus from "./streamline/eventBus";
// I defined that a secure route has secureComponent instead of component
const routes =
[
{ path: "/", component: home }, // Not secure
{ path: "/addNewItem/", secureComponent: addNewItem }, // Secure
];
// For each of the routes...
for(const route of routes)
{
if(route.secureComponent) // ...if it is secure...
{
// intercepts the f7router to check some things...
route.async = function(routeTo, routeFrom, resolve, reject)
{
// My event bus also keeps my plugins and Vue.prototype.$things
// This one checks if the user is authenticated:
if(EventBus.$services.isAuthenticated)
{
// If so, I create a new route pointing the component to that secureComponent o'mine
// It's a constructor, so it is safe to copy it around
const newRoute = { path: routeTo.route.path, component: routeTo.route.secureComponent };
// Now the route is resolved and the secure page thing appears as nothing has happened
resolve(newRoute);
}
else
{
// In my case, I want to use popups, not a new page for authentication
// By the instructions above, a redirect to a non secure page would work as well, but I won't do it 'cos:
// SUGGESTION: F7Router sucks, specially the "ignore the stack and load a new page without keeping the current on history (i.e.: a back on this new page will back to the previous, not the current one)
reject();
const loginScreen = EventBus.$f7.loginScreen.create({ el: EventBus.$$(".loginScreen") });
loginScreen.open();
// SUGGESTION: There should be a better way to handle a modal response
loginScreen.on("loginscreen:closed", () =>
{
loginScreen.destroy();
// Here I test the whole thing again (just to force a new navigation...
// Guess this is needed because I've already rejected the navigation, so...
if(EventBus.$services.isAuthenticated)
{
EventBus.$f7router.navigate(url);
}
});
}
}
}
}
// Export the static thing to whomever handles this thing. Lots of things on my code. Amazing how it works!
export default routes;
There are two suggestions of improvement on the comments above.
Thank you for the help.