How to show login page by default after logout? - spartacus-storefront

I want to show my login screen after logout.
Currently without LogoutModule after logout my page is redirecting to a blank screen and if I implement it as per the documentation, it redirects to homepage.
Documentation reference: https://sap.github.io/spartacus/modules/LogoutModule.html
#NgModule({
imports: [
PageLayoutModule,
RouterModule.forChild([
{
path: null,
canActivate: [LogoutGuard, CmsPageGuard],
component: PageLayoutComponent,
data: { cxRoute: 'logout' },
},
]),
],
})
I have tried protecting my homepage, however if I do that, I am unable to logout at all i.e. nothing is happening if I click logout.

You can achieve this by overriding the default getRedirectUrl from LogoutGuard.
Currently, the base class redirects to login page upon logout if and only if it's a closed shop. Meaning, the user must login before doing any action (early login).
An example of how to override the LogoutGuard behavior is to do the following:
1 - create your custom logout guard
#Injectable({
providedIn: 'root',
})
export class NewLogoutGuard extends LogoutGuard {
constructor(
auth: AuthService,
cms: CmsService,
semanticPathService: SemanticPathService,
protectedRoutes: ProtectedRoutesService,
router: Router,
authRedirectService: AuthRedirectService
) {
super(
auth,
cms,
semanticPathService,
protectedRoutes,
router,
authRedirectService
);
}
protected getRedirectUrl(): UrlTree {
return this.router.parseUrl(this.semanticPathService.get('login'));
}
}
2 - aliasing the class providers by providing the new logout guard
{ provide: LogoutGuard, useExisting: NewLogoutGuard },

Related

How to set scope(or role) of nuxt $auth.user?

I am using nuxt-auth with google oauth2 config, here is my nuxt.config.js config:
auth: {
scopeKey: 'scope',
strategies: {
google: {
client_id: process.env.GOOGLE_KEY,
codeChallengeMethod: '',
scope: ['profile', 'email'],
responseType: 'token id_token'
}
},
redirect: {
login: '/login',
logout: '/logout',
home: '/',
callback: '/welcome'
}
},
router: {
middleware: ['auth']
},
I use this code to login
this.$auth.loginWith('google')
I want to setup a role for user (visit app database) after successful login, so I added this code to my welcome.vue (oauth2 callback page)
<script>
export default {
mounted () {
const user = this.$auth.user
user['scope'] = 'some_role_from_db'
this.$auth.setUser(user)
}
}
</script>
but this code is never called, because application is immediately redirected to the page that user has selected before visiting login page (welcome.vue html markup is shown for 1 sec).
What is the correct way to set some attributes to this.$auth.user immediately after login? Is there some easy way to set role to user after OAUTH2 authentication?
user roles must came from server and it wrong to define it from client side ,
but if that is importent you can do it like that :
this.$auth.loginWith('google').then(() => {
const user = this.$auth.user
user['scope'] = 'some_role_from_db'
this.$auth.setUser(user)
})
I've added this section to my auth object in nuxt.config.js
rewriteRedirects: false
and so my app always redirects me to home url, and on home page I can access auth object like
<script>
export default {
mounted () {
const user = this.$auth.user
user['scope'] = 'some_role_from_db'
this.$auth.setUser(user)
}
}
</script>

How do I automatically redirect the user if they are already logged in using Vue and Firebase authentication?

Description
I am trying to automatically route the user to the "Games.vue" component if they are already logged in. For authentication I am using Firebase and I check if they are logged in using:
var user = firebase.auth().currentUser;
if (user) {
// User is signed in.
} else {
// No user is signed in.
}
What I want to have happen is for the user to not see the Login page if they are already signed in. So they are taken directly to the Games page. I don't know how to accomplish this using Vue. I need something to run before the Login-component that redirects if logged in.
Attempt at solution
The only way I know how to solve this is to show the Login page, check if the Firebase user is logged in and then go to the Games page. This can work, but it isn't the behavior I am looking for. I am using the Vue router. Thank you for your help.
I would suggest to use a VueRouter global guard like so:
const router = new VueRouter({ ... })
router.beforeEach((to, from, next) => {
if (!user) {
next('login');
} else {
next();
}
})
That being said, you then need a way to specify which route requires authentication. I would suggest to use route meta fields like so:
routes = [
{
name: 'login',
path: '/login',
meta: {
requiresAuth: false
}
},
{
name: 'games',
path: '/games',
meta: {
requiresAuth: true
}
}
]
Now your guards becomes:
if (!user && to.meta.requiresAuth) {
next('login');
} else {
next();
}
Vue router provides an example for this use case, take a look at the documentation.
TIP: Make sure to subscribe to auth changes using Firebase onAuthStateChanged method.
let user = firebase.auth().currentUser;
firebase.auth().onAuthStateChanged(function(user) {
user = user;
});
EDIT: To redirect once logged in, just watch for auth changes and redirect using router.push.
auth.onAuthStateChanged(newUserState => {
user = newUserState;
if (user) {
router.push("/games");
}
});

