Open Closed

Maximum call stack size exceeded #4188


User avatar
0
papusa created

Hi!

Having "maximum callstack" error on page refresh. Issue being reported before. You, guys, promised to fix the issue. But the problem still exists :( Workaround provided in previous ticket doesn't work anymore.

Link to previously registered ticket:
https://support.abp.io/QA/Questions/3415/Maximum-call-size-exceeded

Error:
image.png

default-src_app_shared_shared_module_ts.js:1 ERROR RangeError: Maximum call stack size exceeded at SafeSubscriber.<anonymous> (lift.js:13:26) at Observable.js:26:30 at errorContext (errorContext.js:19:9) at AnonymousSubject.subscribe (Observable.js:22:21) at PermissionDirective.ngAfterViewInit (abp-ng.core.mjs:1992:39) at callHook (core.mjs:2498:22) at callHooks (core.mjs:2467:17) at executeInitAndCheckHooks (core.mjs:2418:9) at refreshView (core.mjs:12040:21) at refreshEmbeddedViews (core.mjs:12997:17)

  • ABP Framework version: v6.0.1

  • UI type: Angular

  • Angular version: v14.2.8

  • Node version: v14.20.0


6 Answer(s)
  • User Avatar
    0
    muhammedaltug created

    Hello,

    It was fixed with this pr. I will try reproduce the problem again

  • User Avatar
    0
    papusa created

    Hello,

    It was fixed with this pr. I will try reproduce the problem again

    Hi,

    Unfortunately, we still have the issue. It disappeared for a while, but after lates updates it's back :( Even previously suggested workaround doesn't help anymore.

    Did you reproduce the problem? Do you need any additional information?

  • User Avatar
    0
    papusa created

    Hey, any news?

  • User Avatar
    0
    malik.masis created

    Hey, any news?

    Hi,

    The team could reproduce the issue and still working on it. We're trying to let you know asap.

    Fyi / Regards

  • User Avatar
    0
    muhammedaltug created

    Hello,

    We fixed the error. There is a workaround below for avoid this problem

    export class QueueManager {
      private queue: Array<() => void> = [];
      private isRunning = false;
      private stack = 0;
      private interval = 0;
      private stackSize = 100;
    
      public init(interval: number, stackSize: number) {
        this.interval = interval;
        this.stackSize = stackSize;
      }
    
      public add(fn: () => void) {
        this.queue.push(fn);
        this.run();
      }
    
      private run() {
        if (this.isRunning) return;
        this.stack++;
    
        this.isRunning = true;
    
        const fn = this.queue.shift();
    
        if (!fn) {
          this.isRunning = false;
          return;
        }
    
        fn();
        if (this.stack > this.stackSize) {
          setTimeout(() => {
            this.isRunning = false;
            this.run();
            this.stack = 0;
          }, this.interval);
        } else {
          this.isRunning = false;
          this.run();
        }
      }
    }
    
    function checkCustom() {
      if (this.subscription) {
        this.subscription.unsubscribe();
      }
    
      this.subscription = this.permissionService
        .getGrantedPolicy$(this.condition || '')
        .pipe(distinctUntilChanged())
        .subscribe(isGranted => {
          this.vcRef.clear();
          if (isGranted) this.vcRef.createEmbeddedView(this.templateRef);
          if (this.runChangeDetection) {
            if (!this.rendered) {
              this.cdrSubject.next();
            } else {
              this.cdRef.detectChanges();
            }
          } else {
            this.cdRef.markForCheck();
          }
        });
    }
    function after() {
      this.cdrSubject.pipe(take(1)).subscribe(() => {
        this.queue.add(() => {
          this.cdRef.detectChanges();
        });
      });
      this.rendered = true;
    }
    PermissionDirective.prototype['check'] = checkCustom;
    PermissionDirective.prototype['ngAfterViewInit'] = after;
    
    PermissionDirective.prototype['cdrSubject'] = new ReplaySubject();
    PermissionDirective.prototype['rendered'] = false;
    PermissionDirective.prototype['queue'] = new QueueManager();
    
    
  • User Avatar
    0
    papusa created

    Hi,

    Thanks, workaround works. Are you going to include fix for this in next ABP releases?

Boost Your Development
ABP Live Training
Packages
See Trainings
Mastering ABP Framework Book
Do you need assistance from an ABP expert?
Schedule a Meeting
Mastering ABP Framework Book
The Official Guide
Mastering
ABP Framework
Learn More
Mastering ABP Framework Book
Made with ❤️ on ABP v9.3.0-preview. Updated on April 16, 2025, 12:13