4

I have a requirement where I need to make a http post method request to a Web API i.e. save some data entered by the user. The Web API would return some values as a result and this result would be used for some UI logic.

I tried making the http post in synchronous way, but it doesn't work properly as expected.

Angular2 component calls this service to save the data:-

public SaveCubeReport(userName: any, cubeReport: CubeReportViewModel, APIServiceURL: any)
    {
        var result = this.SaveData(userName, cubeReport, APIServiceURL).subscribe(
            data => {
                console.log(data);
            });

        console.log(result);
}

Http post method call is as follows:-

SaveData(userName: any, cubeReport: CubeReportViewModel, APIServiceURL: any)
{
    var temp = this._http.post(APIServiceURL, JSON.stringify(cubeReport), { headers: ContentHeaders })
        .map((res: Response) => res.json())
        .do(() => {
            console.log('request finished');
        });
    return res;
}

Parent component where the angular2-modal popup is invoked.

var dialog = this.modal.open(SaveCubeReport, overlayConfigFactory(
{
    ReportName: this.ReportItem.rpt_name,
    ReportDescription: this.ReportItem.rpt_description,
    Application: this.ReportItem.application_name,
    Owner: this.ReportItem.owner,
    CubeId: this.CubeId,
    ReportId: this.ReportItem.rpt_id,
    ReportJson: JSON.stringify(this.getState())
}, BSModalContext));

dialog
.then((d) => d.result)
.then((r) => {
    // success
    console.log("Dialog ended with success: ", r);
    this.RefreshReportListDropdown(r);
}, (error) => {
    // failure 
    console.log("Dialog ended with failure: ", error);
});

function from where the service call is made

RefreshReportListDropdown(savedReportName: any)
{
    this._ClientAPIService.GetCubeReportsListByCubeWithEmptyRecord(this._SessionService.LoggedInUser, this._SessionService.SelectedApplication, this.cubeName, this._SessionService.ClientAPIServiceURL)
        .subscribe(
        (res) => {
            this.cubeReportList = res; //This result should contain all records including the recently saved data from the popup
            ....
        }
    );
}

All my request are made a asynch requests i.e. it doesn't wait to get the return values. What is the mistake here?

Krishnan
  • 958
  • 5
  • 21
  • 44
  • Result is a subscription, not the returned value. Please read up on async generally and RxJS specifically, or you'll have a hard time of it. – jonrsharpe Jul 06 '17 at 21:11
  • Possible duplicate of [Angular 2 - Return data directly from an Observable](https://stackoverflow.com/questions/37867020/angular-2-return-data-directly-from-an-observable) – jonrsharpe Jul 06 '17 at 21:11

2 Answers2

4

Return the result of http.post call in the SaveData method.

SaveData(userName: any, cubeReport: CubeReportViewModel, APIServiceURL: any)
{
    return this._http.post(APIServiceURL, JSON.stringify(cubeReport), { headers: ContentHeaders })
        .map((res: Response) => res.json())
        .do(() => {
            console.log('request finished');
        });
}

After this your subscribe in your consumer component will work correctly.

Gosha_Fighten
  • 3,838
  • 1
  • 20
  • 31
  • still it doesn't work correctly or as expected. I am calling this above service while closing a angular2-modal popup. After the record is saved, the modal popup is closed and I need to make a new service to get the list of the records including the recently saved data also and bind a dropdown in the parent component which invoked the popup. But currently it doesn't get the recently saved record in the list? (Please refer the edited question) – Krishnan Jul 07 '17 at 00:32
  • Do you have any sample, for example, in Plunker so that I can see the issue in action? – Gosha_Fighten Jul 07 '17 at 10:21
  • It works fine now, was my mistake. Earlier I was calling SaveCubeReport method which was like a extra wrapper in-between the angular2 component and the api service call. But when I removed this and directly call SaveData() method from my angular2 component it worked fine. – Krishnan Jul 07 '17 at 18:07
1

loginservice.ts :

  checklogin(user) {   
   return this.http.post("API_URL",user).map(resp => resp.json());
  }

logincomponent.ts :

   localvariable={} // or whatever u want 

   customFunction () {
     this.loginservice.checklogin(this.user).subscribe (data => 
     {this.localvariable=data;}) 

     // results is assigned now to this.localvariable
     //write your logic etc ... 
     }