Angular 4 표현식이 확인된 후 변경됨 오류
상위 구성 요소 =>
ExpressionChangedAfterItHasBeenCheckedError: Expression has changed after it was checked. Previous value: ''. Current value: '[object Object]'.
at viewDebugError (vendor.bundle.js:8962)
at expressionChangedAfterItHasBeenCheckedError (vendor.bundle.js:8940)
상위 구성 요소 Html
<div>
<app-child-widget [allItems]="allItems" (notify)="eventCalled($event)"></app-child-widget>
<div>
상위 구성 요소
export class ParentComponent implements OnInit {
returnedItems: Array<any> = [];
allItems: Array<any> = [];
constructor(
) { }
ngOnInit() {
this.allItems = // load from server...
}
eventCalled(items: Array<any>): void {
this.returnedItems = items;
}
}
하위 구성 요소
@Component({
selector: 'app-child-widget',
templateUrl: 'child.component.html',
styleUrls: ['./child.component.css']
})
export class ChildComponent implements OnInit {
@Output() notify: EventEmitter<any> = new EventEmitter();
@Input() private allItems: Array<any>;
constructor() { }
ngOnInit() {
doSomething();
}
doSomething() {
this.notify.emit(allItems);
}
}
오류에 대해 알아야 할 모든 내용은 이 동작을 매우 자세히 설명합니다.
원인
문제는 이 문제와 매우 유사하지만 서비스를 통해 상위 속성을 업데이트하는 대신 동기식 이벤트 브로드캐스트를 통해 업데이트합니다.다음은 링크된 답변의 인용문입니다.
다이제스트 사이클 동안 Angular는 하위 디렉티브에 대해 특정 작업을 수행합니다.이러한 작업 중 하나는 입력을 업데이트하고 하위 지침/구성 요소에서 ngOnInit 라이프사이클 후크를 호출하는 것입니다.중요한 것은 이러한 작업이 엄격한 순서로 수행된다는 것입니다.
- 입력 업데이트
- 호출 초기화
그래서 당신의 경우 Angular 업데이트된 입력 바인딩.allItems
하위 구성 요소에서, 그런 다음 호출onInit
업데이트를 유발한 하위 구성 요소에 대해allItems
상위 구성 요소의.이제 데이터 불일치가 발생합니다.상위 구성 요소에는 하나의 값이 있고 하위 구성 요소에는 다른 값이 있습니다.Angular가 계속해서 변경 사항을 동기화하면 무한 루프가 발생합니다.다음 변화 감지 주기 동안 Angular가 다음을 감지한 이유입니다.allItems
변경되어 오류가 발생했습니다.
해결책
업데이트 중인 응용프로그램 설계 결함인 것 같습니다.details
상위 및 하위 구성 요소 모두에서.그렇지 않은 경우 다음과 같이 이벤트를 비동기적으로 실행하여 문제를 해결할 수 있습니다.
export class ChildComponent implements OnInit {
@Output() notify: EventEmitter<any> = new EventEmitter(true);
^^^^^^-------------
하지만 여러분은 매우 조심해야 합니다.만약 당신이 다른 후크를 사용한다면,ngAfterViewChecked
그것은 모든 다이제스트 사이클에서 호출되고 있으며, 당신은 순환 의존성이 될 것입니다!
저의 경우, 저는 제 데이터의 상태를 변경하고 있었습니다. 이 답변은 AngularInDepth.com 의 다이제스트 사이클 설명을 읽어야 합니다. HTML 레벨에서 제가 해야 할 일은 데이터를 다루는 방식을 다음과 같이 변경하는 것이었습니다.
<div>{{event.subjects.pop()}}</div>
안으로
<div>{{event.subjects[0]}}</div>
요약: 배열의 마지막 요소를 반환하고 제거하여 데이터의 상태를 변경하는 팝핑 대신, 데이터의 상태를 변경하지 않고 데이터를 가져오는 일반적인 방법을 사용하여 예외를 방지했습니다.
이 오류가 발생하면 다음을 사용할 수 있습니다.rxjs
timer
짧은 시간 동안 통화를 지연시키는 것.
이 예에서는 다음을 사용합니다.@angular/material
stepper
URL의 쿼리 매개 변수에서 기본 단계를 로드합니다.
import { timer } from 'rxjs'
@Component({
template: `
<mat-horizontal-stepper #stepper>
<mat-step></mat-step>
<mat-step></mat-step>
<mat-step></mat-step>
</mat-horizontal-stepper>
`
})
export class MyComponent {
@ViewChild('stepper', { static: true })
private stepper: MatHorizontalStepper
public ngOnInit() {
timer(10).subscribe(() => {
this.activatedRoute.queryParams.subscribe(params => {
this.stepper.selectedIndex = parseInt(params.step || 0)
})
})
}
}
언급URL : https://stackoverflow.com/questions/44691745/angular-4-expressionchangedafterithasbeencheckederror
'programing' 카테고리의 다른 글
Tomcat 또는 Jetty Production 등급이 내장된 Spring Boot입니까? (0) | 2023.06.30 |
---|---|
ORA-01849: 시간은 1에서 12 사이여야 합니다. (0) | 2023.06.30 |
상대 URL을 전체 URL로 변환하려면 어떻게 해야 합니까? (0) | 2023.06.30 |
트위터 부트스트랩 툴팁을 동적으로 생성된 요소에 바인딩하려면 어떻게 해야 합니까? (0) | 2023.06.30 |
64비트 마이크로소프트 SQL 서버 데이터 도구 (0) | 2023.06.30 |