Correctly display modal screen in Angular 7 - asp.net

I have an ASP.Net Core 2.0 project with Angular 7 material.
I've correctly implemented the forgot password function within Angular which when invoked, would prompt a user to enter in their email address. This would send them a password reset email link. Once that link is clicked, they are redirected to Angular's page which is where my problem lye. What I'm hoping to achieve is redirect the user to a modal screen instead of a page.
.NET
[HttpGet("reset")]
public IActionResult Reset(string email, string token)
{
if (token == null)
{
return BadRequest();
}
if (token != null)
{
//sends them to angular application with email and token
return Redirect("http://localhost:4200/resetPassword" + $"?email={email}&token={token}");
}
else
{
return BadRequest();
}
}
This is what the link from the server side would look like =>
localhost:4200/reset?emailaddress=samsmith#gmail.com?token=fdsajfdfadsafdasfdsafdsafdasfdsaf
What I've tried so far is to specify the outlet as modal within the route, which didn't work.
{ path: 'reset', outlet: 'modal', component: ResetComponent }
To summarize:
User clicks on Forget password => then request goes to server side, generating a token => token and user email is sent back to Angular modal screen => user enters password and confirms password.
How should I go about it?

Related

How to differentiate NextAuth user signin and signup?

I am building a blog platform using Nextjs 12, NextAuth(Google), Prisma(MySQL). When a user first signs up to my platform, NextAuth automatically saves user's google email address and google name to my database. I want to make user change their nickname when first signing up.
How would I know if the user is signing up or signing in? Currently in NextAuth, you click signup() button and you are good for both signup and signin..
I would extend the base user model with a property such as customName, and then check on the front- or back-end whether the customName property is undefined/empty, and redirect or show a modal accordinglty.
You can perform the front-end check via useSession
const { data: session, status } = useSession()
if(status === "authenticated" && session.user.customName === ""){ // or whatever your default value for non-defined fields is
// Show your modal or redirect to the page where the user can change his username
// after user enters his new name, make an API call and update it in your DB
}
or on the back-end in pages/api/auth/[...nextauth].js:
...
callbacks: {
async signIn({ user, account, profile, email, credentials }) {
if (user.customName) {
return true
} else {
// User has no custom name yet, redirect him
return '/pathWhereUserCanSetHisName'
}
}
}
...
If you want to ensure every user has to set a name before continuing, I would put the logic above into an API middleware or next's edge middleware like this:
For example, if you're using NextAuth JWT sessions via cookies, add a custom cookie name for the sessionToken and parse it within the next.js middleware:
middleware.ts (or .js)
export default async function middleware(request: NextRequest) {
const response = NextResponse.next();
const userCookie = request.cookies.get(YOUR_CUSTOM_COOKIE_NAME) // the cookie name you set for NextAuth's sessionToken
if(!userCookie){
// user not logged in
return NextResponse.redirect('/login')
}
const user = yourCustomUserParsingFunction(userCookie) // parsing the JWT contained in the cookie
if(user.customName){
return response; // user has a custom name, don't intervene
}
// user has no customName, intervene
return NextResponse.redirect('/pathWhereUserCanSetHisName');
}

How to use SSR Firebase Authentication in Nuxt-js with Middleware?

In my project , user can login in system . If users do not choose "Remember me " option in beginning, their session will end after page closed entirely.
My firebase works Client Side
in firebase.js
export default ({ store, $storage }) => {
onAuthStateChanged(auth, async user => {
if (user && !user.isAnonymous) {
store.commit('firebase-auth/setUser', user);
if (user.emailVerified) {
$storage.setCookie('firebase_token', user.accessToken);
}
} else {
enableGoogleOneTapSignIn(user);
}
});
};
in MiddleWare auth.js
export default ({ $storage, req, redirect }) => {
if (process.server) {
const token = !!req.headers.cookie.firebase_token;
if (!token) return redirect('/');
} else if (process.client) {
const token = !!$storage.getCookie('firebase_token');
if (!token) return redirect('/');
}
};
This code controls if user signed in or not . This works in server and client side.
The problem is ; When user chose "remember me" option at the beginning , session will not finish even if user closes entire browser. And if user opens the browser again , his session will continue and he will be logged-in already but in this scenario I can not reach cookie because it was deleted when browser was closed .
If user comes with a direct link like abc.com/user/my-profile when browser was closed, user will not reach his profile beacuse cookie was cleaned . I need to find a good way for this problem .

Show multi-login popup when user is loggedin in multiple google account and bypass the login popup if user is loggedin in only one accout

