I have a logic issue and I’m not sure how to proceed. I have an auth method that sends email and password, and my API responds with a JWT token. Then, I need a getCurrentUser method, but I have multiple roles, each with its own model—for example, I have admin, moderator, and user, and each has its own model. How should I approach this?
I’ve thought about having 3 methods: LoadCurrentUser, LoadCurrentModo, and LoadCurrentAdmin, each receiving its own model. I’m not sure if it’s a good approach and how I could determine which method to call after the user has authenticated. Then, I asked ChatGPT if it has any idea.
export type UserType = Admin | Modo | User;
getCurrentUser(): Observable<UserType> {
return this.http.get<UserType>(`/api/user/current`).pipe(
map((data: any) => {
switch (data.role) {
case 'admin':
return data as Admin;
case 'modo':
return data as Modo;
default:
return data as User;
}
})
);
}
My current method with Ngrx Signal Store :
getCurrentUser: rxMethod<void>(
pipe(
tap(() => patchState(store, { isLoading: true })),
concatMap((input) => {
return infra.loadCurrentUser().pipe(
tapResponse({
next: (user) => {
patchState(store, {
isLoading: false,
user: user,
});
},
error: () => {
patchState(store, { isLoading: false });
},
})
);
})
)
),
Do you have an idea?
As Admin
and Modo
extend from User
, your getCurrentUser()
function should return an Observable of type User
.
getCurrentUser(): Observable<User> {
return this.http.get<User>(`/api/user/current`);
}
Now you can offer functions to check if a user is an admin or modo, using the is
keyword:
isAdminUser(user: User): user is Admin {
return 'role' in user && user.role === 'admin';
}
isModoUser(user: User): user is Modo {
return 'role' in user && user.role === 'modo';
}
And use those functions like the following:
service.getCurrentUser().subscribe(user => {
if (service.isAdminUser(user)) {
// user now has type `Admin` in this block
// you can safely use properties which only exist in the `Admin` type
}
});