0

In componentOne.ts i am sending the data through sharedService as,

  this.sharedService.sendData(this.getCheckedProduct);

In componentTwo.ts i am subscribing the data like,

      productList: any = [];

      getAllProducts: any = [];

      ngOnInit() {
        this.sharedService.getData().subscribe(data => {
          this.productList = data;
          this.getProduct();
        });
      }

I am getting the data here in productlist then i need to call the function this.getProduct() which has the following,

  getProduct() {
    let tempArray = [];
    this.productList.forEach(element => {
        this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id).subscribe(res => {
          tempArray.push(res.data);
        });
    });
    this.getAllProducts = tempArray;
  }

I need to pass the id element.product_obj_id to get the necessary data of that id..

I have tried changing the above like this,

  ngOnInit() {
    this.sharedService.getData().subscribe(data => {
      data.forEach(element => {
        this.getProduct(element);
      })
    });
  }

  async  getProduct(element) {
    let asyncResult = await this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id).toPromise();
    this.getAllProducts.push(asyncResult['data']);
  }

Inside async getProduct(element) function i am, getting the data of this.getAllProducts but in html i am not getting the data.

HTML:

<div *ngFor="let product of getAllProducts">
 Getting data
</div>

If i changed the above with async

<div *ngFor="let product of getAllProducts | async">
 Getting data
</div>

I am getting error as,

ERROR Error: InvalidPipeArgument: '' for pipe 'AsyncPipe'
    at invalidPipeArgumentError

To explain in detail, i need to send a data through sharedservice in componentone and recieve it in componenttwo then need to get the product_obj_id from that shared service data.

The on passing each id, i will get the data of that particular product and i need to store the final data recieved from this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id).toPromise(); to getAllProducts..

AppConfig.settings.product.getProducts 

is the url ..

How to achieve it in a async way.. UPto this i am getting data

this.getAllProducts.push(asyncResult['data']);

but outside the function i am not getting the value, Also the getAllProducts no more working on any scenario in html..

In scenario 1 explained at top of this question i have given the following

this.getAllProducts = tempArray;

This one gives empty array as value and so only i am trying with async function.

In simple words i need to get the final data from this.getAllProducts which will be recieved from the service with get method for which i need to pass an id in the url..

2 Answers 2

1

Simply assign your data inside the async call like this -

getProduct() {
    let tempArray = [];
    this.productList.forEach(element => {
        this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id).subscribe(res => {
          tempArray.push(res.data);
          this.getAllProducts = tempArray; // Here
        });
    });
  }

PS: In your use case no need to use pipe async.

Sign up to request clarification or add additional context in comments.

6 Comments

No in html i am recieving no data.. <!--bindings={ "ng-reflect-ng-for-of": "" }--> Sowing like this..
If you do so as mentioned above in answer, your binding will automatically works whenever data is available for the view part, also try to console your data just to cross check if everything working fine
In console its working.. My exact problem is if it comes out of the service its not giving the value.. Its giving empty array as value..
If i put ``` console.log(this.getAllProducts);``` outside the service i am getting the value as [] empty array...
Yes because outside service it will become synchronous, that's the reason man!
|
0

AsyncPipe is to be applied on an Observable. In Your case, you are applying it on getAllProducts which is an Array, I believe. Hence you are getting that error.

Possible Solution:

  1. remove async from your for loop of getAllProducts
  2. Make getAllProducts return an Observable of your Products

Note: since you are looping through productList and calling the webapi to get the products, you might have to use mergeMap.

Solution 2 Sample:

I believe Solution 2 is best for you, since you productList contains all the products for which you need to hit the webapi to get the details of the products.

Learn MergeMap here

Sample code(untested & you need to add code for error handling with catchError):

import { from } from 'rxjs';
import { mergeMap, map, combineAll } from 'rxjs/operators';

this.getAllProducts = from(this.productList)
    .pipe( 
        mergeMap(element =>
            this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id).pipe(
                map(res => res['data'])
            )
        ),
        combineAll()
    )

<div *ngFor="let product of getAllProducts | async">
    Getting data
</div

Explanation:

since you productList is an Array and you have to loop through it to and fire a request for each product object in that Array

from(this.productList) makes each object in productList into an observable. We add a pipe and using mergeMap we can fire request for each of the product, hence you see this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id) this inside mergeMap. We then map the response we get from the webapi and only return data using res['data']. Finally we combineAll the response which returns an Observable<[]>, which we set into getAllProducts, hence getAllProducts is an Observable and we can use AsyncPipe on it.

Edit:

Add the following in your constructor instead of in ngOnit

const getAllProducts = this.sharedService.getData().pipe(
  mergeMap(data=> from(data))
).pipe( 
    mergeMap(element =>
        this.appService.getRest(AppConfig.settings.product.getProducts + '/' + element.product_obj_id).pipe(
            map(res => res['data'])
        )
    ),
    combineAll()
)

10 Comments

I am not expecting full code from you but expecting the skeleton how to make it.. How to make as observale etc.., Because i am a very beginner in it please help me..
Your last edit shows too many errors cannot find name from,map,combineAll
you need to import all of them.
whether there is no change in the ngOnInit function??
Here i am getting a single error as Property 'product_obj_id' does not exist on type '{}'. in this line AppConfig.settings.product.getProducts + '/' + element.product_obj_id)
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.