I am working to add google sign-in flow on web app. Trying to figure out if we can achieve this functionality,
if user is logged-in in multiple google account, show the multi-login popup where user can choose the account.
if user is logged-in in only one google account and has previously signed into the application, bypass the login page and direct them to the application.
I thought auth2.signIn, it checks to see how many accounts are present, and based on this it achieve those above use-cases.
As further context, the javascript for the login page code is currently:
<script src="https://apis.google.com/js/platform.js?onload=init_google_signin" async defer></script>
<script>
function init_google_signin() {
var auhtInstance,
clientID = 'client_id';
auhtInstance = gapi.load('auth2', function () {
/**
* Retrieve the singleton for the GoogleAuth library and set up the
* client.
*/
auth2 = gapi.auth2.init({
client_id: clientID,
scope: 'email profile'
});
});
}
</script>
Further the google sign-in button click handler is written as,
function handleGoogleSignIn() {
var GoogleAuth,
currentUser,
googleAuthPromise;
GoogleAuth = gapi.auth2.getAuthInstance();
currentUser = GoogleAuth.currentUser.get();
if (currentUser && currentUser.isSignedIn()) {
// submit form with access_token and user info, service will redirect user to logged-in page
setGoogleFormValues(currentUser, currentUser.getBasicProfile());
} else {
googleAuthPromise = GoogleAuth.signIn();
googleAuthPromise.then(function (user) {
// submit form with access_token and user info, service will redirect user to logged-in page
setGoogleFormValues(currentUser, currentUser.getBasicProfile());
});
}
}
To Fix this, i tried,
when user logging-out from app, logout from google GoogleAuth.signOut();
when user clicks on google sign-in button, revoke access first then it will always prompt the login popup GoogleAuth.disconnect();
use prompt: 'select_account' while signin, so handleGoogleSignIn will look like,
function handleGoogleSignIn() {
var GoogleAuth,
currentUser,
googleAuthPromise;
GoogleAuth = gapi.auth2.getAuthInstance();
currentUser = GoogleAuth.currentUser.get();
googleAuthPromise = GoogleAuth.signIn(prompt: 'select_account');
googleAuthPromise.then(function (user) {
// submit form with access_token and user info, service will redirect user to logged-in page
setGoogleFormValues(currentUser, currentUser.getBasicProfile());
});
}
}
These all three fix always open the popup so it fixed the 1st use case but failed on 2nd use case.
I would really appreciate thoughts on how to achieve both use cases.
Many thanks!

Redirect user on login

I've been trying to figure this out for hours but everything I try fails. I'm trying login a user and on success get route the user to the correct url based on the user's role. In the example below, I login successfully, and the user is successfully identified however when I try to redirect or push.history it doesn't let me. There are no errors, it just stays on the login url.
I'm using:
React router 4, Meteorjs
handleSubmit(event) {
event.preventDefault();
Meteor.loginWithPassword(email, password, (error, result) => {
if (error) {
this.setState({ loginError: 'Incorrect username or password.' });
} else {
if (!!Roles.userIsInRole(Meteor.userId(), 'isAdmin')) {
<Redirect to="/admin/dashboard" push />
}
}
});
}
A react component is something that is rendered, it's not just a function that you can call from anywhere.
Use history.push('/admin/dashboard")
If the router is being passed into your component as a prop you might also find yourself doing
this.props.history.push('/admin/dashboard")

Ionic 3 firebase doesn't show that email is verified

I've run into a problem during development of email verification with firebase.
Whenever I try to verify the email address, I can't get the info that user's email address is verified.
I have a code like this:
constructor(private afAuth: AngularFireAuth, public navCtrl: NavController, public navParams: NavParams) {
}
ionViewWillEnter() {
this.afAuth.auth.onAuthStateChanged(user => {
if (user && user.emailVerified) {
this.navCtrl.setRoot(ShoppingListPage);
}
});
}
proceedButtonHandler() {
this.afAuth.auth.onAuthStateChanged(user => {
if (user && user.emailVerified) {
this.navCtrl.setRoot(ShoppingListPage);
}
});
}
But after I verify the email address and run proceedButtonHandler function, in user.emailVerified field I always get "false" result, unless I refresh the page.
What is the right way to know if user's email is currently verified? And is there any way to watch for "emailVerified" field changes and redirect the user to another page without clicking the button? (there is an attempt to do this in "ionViewWillEnter" function)
If the user email is verified out of band via the email verification link, you need to do 2 things on the client after verification:
call currentUser.reload. This will update the emailVerified property on the user.
call currentUser.getIdToken(true) to force token refresh or just wait for the token to be refreshed and automatically pick up the change. This is needed for the email_verified property on the token to update.
Firebase now allows you to return back to the app after email verification. Here is an example via the web client:
https://firebase.google.com/docs/auth/web/passing-state-in-email-actions
You can use this when you return back to the app from such operation to reload the user/token knowing the user just verified their email. The above also allows you to pass state in the flow.

Resources