meteor - resolución - que es un adaptador inalambrico
Redirigiendo a los usuarios que no han iniciado sesión con el enrutador de hierro... De nuevo (5)
Estoy luchando contra la necesidad común de redirigir a un usuario a una página de inicio de sesión si no está conectado (Meteor v0.8.0 en Windows 7).
Hay varias preguntas similares sobre stackoverflow, pero ninguna respuesta parece funcionar para mí.
No funcionará # 1: render ()
De la documentación :
onBeforeAction: function () {
if (!Meteor.user()) {
// render the login template but keep the url in the browser the same
this.render(''login'');
// stop the rest of the before hooks and the action function
this.stop();
}
},
Dos cuestiones aquí:
1- La documentación está desactualizada. this.stop()
no this.stop()
función this.stop()
. Como se indica here , el código debe ser:
onBeforeAction: function (pause) {
if (!Meteor.user()) {
// render the login template but keep the url in the browser the same
this.render(''login'');
// stop the rest of the before hooks and the action function
pause();
}
},
2- Esto funciona solo si la ruta no tiene layoutTemplate
. Si tiene uno, la plantilla de login
se representa en el {{>yield}}
de la layoutTemplate
de layoutTemplate
. Esto generalmente no es lo que quieres para una página de inicio de sesión.
No funcionará # 2: Router.go () o this.redirect ()
Definir una ruta para la página de inicio de sesión suena como la forma natural. Entonces puedes hacer:
Router.onBeforeAction(function(pause) {
if (!Meteor.user()) {
pause();
Router.go(''/login'');
}
}, {except: [''login'']});
O:
Router.onBeforeAction(function() {
if (!Meteor.user())
this.redirect(''/login'');
}, {except: [''login'']});
Pero, extrañamente, todavía hay un problema si la ruta original (antes de la redirección) tiene una layoutTemplate
: la plantilla /login
se representa dentro de {{yield}}
. Lo que de nuevo no es lo que normalmente quiere (y definitivamente no es lo que espera, ya que la plantilla /login
no tiene una plantilla de layoutTemplate
definida).
Encontré una manera de resolver esto parcialmente:
Router.onBeforeAction(function() {
if (!Meteor.user()) {
var that = this;
setTimeout(function() { that.redirect(''/login''); }, 0);
}
}, {except: [''login'']});
Ahora todo está bien: la plantilla /login
muestra como una página limpia ... Excepto que la layoutTemplate
de layoutTemplate
de la ruta original parpadea brevemente antes de que se muestre la plantilla /login
.
¿Tienes este mismo problema?
En Meteor 0.8.3 para mi funciona:
Router.onBeforeAction(function () {
if (_.include([''formLogin''], this.route.name)){
return;
}
if (!Meteor.userId()) {
this.redirect(''formLogin'');
return;
}
});
Ok, entonces parece que la función de renderización en una ruta solo representa una plantilla en el diseño actual. Para representar una plantilla en un diseño diferente, debe llamar a this.setLayout(''templateName'')
. La única advertencia parece ser que tendrá que volver a configurar el diseño después de iniciar sesión.
onBeforeAction: function(pause) {
var routeName = this.route.name;
if (_.include([''login''], routeName))
return;
if (! Meteor.userId()) {
this.setLayout("newLayout");
this.render(''login'');
//if you have named yields it the login form
this.render(''loginForm'', {to:"formRegion"});
//and finally call the pause() to prevent further actions from running
pause();
}else{
this.setLayout(this.lookupLayoutTemplate());
}
}
También puede representar la plantilla de inicio de sesión como diseño si todo lo que necesita es su plantilla de inicio de sesión llamando a this.setLayout(''login'')
Parece que esto tiene algo que ver con esperar en las suscripciones en waitOn.
Lo siguiente resuelve los problemas de representación de diseño para mí:
Router.onBeforeAction(function() {
if (!Meteor.user() && this.ready())
return this.redirect(''/login'');
}, {except: [''login'']});
Puede poner un ayudante de plantilla if o menos en la plantilla de diseño.
{{#unless currentUser}}
{{> loginPage}}
{{else}}
{{> yield}}
{{/unless}}
Solo necesita devolver el resultado de render()
desde su onBeforeAction()
onBeforeAction: function () {
if (_.include([''login''], this.route.name)){
return;
}
if (!Meteor.userId()) {
return this.render(''login'');
}
}
También tenga en cuenta que cambié Meteor.user()
a Meteor.userId()
. Esto evita que el enganche se vuelva a ejecutar cada vez que los usuarios actuales documentan cambios.