cordova-plugin-wkwebview-file-xhr: Angular ChangeDetection doesn't work

Hi, does anybody know why the angular ChangeDetection is not working with cordova-plugin-wkwebview-file-xhr? I load data in my angular 9+ project and get the correct response from api but the view can not be refreshed.

import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core';

import { ICaseLibrary } from '@shared/model';
import { AdminService } from '../admin.service';

@Component({
    selector: 'app-caselibrary',
    templateUrl: './caselibrary.template.html',
    changeDetection: ChangeDetectionStrategy.OnPush,
})
export class CaseLibraryComponent implements OnInit {
    casesFromDB: ICaseLibrary[];

    constructor(
        private adminService: AdminService,
        private cdRef: ChangeDetectorRef) { }

    ngOnInit(): void {
        this.adminService.getCasesForCaseLibrary().subscribe(
            response => {
                this.casesFromDB = response;
                this.cdRef.markForCheck(); // <== does not work in cordova using the WKWebView
            });
    }
}

As soon as this.cdRef.markForCheck(); is run in NgZone the view is going refreshed:

            this.ngZone.run(() => {   
                this.cdRef.markForCheck();
            });

Does cordova-plugin-wkwebview-file-xhr provides its own promise polyfill causing the angular change detection to break? Do I miss something? How to get the angular change detection work without run markForCheck() in NgZone? My angular code is shared between web, desktop and mobile platforms and the change detection should not be run outside of angular zone. Any idea?

About this issue

  • Original URL
  • State: closed
  • Created 4 years ago
  • Reactions: 2
  • Comments: 26 (6 by maintainers)

Most upvoted comments

so there is a simple fix for this. ✔️ the only thing which has to be done is applying a monkey patch to RXJs.

so I have done it inside my HTTP Interceptor for all requests.

// your imports

 @Injectable()
 export class RequestInterceptor implements HttpInterceptor {
 
    runInThisZone(zone) {
     return function patchedobsverable(source) {
       return Observable.create(observer => {
        const onNext = (value) => zone.run(() => observer.next(value));
         const onError = (e) => zone.run(() => observer.error(e));
        const onComplete = () => zone.run(() => observer.complete());
        return source.subscribe(onNext, onError, onComplete);
       });
     };
  }

constructor(private zone: NgZone) {}

intercept(req: HttpRequest < any > , next: HttpHandler): Observable < HttpEvent < any >> {
    if (window.usingCordova) { // your cordova/platform check here
        req = req.clone();
        return this.zone.run(() => next.handle(req).pipe(this.runInThisZone(this.zone)));
    } else {
        return next.handle(req);
    }
  }
}

so there we are. all request are forced into the right zone and the angular change detection triggers correctly. 😄