Remove auth store, move signals around to auth service.

This commit is contained in:
Jesse Brault 2025-12-15 15:42:12 -06:00
parent 68eeeb9467
commit cce55b8ebb
8 changed files with 26 additions and 46 deletions

View File

@ -1,7 +1,8 @@
<h1>Meals Made Easy</h1> <h1>Meals Made Easy</h1>
@if (username(); as username) { @if (isLoggedIn()) {
<h3>Welcome {{ username }}</h3> <h3>Welcome {{ username() }}!</h3>
}
<button (click)="loginClick()">Login</button>
<button (click)="logoutClick()">Logout</button> <button (click)="logoutClick()">Logout</button>
} @else {
<button (click)="loginClick()">Login</button>
}
<a [routerLink]="'/'">Browse Recipes</a> <a [routerLink]="'/'">Browse Recipes</a>

View File

@ -1,4 +1,4 @@
import { Component, inject, signal } from '@angular/core'; import { Component, computed, inject } from '@angular/core';
import { AuthService } from '../service/auth.service'; import { AuthService } from '../service/auth.service';
import { RouterLink } from '@angular/router'; import { RouterLink } from '@angular/router';
@ -11,15 +11,14 @@ import { RouterLink } from '@angular/router';
export class Header { export class Header {
private readonly authService = inject(AuthService); private readonly authService = inject(AuthService);
protected readonly username = signal<string | null>(null); protected readonly username = this.authService.username;
protected readonly isLoggedIn = computed(() => !!this.authService.accessToken());
protected async loginClick() { protected async loginClick() {
const loginView = await this.authService.login('test-user', 'test'); await this.authService.login('test-user', 'test');
this.username.set(loginView.username);
} }
protected async logoutClick() { protected async logoutClick() {
await this.authService.logout(); await this.authService.logout();
this.username.set(null);
} }
} }

View File

@ -1,10 +1,10 @@
import { HttpInterceptorFn } from '@angular/common/http'; import { HttpInterceptorFn } from '@angular/common/http';
import { inject } from '@angular/core'; import { inject } from '@angular/core';
import { AuthStore } from '../service/auth.store'; import { AuthService } from '../service/auth.service';
export const authInterceptor: HttpInterceptorFn = (req, next) => { export const authInterceptor: HttpInterceptorFn = (req, next) => {
const authStore = inject(AuthStore); const authService = inject(AuthService);
const token = authStore.getAccessToken(); const token = authService.accessToken();
if (token) { if (token) {
return next( return next(
req.clone({ req.clone({

View File

@ -1,4 +1,4 @@
import { ResourceOwner } from "./ResourceOwner.model"; import { ResourceOwner } from './ResourceOwner.model';
export interface ImageView { export interface ImageView {
alt: string; alt: string;

View File

@ -23,4 +23,3 @@ export interface Recipe {
text: string; text: string;
title: string; title: string;
} }

View File

@ -3,7 +3,7 @@
} @else if (recipe.isSuccess()) { } @else if (recipe.isSuccess()) {
<app-recipe-view-card [recipe]="recipe.data()"></app-recipe-view-card> <app-recipe-view-card [recipe]="recipe.data()"></app-recipe-view-card>
} @else if (recipe.error(); as error) { } @else if (recipe.error(); as error) {
<p>{{ error }}</p> <p>{{ error.message }}</p>
} @else { } @else {
<p>There was an error loading the recipe.</p> <p>There was an error loading the recipe.</p>
} }

View File

@ -1,8 +1,7 @@
import { inject, Injectable } from '@angular/core'; import { inject, Injectable, Signal, signal } from '@angular/core';
import { HttpClient } from '@angular/common/http'; import { HttpClient } from '@angular/common/http';
import { LoginView } from '../model/LoginView.model'; import { LoginView } from '../model/LoginView.model';
import { firstValueFrom, tap } from 'rxjs'; import { firstValueFrom, tap } from 'rxjs';
import { AuthStore } from './auth.store';
import { QueryClient } from '@tanstack/angular-query-experimental'; import { QueryClient } from '@tanstack/angular-query-experimental';
import { Router } from '@angular/router'; import { Router } from '@angular/router';
@ -10,8 +9,13 @@ import { Router } from '@angular/router';
providedIn: 'root', providedIn: 'root',
}) })
export class AuthService { export class AuthService {
private readonly _accessToken = signal<string | null>(null);
private readonly _username = signal<string | null>(null);
public readonly accessToken: Signal<string | null> = this._accessToken;
public readonly username: Signal<string | null> = this._username;
private readonly http = inject(HttpClient); private readonly http = inject(HttpClient);
private readonly authStore = inject(AuthStore);
private readonly queryClient = inject(QueryClient); private readonly queryClient = inject(QueryClient);
private readonly router = inject(Router); private readonly router = inject(Router);
@ -21,8 +25,8 @@ export class AuthService {
.post<LoginView>('http://localhost:8080/auth/login', { username, password }) .post<LoginView>('http://localhost:8080/auth/login', { username, password })
.pipe( .pipe(
tap((loginView) => { tap((loginView) => {
this.authStore.setAccessToken(loginView.accessToken); this._accessToken.set(loginView.accessToken);
this.authStore.setUsername(loginView.username); this._username.set(loginView.username);
}), }),
), ),
); );
@ -32,7 +36,9 @@ export class AuthService {
public async logout(): Promise<void> { public async logout(): Promise<void> {
await firstValueFrom(this.http.post('http://localhost:8080/auth/logout', null)); await firstValueFrom(this.http.post('http://localhost:8080/auth/logout', null));
await this.queryClient.invalidateQueries(); this._username.set(null);
this._accessToken.set(null);
await this.router.navigate(['/']); await this.router.navigate(['/']);
await this.queryClient.invalidateQueries();
} }
} }

View File

@ -1,25 +0,0 @@
import { Injectable, signal } from '@angular/core';
@Injectable({
providedIn: 'root',
})
export class AuthStore {
private readonly accessToken = signal<string | null>(null);
private readonly username = signal<string | null>(null);
public setAccessToken(accessToken: string | null): void {
this.accessToken.set(accessToken);
}
public getAccessToken(): string | null {
return this.accessToken();
}
public setUsername(username: string | null): void {
this.username.set(username);
}
public getUsername(): string | null {
return this.username();
}
}