Как оценить состояние в app.component от сервиса в angular 7?
У меня проблема с моим app.component.html, я использую этот блок:
<router-outlet *ngIf="!accessGranted"></router-outlet>
<div *ngIf="accessGranted" class="wrapper">
<app-header></app-header>
<app-left-menu></app-left-menu>
<router-outlet></router-outlet>
<app-footer></app-footer>
<app-right-menu></app-right-menu>
</div>
Когда accessGranted
ложно я загружаю тему входа, когда accessGranted
это правда, я загружаю все из приборной панели. Хорошо, это прекрасно, работает, я ожидал. Но проблема в том... как обновить переменную accessGranted
из службы? В настоящее время у меня есть это в app.component.ts:
app.component.ts
import { Component, OnInit, OnDestroy } from '@angular/core';
import { ThemeService } from './services/theme.service';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit, OnDestroy {
title = 'SmartliveWeb';
accessGranted: boolean;
constructor (private _themeService: ThemeService) {
this.accessGranted = _themeService.accessGranted;
}
}
theme.service.ts
import { Injectable } from '@angular/core';
@Injectable({
providedIn: 'root'
})
export class ThemeService {
accessGranted = false;
constructor() {
}
}
Когда пользователь входит в приложение, я хочу изменить accessGranted
чтобы изменить тему, но всегда оставайтесь ложным. Любой способ применить изменения в app.component, когда accessGranted
в сервисе меняется?
4 ответа
Чтобы обновить значение в компоненте, вам нужно создать Observable для этой переменной, чтобы при изменении переменной запускать значение и компонент мог его прослушивать. Например:
private static accessGranted = new Subject();
accessGranted$ = ThemeService.accessGranted.asObservable();
onLogin(){
if(loginSuccess){
ThemeService.accessGranted.next(true);
}else{
ThemeService.accessGranted.next(false);
}
}
А в app.component вы можете подписаться следующим образом:
ngOnInit(){
this._themeService.accessGranted$
.subscribe((res) => this.accessGranted = res)
}
Но я думаю, что это не правильный способ сделать это. Вы можете использовать в качестве дочернего маршрута и использовать охранников маршрута, предоставляемых от angular, как canActivate. Более подробная информация здесь: CanActivate Doc
Вы можете написать метод для обслуживания и сделать accessGranted
Observable
или даже лучше: BehaviorSubject
,
В сервисе:
export class ThemeService {
private accessGrantedSubject$: BehaviorSubject<boolean> = new BehaviorSubject(false);
accessGranted = () => this.accessGrantedSubject$.asObservable();
constructor() {
}
setAccessGranted = (isGranted: boolean): void => {
this.accessGrantedSubject$.next(isGranted);
}
}
В компоненте:
export class AppComponent implements OnInit, OnDestroy {
title = 'SmartliveWeb';
accessGranted: Observable<boolean>;
constructor (private _themeService: ThemeService) {
this.accessGranted = this._themeService.accessGranted();
}
}
А в шаблоне вы можете использовать async
трубы:
<div *ngIf="accessGranted | async" class="wrapper">
...
</div>
Если вы хотите изменить accessGranted
собственности, вы могли бы назвать setAccessGranted()
способ обслуживания.
Надеюсь, это поможет.
Это может быть достигнуто с помощью общего сервиса. Вот как будет выглядеть код:
Создайте новый файл Service.ts
import { Injectable } from '@angular/core';
import { Subject } from 'rxjs/Subject';
@Injectable()
export class SharedService {
// Subject (emitter) for User Name Change
AccessGrantChange: Subject<boolean> = new Subject<boolean>();
// SetUserChange() - This method sets the local variable and emits the change
SetAccessGrant(param: boolean) {
this.AccessGrantChange.next(param);
}
}
В компоненте входа в систему, как только вы получите результат от сервиса, то есть в методе подписки напишите следующий код:
this._sharedService.SetAccessGrant(newCityName);
Убедитесь, что в конструкторе вы ввели класс обслуживания. А в файле app.component.ts в ngOnInit подпишитесь на событие и измените значение:
import { Component, OnInit, OnDestroy } from '@angular/core';
import { ThemeService } from './services/theme.service';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit, OnDestroy {
title = 'SmartliveWeb';
accessGranted: boolean;
constructor (private _themeService: ThemeService) {
_themeService.accessGranted = this.accessGranted;
}
ngOnInit(){
this._sharedService.AccessGrantChange
.subscribe((value) => {
this..accessGranted=value;
});
}
Ваше назначение в конструкторе неверно
constructor (private _themeService: ThemeService) {
this.accessGranted = _themeService.accessGranted;
}
constructor (private themeService: ThemeService) {
this.themeService = themeService;
}
login()
{
this.themeService.login((res) => {
this.themeService = res;
});
}
в вашем сервисе тем осуществите вход и возврат true
на успех