Я пытаюсь транслировать событие из компонента authguard в свой компонент заголовка.
Служба вещания
@Injectable()
export class BroadcastService {
public subject = new Subject<any>();
sendMessage(message: string) {
this.subject.next(message);
}
}
Получатель (компонент заголовка)
export class HeaderComponent {
constructor(public broadcast: BroadcastService) {
this.broadcast.subject.subscribe(message => {
alert('broadcast received: ' + message);
});
}
}
Трансляция (компонент authguard - не работает)
export class AuthGuard implements CanActivate {
constructor(public broadcast: BroadcastService) {
}
canActivate(): boolean {
this.broadcast.sendMessage('Hi from AuthGuard');
return true;
}
}
Трансляция (компонент дашборда - работает)
export class DashbardComponent {
constructor(public broadcast: BroadcastService) {
}
ngOnInit() {
this.broadcast.sendMessage('Hi from AppComponent');
}
}
app.component.html
<headerComponent></headerComponent>
<router-outlet></router-outlet>
маршрутизация
{
path: 'dashboard',
component: DashboardComponent,
canActivate: [AuthGuard]
}
Проблема в том, что когда я транслирую из своего компонента authguard, получатель в моем компоненте заголовка никогда не получает сообщение. Я могу подтвердить, что метод canActivate в authGuard вызывается для каждого пути.
Но когда я транслирую из компонента страницы (например, приборной панели), получатель в компоненте заголовка действительно получает сообщение.
Кто-нибудь знает, как опубликовать сообщение от authguard в моем компоненте заголовка?





Пожалуйста, используйте BehaviorSubject вместо Subject
BehaviorSubject содержит одно значение. Когда он подписан, он сразу же выдает значение. Тема не имеет ценности.
Пожалуйста, проверьте это https://stackoverflow.com/a/43351340/2742156
let bSubject = new BehaviorSubject(null); // null or any default value
bSubject.subscribe(value => {
console.info("Subscription got", value);
});
Подписчик всегда получает последнее переданное значение
Обновлено:
Сторожить
@Injectable()
export class AuthGuard implements CanActivate {
constructor(private broadcastService: BroadcastService) {}
canActivate(): boolean {
console.info('auth guard called');
this.broadcastService.subject.next('from guard');
return true;
}
}
служба вещания
@Injectable()
export class BroadcastService {
public subject = new BehaviorSubject<any>('hello');
sendMessage(message: string) {
this.subject.next(message);
}
}
подписчик (компонент заголовка)
constructor(private broadcastService: BroadcastService) {
broadcastService.subject.subscribe((res) => {
console.info('Inside login', res);
});
}
конфигурация маршрута
{
path: 'some route',
component: SomeComponent,
canActivate: [AuthGuard]
}
Спасибо, BehaviorSubject кажется лучшей практикой. Но это все еще не решает проблему с передачей AuthGuard, не полученной в заголовке.
@FruitDealer вы не возвращаете логическое значение из метода canActivate. Пожалуйста, верните истину или ложь
извините, я оставил код, чтобы он был понятнее для демонстрационных целей. Я отредактировал сообщение, чтобы включить возвращаемый тип.
@FruitDealer у меня работает с BehaviorSubject. Я дополню свой ответ тем, что пробовал. Если это все еще не сработало, создайте stackblitz, JsFiddle я исправлю для вас
Вы должны использовать BehaviorSubject
вот пример
boradcast.service.ts
import { Injectable } from '@angular/core';
import { Subject, BehaviorSubject } from 'rxjs'
@Injectable({
providedIn: 'root'
})
export class BroadcastService {
constructor() { }
public subject = new BehaviorSubject<any>('');
sendMessage(message: string) {
this.subject.next(message);
}
}
вот демо Stackblitz
отличается ли этот ответ от того, что я упомянул, за исключением Stackblitz?
@FruitDealer попросил вас предоставить stackblitz, и я поставил эту демонстрацию перед вашим ответом, но я опоздал, чтобы опубликовать здесь .... и главное, что когда вы даете ответ другим с демонстрацией, это будет иметь значение ..
так что это зависит от @FruitDealer, ответ которого полезен для него.
@AniketAvhad Header - это компонент в моем app.component.html. Также на панели инструментов есть путь с авторизацией на нем. Я обновлю свой вопрос кодом
@FruitDealer сказал, что BehaviorSubject не работает для него, хотя он работает для меня и вас. Поэтому попросил его предоставить скрипку для определения проблемы.
Насколько я понимаю, вы хотите, чтобы при нажатии на dashboard link вы хотели, чтобы сообщение было в header.component.
@AniketAvhad Да, правильно. Когда дашборд загружается, он вызывает authguard, который отправляет сообщение компоненту заголовка.
@AniketAvhad Кажется, ваше решение работает. Мой похож, и он не работает. Будет ли проблема с использованием Angular 5?
Пожалуйста, используйте BehaviorSubject вместо Subject. Может быть, компонент заголовка вообще не активен, когда вы генерируете событие и нет подписки для вашего объекта.