Итак, сначала немного контекста. У меня есть приборная панель angular 2, она находится за логином и также имеет встроенный signalr. Для запроса, отправленного через http-клиент angular, я могу использовать перехватчик URL-адреса, чтобы проверить, истек ли токен, и если да, запросите новый токен из api. Это отлично работает для всех аутентифицированных вызовов, кроме signalr.
С помощью signalr при входе в систему мы устанавливаем соединение и отправляем токен-носитель как часть строки запроса. Однако, поскольку signalr является отдельным, он не использует http-клиент angular, и поэтому перехватчик URL-адреса не попадает. Я думал о разных способах справиться с этим, и для меня самым чистым из них было бы подписаться на наблюдаемый объект, который срабатывает, когда истекает срок действия токена.
Итак, теперь мой вопрос в том, есть ли у меня срок годности, могу ли я написать наблюдаемое, которое триггеры сообщают, когда срок действия истекает на пять минут раньше текущего времени. Таким образом, я мог подписаться на этот наблюдаемый объект в моем сигнальном сервисе и отключиться и подключиться с обновленным токеном аутентификации. При необходимости я могу предоставить образцы кода, но я не знаю, насколько они помогут с моим вопросом.
Спасибо за любую помощь с этим.





Этот наблюдатель сделает это
const tokenTimeout = timeout;
let currentTime = new Date();
return new Observable(observer => {
while(tokenTimeout > currentTime) {
currentTime = new Date();
}
observer.next();
observer.complete();
});
В качестве альтернативы, когда вы регистрируете клиентское соединение на сервере, зарегистрируйте время ожидания их токена с помощью регистрации клиента, затем при отправке сообщения клиенту проверьте тайм-аут, и, если он истек, сначала отправьте сообщение клиенту, чтобы обновить его токен. , то на стороне клиента в JS есть метод, обновляющий токен. Этот статья говорит о регистрации клиентских подключений. Я думаю, что у этого будет меньше шансов потерпеть неудачу.
Я не знаю о сигнализаторе, но могу предложить решение для ваших требований.
Вы можете использовать timer из rxjs, это точно так же, как setTimeout(), но только Observable.
Создайте объекты даты для expirationDate и еще одного за пять минут до истечения срока годности. Вычтите их, чтобы найти время, в течение которого Observable должен сработать.
Передайте time за миллисекунды таймеру, по которому вы сможете оформить подписку. После завершения вызова API вызовите тот же метод еще раз, чтобы повторно инициализировать таймер.
timerSubs: Subscription; // to cancel existing timer
ngOnInit() {
this.calculateTimeForTimer()
}
calculateTimeForTimer() {
let expirationDate = new Date();
expirationDate.setTime(expirationDate.getTime() + 10 * 1000); // 10 seconds from now.
// in your case use your own duration/date of expiration
let alertDate = new Date(expirationDate);
alertDate.setTime(alertDate.getTime() - 5 * 1000); // 5 seconds before expiration
// in your case subtract 5 minutes instead of 5 seconds
let timeDuration = (expirationDate.getTime() - alertDate.getTime());
this._startTimer(timeDuration);
}
private _startTimer(timeDuration) {
if (this.timerSubs) {
this.timerSubs.unsubscribe();
}
this.timerSubs = timer(timeDuration).subscribe((data) => {
// make the API call, and then calculate appropriate duartion and call startTimer() again
of("This is your new Token").pipe(delay(2000)).subscribe((apiData) => {
console.info("Data from API", apiData);
this.calculateTimeForTimer();
})
})
}
См. Образец здесь, у него есть срок годности 10 секунд от текущего времени. https://stackblitz.com/edit/angular-bhupgg
Спасибо, именно то, что мне было нужно.