-1

Its a POST API created by API Gateway from AWS, however it always returns infinite repetition of arrays as you see in the below picture. How to return only one array?

Mutiple requests

Here's the code

Angular

import { Component, OnInit, ViewChild, OnChanges, OnDestroy } from '@angular/core';
import { HttpClient } from '@angular/common/http'; 
import { GetService } from '../get.service';
import { Observable, Subject } from 'rxjs';
import { IonSlides, IonSlide } from '@ionic/angular';

@Component({
  selector: 'app-home',
  templateUrl: 'home.page.html',
  styleUrls: ['home.page.scss'],
})
export class HomePage implements OnInit   {
  protected ngUnsubscribe: Subject<void> = new Subject<void>();


constructor(public http:HttpClient) {}
  @ViewChild(IonSlides,{'static':false}) slides: IonSlides;

  slideOpts = {
    initialSlide: 1,
    speed: 400
 };
public result:any
public res:any
data:Observable<any>;
ata:Observable<any>;

ngOnInit(){
}

  getdata(){


   this.ata=this.http.post("XXXXXXXXXXXXXXXXXXXXXXXXX",{"freq":1});
   this.ata.subscribe(data=>{console.log(data)})

  return   this.res




}
INDEX:any

slideChanged() {

  this.INDEX =this.slides.getActiveIndex().then(data=>console.log(data))
  return this.INDEX

}
   }

HTML

   <ion-header>
  <ion-toolbar>
    <ion-title>
      Ionic Blank
    </ion-title>
  </ion-toolbar>
</ion-header>
<p *ngFor="let a of getdata()">{{a}}</p >
<ion-card>
  <ion-card-content>
  <ion-slides  [options]="slideOpts" (ionSlideWillChange)="slideChanged()">
    <ion-slide  >
        <h1></h1>
    </ion-slide>
s


  </ion-slides>
</ion-card-content>
</ion-card>
Paolo Casciello
  • 7,982
  • 1
  • 43
  • 42
Aboulezz
  • 11
  • 5

1 Answers1

3

That is not the API. Why am I sure about this? Because you're using Angular's HttpClient and you need quite a bit of boilerplate around it to make multiple requests. Your issue is because your page is renderer multiple times while Angular's rendered manages the page layout.

The real issue lies at this line:

<p *ngFor="let a of getdata()">{{a}}</p >

Everytime that line is rendered angular calls getdata() issuing another request.

You must decouple the result list from the function requesting it. From your code seems like ata is an Observable. Something like the following should work:

<p *ngFor="let a of ata | async">{{a}}</p>

Please note the async pipe used.

From Angular documentation

The async pipe subscribes to an Observable or Promise and returns the latest value it has emitted. When a new value is emitted, the async pipe marks the component to be checked for changes. When the component gets destroyed, the async pipe unsubscribes automatically to avoid potential memory leaks.

Of course you must call getdata() somewhere and usually the right place is in ngOnInit().

Side note: How to get only one response from an Observable subscription

Since in this question there is confusion on this topic if you need to get only one response from an Observable the common way is to use take operator.

import { take } from 'rxjs/operators';

[...]

someService.getObservable(...)
           .pipe( take(1) ) // <-- take first response
           .subscribe( (r) => { ... } );
Paolo Casciello
  • 7,982
  • 1
  • 43
  • 42
  • No , you see this line "this.ata.subscribe(data=>{console.log(data)})" ??? it return repetitive api responses ... as its clarified in the attached picture there in the post , I just want to get one response . – Aboulezz Jan 15 '20 at 20:00
  • @Aboulezz try to read carefully my answer :) That line gets called multiple times and is subscribing multiple times. You must call `getdata()` once in the `ngOnInit()` and then use the `ata` observable. Btw, if you just want to unsibscribe from a subscriptio, you can pipe it through a `take(1)` rxjs operator or call `.unsubscribe` on the subscription itself. I add this latter tip in the answer. – Paolo Casciello Jan 16 '20 at 08:30