Что такое дегидратированный детектор и как я его использую?
Я использую простую директиву для фокусировки текстового ввода, когда элемент активен с помощью *ngIf
. Это содержится в цикле *ngFor
.
Когда первый *ngIf
активирован, вход фокусируется, как ожидалось. Когда активируется другой вход, я получаю сообщение об ошибке:
EXCEPTION: Attempt to use a dehydrated detector.
Я не понимаю, что это значит и как я могу предотвратить ошибку. Функциональность по-прежнему работает даже с ошибкой.
@Directive({
selector: '[myAutoFocus]'
})
export class AutoFocusDirective {
constructor(private elem: ElementRef) {
window.setTimeout(function() {
elem.nativeElement.querySelector('input').focus();
});
}
}
`` `
Ответы
Ответ 1
Дегидратированный детектор - это компонент, который был удален из системы обнаружения изменений, обычно потому, что он был удален из DOM с помощью *ngIf
или другого означает:
Если в приложении есть асинхронное действие, которое попадает на этот уже незамонтированный детектор, ошибка thrown:
решение должно использовать [hidden]
вместо *ngIf
для затронутого компонента или отложить действие оскорбления до следующего тика с помощью setTimeout( () => this.offendingAction(), 0)
Ответ 2
Для GitHub существует открытая проблема: https://github.com/angular/angular/issues/6786#issuecomment-185429140
В бета-версии 2 исключение не было. В бета-версии 3-6 (4,5 и 6, похоже, просто приращения без изменений) код был изменен, чтобы исключить исключение. Вы правы, что это в настоящее время не представляет проблемы.
Пока я не знаю точной причины, по которой вы получаете эту ошибку, одна из моих учетных записей была связана с удалением компонента во время цикла проверки angular, где он обновляет представления. Другие записали свои проблемы в потоке github.
Ответ 3
"Дегидратированный детектор" означает, что детектор изменения для этого компонента/директивы больше не гидратируется. (Извините, я просто не мог устоять - я понятия не имею, что означает эта ошибка, и я не знаю, что, по-видимому, должно передавать "гидратированный" или "обезвоженный".)
Этот исходный файл говорит:
/**
* Thrown when change detector executes on dehydrated view.
*
* This error indicates a bug in the framework.
*
* This is an internal Angular error.
*/
export class DehydratedException extends BaseException {
constructor(details: string) { super(`Attempt to use a dehydrated detector: ${details}`); }
}
Итак, вы, вероятно, обнаружили внутреннюю ошибку Angular.
Я не могу воспроизвести вашу ошибку с помощью простого плунжера. У вас есть плункер, который показывает проблему?
См. также https://github.com/angular/angular/issues/6786
Ответ 4
У меня было это исключение раньше, и это очень важно, что вы используете то, что больше не существует в виртуальной памяти. В моем случае я делал почти то же, что и вы. Обратите внимание, что вы пытаетесь получить доступ к элементу после таймаута, но уверены ли вы, что этот элемент существует в памяти по истечении этого времени? У меня есть * ngIf на этом элементе, и я получил доступ после того, как условие было ложным, и оно уже было удалено.