Aurelia - Update the menubar once a user has logged out

I have navmenu that needs to reloaded after a user logs out.
I have a logout.ts that essentially clears the JWT and loggedIn value.
import { autoinject } from "aurelia-framework";
import { TokenService } from "../../auth/tokenService"; z
import { Router } from 'aurelia-router';
#autoinject
export class Logout {
constructor(private tokenService: TokenService, public router: Router) {
tokenService.clearJWT();
this.router.refreshNavigation()
}
}
Thats all fine but I wanted to redirect to the home page but at the same time update the menu this time rechecking for loggedIn status.
I tried redirect, I have tried:
this.router.navigateToRoute('home')
and the one above. In all cases the navmenu does not update. By updating the navmenu it will check for a loggedin value in localstorage and change the structure of the menu.
I also wanted it to go the home page after removing those items but more importantly how do I get it to refresh the navmenu?
It sounds like you need to make sure your home route is refreshed even though it is already the current route. If so, in your configureRouter method, add activationStrategy.replace:
import {activationStrategy} from 'aurelia-router';
export class MyClass {
configureRouter(config) {
config.map([{
route: 'home',
name: 'home',
activationStrategy: activationStrategy.replace,
title: 'My Title',
moduleId: 'myModule',
}]);
}
}

How to Load Certain Route on Electron App Activate Event

I'm having a really hard time to figure out how to load a particular route when the activate event is fired. I'm creating an Electron application using the Electron-Vue framework and I've these following routes:
export default [
{
path: '/',
name: 'login-page',
component: require('components/LoginPageView')
},
{
path: '/tracker',
name: 'tracker-page',
component: require('components/TrackerPageView')
},
{
path: '*',
redirect: '/'
}
]
Now, I'd like to load the /tracker route once the app.on('activate') is fired on the following:
app.on('activate', () => {
if (mainWindow === null) {
createWindow()
}
})
The main reason behind this is I'm creating a two window Electron application. The first window would be the login and the second window would be user profiles. When the user already logged in and closed the app using the system close button, the app stays in the Dock bar and when the app is clicked, the Electron activate event is fired and the login screen shows again. Since the user is already logged in, I don't want the user to show the login window again. Any suggestion would be must appreciated.
I was finally able to achieve this by using the Vue-Router Per-Route Guard beforeEnter method. Here's my draft:
let auth = true
export default [
{
path: '/',
name: 'login-page',
component: require('components/LoginPageView'),
meta: {
auth: false
},
beforeEnter: (to, from, next) => {
if (auth) {
next('/tracker')
} else {
next()
}
}
},
{
path: '/tracker',
name: 'tracker-page',
component: require('components/TrackerPageView'),
meta: {
auth: true
}
},
{
path: '*',
redirect: '/'
}
]
Any feedbacks are most welcome to improve this even better :)

Angular 2 security: redirect to clicked route after login?

I'm building my first app using the release version of Angular 2 (I'm on 2.1.0 currently). I have set up a Route Guard, and I am using it in my routing.ts to secure one of the routes with authentication. When clicked, if not logged in, it redirects the user to the login route. There they can login, and if authenticated, it sets a localStorage token. Here's where I have a problem. I want to then redirect the user to the route they clicked on initially before they were redirected to the login, but I can't figure out how to get the clicked route once they hit the Guard canActivate method, or on the login. This seems like a fairly common usage scenario, but I can't find any examples of doing this.
Ok this is my stripped out example which should illustrate the point:
#Injectable()
export class AuthGuardService implements CanActivate
{
toUrl;
constructor(public authenticationService: AuthenticationService,
public router: Router)
{
}
canActivate(route, state): boolean
{
this.toUrl = state.url; //This is the url where its going
if (this.authenticationService.isLoggedIn()) return true;
this.router.navigate(['/login', {redirect: this.toUrl}]);
}
}
and in the login component use the ngOnInit to check for any redirect ulrs:
export class LoginComponent
{
redirect;
constructor(
private authenticationService: AuthenticationService,
private route: ActivatedRoute,
private router: Router)
{
}
ngOnInit()
{
this.redirect = this.route.snapshot.params['redirect'];
}
logIn(): void
{
this.authenticationService
.login(this.searchParams)
.subscribe(
() =>
{
this.logInSuccess();
},
error =>
{
this.logInFail(error)
})
}
logInSuccess(): void
{
if (this.redirect)
{
this.router.navigateByUrl(this.redirect);
}
else
{
this.router.navigate([''])
}
}
}