Skip to content
Advertisement

Angular MatStepper fails to recognize cached values from two str arrays (but successfully recognizes values from another str array)

I have a MatStepper that’s used to navigate to the next page of a signup flow. I also have a method that loads values from a cache if it’s available, and if so then the MatStepper skips to Page 2. After that, a future method pre-fills the form will those cached values.

The scenario where cachedSports are retrieved causes the MatStepper to work and skip to Page 2, but when I try to pre-fill with cachedPets or cachedAnimals the MatStepper fails and gives me the following error:

Cannot read properties of undefined (reading 'next')

There aren’t a lot of differences between cachedSports and the two failing scenarios, so I don’t know what the culprit is. All three are arrays of strings and the values from their caches are coming in successfully.


    // Cached values are retrieved from another file, memory-cache.service.ts
    loadFromCache(): void {
        const cachedPets: string[] = this.cacheService.get<string[]>(MemoryCacheService.WellKnownKeys.pets) ?? [];
        const cachedSports: string[] = this.cacheService.get<string[]>(MemoryCacheService.WellKnownKeys.sports) ?? [];
        const cachedAnimalNames: string[] = this.cacheService.get<string[]>(MemoryCacheService.WellKnownKeys.animals) ?? [];

        // Note that cachedPets and cachedAnimalNames share ('targetEveryAnimal')
        if (cachedPets.length > 0) {
          this.targetingFormGroup.get('targetEveryAnimal').setValue('Specific'); 
          this.targetPetChange({ value: 'Specific' }, cachedPets);
        } else if (cachedSports.length > 0) {
          this.targetingFormGroup.get('targetEverySport').setValue('Specific');
          this.targetSportChange({ value: 'Specific' }, cachedSports);
        } else if (cachedAnimalNames.length > 0) {
          this.targetingFormGroup.get('targetEveryAnimal').setValue('Specific');
          this.targetAnimalChange({ value: 'Specific' }, cachedAnimalNames);
        } 

        // The values correctly come through:
        console.log('cachedPets: ', cachedPets); // ["Cat"]
        console.log('cachedSports: ', cachedSports); // ["Tennis"]
        console.log('cachedAnimalNames: ', cachedAnimalNames); // ["Chinchilla"]

        this.goForward();
        this.location.replaceState('filters/setup/create/page2');
        this.skipPageOne = true;

        this.cacheService.remove(MemoryCacheService.WellKnownKeys.pets);
        this.cacheService.remove(MemoryCacheService.WellKnownKeys.sports);
        this.cacheService.remove(MemoryCacheService.WellKnownKeys.animals);

    }

  goForward(){
    this.myStepper.next();
    // Defined as: @ViewChild('stepper') private myStepper: MatStepper;
  }


This is where the cached values are actually added into the form

// Same file as the above code

validateFormTargeting() {

  const sports = (spt === 'Specific') ? this.targetingFormGroup.get('sports').value : [];
  console.log('tfg-sports: ', this.targetingFormGroup.get('sports').value) // ["Tennis"]
  console.log('sports: ', sports) // ["Tennis"]

  let pets;
  let animalNames;

  if (animt === 'Specific') {
    // pets = this.tarFormGroup.get // etc
    animalNames = this.targetingFormGroup.get('animalNames') ? this.targetingFormGroup.get('animalNames').value : [];
    
    // The console messages (therefore this code block) is not reached because of the "Cannot read properties of undefined" error
    console.log('tfg-animalNames: ', this.targetingFormGroup.get('animalNames').value)
    console.log('animalNames: ', animalNames)
  }
}


Verbose err message:

TypeError: Cannot read properties of undefined (reading 'next')
    at AppModalFormCreateComponent.goForward (myForm.component.ts:371:20)
    at AppModalFormCreateComponent.loadFromCache (myForm.component.ts:357:10)
    at AppModalFormCreateComponent.ngOnInit (myForm.component.ts:227:10)

Advertisement

Answer

It’s the ViewChild not being defined/set when goForward is called.

If the template is being updated then it’s probably a timing issue. For testing purposes you can wrap the code in goForward in a setTimeout()

User contributions licensed under: CC BY-SA
4 People found this is helpful
Advertisement