페이지 지정과 관찰 가능 및 각도 9의 비동기 파이프를 결합하는 방법?
API에서 나온 제품 목록이 있어.제품은 페이지 지정되어 있으며 사용자는 다른 페이지로 전환할 수 있다.단순화된 템플릿은 다음과 같다.
<ul>
<li *ngFor="let product of products$ | async">{{ product.name }}</li>
</ul>
<button type="button" (click)="gotoPage(1)">1</button>
<button type="button" (click)="gotoPage(2)">2</button>
구성 요소는 다음과 같다.
export class ProductsComponent implements OnInit {
products$: Observable<Product[]>;
constructor(
private service: ProductService
) { }
ngOnInit() {
this.products$ = this.service.getAll({page: 1});
}
gotoPage(page: number): void {
this.products$ = this.service.getAll({page: page});
}
}
제 질문은: 이것이 오버사블을 업데이트하는 올바른 방법인가?아니면 이것이 기억의 누수를 야기하는가?
참고 사항:URL은 변경되지 않으며 페이지 지정 변경 시 구성 요소가 다시 로드되지 않아야 한다.
비동기 파이프의 근원을 보면, 내부를 볼 수 있다.transform()
함수:
if (obj !== this._obj) {
this._dispose();
return this.transform(obj as any);
}
이전에 관찰할 수 있는 것이 있다면, 새로운 사물일 경우, 이전 관찰 가능을 취소하는 것.그래서 너는 그것을 그런 식으로 사용해도 안전해.
당신은 관찰할 수 있는 것에 가입하지도 않아서 메모리 누수가 있을 것 같지도 않고, 단지 약간의 데이터만 얻으면 비동기 파이프가 당신을 위해 '변환'을 처리한다.
관찰 가능한 것을 구독할 때, 적절히 구독을 취소하고 메모리 누수를 방지하기 위해 몇 줄의 코드를 추가해야 한다.
ngUnsubscribe = new Subject();
myObservable: Observable<any>;
ngOnInit(){
this.myObservable.pipe(takeUntil(ngUnsubscribe))
.subscribe(...)
}
ngOnDestroy() {
this.ngUnsubscribe.next();
this.ngUnsubscribe.complete();
}
모든 구독에서 올바른 구독 취소를 트리거할 수 있는 제목:takeUntil
.
그.next
그리고.complete
때문에 필요하다.unsubscribe
예상대로 작동하지 않음(NGRX와 함께 작업할 때 알림이 표시되고 NGRX와 관련된 스택 오버플로 스레드가 발견됨).
takeEngOnDestroy 패턴이 항상 메모리 누수를 방지할 수 있다.
예를 들어,
새로운 변수를 선언하다private onDestroy$: Subject<void> = new Subject<void>();
this.service.getAll({page: page})
.pipe(takeUntil(this.onDestroy$))
.subscribe(... do the necessary ...);
그리고 나중에 onDestroy() 라이프 사이클 훅에서 다음을 실행할 수 있다.
public ngOnDestroy(): void {
this.onDestroy$.next();
this.onDestroy$.complete()
}
우리가 실제로 한 일은 관찰할 수 있는 새로운 것을 선언한 것이다.그런 다음 take와 함께 파이프 방법을 사용하여 컴파일러에 값이 Destroy$에 나타날 때 관측 가능한 값을 사용할 수 없음을 알릴 때까지 take와 함께 파이프 방법을 사용하여 컴파일러에 값이 Destroy$에 표시될 때 관측 가능한 값을 사용할 수 없도록 함으로써 메모리 누출을 방지한다는 것을 알릴 때까지.
우리 모두가 페이지당 알고 있듯이, 페이지당 항목 수도 나온다.
나는 행동 과목으로 기준을 바꾸고 두 개의 관찰 자료를 결합하는 것을 선호한다.mergeMap
class ProductService {
constructor() {
this.defaultCriteria = {
page: 0,
pageSize: 5
}
}
getAll(criteria) {
criteria = {
...this.defaultCriteria,
...criteria
}
return rxjs.of(Array(criteria.pageSize).fill(0).map((pr, index) => {
const num = index + criteria.pageSize * criteria.page + 1;
return {
id: num,
name: `Product ${num}`
}
}))
}
}
class ProductsComponent {
constructor(service) {
this.service = service;
this.page$ = new rxjs.BehaviorSubject(0);
this.products$ = null;
}
ngOnInit() {
this.products$ = this.page$.asObservable()
.pipe(rxjs.operators.mergeMap(page => this.service.getAll({
page
})))
}
gotoPage(page) {
this.page$.next(page);
}
}
const service = new ProductService();
const component = new ProductsComponent(service);
component.ngOnInit();
component.products$.subscribe(products => console.log(products));
component.gotoPage(1);
component.gotoPage(2);
<script src="https://cdnjs.cloudflare.com/ajax/libs/rxjs/6.5.5/rxjs.umd.js"></script>
'programing' 카테고리의 다른 글
ConfigParser에서 사례를 유지하시겠습니까? (0) | 2022.03.13 |
---|---|
MD 크기의 장치에 대해서만 요소 표시 (0) | 2022.03.13 |
vue-cli 구성 요소에서 lib를 빌드하고 가져오기 (0) | 2022.03.13 |
성분 nnxt의 process.env 변수에 액세스할 수 없음 (0) | 2022.03.13 |
Thunk 디스패치 대기 결과를 입력하려면 어떻게 해야 하는가? (0) | 2022.03.13 |