我的身份验证服务+组件存在问题,因为每次加载auth组件时,服务似乎都会重新初始化。我应用程序中应该出现的流程是,应用程序启动时,根应用程序组件应发送一个登录请求,以检查当前会话是否经过身份验证。此登录请求正在从身份验证服务发送。 auth-service有一个主题广播一个布尔值,指示用户是否经过身份验证,具体取决于登录/注销操作的结果。
除了一种情况外,这种方法很有效。如果我在auth页面上启动应用程序,导航离开组件并返回到它,我无法从服务获得正确的身份验证状态(true / false)。打印时的字段(在服务中)由于某种原因未定义。为了调试,我甚至在ngOnInit函数中插入了console.logs,以查看是否正在重新初始化任何组件/服务,但没有。
以下是它现在看起来的代码示例,app.component.ts
(根组件):
constructor(private requestService: RequestService,
private authService: AuthService) {}
ngOnInit() {
console.log("App component init");
this.requestService.get('http://localhost:8000/api/csrf/')
.subscribe(
success => {
this.authService.login('', '');
}
);
}
登录请求是第一次CSRF检查的结果,到目前为止效果很好。
auth.service.ts
@Injectable()
export class AuthService implements OnInit, OnDestroy {
authenticated: boolean;
authSubject: Subject<boolean>;
constructor(private requestService: RequestService) {
console.log("Auth service constructor");
this.authSubject = new Subject<boolean>();
}
ngOnInit() {
console.log("Auth service init");
this.authSubject.subscribe(
next => {
this.authenticated = next;
}
);
}
login(username: string, password: string) {
console.log("Auth service login");
this.requestService.post(LOGIN_URL, { username: username, password: password })
.subscribe(
next => {
this.authSubject.next(true);
console.log("[AuthService] Success logging in.");
},
error => {
console.log("[AuthService] Error logging in.");
},
() => {
console.log("[AuthService] Auth service completed.");
}
);
}
logout() {
this.requestService.post(LOGOUT_URL, {})
.subscribe(
next => {
this.authSubject.next(false);
console.log('[AuthService] Success logging out.');
},
error => {
console.log("[AuthService] Error logging out.");
},
() => {
console.log("[AuthService] Auth service completed.");
});
}
isAuthenticated(): boolean {
return this.authenticated;
}
ngOnDestroy() {
console.log("Auth service destroyed");
this.authSubject.unsubscribe();
}
}
在这里,我们可以看到,我已经在构造函数中而不是在ngOnInit中实例化了Subject。这是因为当从app.component.ts
触发登录时,尚未创建导致崩溃的主题。这仍然有用。
auth.component.ts
export class AuthComponent implements OnInit {
authenticated: boolean;
constructor(private authService: AuthService) { }
ngOnInit() {
console.log("Auth component init");
this.authService.authSubject.subscribe(
next => {
this.authenticated = next;
}
);
this.authenticated = this.authService.isAuthenticated();
console.log(this.authenticated);
}
onLogin(form: NgForm) {
const username = form.value.username;
const password = form.value.password;
this.authService.login(username, password);
}
onLogout() {
this.authService.logout();
}
所以,这就是我被困的地方。当我登录时,看到我成功获得响应并且authenticated = true。但是,当我离开auth视图然后返回到它时,从authService.isAuthenticated获取经过身份验证的值会让我回到&#34; undefined&#34;!服务在那里并且完好无损(我点击了ngOnDestroy服务,没有任何东西被解雇)所以我猜测有一个参考问题或什么,我只是无法在文档中找到任何帮助我的东西。
请告知。
答案 0 :(得分:0)
尝试使用BehaviorSubject
而不只是Subject
。 BehaviorSubject
将在订阅之前广播最后一个值加上任何新值,而主题只会在您订阅后广播出任何新数据。
答案 1 :(得分:0)
问题在于没有为角度服务调用ngOnInit,因此在auth服务中从未激活订阅。当我将订阅移动到服务构造函数时,一切正常!